diff --git a/.ci/monolithic-linux.sh b/.ci/monolithic-linux.sh index b347c443da677fd530afb91936a9605ec1218b2b..b00a4b984a1d23f4cdedb601a0e22a2ac518f162 100755 --- a/.ci/monolithic-linux.sh +++ b/.ci/monolithic-linux.sh @@ -48,7 +48,6 @@ cmake -S "${MONOREPO_ROOT}"/llvm -B "${BUILD_DIR}" \ -D LLVM_LIT_ARGS="-v --xunit-xml-output ${BUILD_DIR}/test-results.xml --timeout=1200 --time-tests" \ -D LLVM_ENABLE_LLD=ON \ -D CMAKE_CXX_FLAGS=-gmlt \ - -D BOLT_CLANG_EXE=/usr/bin/clang \ -D LLVM_CCACHE_BUILD=ON \ -D MLIR_ENABLE_BINDINGS_PYTHON=ON diff --git a/.github/new-prs-labeler.yml b/.github/new-prs-labeler.yml index 9cf64417d3cb2cce3a61707ae1693e692c6e1a0e..d608ea449f1d40c841e2ae356f4a0fa8431d2d48 100644 --- a/.github/new-prs-labeler.yml +++ b/.github/new-prs-labeler.yml @@ -1,3 +1,6 @@ +BOLT: + - bolt/**/* + ClangIR: - clang/include/clang/CIR/**/* - clang/lib/CIR/**/* @@ -467,6 +470,7 @@ backend:m68k: libc++: - libcxx/** + - .github/workflows/libcxx-* libc++abi: - libcxxabi/** diff --git a/.github/workflows/libcxx-build-and-test.yaml b/.github/workflows/libcxx-build-and-test.yaml index 1e9367732e591118445fef2c69acf3339c2cbf5d..44a3d79c72c0ac9b80598d946d93f9af110f9df3 100644 --- a/.github/workflows/libcxx-build-and-test.yaml +++ b/.github/workflows/libcxx-build-and-test.yaml @@ -61,12 +61,10 @@ jobs: ] cc: [ 'clang-19' ] cxx: [ 'clang++-19' ] - clang_tidy: [ 'ON' ] include: - config: 'generic-gcc' cc: 'gcc-13' cxx: 'g++-13' - clang_tidy: 'OFF' steps: - uses: actions/checkout@v4 - name: ${{ matrix.config }}.${{ matrix.cxx }} @@ -74,7 +72,6 @@ jobs: env: CC: ${{ matrix.cc }} CXX: ${{ matrix.cxx }} - ENABLE_CLANG_TIDY: ${{ matrix.clang_tidy }} - uses: actions/upload-artifact@26f96dfa697d77e81fd5907df203aa23a56210a8 # v4.3.0 if: always() with: @@ -102,20 +99,16 @@ jobs: ] cc: [ 'clang-19' ] cxx: [ 'clang++-19' ] - clang_tidy: [ 'ON' ] include: - config: 'generic-gcc-cxx11' cc: 'gcc-13' cxx: 'g++-13' - clang_tidy: 'OFF' - config: 'generic-cxx23' cc: 'clang-17' cxx: 'clang++-17' - clang_tidy: 'OFF' - config: 'generic-cxx26' cc: 'clang-18' cxx: 'clang++-18' - clang_tidy: 'ON' steps: - uses: actions/checkout@v4 - name: ${{ matrix.config }} @@ -123,7 +116,6 @@ jobs: env: CC: ${{ matrix.cc }} CXX: ${{ matrix.cxx }} - ENABLE_CLANG_TIDY: ${{ matrix.clang_tidy }} - uses: actions/upload-artifact@26f96dfa697d77e81fd5907df203aa23a56210a8 # v4.3.0 if: always() # Upload artifacts even if the build or test suite fails with: @@ -188,7 +180,6 @@ jobs: env: CC: clang-19 CXX: clang++-19 - ENABLE_CLANG_TIDY: "OFF" - uses: actions/upload-artifact@26f96dfa697d77e81fd5907df203aa23a56210a8 # v4.3.0 if: always() with: diff --git a/bolt/include/bolt/Passes/BinaryPasses.h b/bolt/include/bolt/Passes/BinaryPasses.h index 8d89ef8b5484f8e18d7ea034c3d38df57746760a..5d7692559eda882b125ee5314117eb5fe65932d0 100644 --- a/bolt/include/bolt/Passes/BinaryPasses.h +++ b/bolt/include/bolt/Passes/BinaryPasses.h @@ -400,8 +400,7 @@ public: /// dyno stats categories. class PrintProgramStats : public BinaryFunctionPass { public: - explicit PrintProgramStats(const cl::opt &PrintPass) - : BinaryFunctionPass(PrintPass) {} + explicit PrintProgramStats() : BinaryFunctionPass(false) {} const char *getName() const override { return "print-stats"; } bool shouldPrint(const BinaryFunction &) const override { return false; } diff --git a/bolt/include/bolt/Rewrite/RewriteInstance.h b/bolt/include/bolt/Rewrite/RewriteInstance.h index af832b4c7c84cf32b059f99adba4ed4df6fc5b19..2561468a0f99af4d46c04f78aa3eff5d9dfbcb4a 100644 --- a/bolt/include/bolt/Rewrite/RewriteInstance.h +++ b/bolt/include/bolt/Rewrite/RewriteInstance.h @@ -426,6 +426,9 @@ private: static StringRef getEHFrameSectionName() { return ".eh_frame"; } static StringRef getRelaDynSectionName() { return ".rela.dyn"; } + /// FILE symbol name used for local fragments of global functions. + static StringRef getBOLTFileSymbolName() { return "bolt-pseudo.o"; } + /// An instance of the input binary we are processing, externally owned. llvm::object::ELFObjectFileBase *InputFile; diff --git a/bolt/lib/Profile/DataAggregator.cpp b/bolt/lib/Profile/DataAggregator.cpp index 0b2a4e86561f3aaa56a7385bf4fd8e5439f2d56a..70e324cc0165bb969c6a63d8f9334b80fb8fbd6c 100644 --- a/bolt/lib/Profile/DataAggregator.cpp +++ b/bolt/lib/Profile/DataAggregator.cpp @@ -14,6 +14,7 @@ #include "bolt/Profile/DataAggregator.h" #include "bolt/Core/BinaryContext.h" #include "bolt/Core/BinaryFunction.h" +#include "bolt/Passes/BinaryPasses.h" #include "bolt/Profile/BoltAddressTranslation.h" #include "bolt/Profile/Heatmap.h" #include "bolt/Profile/YAMLProfileWriter.h" @@ -611,6 +612,7 @@ Error DataAggregator::readProfile(BinaryContext &BC) { if (std::error_code EC = writeBATYAML(BC, opts::SaveProfile)) report_error("cannot create output data file", EC); } + BC.logBOLTErrorsAndQuitOnFatal(PrintProgramStats().runOnFunctions(BC)); } return Error::success(); diff --git a/bolt/lib/Rewrite/BinaryPassManager.cpp b/bolt/lib/Rewrite/BinaryPassManager.cpp index be4888ccfa56457fe2f59dcee91abdd05b947021..cbb7199a53ddd14f77730645efd8a8fd2a4109a4 100644 --- a/bolt/lib/Rewrite/BinaryPassManager.cpp +++ b/bolt/lib/Rewrite/BinaryPassManager.cpp @@ -356,7 +356,7 @@ Error BinaryFunctionPassManager::runAllPasses(BinaryContext &BC) { // order they're registered. // Run this pass first to use stats for the original functions. - Manager.registerPass(std::make_unique(NeverPrint)); + Manager.registerPass(std::make_unique()); if (opts::PrintProfileStats) Manager.registerPass(std::make_unique(NeverPrint)); diff --git a/bolt/lib/Rewrite/BoltDiff.cpp b/bolt/lib/Rewrite/BoltDiff.cpp index fa43b7a2f92c23d04270bb13930faea443e91add..74b5ca18abce429410d11306189b3c5bfa5f4c73 100644 --- a/bolt/lib/Rewrite/BoltDiff.cpp +++ b/bolt/lib/Rewrite/BoltDiff.cpp @@ -292,7 +292,7 @@ class RewriteInstanceDiff { } } } - PrintProgramStats PPS(opts::NeverPrint); + PrintProgramStats PPS; outs() << "* BOLT-DIFF: Starting print program stats pass for binary 1\n"; RI1.BC->logBOLTErrorsAndQuitOnFatal(PPS.runOnFunctions(*RI1.BC)); outs() << "* BOLT-DIFF: Starting print program stats pass for binary 2\n"; diff --git a/bolt/lib/Rewrite/RewriteInstance.cpp b/bolt/lib/Rewrite/RewriteInstance.cpp index 4e0096cf988aed4031523e3a8343023f88ed7322..3cf0e749f9d6671fba629e5a97120ce2bc7852f3 100644 --- a/bolt/lib/Rewrite/RewriteInstance.cpp +++ b/bolt/lib/Rewrite/RewriteInstance.cpp @@ -1725,12 +1725,6 @@ void RewriteInstance::adjustFunctionBoundaries() { if (!Function.isSymbolValidInScope(Symbol, SymbolSize)) break; - // Ignore unnamed symbols. Used, for example, by debugging info on RISC-V. - if (BC->isRISCV() && cantFail(Symbol.getName()).empty()) { - ++NextSymRefI; - continue; - } - // Skip basic block labels. This happens on RISC-V with linker relaxation // enabled because every branch needs a relocation and corresponding // symbol. We don't want to add such symbols as entry points. @@ -4493,6 +4487,8 @@ void RewriteInstance::updateELFSymbolTable( // Symbols for the new symbol table. std::vector Symbols; + bool EmittedColdFileSymbol = false; + auto getNewSectionIndex = [&](uint32_t OldIndex) { // For dynamic symbol table, the section index could be wrong on the input, // and its value is ignored by the runtime if it's different from @@ -4551,6 +4547,20 @@ void RewriteInstance::updateELFSymbolTable( Symbols.emplace_back(ICFSymbol); } if (Function.isSplit()) { + // Prepend synthetic FILE symbol to prevent local cold fragments from + // colliding with existing symbols with the same name. + if (!EmittedColdFileSymbol && + FunctionSymbol.getBinding() == ELF::STB_GLOBAL) { + ELFSymTy FileSymbol; + FileSymbol.st_shndx = ELF::SHN_ABS; + FileSymbol.st_name = AddToStrTab(getBOLTFileSymbolName()); + FileSymbol.st_value = 0; + FileSymbol.st_size = 0; + FileSymbol.st_other = 0; + FileSymbol.setBindingAndType(ELF::STB_LOCAL, ELF::STT_FILE); + Symbols.emplace_back(FileSymbol); + EmittedColdFileSymbol = true; + } for (const FunctionFragment &FF : Function.getLayout().getSplitFragments()) { if (FF.getAddress()) { @@ -5432,6 +5442,17 @@ uint64_t RewriteInstance::getNewFunctionOrDataAddress(uint64_t OldAddress) { if (BD && BD->isMoved()) return BD->getOutputAddress(); + if (const BinaryFunction *BF = + BC->getBinaryFunctionContainingAddress(OldAddress)) { + if (BF->isEmitted()) { + BC->errs() << "BOLT-ERROR: unable to get new address corresponding to " + "input address 0x" + << Twine::utohexstr(OldAddress) << " in function " << *BF + << ". Consider adding this function to --skip-funcs=...\n"; + exit(1); + } + } + return 0; } diff --git a/bolt/test/RISCV/unnamed-sym-no-entry.c b/bolt/test/RISCV/fake-label-no-entry.c similarity index 85% rename from bolt/test/RISCV/unnamed-sym-no-entry.c rename to bolt/test/RISCV/fake-label-no-entry.c index 605bbc00aeec4638deaaef54f2505c361055e76f..bd125263101bb461149967745d23f52e32128781 100644 --- a/bolt/test/RISCV/unnamed-sym-no-entry.c +++ b/bolt/test/RISCV/fake-label-no-entry.c @@ -5,12 +5,12 @@ // RUN: %clang %cflags -g -Wl,-q -o %t %s -/// Verify that the binary indeed contains an unnamed symbol at _start +/// Verify that the binary indeed contains a fake label ".L0 " at _start. // RUN: llvm-readelf -s %t | FileCheck %s --check-prefix=CHECK-ELF // CHECK-ELF-DAG: [[#%x,START:]] {{.*}} FUNC GLOBAL DEFAULT [[#%d,SECTION:]] _start{{$}} -// CHECK-ELF-DAG: [[#%x,START]] {{.*}} NOTYPE LOCAL DEFAULT [[#SECTION]] {{$}} +// CHECK-ELF-DAG: [[#%x,START]] {{.*}} NOTYPE LOCAL DEFAULT [[#SECTION]] .L0 {{$}} -/// Verify that BOLT did not create an extra entry point for the unnamed symbol +/// Verify that BOLT did not create an extra entry point for the fake label. // RUN: llvm-bolt -o %t.bolt %t --print-cfg | FileCheck %s // CHECK: Binary Function "_start" after building cfg { // CHECK: IsMultiEntry: 0 diff --git a/bolt/test/X86/cdsplit-symbol-names.s b/bolt/test/X86/cdsplit-symbol-names.s index e2259276e2554c406223f9d209a52863fa184ab0..e53863e22246d63d54ce4f56283d69c8ac37c856 100644 --- a/bolt/test/X86/cdsplit-symbol-names.s +++ b/bolt/test/X86/cdsplit-symbol-names.s @@ -10,6 +10,7 @@ # RUN: --call-scale=2 --data=%t.fdata --reorder-blocks=ext-tsp # RUN: llvm-objdump --syms %t.bolt | FileCheck %s --check-prefix=CHECK-SYMS-WARM +# CHECK-SYMS-WARM: 0000000000000000 l df *ABS* 0000000000000000 bolt-pseudo.o # CHECK-SYMS-WARM: .text.warm # CHECK-SYMS-WARM-SAME: chain.warm # CHECK-SYMS-WARM: .text.cold diff --git a/bolt/test/X86/indirect-goto-pie.test b/bolt/test/X86/indirect-goto-pie.test new file mode 100644 index 0000000000000000000000000000000000000000..039ff5c41d3d6842d2e9de2d94908f7dda88fd7f --- /dev/null +++ b/bolt/test/X86/indirect-goto-pie.test @@ -0,0 +1,16 @@ +# Check that llvm-bolt fails to process PIC binaries with computed goto, as the +# support is not there yet for correctly updating dynamic relocations +# referencing code inside functions. + +REQUIRES: x86_64-linux + +RUN: %clang %S/Inputs/indirect_goto.c -o %t -fpic -pie -Wl,-q +RUN: not llvm-bolt %t -o %t.bolt --relocs=1 --print-cfg --print-only=main \ +RUN: |& FileCheck %s + +# Check that processing works if main() is skipped. +RUN: llvm-bolt %t -o %t.bolt --relocs=1 --skip-funcs=main + +CHECK: jmpq *%rax # UNKNOWN CONTROL FLOW + +CHECK: BOLT-ERROR: unable to get new address diff --git a/bolt/test/X86/pre-aggregated-perf.test b/bolt/test/X86/pre-aggregated-perf.test index e8c3f64239a27ddb831f801ccf76b09d44fda6b1..0bd44720f1b7a102f8590d575d3156277c488624 100644 --- a/bolt/test/X86/pre-aggregated-perf.test +++ b/bolt/test/X86/pre-aggregated-perf.test @@ -11,7 +11,14 @@ REQUIRES: system-linux RUN: yaml2obj %p/Inputs/blarge.yaml &> %t.exe RUN: perf2bolt %t.exe -o %t --pa -p %p/Inputs/pre-aggregated.txt -w %t.new \ -RUN: --profile-use-dfs +RUN: --profile-use-dfs | FileCheck %s + +RUN: llvm-bolt %t.exe -data %t -o %t.null | FileCheck %s +RUN: llvm-bolt %t.exe -data %t.new -o %t.null | FileCheck %s +RUN: llvm-bolt %t.exe -p %p/Inputs/pre-aggregated.txt --pa -o %t.null | FileCheck %s + +CHECK: BOLT-INFO: 4 out of 7 functions in the binary (57.1%) have non-empty execution profile + RUN: cat %t | sort | FileCheck %s -check-prefix=PERF2BOLT RUN: cat %t.new | FileCheck %s -check-prefix=NEWFORMAT diff --git a/bolt/test/X86/shrinkwrapping-do-not-pessimize.s b/bolt/test/X86/shrinkwrapping-do-not-pessimize.s index a57131131423efc2e0bfdb1b807985631566f6a5..3fdd5f5e38fe0da9b964a36fbfb0edb35b6a15e5 100644 --- a/bolt/test/X86/shrinkwrapping-do-not-pessimize.s +++ b/bolt/test/X86/shrinkwrapping-do-not-pessimize.s @@ -53,6 +53,6 @@ end_if_1: .size _start, .-_start .data -rel: .quad end_if_1 +rel: .quad _start # CHECK: BOLT-INFO: Shrink wrapping moved 0 spills inserting load/stores and 0 spills inserting push/pops diff --git a/bolt/test/runtime/X86/Inputs/indirect_goto.c b/bolt/test/runtime/X86/Inputs/indirect_goto.c deleted file mode 100644 index b781e9e03b6d44b40567a3111d64394399ad4421..0000000000000000000000000000000000000000 --- a/bolt/test/runtime/X86/Inputs/indirect_goto.c +++ /dev/null @@ -1,18 +0,0 @@ -int main(int argc, char *argv[]) { - static const void *T1[] = { &&L1, &&L2 }; - static const void *T2[] = { &&L2, &&L3 }; - - const void **T = (argc > 1) ? T1 : T2; - - int i = 0; - -L0: - goto *T[argc]; -L1: - ++i; -L2: - i++; -L3: - i++; - return i; -} diff --git a/bolt/test/runtime/X86/indirect-goto-pie.test b/bolt/test/runtime/X86/indirect-goto-pie.test deleted file mode 100644 index 76089fda3abfb27f0daeba13db224fafc23266ab..0000000000000000000000000000000000000000 --- a/bolt/test/runtime/X86/indirect-goto-pie.test +++ /dev/null @@ -1,10 +0,0 @@ -# Check llvm-bolt processes binaries compiled from sources that use indirect goto. -REQUIRES: x86_64-linux - -RUN: %clang %S/Inputs/indirect_goto.c -o %t -fpic -pie -Wl,-q -RUN: llvm-bolt %t -o %t.bolt --relocs=1 --print-cfg --print-only=main \ -RUN: |& FileCheck %s -# The test fails as we don't update corresponding dynamic relocations. -RUN: not %t.bolt - -CHECK: jmpq *%rax # UNKNOWN CONTROL FLOW diff --git a/clang-tools-extra/clang-tidy/bugprone/BugproneTidyModule.cpp b/clang-tools-extra/clang-tidy/bugprone/BugproneTidyModule.cpp index 2931325d8b57981fc097fb19a3f6cfbc0746ad54..1b92d2e60cc1731171a402e736e5c7992ab9e145 100644 --- a/clang-tools-extra/clang-tidy/bugprone/BugproneTidyModule.cpp +++ b/clang-tools-extra/clang-tidy/bugprone/BugproneTidyModule.cpp @@ -54,6 +54,7 @@ #include "PosixReturnCheck.h" #include "RedundantBranchConditionCheck.h" #include "ReservedIdentifierCheck.h" +#include "ReturnConstRefFromParameterCheck.h" #include "SharedPtrArrayMismatchCheck.h" #include "SignalHandlerCheck.h" #include "SignedCharMisuseCheck.h" @@ -137,6 +138,8 @@ public: "bugprone-inaccurate-erase"); CheckFactories.registerCheck( "bugprone-incorrect-enable-if"); + CheckFactories.registerCheck( + "bugprone-return-const-ref-from-parameter"); CheckFactories.registerCheck( "bugprone-switch-missing-default-case"); CheckFactories.registerCheck( diff --git a/clang-tools-extra/clang-tidy/bugprone/CMakeLists.txt b/clang-tools-extra/clang-tidy/bugprone/CMakeLists.txt index 081ba67efe1538e3378e53a1f7718299a650d4e7..2d303191f88650bd1b611d95376f0f6f84916570 100644 --- a/clang-tools-extra/clang-tidy/bugprone/CMakeLists.txt +++ b/clang-tools-extra/clang-tidy/bugprone/CMakeLists.txt @@ -26,6 +26,7 @@ add_clang_library(clangTidyBugproneModule ImplicitWideningOfMultiplicationResultCheck.cpp InaccurateEraseCheck.cpp IncorrectEnableIfCheck.cpp + ReturnConstRefFromParameterCheck.cpp SuspiciousStringviewDataUsageCheck.cpp SwitchMissingDefaultCaseCheck.cpp IncDecInConditionsCheck.cpp diff --git a/clang-tools-extra/clang-tidy/bugprone/EasilySwappableParametersCheck.cpp b/clang-tools-extra/clang-tidy/bugprone/EasilySwappableParametersCheck.cpp index 84e99c7fafc74b2930bea63155fa3a1506152713..10868129e76da955c45a4555b55088c806420b65 100644 --- a/clang-tools-extra/clang-tidy/bugprone/EasilySwappableParametersCheck.cpp +++ b/clang-tools-extra/clang-tidy/bugprone/EasilySwappableParametersCheck.cpp @@ -967,7 +967,8 @@ approximateStandardConversionSequence(const TheCheck &Check, QualType From, // Get out the qualifiers of the original type. This will always be // re-applied to the WorkType to ensure it is the same qualification as the // original From was. - auto QualifiersToApply = From.split().Quals.getAsOpaqueValue(); + auto FastQualifiersToApply = static_cast( + From.split().Quals.getAsOpaqueValue() & Qualifiers::FastMask); // LValue->RValue is irrelevant for the check, because it is a thing to be // done at a call site, and will be performed if need be performed. @@ -993,7 +994,7 @@ approximateStandardConversionSequence(const TheCheck &Check, QualType From, // "const double -> double". LLVM_DEBUG(llvm::dbgs() << "--- approximateStdConv. Conversion between numerics.\n"); - WorkType = QualType{ToBuiltin, QualifiersToApply}; + WorkType = QualType{ToBuiltin, FastQualifiersToApply}; } const auto *FromEnum = WorkType->getAs(); @@ -1002,7 +1003,7 @@ approximateStandardConversionSequence(const TheCheck &Check, QualType From, // Unscoped enumerations (or enumerations in C) convert to numerics. LLVM_DEBUG(llvm::dbgs() << "--- approximateStdConv. Unscoped enum to numeric.\n"); - WorkType = QualType{ToBuiltin, QualifiersToApply}; + WorkType = QualType{ToBuiltin, FastQualifiersToApply}; } else if (FromNumeric && ToEnum && ToEnum->isUnscopedEnumerationType()) { // Numeric types convert to enumerations only in C. if (Ctx.getLangOpts().CPlusPlus) { @@ -1013,7 +1014,7 @@ approximateStandardConversionSequence(const TheCheck &Check, QualType From, LLVM_DEBUG(llvm::dbgs() << "--- approximateStdConv. Numeric to unscoped enum.\n"); - WorkType = QualType{ToEnum, QualifiersToApply}; + WorkType = QualType{ToEnum, FastQualifiersToApply}; } // Check for pointer conversions. @@ -1022,14 +1023,14 @@ approximateStandardConversionSequence(const TheCheck &Check, QualType From, if (FromPtr && ToPtr) { if (ToPtr->isVoidPointerType()) { LLVM_DEBUG(llvm::dbgs() << "--- approximateStdConv. To void pointer.\n"); - WorkType = QualType{ToPtr, QualifiersToApply}; + WorkType = QualType{ToPtr, FastQualifiersToApply}; } const auto *FromRecordPtr = FromPtr->getPointeeCXXRecordDecl(); const auto *ToRecordPtr = ToPtr->getPointeeCXXRecordDecl(); if (isDerivedToBase(FromRecordPtr, ToRecordPtr)) { LLVM_DEBUG(llvm::dbgs() << "--- approximateStdConv. Derived* to Base*\n"); - WorkType = QualType{ToPtr, QualifiersToApply}; + WorkType = QualType{ToPtr, FastQualifiersToApply}; } } @@ -1039,7 +1040,7 @@ approximateStandardConversionSequence(const TheCheck &Check, QualType From, const auto *ToRecord = To->getAsCXXRecordDecl(); if (isDerivedToBase(FromRecord, ToRecord)) { LLVM_DEBUG(llvm::dbgs() << "--- approximateStdConv. Derived To Base.\n"); - WorkType = QualType{ToRecord->getTypeForDecl(), QualifiersToApply}; + WorkType = QualType{ToRecord->getTypeForDecl(), FastQualifiersToApply}; } if (Ctx.getLangOpts().CPlusPlus17 && FromPtr && ToPtr) { @@ -1054,7 +1055,7 @@ approximateStandardConversionSequence(const TheCheck &Check, QualType From, !ToFunctionPtr->hasNoexceptExceptionSpec()) { LLVM_DEBUG(llvm::dbgs() << "--- approximateStdConv. noexcept function " "pointer to non-noexcept.\n"); - WorkType = QualType{ToPtr, QualifiersToApply}; + WorkType = QualType{ToPtr, FastQualifiersToApply}; } } diff --git a/clang-tools-extra/clang-tidy/bugprone/ReturnConstRefFromParameterCheck.cpp b/clang-tools-extra/clang-tidy/bugprone/ReturnConstRefFromParameterCheck.cpp new file mode 100644 index 0000000000000000000000000000000000000000..8ae37d4f774d23041cb9b9816ae6e0d0e2c792d7 --- /dev/null +++ b/clang-tools-extra/clang-tidy/bugprone/ReturnConstRefFromParameterCheck.cpp @@ -0,0 +1,34 @@ +//===--- ReturnConstRefFromParameterCheck.cpp - clang-tidy ----------------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#include "ReturnConstRefFromParameterCheck.h" +#include "../utils/Matchers.h" +#include "clang/ASTMatchers/ASTMatchFinder.h" +#include "clang/ASTMatchers/ASTMatchers.h" + +using namespace clang::ast_matchers; + +namespace clang::tidy::bugprone { + +void ReturnConstRefFromParameterCheck::registerMatchers(MatchFinder *Finder) { + Finder->addMatcher( + returnStmt(hasReturnValue(declRefExpr(to(parmVarDecl(hasType( + hasCanonicalType(matchers::isReferenceToConst()))))))) + .bind("ret"), + this); +} + +void ReturnConstRefFromParameterCheck::check( + const MatchFinder::MatchResult &Result) { + const auto *R = Result.Nodes.getNodeAs("ret"); + diag(R->getRetValue()->getBeginLoc(), + "returning a constant reference parameter may cause a use-after-free " + "when the parameter is constructed from a temporary"); +} + +} // namespace clang::tidy::bugprone diff --git a/clang-tools-extra/clang-tidy/bugprone/ReturnConstRefFromParameterCheck.h b/clang-tools-extra/clang-tidy/bugprone/ReturnConstRefFromParameterCheck.h new file mode 100644 index 0000000000000000000000000000000000000000..8768d07087383f387f922b122259e4d2af67d028 --- /dev/null +++ b/clang-tools-extra/clang-tidy/bugprone/ReturnConstRefFromParameterCheck.h @@ -0,0 +1,40 @@ +//===--- ReturnConstRefFromParameterCheck.h - clang-tidy --------*- C++ -*-===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#ifndef LLVM_CLANG_TOOLS_EXTRA_CLANG_TIDY_BUGPRONE_RETURNCONSTREFFROMPARAMETERCHECK_H +#define LLVM_CLANG_TOOLS_EXTRA_CLANG_TIDY_BUGPRONE_RETURNCONSTREFFROMPARAMETERCHECK_H + +#include "../ClangTidyCheck.h" + +namespace clang::tidy::bugprone { + +/// Detects return statements that return a constant reference parameter as +/// constant reference. This may cause use-after-free errors if the caller uses +/// xvalues as arguments. +/// +/// For the user-facing documentation see: +/// http://clang.llvm.org/extra/clang-tidy/checks/bugprone/return-const-ref-from-parameter.html +class ReturnConstRefFromParameterCheck : public ClangTidyCheck { +public: + ReturnConstRefFromParameterCheck(StringRef Name, ClangTidyContext *Context) + : ClangTidyCheck(Name, Context) {} + void registerMatchers(ast_matchers::MatchFinder *Finder) override; + void check(const ast_matchers::MatchFinder::MatchResult &Result) override; + std::optional getCheckTraversalKind() const override { + // Use 'AsIs' to make sure the return type is exactly the same as the + // parameter type. + return TK_AsIs; + } + bool isLanguageVersionSupported(const LangOptions &LangOpts) const override { + return LangOpts.CPlusPlus; + } +}; + +} // namespace clang::tidy::bugprone + +#endif // LLVM_CLANG_TOOLS_EXTRA_CLANG_TIDY_BUGPRONE_RETURNCONSTREFFROMPARAMETERCHECK_H diff --git a/clang-tools-extra/clang-tidy/modernize/CMakeLists.txt b/clang-tools-extra/clang-tidy/modernize/CMakeLists.txt index 6852db6c2ee31103b684e93114cc29b9d9c5f633..8005d6e91c060c6e9b0e08d8f11cffb094c5fa4e 100644 --- a/clang-tools-extra/clang-tidy/modernize/CMakeLists.txt +++ b/clang-tools-extra/clang-tidy/modernize/CMakeLists.txt @@ -16,6 +16,7 @@ add_clang_library(clangTidyModernizeModule MakeSharedCheck.cpp MakeSmartPtrCheck.cpp MakeUniqueCheck.cpp + MinMaxUseInitializerListCheck.cpp ModernizeTidyModule.cpp PassByValueCheck.cpp RawStringLiteralCheck.cpp diff --git a/clang-tools-extra/clang-tidy/modernize/MinMaxUseInitializerListCheck.cpp b/clang-tools-extra/clang-tidy/modernize/MinMaxUseInitializerListCheck.cpp new file mode 100644 index 0000000000000000000000000000000000000000..45f7700463d5708673a78d5caf31cea9a3d0dd17 --- /dev/null +++ b/clang-tools-extra/clang-tidy/modernize/MinMaxUseInitializerListCheck.cpp @@ -0,0 +1,271 @@ +//===--- MinMaxUseInitializerListCheck.cpp - clang-tidy -------------------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#include "MinMaxUseInitializerListCheck.h" +#include "../utils/ASTUtils.h" +#include "../utils/LexerUtils.h" +#include "clang/ASTMatchers/ASTMatchFinder.h" +#include "clang/Frontend/CompilerInstance.h" +#include "clang/Lex/Lexer.h" + +using namespace clang; + +namespace { + +struct FindArgsResult { + const Expr *First; + const Expr *Last; + const Expr *Compare; + SmallVector Args; +}; + +} // anonymous namespace + +using namespace clang::ast_matchers; + +namespace clang::tidy::modernize { + +static FindArgsResult findArgs(const CallExpr *Call) { + FindArgsResult Result; + Result.First = nullptr; + Result.Last = nullptr; + Result.Compare = nullptr; + + // check if the function has initializer list argument + if (Call->getNumArgs() < 3) { + auto ArgIterator = Call->arguments().begin(); + + const auto *InitListExpr = + dyn_cast(*ArgIterator); + const auto *InitList = + InitListExpr != nullptr + ? dyn_cast( + InitListExpr->getSubExpr()->IgnoreImplicit()) + : nullptr; + + if (InitList) { + Result.Args.append(InitList->inits().begin(), InitList->inits().end()); + Result.First = *ArgIterator; + Result.Last = *ArgIterator; + + // check if there is a comparison argument + std::advance(ArgIterator, 1); + if (ArgIterator != Call->arguments().end()) + Result.Compare = *ArgIterator; + + return Result; + } + Result.Args = SmallVector(Call->arguments()); + } else { + // if it has 3 arguments then the last will be the comparison + Result.Compare = *(std::next(Call->arguments().begin(), 2)); + Result.Args = SmallVector(llvm::drop_end(Call->arguments())); + } + Result.First = Result.Args.front(); + Result.Last = Result.Args.back(); + + return Result; +} + +static SmallVector +generateReplacements(const MatchFinder::MatchResult &Match, + const CallExpr *TopCall, const FindArgsResult &Result, + const bool IgnoreNonTrivialTypes, + const std::uint64_t IgnoreTrivialTypesOfSizeAbove) { + SmallVector FixItHints; + const SourceManager &SourceMngr = *Match.SourceManager; + const LangOptions &LanguageOpts = Match.Context->getLangOpts(); + + const QualType ResultType = TopCall->getDirectCallee() + ->getReturnType() + .getCanonicalType() + .getNonReferenceType() + .getUnqualifiedType(); + + // check if the type is trivial + const bool IsResultTypeTrivial = ResultType.isTrivialType(*Match.Context); + + if ((!IsResultTypeTrivial && IgnoreNonTrivialTypes)) + return FixItHints; + + if (IsResultTypeTrivial && + static_cast( + Match.Context->getTypeSizeInChars(ResultType).getQuantity()) > + IgnoreTrivialTypesOfSizeAbove) + return FixItHints; + + for (const Expr *Arg : Result.Args) { + const auto *InnerCall = dyn_cast(Arg->IgnoreParenImpCasts()); + + // If the argument is not a nested call + if (!InnerCall) { + // check if typecast is required + const QualType ArgType = Arg->IgnoreParenImpCasts() + ->getType() + .getCanonicalType() + .getUnqualifiedType(); + + if (ArgType == ResultType) + continue; + + const StringRef ArgText = Lexer::getSourceText( + CharSourceRange::getTokenRange(Arg->getSourceRange()), SourceMngr, + LanguageOpts); + + const auto Replacement = Twine("static_cast<") + .concat(ResultType.getAsString(LanguageOpts)) + .concat(">(") + .concat(ArgText) + .concat(")") + .str(); + + FixItHints.push_back( + FixItHint::CreateReplacement(Arg->getSourceRange(), Replacement)); + continue; + } + + const FindArgsResult InnerResult = findArgs(InnerCall); + + // if the nested call doesn't have arguments skip it + if (!InnerResult.First || !InnerResult.Last) + continue; + + // if the nested call is not the same as the top call + if (InnerCall->getDirectCallee()->getQualifiedNameAsString() != + TopCall->getDirectCallee()->getQualifiedNameAsString()) + continue; + + // if the nested call doesn't have the same compare function + if ((Result.Compare || InnerResult.Compare) && + !utils::areStatementsIdentical(Result.Compare, InnerResult.Compare, + *Match.Context)) + continue; + + // remove the function call + FixItHints.push_back( + FixItHint::CreateRemoval(InnerCall->getCallee()->getSourceRange())); + + // remove the parentheses + const auto LParen = utils::lexer::findNextTokenSkippingComments( + InnerCall->getCallee()->getEndLoc(), SourceMngr, LanguageOpts); + if (LParen.has_value() && LParen->is(tok::l_paren)) + FixItHints.push_back( + FixItHint::CreateRemoval(SourceRange(LParen->getLocation()))); + FixItHints.push_back( + FixItHint::CreateRemoval(SourceRange(InnerCall->getRParenLoc()))); + + // if the inner call has an initializer list arg + if (InnerResult.First == InnerResult.Last) { + // remove the initializer list braces + FixItHints.push_back(FixItHint::CreateRemoval( + CharSourceRange::getTokenRange(InnerResult.First->getBeginLoc()))); + FixItHints.push_back(FixItHint::CreateRemoval( + CharSourceRange::getTokenRange(InnerResult.First->getEndLoc()))); + } + + const SmallVector InnerReplacements = generateReplacements( + Match, InnerCall, InnerResult, IgnoreNonTrivialTypes, + IgnoreTrivialTypesOfSizeAbove); + + FixItHints.append(InnerReplacements); + + if (InnerResult.Compare) { + // find the comma after the value arguments + const auto Comma = utils::lexer::findNextTokenSkippingComments( + InnerResult.Last->getEndLoc(), SourceMngr, LanguageOpts); + + // remove the comma and the comparison + if (Comma.has_value() && Comma->is(tok::comma)) + FixItHints.push_back( + FixItHint::CreateRemoval(SourceRange(Comma->getLocation()))); + + FixItHints.push_back( + FixItHint::CreateRemoval(InnerResult.Compare->getSourceRange())); + } + } + + return FixItHints; +} + +MinMaxUseInitializerListCheck::MinMaxUseInitializerListCheck( + StringRef Name, ClangTidyContext *Context) + : ClangTidyCheck(Name, Context), + IgnoreNonTrivialTypes(Options.get("IgnoreNonTrivialTypes", true)), + IgnoreTrivialTypesOfSizeAbove( + Options.get("IgnoreTrivialTypesOfSizeAbove", 32L)), + Inserter(Options.getLocalOrGlobal("IncludeStyle", + utils::IncludeSorter::IS_LLVM), + areDiagsSelfContained()) {} + +void MinMaxUseInitializerListCheck::storeOptions( + ClangTidyOptions::OptionMap &Opts) { + Options.store(Opts, "IgnoreNonTrivialTypes", IgnoreNonTrivialTypes); + Options.store(Opts, "IgnoreTrivialTypesOfSizeAbove", + IgnoreTrivialTypesOfSizeAbove); + Options.store(Opts, "IncludeStyle", Inserter.getStyle()); +} + +void MinMaxUseInitializerListCheck::registerMatchers(MatchFinder *Finder) { + auto CreateMatcher = [](const StringRef FunctionName) { + auto FuncDecl = functionDecl(hasName(FunctionName)); + auto Expression = callExpr(callee(FuncDecl)); + + return callExpr(callee(FuncDecl), + anyOf(hasArgument(0, Expression), + hasArgument(1, Expression), + hasArgument(0, cxxStdInitializerListExpr())), + unless(hasParent(Expression))) + .bind("topCall"); + }; + + Finder->addMatcher(CreateMatcher("::std::max"), this); + Finder->addMatcher(CreateMatcher("::std::min"), this); +} + +void MinMaxUseInitializerListCheck::registerPPCallbacks( + const SourceManager &SM, Preprocessor *PP, Preprocessor *ModuleExpanderPP) { + Inserter.registerPreprocessor(PP); +} + +void MinMaxUseInitializerListCheck::check( + const MatchFinder::MatchResult &Match) { + + const auto *TopCall = Match.Nodes.getNodeAs("topCall"); + + const FindArgsResult Result = findArgs(TopCall); + const SmallVector Replacements = + generateReplacements(Match, TopCall, Result, IgnoreNonTrivialTypes, + IgnoreTrivialTypesOfSizeAbove); + + if (Replacements.empty()) + return; + + const DiagnosticBuilder Diagnostic = + diag(TopCall->getBeginLoc(), + "do not use nested 'std::%0' calls, use an initializer list instead") + << TopCall->getDirectCallee()->getName() + << Inserter.createIncludeInsertion( + Match.SourceManager->getFileID(TopCall->getBeginLoc()), + ""); + + // if the top call doesn't have an initializer list argument + if (Result.First != Result.Last) { + // add { and } insertions + Diagnostic << FixItHint::CreateInsertion(Result.First->getBeginLoc(), "{"); + + Diagnostic << FixItHint::CreateInsertion( + Lexer::getLocForEndOfToken(Result.Last->getEndLoc(), 0, + *Match.SourceManager, + Match.Context->getLangOpts()), + "}"); + } + + Diagnostic << Replacements; +} + +} // namespace clang::tidy::modernize diff --git a/clang-tools-extra/clang-tidy/modernize/MinMaxUseInitializerListCheck.h b/clang-tools-extra/clang-tidy/modernize/MinMaxUseInitializerListCheck.h new file mode 100644 index 0000000000000000000000000000000000000000..577d12653076124235cf25227544ce4ad091bb15 --- /dev/null +++ b/clang-tools-extra/clang-tidy/modernize/MinMaxUseInitializerListCheck.h @@ -0,0 +1,56 @@ +//===--- MinMaxUseInitializerListCheck.h - clang-tidy -----------*- C++ -*-===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#ifndef LLVM_CLANG_TOOLS_EXTRA_CLANG_TIDY_MODERNIZE_MINMAXUSEINITIALIZERLISTCHECK_H +#define LLVM_CLANG_TOOLS_EXTRA_CLANG_TIDY_MODERNIZE_MINMAXUSEINITIALIZERLISTCHECK_H + +#include "../ClangTidyCheck.h" +#include "../utils/IncludeInserter.h" + +namespace clang::tidy::modernize { + +/// Replaces nested ``std::min`` and ``std::max`` calls with an initializer list +/// where applicable. +/// +/// For example: +/// +/// \code +/// int a = std::max(std::max(i, j), k); +/// \endcode +/// +/// This code is transformed to: +/// +/// \code +/// int a = std::max({i, j, k}); +/// \endcode +class MinMaxUseInitializerListCheck : public ClangTidyCheck { +public: + MinMaxUseInitializerListCheck(StringRef Name, ClangTidyContext *Context); + + void storeOptions(ClangTidyOptions::OptionMap &Opts) override; + void registerMatchers(ast_matchers::MatchFinder *Finder) override; + void registerPPCallbacks(const SourceManager &SM, Preprocessor *PP, + Preprocessor *ModuleExpanderPP) override; + void check(const ast_matchers::MatchFinder::MatchResult &Match) override; + + bool isLanguageVersionSupported(const LangOptions &LangOpts) const override { + return LangOpts.CPlusPlus11; + } + std::optional getCheckTraversalKind() const override { + return TK_IgnoreUnlessSpelledInSource; + } + +private: + bool IgnoreNonTrivialTypes; + std::uint64_t IgnoreTrivialTypesOfSizeAbove; + utils::IncludeInserter Inserter; +}; + +} // namespace clang::tidy::modernize + +#endif // LLVM_CLANG_TOOLS_EXTRA_CLANG_TIDY_MODERNIZE_MINMAXUSEINITIALIZERLISTCHECK_H diff --git a/clang-tools-extra/clang-tidy/modernize/ModernizeTidyModule.cpp b/clang-tools-extra/clang-tidy/modernize/ModernizeTidyModule.cpp index e96cf274f58cfefccb746abd6f6f5d89f69dfe26..776558433c5baa492e8f33637becee5d85775de1 100644 --- a/clang-tools-extra/clang-tidy/modernize/ModernizeTidyModule.cpp +++ b/clang-tools-extra/clang-tidy/modernize/ModernizeTidyModule.cpp @@ -18,6 +18,7 @@ #include "MacroToEnumCheck.h" #include "MakeSharedCheck.h" #include "MakeUniqueCheck.h" +#include "MinMaxUseInitializerListCheck.h" #include "PassByValueCheck.h" #include "RawStringLiteralCheck.h" #include "RedundantVoidArgCheck.h" @@ -68,6 +69,8 @@ public: CheckFactories.registerCheck("modernize-macro-to-enum"); CheckFactories.registerCheck("modernize-make-shared"); CheckFactories.registerCheck("modernize-make-unique"); + CheckFactories.registerCheck( + "modernize-min-max-use-initializer-list"); CheckFactories.registerCheck("modernize-pass-by-value"); CheckFactories.registerCheck( "modernize-use-designated-initializers"); diff --git a/clang-tools-extra/clang-tidy/modernize/UseStartsEndsWithCheck.cpp b/clang-tools-extra/clang-tidy/modernize/UseStartsEndsWithCheck.cpp index 062f6e9911dbed35d3848a8cf7e1202ae1ec85ba..89ee45faecd7f33e8f80189ee59fad02849695aa 100644 --- a/clang-tools-extra/clang-tidy/modernize/UseStartsEndsWithCheck.cpp +++ b/clang-tools-extra/clang-tidy/modernize/UseStartsEndsWithCheck.cpp @@ -43,7 +43,9 @@ void UseStartsEndsWithCheck::registerMatchers(MatchFinder *Finder) { callee(cxxMethodDecl(hasName("find")).bind("find_fun")), // ... on a class with a starts_with function. on(hasType( - hasCanonicalType(hasDeclaration(ClassWithStartsWithFunction))))); + hasCanonicalType(hasDeclaration(ClassWithStartsWithFunction)))), + // Bind search expression. + hasArgument(0, expr().bind("search_expr"))); const auto RFindExpr = cxxMemberCallExpr( // A method call with a second argument of zero... @@ -52,15 +54,68 @@ void UseStartsEndsWithCheck::registerMatchers(MatchFinder *Finder) { callee(cxxMethodDecl(hasName("rfind")).bind("find_fun")), // ... on a class with a starts_with function. on(hasType( - hasCanonicalType(hasDeclaration(ClassWithStartsWithFunction))))); + hasCanonicalType(hasDeclaration(ClassWithStartsWithFunction)))), + // Bind search expression. + hasArgument(0, expr().bind("search_expr"))); + + // Match a string literal and an integer or strlen() call matching the length. + const auto HasStringLiteralAndLengthArgs = [](const auto StringArgIndex, + const auto LengthArgIndex) { + return allOf( + hasArgument(StringArgIndex, stringLiteral().bind("string_literal_arg")), + hasArgument(LengthArgIndex, + anyOf(integerLiteral().bind("integer_literal_size_arg"), + callExpr(callee(functionDecl(parameterCountIs(1), + hasName("strlen"))), + hasArgument(0, stringLiteral().bind( + "strlen_arg")))))); + }; + + // Match a string variable and a call to length() or size(). + const auto HasStringVariableAndSizeCallArgs = [](const auto StringArgIndex, + const auto LengthArgIndex) { + return allOf( + hasArgument(StringArgIndex, declRefExpr(hasDeclaration( + decl().bind("string_var_decl")))), + hasArgument(LengthArgIndex, + cxxMemberCallExpr( + callee(cxxMethodDecl(isConst(), parameterCountIs(0), + hasAnyName("size", "length"))), + on(declRefExpr( + to(decl(equalsBoundNode("string_var_decl")))))))); + }; - const auto FindOrRFindExpr = - cxxMemberCallExpr(anyOf(FindExpr, RFindExpr)).bind("find_expr"); + // Match either one of the two cases above. + const auto HasStringAndLengthArgs = + [HasStringLiteralAndLengthArgs, HasStringVariableAndSizeCallArgs]( + const auto StringArgIndex, const auto LengthArgIndex) { + return anyOf( + HasStringLiteralAndLengthArgs(StringArgIndex, LengthArgIndex), + HasStringVariableAndSizeCallArgs(StringArgIndex, LengthArgIndex)); + }; + + const auto CompareExpr = cxxMemberCallExpr( + // A method call with three arguments... + argumentCountIs(3), + // ... where the first argument is zero... + hasArgument(0, ZeroLiteral), + // ... named compare... + callee(cxxMethodDecl(hasName("compare")).bind("find_fun")), + // ... on a class with a starts_with function... + on(hasType( + hasCanonicalType(hasDeclaration(ClassWithStartsWithFunction)))), + // ... where the third argument is some string and the second a length. + HasStringAndLengthArgs(2, 1), + // Bind search expression. + hasArgument(2, expr().bind("search_expr"))); Finder->addMatcher( - // Match [=!]= with a zero on one side and a string.(r?)find on the other. - binaryOperator(hasAnyOperatorName("==", "!="), - hasOperands(FindOrRFindExpr, ZeroLiteral)) + // Match [=!]= with a zero on one side and (r?)find|compare on the other. + binaryOperator( + hasAnyOperatorName("==", "!="), + hasOperands(cxxMemberCallExpr(anyOf(FindExpr, RFindExpr, CompareExpr)) + .bind("find_expr"), + ZeroLiteral)) .bind("expr"), this); } @@ -69,9 +124,28 @@ void UseStartsEndsWithCheck::check(const MatchFinder::MatchResult &Result) { const auto *ComparisonExpr = Result.Nodes.getNodeAs("expr"); const auto *FindExpr = Result.Nodes.getNodeAs("find_expr"); const auto *FindFun = Result.Nodes.getNodeAs("find_fun"); + const auto *SearchExpr = Result.Nodes.getNodeAs("search_expr"); const auto *StartsWithFunction = Result.Nodes.getNodeAs("starts_with_fun"); + const auto *StringLiteralArg = + Result.Nodes.getNodeAs("string_literal_arg"); + const auto *IntegerLiteralSizeArg = + Result.Nodes.getNodeAs("integer_literal_size_arg"); + const auto *StrlenArg = Result.Nodes.getNodeAs("strlen_arg"); + + // Filter out compare cases where the length does not match string literal. + if (StringLiteralArg && IntegerLiteralSizeArg && + StringLiteralArg->getLength() != + IntegerLiteralSizeArg->getValue().getZExtValue()) { + return; + } + + if (StringLiteralArg && StrlenArg && + StringLiteralArg->getLength() != StrlenArg->getLength()) { + return; + } + if (ComparisonExpr->getBeginLoc().isMacroID()) { return; } @@ -79,13 +153,13 @@ void UseStartsEndsWithCheck::check(const MatchFinder::MatchResult &Result) { const bool Neg = ComparisonExpr->getOpcode() == BO_NE; auto Diagnostic = - diag(FindExpr->getBeginLoc(), "use %0 instead of %1() %select{==|!=}2 0") + diag(FindExpr->getExprLoc(), "use %0 instead of %1() %select{==|!=}2 0") << StartsWithFunction->getName() << FindFun->getName() << Neg; - // Remove possible zero second argument and ' [!=]= 0' suffix. + // Remove possible arguments after search expression and ' [!=]= 0' suffix. Diagnostic << FixItHint::CreateReplacement( CharSourceRange::getTokenRange( - Lexer::getLocForEndOfToken(FindExpr->getArg(0)->getEndLoc(), 0, + Lexer::getLocForEndOfToken(SearchExpr->getEndLoc(), 0, *Result.SourceManager, getLangOpts()), ComparisonExpr->getEndLoc()), ")"); @@ -94,11 +168,12 @@ void UseStartsEndsWithCheck::check(const MatchFinder::MatchResult &Result) { Diagnostic << FixItHint::CreateRemoval(CharSourceRange::getCharRange( ComparisonExpr->getBeginLoc(), FindExpr->getBeginLoc())); - // Replace '(r?)find' with 'starts_with'. + // Replace method name by 'starts_with'. + // Remove possible arguments before search expression. Diagnostic << FixItHint::CreateReplacement( - CharSourceRange::getTokenRange(FindExpr->getExprLoc(), - FindExpr->getExprLoc()), - StartsWithFunction->getName()); + CharSourceRange::getCharRange(FindExpr->getExprLoc(), + SearchExpr->getBeginLoc()), + (StartsWithFunction->getName() + "(").str()); // Add possible negation '!'. if (Neg) { diff --git a/clang-tools-extra/clang-tidy/modernize/UseStartsEndsWithCheck.h b/clang-tools-extra/clang-tidy/modernize/UseStartsEndsWithCheck.h index 34e97177682575c97849f542f5679a3366ba0ec6..840191f321493fe49e440b4bb7bbfc5407c64b3b 100644 --- a/clang-tools-extra/clang-tidy/modernize/UseStartsEndsWithCheck.h +++ b/clang-tools-extra/clang-tidy/modernize/UseStartsEndsWithCheck.h @@ -13,9 +13,10 @@ namespace clang::tidy::modernize { -/// Checks whether a ``find`` or ``rfind`` result is compared with 0 and -/// suggests replacing with ``starts_with`` when the method exists in the class. -/// Notably, this will work with ``std::string`` and ``std::string_view``. +/// Checks for common roundabout ways to express ``starts_with`` and +/// ``ends_with`` and suggests replacing with ``starts_with`` when the method is +/// available. Notably, this will work with ``std::string`` and +/// ``std::string_view``. /// /// For the user-facing documentation see: /// http://clang.llvm.org/extra/clang-tidy/checks/modernize/use-starts-ends-with.html diff --git a/clang-tools-extra/clang-tidy/readability/CMakeLists.txt b/clang-tools-extra/clang-tidy/readability/CMakeLists.txt index dd772d692025481a9eae7475168f96ec29baf6fe..41065fc8e8785903b220113cde72e3e286166c3b 100644 --- a/clang-tools-extra/clang-tidy/readability/CMakeLists.txt +++ b/clang-tools-extra/clang-tidy/readability/CMakeLists.txt @@ -28,6 +28,7 @@ add_clang_library(clangTidyReadabilityModule IsolateDeclarationCheck.cpp MagicNumbersCheck.cpp MakeMemberFunctionConstCheck.cpp + MathMissingParenthesesCheck.cpp MisleadingIndentationCheck.cpp MisplacedArrayIndexCheck.cpp NamedParameterCheck.cpp diff --git a/clang-tools-extra/clang-tidy/readability/MathMissingParenthesesCheck.cpp b/clang-tools-extra/clang-tidy/readability/MathMissingParenthesesCheck.cpp new file mode 100644 index 0000000000000000000000000000000000000000..d1e20b9074cec1b823aee92c927544c7a3ae6590 --- /dev/null +++ b/clang-tools-extra/clang-tidy/readability/MathMissingParenthesesCheck.cpp @@ -0,0 +1,97 @@ +//===--- MathMissingParenthesesCheck.cpp - clang-tidy ---------------------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#include "MathMissingParenthesesCheck.h" +#include "clang/AST/ASTContext.h" +#include "clang/ASTMatchers/ASTMatchFinder.h" +#include "clang/Lex/Lexer.h" + +using namespace clang::ast_matchers; + +namespace clang::tidy::readability { + +void MathMissingParenthesesCheck::registerMatchers(MatchFinder *Finder) { + Finder->addMatcher(binaryOperator(unless(hasParent(binaryOperator())), + unless(isAssignmentOperator()), + unless(isComparisonOperator()), + unless(hasAnyOperatorName("&&", "||")), + hasDescendant(binaryOperator())) + .bind("binOp"), + this); +} + +static int getPrecedence(const BinaryOperator *BinOp) { + if (!BinOp) + return 0; + switch (BinOp->getOpcode()) { + case BO_Mul: + case BO_Div: + case BO_Rem: + return 5; + case BO_Add: + case BO_Sub: + return 4; + case BO_And: + return 3; + case BO_Xor: + return 2; + case BO_Or: + return 1; + default: + return 0; + } +} +static void addParantheses(const BinaryOperator *BinOp, + const BinaryOperator *ParentBinOp, + ClangTidyCheck *Check, + const clang::SourceManager &SM, + const clang::LangOptions &LangOpts) { + if (!BinOp) + return; + + int Precedence1 = getPrecedence(BinOp); + int Precedence2 = getPrecedence(ParentBinOp); + + if (ParentBinOp != nullptr && Precedence1 != Precedence2) { + const clang::SourceLocation StartLoc = BinOp->getBeginLoc(); + const clang::SourceLocation EndLoc = + clang::Lexer::getLocForEndOfToken(BinOp->getEndLoc(), 0, SM, LangOpts); + if (EndLoc.isInvalid()) + return; + + Check->diag(StartLoc, + "'%0' has higher precedence than '%1'; add parentheses to " + "explicitly specify the order of operations") + << (Precedence1 > Precedence2 ? BinOp->getOpcodeStr() + : ParentBinOp->getOpcodeStr()) + << (Precedence1 > Precedence2 ? ParentBinOp->getOpcodeStr() + : BinOp->getOpcodeStr()) + << FixItHint::CreateInsertion(StartLoc, "(") + << FixItHint::CreateInsertion(EndLoc, ")") + << SourceRange(StartLoc, EndLoc); + } + + addParantheses(dyn_cast(BinOp->getLHS()->IgnoreImpCasts()), + BinOp, Check, SM, LangOpts); + addParantheses(dyn_cast(BinOp->getRHS()->IgnoreImpCasts()), + BinOp, Check, SM, LangOpts); +} + +void MathMissingParenthesesCheck::check( + const MatchFinder::MatchResult &Result) { + const auto *BinOp = Result.Nodes.getNodeAs("binOp"); + std::vector< + std::pair>> + Insertions; + const SourceManager &SM = *Result.SourceManager; + const clang::LangOptions &LO = Result.Context->getLangOpts(); + addParantheses(BinOp, nullptr, this, SM, LO); +} + +} // namespace clang::tidy::readability diff --git a/clang-tools-extra/clang-tidy/readability/MathMissingParenthesesCheck.h b/clang-tools-extra/clang-tidy/readability/MathMissingParenthesesCheck.h new file mode 100644 index 0000000000000000000000000000000000000000..9a9d2b3cfaabaeb928b18a088791a2dec723434c --- /dev/null +++ b/clang-tools-extra/clang-tidy/readability/MathMissingParenthesesCheck.h @@ -0,0 +1,34 @@ +//===--- MathMissingParenthesesCheck.h - clang-tidy -------------*- C++ -*-===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#ifndef LLVM_CLANG_TOOLS_EXTRA_CLANG_TIDY_READABILITY_MATHMISSINGPARENTHESESCHECK_H +#define LLVM_CLANG_TOOLS_EXTRA_CLANG_TIDY_READABILITY_MATHMISSINGPARENTHESESCHECK_H + +#include "../ClangTidyCheck.h" + +namespace clang::tidy::readability { + +/// Check for mising parantheses in mathematical expressions that involve +/// operators of different priorities. +/// +/// For the user-facing documentation see: +/// http://clang.llvm.org/extra/clang-tidy/checks/readability/math-missing-parentheses.html +class MathMissingParenthesesCheck : public ClangTidyCheck { +public: + MathMissingParenthesesCheck(StringRef Name, ClangTidyContext *Context) + : ClangTidyCheck(Name, Context) {} + void registerMatchers(ast_matchers::MatchFinder *Finder) override; + void check(const ast_matchers::MatchFinder::MatchResult &Result) override; + std::optional getCheckTraversalKind() const override { + return TK_IgnoreUnlessSpelledInSource; + } +}; + +} // namespace clang::tidy::readability + +#endif // LLVM_CLANG_TOOLS_EXTRA_CLANG_TIDY_READABILITY_MATHMISSINGPARENTHESESCHECK_H diff --git a/clang-tools-extra/clang-tidy/readability/ReadabilityTidyModule.cpp b/clang-tools-extra/clang-tidy/readability/ReadabilityTidyModule.cpp index 376b84683df74e4e8880431b58a70220b600e486..d61c0ba39658e5ff47fdd0a3ac2fdec28a10e155 100644 --- a/clang-tools-extra/clang-tidy/readability/ReadabilityTidyModule.cpp +++ b/clang-tools-extra/clang-tidy/readability/ReadabilityTidyModule.cpp @@ -32,6 +32,7 @@ #include "IsolateDeclarationCheck.h" #include "MagicNumbersCheck.h" #include "MakeMemberFunctionConstCheck.h" +#include "MathMissingParenthesesCheck.h" #include "MisleadingIndentationCheck.h" #include "MisplacedArrayIndexCheck.h" #include "NamedParameterCheck.h" @@ -105,6 +106,8 @@ public: "readability-identifier-naming"); CheckFactories.registerCheck( "readability-implicit-bool-conversion"); + CheckFactories.registerCheck( + "readability-math-missing-parentheses"); CheckFactories.registerCheck( "readability-redundant-inline-specifier"); CheckFactories.registerCheck( diff --git a/clang-tools-extra/clangd/CodeCompletionStrings.cpp b/clang-tools-extra/clangd/CodeCompletionStrings.cpp index 2075e5965f181ede2a7c2b737b63afbc91ba8285..9b4442b0bb76fd780af6909772a89d2e6e069cde 100644 --- a/clang-tools-extra/clangd/CodeCompletionStrings.cpp +++ b/clang-tools-extra/clangd/CodeCompletionStrings.cpp @@ -253,7 +253,7 @@ void getSignature(const CodeCompletionString &CCS, std::string *Signature, if (!IncludeFunctionArguments && ResultKind == CodeCompletionResult::RK_Declaration) TruncateSnippetAt.emplace(Snippet->size()); - LLVM_FALLTHROUGH; + [[fallthrough]]; case CodeCompletionString::CK_RightParen: case CodeCompletionString::CK_LeftBracket: case CodeCompletionString::CK_RightBracket: diff --git a/clang-tools-extra/clangd/unittests/FindTargetTests.cpp b/clang-tools-extra/clangd/unittests/FindTargetTests.cpp index 799a549ff0816e388cb6acdda5e04d1ddb7f38b4..88aae2729904f4ae0859fe580cda0665b3104b45 100644 --- a/clang-tools-extra/clangd/unittests/FindTargetTests.cpp +++ b/clang-tools-extra/clangd/unittests/FindTargetTests.cpp @@ -839,7 +839,9 @@ TEST_F(TargetDeclTest, OverloadExpr) { [[delete]] x; } )cpp"; - EXPECT_DECLS("CXXDeleteExpr", "void operator delete(void *) noexcept"); + // Sized deallocation is enabled by default in C++14 onwards. + EXPECT_DECLS("CXXDeleteExpr", + "void operator delete(void *, unsigned long) noexcept"); } TEST_F(TargetDeclTest, DependentExprs) { diff --git a/clang-tools-extra/docs/ReleaseNotes.rst b/clang-tools-extra/docs/ReleaseNotes.rst index 28840b9beae881865b8836b855f737880f91f70a..2867fc9580304816616648686aa45c5fae87a6ac 100644 --- a/clang-tools-extra/docs/ReleaseNotes.rst +++ b/clang-tools-extra/docs/ReleaseNotes.rst @@ -117,6 +117,13 @@ New checks Detects error-prone Curiously Recurring Template Pattern usage, when the CRTP can be constructed outside itself and the derived class. +- New :doc:`bugprone-return-const-ref-from-parameter + ` check. + + Detects return statements that return a constant reference parameter as constant + reference. This may cause use-after-free errors if the caller uses xvalues as + arguments. + - New :doc:`bugprone-suspicious-stringview-data-usage ` check. @@ -124,6 +131,12 @@ New checks to reading out-of-bounds data due to inadequate or incorrect string null termination. +- New :doc:`modernize-min-max-use-initializer-list + ` check. + + Replaces nested ``std::min`` and ``std::max`` calls with an initializer list + where applicable. + - New :doc:`modernize-use-designated-initializers ` check. @@ -136,6 +149,12 @@ New checks Enforces consistent style for enumerators' initialization, covering three styles: none, first only, or all initialized explicitly. +- New :doc:`readability-math-missing-parentheses + ` check. + + Check for missing parentheses in mathematical expressions that involve + operators of different priorities. + - New :doc:`readability-use-std-min-max ` check. @@ -266,6 +285,10 @@ Changes in existing checks ` check to also remove any trailing whitespace when deleting the ``virtual`` keyword. +- Improved :doc:`modernize-use-starts-ends-with + ` check to also handle + calls to ``compare`` method. + - Improved :doc:`modernize-use-using ` check by adding support for detection of typedefs declared on function level. diff --git a/clang-tools-extra/docs/clang-tidy/checks/bugprone/return-const-ref-from-parameter.rst b/clang-tools-extra/docs/clang-tidy/checks/bugprone/return-const-ref-from-parameter.rst new file mode 100644 index 0000000000000000000000000000000000000000..f007dfe5499908d261e0939c21ff9412e3499656 --- /dev/null +++ b/clang-tools-extra/docs/clang-tidy/checks/bugprone/return-const-ref-from-parameter.rst @@ -0,0 +1,31 @@ +.. title:: clang-tidy - bugprone-return-const-ref-from-parameter + +bugprone-return-const-ref-from-parameter +======================================== + +Detects return statements that return a constant reference parameter as constant +reference. This may cause use-after-free errors if the caller uses xvalues as +arguments. + +In C++, constant reference parameters can accept xvalues which will be destructed +after the call. When the function returns such a parameter also as constant reference, +then the returned reference can be used after the object it refers to has been +destroyed. + +Example +------- + +.. code-block:: c++ + + struct S { + int v; + S(int); + ~S(); + }; + + const S &fn(const S &a) { + return a; + } + + const S& s = fn(S{1}); + s.v; // use after free diff --git a/clang-tools-extra/docs/clang-tidy/checks/list.rst b/clang-tools-extra/docs/clang-tidy/checks/list.rst index 3a06d7c30c9b79e647e2525a67577acf84121345..49747ff896ba5c6f8556af99a0993090328e406b 100644 --- a/clang-tools-extra/docs/clang-tidy/checks/list.rst +++ b/clang-tools-extra/docs/clang-tidy/checks/list.rst @@ -120,6 +120,7 @@ Clang-Tidy Checks :doc:`bugprone-posix-return `, "Yes" :doc:`bugprone-redundant-branch-condition `, "Yes" :doc:`bugprone-reserved-identifier `, "Yes" + :doc:`bugprone-return-const-ref-from-parameter ` :doc:`bugprone-shared-ptr-array-mismatch `, "Yes" :doc:`bugprone-signal-handler `, :doc:`bugprone-signed-char-misuse `, @@ -275,6 +276,7 @@ Clang-Tidy Checks :doc:`modernize-macro-to-enum `, "Yes" :doc:`modernize-make-shared `, "Yes" :doc:`modernize-make-unique `, "Yes" + :doc:`modernize-min-max-use-initializer-list `, "Yes" :doc:`modernize-pass-by-value `, "Yes" :doc:`modernize-raw-string-literal `, "Yes" :doc:`modernize-redundant-void-arg `, "Yes" @@ -362,6 +364,7 @@ Clang-Tidy Checks :doc:`readability-isolate-declaration `, "Yes" :doc:`readability-magic-numbers `, :doc:`readability-make-member-function-const `, "Yes" + :doc:`readability-math-missing-parentheses `, "Yes" :doc:`readability-misleading-indentation `, :doc:`readability-misplaced-array-index `, "Yes" :doc:`readability-named-parameter `, "Yes" diff --git a/clang-tools-extra/docs/clang-tidy/checks/modernize/min-max-use-initializer-list.rst b/clang-tools-extra/docs/clang-tidy/checks/modernize/min-max-use-initializer-list.rst new file mode 100644 index 0000000000000000000000000000000000000000..d6721a25629b05c71e5e5197de98d9ec7964c38a --- /dev/null +++ b/clang-tools-extra/docs/clang-tidy/checks/modernize/min-max-use-initializer-list.rst @@ -0,0 +1,50 @@ +.. title:: clang-tidy - modernize-min-max-use-initializer-list + +modernize-min-max-use-initializer-list +====================================== + +Replaces nested ``std::min`` and ``std::max`` calls with an initializer list +where applicable. + +For instance, consider the following code: + +.. code-block:: cpp + + int a = std::max(std::max(i, j), k); + +The check will transform the above code to: + +.. code-block:: cpp + + int a = std::max({i, j, k}); + +Performance Considerations +========================== + +While this check simplifies the code and makes it more readable, it may cause +performance degradation for non-trivial types due to the need to copy objects +into the initializer list. + +To avoid this, it is recommended to use `std::ref` or `std::cref` for +non-trivial types: + +.. code-block:: cpp + + std::string b = std::max({std::ref(i), std::ref(j), std::ref(k)}); + +Options +======= + +.. option:: IncludeStyle + + A string specifying which include-style is used, `llvm` or `google`. Default + is `llvm`. + +.. option:: IgnoreNonTrivialTypes + + A boolean specifying whether to ignore non-trivial types. Default is `true`. + +.. option:: IgnoreTrivialTypesOfSizeAbove + + An integer specifying the size (in bytes) above which trivial types are + ignored. Default is `32`. \ No newline at end of file diff --git a/clang-tools-extra/docs/clang-tidy/checks/modernize/use-starts-ends-with.rst b/clang-tools-extra/docs/clang-tidy/checks/modernize/use-starts-ends-with.rst index 7f8a262d2ab3aac9f4e13064062f584ea5d1460e..34237ede30a30b51f4c35703d7a2151171c356c4 100644 --- a/clang-tools-extra/docs/clang-tidy/checks/modernize/use-starts-ends-with.rst +++ b/clang-tools-extra/docs/clang-tidy/checks/modernize/use-starts-ends-with.rst @@ -3,15 +3,16 @@ modernize-use-starts-ends-with ============================== -Checks whether a ``find`` or ``rfind`` result is compared with 0 and suggests -replacing with ``starts_with`` when the method exists in the class. Notably, -this will work with ``std::string`` and ``std::string_view``. +Checks for common roundabout ways to express ``starts_with`` and ``ends_with`` +and suggests replacing with ``starts_with`` when the method is available. +Notably, this will work with ``std::string`` and ``std::string_view``. .. code-block:: c++ std::string s = "..."; if (s.find("prefix") == 0) { /* do something */ } if (s.rfind("prefix", 0) == 0) { /* do something */ } + if (s.compare(0, strlen("prefix"), "prefix") == 0) { /* do something */ } becomes @@ -20,3 +21,4 @@ becomes std::string s = "..."; if (s.starts_with("prefix")) { /* do something */ } if (s.starts_with("prefix")) { /* do something */ } + if (s.starts_with("prefix")) { /* do something */ } diff --git a/clang-tools-extra/docs/clang-tidy/checks/readability/math-missing-parentheses.rst b/clang-tools-extra/docs/clang-tidy/checks/readability/math-missing-parentheses.rst new file mode 100644 index 0000000000000000000000000000000000000000..21d66daab334c60d4b1cc6e1122ff75cab9b15e1 --- /dev/null +++ b/clang-tools-extra/docs/clang-tidy/checks/readability/math-missing-parentheses.rst @@ -0,0 +1,27 @@ +.. title:: clang-tidy - readability-math-missing-parentheses + +readability-math-missing-parentheses +==================================== + +Check for missing parentheses in mathematical expressions that involve operators +of different priorities. + +Parentheses in mathematical expressions clarify the order +of operations, especially with different-priority operators. Lengthy or multiline +expressions can obscure this order, leading to coding errors. IDEs can aid clarity +by highlighting parentheses. Explicitly using parentheses also clarifies what the +developer had in mind when writing the expression. Ensuring their presence reduces +ambiguity and errors, promoting clearer and more maintainable code. + +Before: + +.. code-block:: c++ + + int x = 1 + 2 * 3 - 4 / 5; + + +After: + +.. code-block:: c++ + + int x = 1 + (2 * 3) - (4 / 5); \ No newline at end of file diff --git a/clang-tools-extra/test/clang-tidy/checkers/Inputs/Headers/string b/clang-tools-extra/test/clang-tidy/checkers/Inputs/Headers/string index 28e2b4a231e52edbb3697d2e5c76d513c3062089..d031f27beb9dfef99d61b44bff19a6dc8e1a885f 100644 --- a/clang-tools-extra/test/clang-tidy/checkers/Inputs/Headers/string +++ b/clang-tools-extra/test/clang-tidy/checkers/Inputs/Headers/string @@ -44,6 +44,8 @@ struct basic_string { int compare(const C* s) const; int compare(size_type pos, size_type len, const _Type&) const; int compare(size_type pos, size_type len, const C* s) const; + template + int compare(size_type pos1, size_type count1, const StringViewLike& t) const; size_type find(const _Type& str, size_type pos = 0) const; size_type find(const C* s, size_type pos = 0) const; @@ -129,6 +131,8 @@ bool operator!=(const char*, const std::string&); bool operator==(const std::wstring&, const std::wstring&); bool operator==(const std::wstring&, const wchar_t*); bool operator==(const wchar_t*, const std::wstring&); + +size_t strlen(const char* str); } #endif // _STRING_ diff --git a/clang-tools-extra/test/clang-tidy/checkers/Inputs/Headers/string.h b/clang-tools-extra/test/clang-tidy/checkers/Inputs/Headers/string.h index 4ab7e930e4b5067f1b87529a5a9b3378a4bb59eb..af205868059a82aa0b34a4bf908538a6d71caad4 100644 --- a/clang-tools-extra/test/clang-tidy/checkers/Inputs/Headers/string.h +++ b/clang-tools-extra/test/clang-tidy/checkers/Inputs/Headers/string.h @@ -12,5 +12,6 @@ #include "stddef.h" void *memcpy(void *dest, const void *src, size_t n); +size_t strlen(const char* str); #endif // _STRING_H_ diff --git a/clang-tools-extra/test/clang-tidy/checkers/abseil/redundant-strcat-calls.cpp b/clang-tools-extra/test/clang-tidy/checkers/abseil/redundant-strcat-calls.cpp index ecd17bba293c5bf5eb524f310d376648e9f297de..dbd354b132e2ff4f46012dc4c1cf006e825d041d 100644 --- a/clang-tools-extra/test/clang-tidy/checkers/abseil/redundant-strcat-calls.cpp +++ b/clang-tools-extra/test/clang-tidy/checkers/abseil/redundant-strcat-calls.cpp @@ -1,8 +1,6 @@ // RUN: %check_clang_tidy %s abseil-redundant-strcat-calls %t -- -- -isystem %clang_tidy_headers #include -int strlen(const char *); - namespace absl { class string_view { diff --git a/clang-tools-extra/test/clang-tidy/checkers/bugprone/return-const-ref-from-parameter.cpp b/clang-tools-extra/test/clang-tidy/checkers/bugprone/return-const-ref-from-parameter.cpp new file mode 100644 index 0000000000000000000000000000000000000000..a83a019ec7437da6ccda446b20af87f0639ee303 --- /dev/null +++ b/clang-tools-extra/test/clang-tidy/checkers/bugprone/return-const-ref-from-parameter.cpp @@ -0,0 +1,31 @@ +// RUN: %check_clang_tidy %s bugprone-return-const-ref-from-parameter %t + +using T = int; +using TConst = int const; +using TConstRef = int const&; + +namespace invalid { + +int const &f1(int const &a) { return a; } +// CHECK-MESSAGES: :[[@LINE-1]]:38: warning: returning a constant reference parameter + +int const &f2(T const &a) { return a; } +// CHECK-MESSAGES: :[[@LINE-1]]:36: warning: returning a constant reference parameter + +int const &f3(TConstRef a) { return a; } +// CHECK-MESSAGES: :[[@LINE-1]]:37: warning: returning a constant reference parameter + +int const &f4(TConst &a) { return a; } +// CHECK-MESSAGES: :[[@LINE-1]]:35: warning: returning a constant reference parameter + +} // namespace invalid + +namespace valid { + +int const &f1(int &a) { return a; } + +int const &f2(int &&a) { return a; } + +int f1(int const &a) { return a; } + +} // namespace valid diff --git a/clang-tools-extra/test/clang-tidy/checkers/misc/new-delete-overloads.cpp b/clang-tools-extra/test/clang-tidy/checkers/misc/new-delete-overloads.cpp index 78f021144b2e19c1d8f91534cf0c6b0242e8dec7..f86fe8a4c5b14f606bd5a37c6c8b283682223a11 100644 --- a/clang-tools-extra/test/clang-tidy/checkers/misc/new-delete-overloads.cpp +++ b/clang-tools-extra/test/clang-tidy/checkers/misc/new-delete-overloads.cpp @@ -12,16 +12,6 @@ struct S { // CHECK-MESSAGES: :[[@LINE+1]]:7: warning: declaration of 'operator new' has no matching declaration of 'operator delete' at the same scope void *operator new(size_t size) noexcept(false); -struct T { - // Sized deallocations are not enabled by default, and so this new/delete pair - // does not match. However, we expect only one warning, for the new, because - // the operator delete is a placement delete and we do not warn on mismatching - // placement operations. - // CHECK-MESSAGES: :[[@LINE+1]]:9: warning: declaration of 'operator new' has no matching declaration of 'operator delete' at the same scope - void *operator new(size_t size) noexcept; - void operator delete(void *ptr, size_t) noexcept; // ok only if sized deallocation is enabled -}; - struct U { void *operator new(size_t size) noexcept; void operator delete(void *ptr) noexcept; diff --git a/clang-tools-extra/test/clang-tidy/checkers/modernize/min-max-use-initializer-list.cpp b/clang-tools-extra/test/clang-tidy/checkers/modernize/min-max-use-initializer-list.cpp new file mode 100644 index 0000000000000000000000000000000000000000..51ab9bda975f10baba00221fe02a6ab13f07ae90 --- /dev/null +++ b/clang-tools-extra/test/clang-tidy/checkers/modernize/min-max-use-initializer-list.cpp @@ -0,0 +1,305 @@ +// RUN: %check_clang_tidy %s modernize-min-max-use-initializer-list %t + +// CHECK-FIXES: #include +namespace utils { +template +T max(T a, T b) { + return (a < b) ? b : a; +} +} // namespace utils + +namespace std { +template< class T > +struct initializer_list { + initializer_list()=default; + initializer_list(T*,int){} + const T* begin() const {return nullptr;} + const T* end() const {return nullptr;} +}; + +template +ForwardIt min_element(ForwardIt first, ForwardIt last) +{ + if (first == last) + return last; + + ForwardIt smallest = first; + + while (++first != last) + if (*first < *smallest) + smallest = first; + + return smallest; +} + +template +ForwardIt min_element(ForwardIt first, ForwardIt last, Compare comp) +{ + if (first == last) + return last; + + ForwardIt smallest = first; + + while (++first != last) + if (comp(*first, *smallest)) + smallest = first; + + return smallest; +} + +template +ForwardIt max_element(ForwardIt first, ForwardIt last) +{ + if (first == last) + return last; + + ForwardIt largest = first; + + while (++first != last) + if (*largest < *first) + largest = first; + + return largest; +} + +template +ForwardIt max_element(ForwardIt first, ForwardIt last, Compare comp) +{ + if (first == last) + return last; + + ForwardIt largest = first; + + while(++first != last) + if (comp(*largest, *first)) + largest = first; + + return largest; +} + +template< class T > +const T& max( const T& a, const T& b ) { + return (a < b) ? b : a; +}; + +template< class T > +T max(std::initializer_list ilist) +{ + return *std::max_element(ilist.begin(), ilist.end()); +} + +template< class T, class Compare > +const T& max( const T& a, const T& b, Compare comp ) { + return (comp(a, b)) ? b : a; +}; + +template< class T, class Compare > +T max(std::initializer_list ilist, Compare comp) { + return *std::max_element(ilist.begin(), ilist.end(), comp); +}; + +template< class T > +const T& min( const T& a, const T& b ) { + return (b < a) ? b : a; +}; + +template< class T > +T min(std::initializer_list ilist) +{ + return *std::min_element(ilist.begin(), ilist.end()); +} + + +template< class T, class Compare > +const T& min( const T& a, const T& b, Compare comp ) { + return (comp(b, a)) ? b : a; +}; + +template< class T, class Compare > +T min(std::initializer_list ilist, Compare comp) { + return *std::min_element(ilist.begin(), ilist.end(), comp); +}; + +} // namespace std + +using namespace std; + +namespace { +bool fless_than(int a, int b) { +return a < b; +} + +bool fgreater_than(int a, int b) { +return a > b; +} +auto less_than = [](int a, int b) { return a < b; }; +auto greater_than = [](int a, int b) { return a > b; }; + +int max1 = std::max(1, std::max(2, 3)); +// CHECK-MESSAGES: :[[@LINE-1]]:12: warning: do not use nested 'std::max' calls, use an initializer list instead [modernize-min-max-use-initializer-list] +// CHECK-FIXES: int max1 = std::max({1, 2, 3}); + +int min1 = std::min(1, std::min(2, 3)); +// CHECK-MESSAGES: :[[@LINE-1]]:12: warning: do not use nested 'std::min' calls, use an initializer list instead [modernize-min-max-use-initializer-list] +// CHECK-FIXES: int min1 = std::min({1, 2, 3}); + +int max2 = std::max(1, std::max(2, std::max(3, 4))); +// CHECK-MESSAGES: :[[@LINE-1]]:12: warning: do not use nested 'std::max' calls, use an initializer list instead [modernize-min-max-use-initializer-list] +// CHECK-FIXES: int max2 = std::max({1, 2, 3, 4}); + +int max2b = std::max(std::max(std::max(1, 2), std::max(3, 4)), std::max(std::max(5, 6), std::max(7, 8))); +// CHECK-MESSAGES: :[[@LINE-1]]:13: warning: do not use nested 'std::max' calls, use an initializer list instead [modernize-min-max-use-initializer-list] +// CHECK-FIXES: int max2b = std::max({1, 2, 3, 4, 5, 6, 7, 8}); + +int max2c = std::max(std::max(1, std::max(2, 3)), 4); +// CHECK-MESSAGES: :[[@LINE-1]]:13: warning: do not use nested 'std::max' calls, use an initializer list instead [modernize-min-max-use-initializer-list] +// CHECK-FIXES: int max2c = std::max({1, 2, 3, 4}); + +int max2d = std::max(std::max({1, 2, 3}), 4); +// CHECK-MESSAGES: :[[@LINE-1]]:13: warning: do not use nested 'std::max' calls, use an initializer list instead [modernize-min-max-use-initializer-list] +// CHECK-FIXES: int max2d = std::max({1, 2, 3, 4}); + + +int max2e = std::max(1, max(2, max(3, 4))); +// CHECK-MESSAGES: :[[@LINE-1]]:13: warning: do not use nested 'std::max' calls, use an initializer list instead [modernize-min-max-use-initializer-list] +// CHECK-FIXES: int max2e = std::max({1, 2, 3, 4}); + +int min2 = std::min(1, std::min(2, std::min(3, 4))); +// CHECK-MESSAGES: :[[@LINE-1]]:12: warning: do not use nested 'std::min' calls, use an initializer list instead [modernize-min-max-use-initializer-list] +// CHECK-FIXES: int min2 = std::min({1, 2, 3, 4}); + +int max3 = std::max(std::max(4, 5), std::min(2, std::min(3, 1))); +// CHECK-MESSAGES: :[[@LINE-1]]:12: warning: do not use nested 'std::max' calls, use an initializer list instead [modernize-min-max-use-initializer-list] +// CHECK-MESSAGES: :[[@LINE-2]]:37: warning: do not use nested 'std::min' calls, use an initializer list instead [modernize-min-max-use-initializer-list] +// CHECK-FIXES: int max3 = std::max({4, 5, std::min({2, 3, 1})}); + +int min3 = std::min(std::min(4, 5), std::max(2, std::max(3, 1))); +// CHECK-MESSAGES: :[[@LINE-1]]:12: warning: do not use nested 'std::min' calls, use an initializer list instead [modernize-min-max-use-initializer-list] +// CHECK-MESSAGES: :[[@LINE-2]]:37: warning: do not use nested 'std::max' calls, use an initializer list instead [modernize-min-max-use-initializer-list] +// CHECK-FIXES: int min3 = std::min({4, 5, std::max({2, 3, 1})}); + +int max4 = std::max(1, std::max(2, 3, greater_than), less_than); +// CHECK-FIXES: int max4 = std::max(1, std::max(2, 3, greater_than), less_than); + +int min4 = std::min(1, std::min(2, 3, greater_than), less_than); +// CHECK-FIXES: int min4 = std::min(1, std::min(2, 3, greater_than), less_than); + +int max5 = std::max(1, std::max(2, 3), less_than); +// CHECK-FIXES: int max5 = std::max(1, std::max(2, 3), less_than); + +int min5 = std::min(1, std::min(2, 3), less_than); +// CHECK-FIXES: int min5 = std::min(1, std::min(2, 3), less_than); + +int max6 = std::max(1, std::max(2, 3, greater_than), greater_than); +// CHECK-MESSAGES: :[[@LINE-1]]:12: warning: do not use nested 'std::max' calls, use an initializer list instead [modernize-min-max-use-initializer-list] +// CHECK-FIXES: int max6 = std::max({1, 2, 3 }, greater_than); + +int min6 = std::min(1, std::min(2, 3, greater_than), greater_than); +// CHECK-MESSAGES: :[[@LINE-1]]:12: warning: do not use nested 'std::min' calls, use an initializer list instead [modernize-min-max-use-initializer-list] +// CHECK-FIXES: int min6 = std::min({1, 2, 3 }, greater_than); + +int max7 = std::max(1, std::max(2, 3, fless_than), fgreater_than); +// CHECK-FIXES: int max7 = std::max(1, std::max(2, 3, fless_than), fgreater_than); + +int min7 = std::min(1, std::min(2, 3, fless_than), fgreater_than); +// CHECK-FIXES: int min7 = std::min(1, std::min(2, 3, fless_than), fgreater_than); + +int max8 = std::max(1, std::max(2, 3, fless_than), less_than); +// CHECK-FIXES: int max8 = std::max(1, std::max(2, 3, fless_than), less_than) + +int min8 = std::min(1, std::min(2, 3, fless_than), less_than); +// CHECK-FIXES: int min8 = std::min(1, std::min(2, 3, fless_than), less_than); + +int max9 = std::max(1, std::max(2, 3, fless_than), fless_than); +// CHECK-MESSAGES: :[[@LINE-1]]:12: warning: do not use nested 'std::max' calls, use an initializer list instead [modernize-min-max-use-initializer-list] +// CHECK-FIXES: int max9 = std::max({1, 2, 3 }, fless_than); + +int min9 = std::min(1, std::min(2, 3, fless_than), fless_than); +// CHECK-MESSAGES: :[[@LINE-1]]:12: warning: do not use nested 'std::min' calls, use an initializer list instead [modernize-min-max-use-initializer-list] +// CHECK-FIXES: int min9 = std::min({1, 2, 3 }, fless_than); + +int min10 = std::min(std::min(4, 5), std::max(2, utils::max(3, 1))); +// CHECK-MESSAGES: :[[@LINE-1]]:13: warning: do not use nested 'std::min' calls, use an initializer list instead [modernize-min-max-use-initializer-list] +// CHECK-FIXES: int min10 = std::min({4, 5, std::max(2, utils::max(3, 1))}); + +int max10 = std::max({std::max(1, 2), std::max({5, 6, 1}), 2, std::min({1, 2, 4})}); +// CHECK-MESSAGES: :[[@LINE-1]]:13: warning: do not use nested 'std::max' calls, use an initializer list instead [modernize-min-max-use-initializer-list] +// CHECK-FIXES: int max10 = std::max({1, 2, 5, 6, 1, 2, std::min({1, 2, 4})}); + +int typecastTest = std::max(std::max(0U, 0.0f), 0); +// CHECK-MESSAGES: :[[@LINE-1]]:20: warning: do not use nested 'std::max' calls, use an initializer list instead [modernize-min-max-use-initializer-list] +// CHECK-FIXES: int typecastTest = std::max({static_cast(0U), static_cast(0.0f), 0}); + +int typecastTest1 = std::max(std::max(0U, 0.0f), 0L); +// CHECK-MESSAGES: :[[@LINE-1]]:21: warning: do not use nested 'std::max' calls, use an initializer list instead [modernize-min-max-use-initializer-list] +// CHECK-FIXES: int typecastTest1 = std::max({static_cast(0U), static_cast(0.0f), 0L}); + +int typecastTest2 = std::max(std::max(10U, 20.0f), 30); +// CHECK-MESSAGES: :[[@LINE-1]]:21: warning: do not use nested 'std::max' calls, use an initializer list instead [modernize-min-max-use-initializer-list] +// CHECK-FIXES: int typecastTest2 = std::max({static_cast(10U), static_cast(20.0f), 30}); + +int typecastTest3 = std::max(std::max(0U, std::max(0.0f, 1.0f)), 0); +// CHECK-MESSAGES: :[[@LINE-1]]:21: warning: do not use nested 'std::max' calls, use an initializer list instead [modernize-min-max-use-initializer-list] +// CHECK-FIXES: int typecastTest3 = std::max({static_cast(0U), static_cast(0.0f), static_cast(1.0f), 0}); + +#define max3f(a, b, c) std::max(a, std::max(b, c)) +// CHECK-FIXES: #define max3f(a, b, c) std::max(a, std::max(b, c)) + +#define value 4545 +int macroVarMax = std::max(value, std::max(1, 2)); +// CHECK-MESSAGES: :[[@LINE-1]]:19: warning: do not use nested 'std::max' calls, use an initializer list instead [modernize-min-max-use-initializer-list] +// CHECK-FIXES: int macroVarMax = std::max({value, 1, 2}); + +#define value2 45U +int macroVarMax2 = std::max(1, std::max(value2, 2.0f)); +// CHECK-MESSAGES: :[[@LINE-1]]:20: warning: do not use nested 'std::max' calls, use an initializer list instead [modernize-min-max-use-initializer-list] +// CHECK-FIXES: int macroVarMax2 = std::max({1, static_cast(value2), static_cast(2.0f)}); + +// True-negative tests +int maxTN1 = std::max(1, 2); +// CHECK-FIXES: int maxTN1 = std::max(1, 2); + +int maxTN2 = std::max({1, 2, 3}); +// CHECK-FIXES: int maxTN2 = std::max({1, 2, 3}); + +int maxTN3 = std::max({1, 2, 3}, less_than); +// CHECK-FIXES: int maxTN3 = std::max({1, 2, 3}, less_than); + +// non-trivial types +struct A { + int a; + A(int a) : a(a) {} + bool operator<(const A &rhs) const { return a < rhs.a; } +}; + +A maxNT1 = std::max(A(1), A(2)); +// CHECK-FIXES: A maxNT1 = std::max(A(1), A(2)); + +A maxNT2 = std::max(A(1), std::max(A(2), A(3))); +// CHECK-FIXES: A maxNT2 = std::max(A(1), std::max(A(2), A(3))); + +A maxNT3 = std::max(A(1), std::max(A(2), A(3)), [](const A &lhs, const A &rhs) { return lhs.a < rhs.a; }); +// CHECK-FIXES: A maxNT3 = std::max(A(1), std::max(A(2), A(3)), [](const A &lhs, const A &rhs) { return lhs.a < rhs.a; }); + +// Trivial type with size greater than 32 +struct B { + // 9*4 = 36 bytes > 32 bytes + int a[9]; + + bool operator<(const B& rhs) const { + return a[0] < rhs.a[0]; + } +}; + +B maxTT1 = std::max(B(), B()); +// CHECK-FIXES: B maxTT1 = std::max(B(), B()); + +B maxTT2 = std::max(B(), std::max(B(), B())); +// CHECK-FIXES: B maxTT2 = std::max(B(), std::max(B(), B())); + +B maxTT3 = std::max(B(), std::max(B(), B()), [](const B &lhs, const B &rhs) { return lhs.a[0] < rhs.a[0]; }); +// CHECK-FIXES: B maxTT3 = std::max(B(), std::max(B(), B()), [](const B &lhs, const B &rhs) { return lhs.a[0] < rhs.a[0]; }); + + +} // namespace + diff --git a/clang-tools-extra/test/clang-tidy/checkers/modernize/use-starts-ends-with.cpp b/clang-tools-extra/test/clang-tidy/checkers/modernize/use-starts-ends-with.cpp index 65ed9ed895bc4731e8c3fa8ab13ff0db11445ab8..c5b2c86befd1fec8c42c9f980367d07de51b4c69 100644 --- a/clang-tools-extra/test/clang-tidy/checkers/modernize/use-starts-ends-with.cpp +++ b/clang-tools-extra/test/clang-tidy/checkers/modernize/use-starts-ends-with.cpp @@ -1,6 +1,7 @@ // RUN: %check_clang_tidy -std=c++20 %s modernize-use-starts-ends-with %t -- \ // RUN: -- -isystem %clang_tidy_headers +#include #include std::string foo(std::string); @@ -158,10 +159,64 @@ void test(std::string s, std::string_view sv, sub_string ss, sub_sub_string sss, // CHECK-MESSAGES: :[[@LINE-1]]:{{[0-9]+}}: warning: use startsWith // CHECK-FIXES: puvi.startsWith("a"); + s.compare(0, 1, "a") == 0; + // CHECK-MESSAGES: :[[@LINE-1]]:{{[0-9]+}}: warning: use starts_with instead of compare() == 0 + // CHECK-FIXES: s.starts_with("a"); + + s.compare(0, 1, "a") != 0; + // CHECK-MESSAGES: :[[@LINE-1]]:{{[0-9]+}}: warning: use starts_with instead of compare() != 0 + // CHECK-FIXES: !s.starts_with("a"); + + s.compare(0, strlen("a"), "a") == 0; + // CHECK-MESSAGES: :[[@LINE-1]]:{{[0-9]+}}: warning: use starts_with + // CHECK-FIXES: s.starts_with("a"); + + s.compare(0, std::strlen("a"), "a") == 0; + // CHECK-MESSAGES: :[[@LINE-1]]:{{[0-9]+}}: warning: use starts_with + // CHECK-FIXES: s.starts_with("a"); + + s.compare(0, std::strlen(("a")), "a") == 0; + // CHECK-MESSAGES: :[[@LINE-1]]:{{[0-9]+}}: warning: use starts_with + // CHECK-FIXES: s.starts_with("a"); + + s.compare(0, std::strlen(("a")), (("a"))) == 0; + // CHECK-MESSAGES: :[[@LINE-1]]:{{[0-9]+}}: warning: use starts_with + // CHECK-FIXES: s.starts_with("a"); + + s.compare(0, s.size(), s) == 0; + // CHECK-MESSAGES: :[[@LINE-1]]:{{[0-9]+}}: warning: use starts_with + // CHECK-FIXES: s.starts_with(s); + + s.compare(0, s.length(), s) == 0; + // CHECK-MESSAGES: :[[@LINE-1]]:{{[0-9]+}}: warning: use starts_with + // CHECK-FIXES: s.starts_with(s); + + 0 != s.compare(0, sv.length(), sv); + // CHECK-MESSAGES: :[[@LINE-1]]:{{[0-9]+}}: warning: use starts_with + // CHECK-FIXES: s.starts_with(sv); + + #define LENGTH(x) (x).length() + s.compare(0, LENGTH(s), s) == 0; + // CHECK-MESSAGES: :[[@LINE-1]]:{{[0-9]+}}: warning: use starts_with + // CHECK-FIXES: s.starts_with(s); + + s.compare(ZERO, LENGTH(s), s) == ZERO; + // CHECK-MESSAGES: :[[@LINE-1]]:{{[0-9]+}}: warning: use starts_with + // CHECK-FIXES: s.starts_with(s); + + s.compare(ZERO, LENGTH(sv), sv) != 0; + // CHECK-MESSAGES: :[[@LINE-1]]:{{[0-9]+}}: warning: use starts_with + // CHECK-FIXES: !s.starts_with(sv); + // Expressions that don't trigger the check are here. #define EQ(x, y) ((x) == (y)) EQ(s.find("a"), 0); #define DOTFIND(x, y) (x).find(y) DOTFIND(s, "a") == 0; + + #define STARTS_WITH_COMPARE(x, y) (x).compare(0, (x).size(), (y)) + STARTS_WITH_COMPARE(s, s) == 0; + + s.compare(0, 1, "ab") == 0; } diff --git a/clang-tools-extra/test/clang-tidy/checkers/readability/math-missing-parentheses.cpp b/clang-tools-extra/test/clang-tidy/checkers/readability/math-missing-parentheses.cpp new file mode 100644 index 0000000000000000000000000000000000000000..edbe2e1c37c770c013423593675a89f301794c46 --- /dev/null +++ b/clang-tools-extra/test/clang-tidy/checkers/readability/math-missing-parentheses.cpp @@ -0,0 +1,120 @@ +// RUN: %check_clang_tidy %s readability-math-missing-parentheses %t + +#define MACRO_AND & +#define MACRO_ADD + +#define MACRO_OR | +#define MACRO_MULTIPLY * +#define MACRO_XOR ^ +#define MACRO_SUBTRACT - +#define MACRO_DIVIDE / + +int foo(){ + return 5; +} + +int bar(){ + return 4; +} + +class fun{ +public: + int A; + double B; + fun(){ + A = 5; + B = 5.4; + } +}; + +void f(){ + //CHECK-MESSAGES: :[[@LINE+2]]:17: warning: '*' has higher precedence than '+'; add parentheses to explicitly specify the order of operations [readability-math-missing-parentheses] + //CHECK-FIXES: int a = 1 + (2 * 3); + int a = 1 + 2 * 3; + + int a_negative = 1 + (2 * 3); // No warning + + int b = 1 + 2 + 3; // No warning + + int c = 1 * 2 * 3; // No warning + + //CHECK-MESSAGES: :[[@LINE+3]]:17: warning: '*' has higher precedence than '+'; add parentheses to explicitly specify the order of operations [readability-math-missing-parentheses] + //CHECK-MESSAGES: :[[@LINE+2]]:25: warning: '/' has higher precedence than '-'; add parentheses to explicitly specify the order of operations [readability-math-missing-parentheses] + //CHECK-FIXES: int d = 1 + (2 * 3) - (4 / 5); + int d = 1 + 2 * 3 - 4 / 5; + + int d_negative = 1 + (2 * 3) - (4 / 5); // No warning + + //CHECK-MESSAGES: :[[@LINE+4]]:13: warning: '&' has higher precedence than '|'; add parentheses to explicitly specify the order of operations [readability-math-missing-parentheses] + //CHECK-MESSAGES: :[[@LINE+3]]:17: warning: '+' has higher precedence than '&'; add parentheses to explicitly specify the order of operations [readability-math-missing-parentheses] + //CHECK-MESSAGES: :[[@LINE+2]]:25: warning: '*' has higher precedence than '|'; add parentheses to explicitly specify the order of operations [readability-math-missing-parentheses] + //CHECK-FIXES: int e = (1 & (2 + 3)) | (4 * 5); + int e = 1 & 2 + 3 | 4 * 5; + + int e_negative = (1 & (2 + 3)) | (4 * 5); // No warning + + //CHECK-MESSAGES: :[[@LINE+2]]:13: warning: '*' has higher precedence than '+'; add parentheses to explicitly specify the order of operations [readability-math-missing-parentheses] + //CHECK-FIXES: int f = (1 * -2) + 4; + int f = 1 * -2 + 4; + + int f_negative = (1 * -2) + 4; // No warning + + //CHECK-MESSAGES: :[[@LINE+2]]:13: warning: '*' has higher precedence than '+'; add parentheses to explicitly specify the order of operations [readability-math-missing-parentheses] + //CHECK-FIXES: int g = (1 * 2 * 3) + 4 + 5; + int g = 1 * 2 * 3 + 4 + 5; + + int g_negative = (1 * 2 * 3) + 4 + 5; // No warning + + //CHECK-MESSAGES: :[[@LINE+4]]:13: warning: '&' has higher precedence than '|'; add parentheses to explicitly specify the order of operations [readability-math-missing-parentheses] + //CHECK-MESSAGES: :[[@LINE+3]]:19: warning: '+' has higher precedence than '&'; add parentheses to explicitly specify the order of operations [readability-math-missing-parentheses] + //CHECK-MESSAGES: :[[@LINE+2]]:27: warning: '*' has higher precedence than '|'; add parentheses to explicitly specify the order of operations [readability-math-missing-parentheses] + //CHECK-FIXES: int h = (120 & (2 + 3)) | (22 * 5); + int h = 120 & 2 + 3 | 22 * 5; + + int h_negative = (120 & (2 + 3)) | (22 * 5); // No warning + + int i = 1 & 2 & 3; // No warning + + int j = 1 | 2 | 3; // No warning + + int k = 1 ^ 2 ^ 3; // No warning + + //CHECK-MESSAGES: :[[@LINE+2]]:13: warning: '+' has higher precedence than '^'; add parentheses to explicitly specify the order of operations [readability-math-missing-parentheses] + //CHECK-FIXES: int l = (1 + 2) ^ 3; + int l = 1 + 2 ^ 3; + + int l_negative = (1 + 2) ^ 3; // No warning + + //CHECK-MESSAGES: :[[@LINE+2]]:13: warning: '*' has higher precedence than '+'; add parentheses to explicitly specify the order of operations [readability-math-missing-parentheses] + //CHECK-FIXES: int m = (2 * foo()) + bar(); + int m = 2 * foo() + bar(); + + int m_negative = (2 * foo()) + bar(); // No warning + + //CHECK-MESSAGES: :[[@LINE+2]]:13: warning: '*' has higher precedence than '+'; add parentheses to explicitly specify the order of operations [readability-math-missing-parentheses] + //CHECK-FIXES: int n = (1.05 * foo()) + double(bar()); + int n = 1.05 * foo() + double(bar()); + + int n_negative = (1.05 * foo()) + double(bar()); // No warning + + //CHECK-MESSAGES: :[[@LINE+3]]:17: warning: '*' has higher precedence than '+'; add parentheses to explicitly specify the order of operations [readability-math-missing-parentheses] + //CHECK-FIXES: int o = 1 + (obj.A * 3) + obj.B; + fun obj; + int o = 1 + obj.A * 3 + obj.B; + + int o_negative = 1 + (obj.A * 3) + obj.B; // No warning + + //CHECK-MESSAGES: :[[@LINE+2]]:18: warning: '*' has higher precedence than '+'; add parentheses to explicitly specify the order of operations [readability-math-missing-parentheses] + //CHECK-FIXES: int p = 1U + (2 * 3); + int p = 1U + 2 * 3; + + int p_negative = 1U + (2 * 3); // No warning + + //CHECK-MESSAGES: :[[@LINE+7]]:13: warning: '+' has higher precedence than '|'; add parentheses to explicitly specify the order of operations [readability-math-missing-parentheses] + //CHECK-MESSAGES: :[[@LINE+6]]:25: warning: '*' has higher precedence than '+'; add parentheses to explicitly specify the order of operations [readability-math-missing-parentheses] + //CHECK-MESSAGES: :[[@LINE+5]]:53: warning: '&' has higher precedence than '^'; add parentheses to explicitly specify the order of operations [readability-math-missing-parentheses] + //CHECK-MESSAGES: :[[@LINE+4]]:53: warning: '^' has higher precedence than '|'; add parentheses to explicitly specify the order of operations [readability-math-missing-parentheses] + //CHECK-MESSAGES: :[[@LINE+3]]:77: warning: '-' has higher precedence than '^'; add parentheses to explicitly specify the order of operations [readability-math-missing-parentheses] + //CHECK-MESSAGES: :[[@LINE+2]]:94: warning: '/' has higher precedence than '-'; add parentheses to explicitly specify the order of operations [readability-math-missing-parentheses] + //CHECK-FIXES: int q = (1 MACRO_ADD (2 MACRO_MULTIPLY 3)) MACRO_OR ((4 MACRO_AND 5) MACRO_XOR (6 MACRO_SUBTRACT (7 MACRO_DIVIDE 8))); + int q = 1 MACRO_ADD 2 MACRO_MULTIPLY 3 MACRO_OR 4 MACRO_AND 5 MACRO_XOR 6 MACRO_SUBTRACT 7 MACRO_DIVIDE 8; // No warning +} diff --git a/clang/CMakeLists.txt b/clang/CMakeLists.txt index f092766fa19f07f754960ec9524078d6b65070d4..cf97e3c6e851aee92dd5378b85515304fc875999 100644 --- a/clang/CMakeLists.txt +++ b/clang/CMakeLists.txt @@ -166,6 +166,10 @@ if(CLANG_ENABLE_LIBXML2) endif() if(CLANG_ENABLE_CIR) + if (CLANG_BUILT_STANDALONE) + message(FATAL_ERROR + "ClangIR is not yet supported in the standalone build.") + endif() if (NOT "${LLVM_ENABLE_PROJECTS}" MATCHES "MLIR|mlir") message(FATAL_ERROR "Cannot build ClangIR without MLIR in LLVM_ENABLE_PROJECTS") diff --git a/clang/cmake/caches/Release.cmake b/clang/cmake/caches/Release.cmake index bd1f688d61a7ea2aaa475aaec7d6a0970c12139f..c164d5497275f39aad374dff0aa55bdcbc3dc2cf 100644 --- a/clang/cmake/caches/Release.cmake +++ b/clang/cmake/caches/Release.cmake @@ -1,93 +1,93 @@ # Plain options configure the first build. # BOOTSTRAP_* options configure the second build. # BOOTSTRAP_BOOTSTRAP_* options configure the third build. +# PGO Builds have 3 stages (stage1, stage2-instrumented, stage2) +# non-PGO Builds have 2 stages (stage1, stage2) -# General Options + +function (set_final_stage_var name value type) + if (LLVM_RELEASE_ENABLE_PGO) + set(BOOTSTRAP_BOOTSTRAP_${name} ${value} CACHE ${type} "") + else() + set(BOOTSTRAP_${name} ${value} CACHE ${type} "") + endif() +endfunction() + +function (set_instrument_and_final_stage_var name value type) + # This sets the varaible for the final stage in non-PGO builds and in + # the stage2-instrumented stage for PGO builds. + set(BOOTSTRAP_${name} ${value} CACHE ${type} "") + if (LLVM_RELEASE_ENABLE_PGO) + # Set the variable in the final stage for PGO builds. + set(BOOTSTRAP_BOOTSTRAP_${name} ${value} CACHE ${type} "") + endif() +endfunction() + +# General Options: +# If you want to override any of the LLVM_RELEASE_* variables you can set them +# on the command line via -D, but you need to do this before you pass this +# cache file to CMake via -C. e.g. +# +# cmake -D LLVM_RELEASE_ENABLE_PGO=ON -C Release.cmake set(LLVM_RELEASE_ENABLE_LTO THIN CACHE STRING "") set(LLVM_RELEASE_ENABLE_PGO OFF CACHE BOOL "") - +set(LLVM_RELEASE_ENABLE_RUNTIMES "compiler-rt;libcxx;libcxxabi;libunwind" CACHE STRING "") +set(LLVM_RELEASE_ENABLE_PROJECTS "clang;lld;lldb;clang-tools-extra;bolt;polly;mlir;flang" CACHE STRING "") +# Note we don't need to add install here, since it is one of the pre-defined +# steps. +set(LLVM_RELEASE_FINAL_STAGE_TARGETS "clang;package;check-all;check-llvm;check-clang" CACHE STRING "") set(CMAKE_BUILD_TYPE RELEASE CACHE STRING "") -# Stage 1 Bootstrap Setup +# Stage 1 Options +set(LLVM_TARGETS_TO_BUILD Native CACHE STRING "") set(CLANG_ENABLE_BOOTSTRAP ON CACHE BOOL "") + +set(STAGE1_PROJECTS "clang") +set(STAGE1_RUNTIMES "") + if (LLVM_RELEASE_ENABLE_PGO) + list(APPEND STAGE1_PROJECTS "lld") + list(APPEND STAGE1_RUNTIMES "compiler-rt") set(CLANG_BOOTSTRAP_TARGETS generate-profdata - stage2 + stage2-package stage2-clang - stage2-distribution stage2-install - stage2-install-distribution - stage2-install-distribution-toolchain stage2-check-all stage2-check-llvm - stage2-check-clang - stage2-test-suite CACHE STRING "") -else() - set(CLANG_BOOTSTRAP_TARGETS - clang - check-all - check-llvm - check-clang - test-suite - stage3 - stage3-clang - stage3-check-all - stage3-check-llvm - stage3-check-clang - stage3-install - stage3-test-suite CACHE STRING "") -endif() + stage2-check-clang CACHE STRING "") -# Stage 1 Options -set(STAGE1_PROJECTS "clang") -set(STAGE1_RUNTIMES "") + # Configuration for stage2-instrumented + set(BOOTSTRAP_CLANG_ENABLE_BOOTSTRAP ON CACHE STRING "") + # This enables the build targets for the final stage which is called stage2. + set(BOOTSTRAP_CLANG_BOOTSTRAP_TARGETS ${LLVM_RELEASE_FINAL_STAGE_TARGETS} CACHE STRING "") + set(BOOTSTRAP_LLVM_BUILD_INSTRUMENTED IR CACHE STRING "") + set(BOOTSTRAP_LLVM_ENABLE_RUNTIMES "compiler-rt" CACHE STRING "") + set(BOOTSTRAP_LLVM_ENABLE_PROJECTS "clang;lld" CACHE STRING "") -if (LLVM_RELEASE_ENABLE_PGO) - list(APPEND STAGE1_PROJECTS "lld") - list(APPEND STAGE1_RUNTIMES "compiler-rt") +else() + if (LLVM_RELEASE_ENABLE_LTO) + list(APPEND STAGE1_PROJECTS "lld") + endif() + # Any targets added here will be given the target name stage2-${target}, so + # if you want to run them you can just use: + # ninja -C $BUILDDIR stage2-${target} + set(CLANG_BOOTSTRAP_TARGETS ${LLVM_RELEASE_FINAL_STAGE_TARGETS} CACHE STRING "") endif() +# Stage 1 Common Config set(LLVM_ENABLE_RUNTIMES ${STAGE1_RUNTIMES} CACHE STRING "") set(LLVM_ENABLE_PROJECTS ${STAGE1_PROJECTS} CACHE STRING "") -set(LLVM_TARGETS_TO_BUILD Native CACHE STRING "") - -# Stage 2 Bootstrap Setup -set(BOOTSTRAP_CLANG_ENABLE_BOOTSTRAP ON CACHE STRING "") -set(BOOTSTRAP_CLANG_BOOTSTRAP_TARGETS - clang - check-all - check-llvm - check-clang CACHE STRING "") - -# Stage 2 Options -set(STAGE2_PROJECTS "clang") -set(STAGE2_RUNTIMES "") - -if (LLVM_RELEASE_ENABLE_LTO OR LLVM_RELEASE_ENABLE_PGO) - list(APPEND STAGE2_PROJECTS "lld") -endif() - -if (LLVM_RELEASE_ENABLE_PGO) - set(BOOTSTRAP_LLVM_BUILD_INSTRUMENTED IR CACHE STRING "") - list(APPEND STAGE2_RUNTIMES "compiler-rt") - set(BOOTSTRAP_LLVM_ENABLE_LTO ${LLVM_RELEASE_ENABLE_LTO}) - if (LLVM_RELEASE_ENABLE_LTO) - set(BOOTSTRAP_LLVM_ENABLE_LLD ON CACHE BOOL "") - endif() +# stage2-instrumented and Final Stage Config: +# Options that need to be set in both the instrumented stage (if we are doing +# a pgo build) and the final stage. +set_instrument_and_final_stage_var(LLVM_ENABLE_LTO "${LLVM_RELEASE_ENABLE_LTO}" STRING) +if (LLVM_RELEASE_ENABLE_LTO) + set_instrument_and_final_stage_var(LLVM_ENABLE_LLD "ON" BOOL) endif() -set(BOOTSTRAP_LLVM_ENABLE_PROJECTS ${STAGE2_PROJECTS} CACHE STRING "") -set(BOOTSTRAP_LLVM_ENABLE_RUNTIMES ${STAGE2_RUNTIMES} CACHE STRING "") -if (NOT LLVM_RELEASE_ENABLE_PGO) - set(BOOTSTRAP_LLVM_TARGETS_TO_BUILD Native CACHE STRING "") -endif() +# Final Stage Config (stage2) +set_final_stage_var(LLVM_ENABLE_RUNTIMES "${LLVM_RELEASE_ENABLE_RUNTIMES}" STRING) +set_final_stage_var(LLVM_ENABLE_PROJECTS "${LLVM_RELEASE_ENABLE_PROJECTS}" STRING) -# Stage 3 Options -set(BOOTSTRAP_BOOTSTRAP_LLVM_ENABLE_RUNTIMES "compiler-rt;libcxx;libcxxabi;libunwind" CACHE STRING "") -set(BOOTSTRAP_BOOTSTRAP_LLVM_ENABLE_PROJECTS "clang;lld;lldb;clang-tools-extra;bolt;polly;mlir;flang" CACHE STRING "") -set(BOOTSTRAP_BOOTSTRAP_LLVM_ENABLE_LTO ${LLVM_RELEASE_ENABLE_LTO} CACHE STRING "") -if (LLVM_RELEASE_ENABLE_LTO) - set(BOOTSTRAP_BOOTSTRAP_LLVM_ENABLE_LLD ON CACHE BOOL "") -endif() diff --git a/clang/cmake/caches/VectorEngine.cmake b/clang/cmake/caches/VectorEngine.cmake index e3976f3206db5309780e3b2625812ee413ae106b..2f968a21cc407e7a79220b68cec30229101d22cf 100644 --- a/clang/cmake/caches/VectorEngine.cmake +++ b/clang/cmake/caches/VectorEngine.cmake @@ -40,6 +40,7 @@ set(RUNTIMES_x86_64-unknown-linux-gnu_COMPILER_RT_BUILD_CRT OFF CACHE BOOL "") set(RUNTIMES_x86_64-unknown-linux-gnu_COMPILER_RT_BUILD_SANITIZERS OFF CACHE BOOL "") set(RUNTIMES_x86_64-unknown-linux-gnu_COMPILER_RT_BUILD_XRAY OFF CACHE BOOL "") set(RUNTIMES_x86_64-unknown-linux-gnu_COMPILER_RT_BUILD_LIBFUZZER OFF CACHE BOOL "") +set(RUNTIMES_x86_64-unknown-linux-gnu_COMPILER_RT_BUILD_CTX_PROFILE OFF CACHE BOOL "") set(RUNTIMES_x86_64-unknown-linux-gnu_COMPILER_RT_BUILD_PROFILE OFF CACHE BOOL "") set(RUNTIMES_x86_64-unknown-linux-gnu_COMPILER_RT_BUILD_MEMPROF OFF CACHE BOOL "") set(RUNTIMES_x86_64-unknown-linux-gnu_COMPILER_RT_BUILD_ORC OFF CACHE BOOL "") @@ -52,6 +53,7 @@ set(RUNTIMES_ve-unknown-linux-gnu_COMPILER_RT_BUILD_SANITIZERS OFF CACHE BOOL "" set(RUNTIMES_ve-unknown-linux-gnu_COMPILER_RT_BUILD_XRAY OFF CACHE BOOL "") set(RUNTIMES_ve-unknown-linux-gnu_COMPILER_RT_BUILD_LIBFUZZER OFF CACHE BOOL "") set(RUNTIMES_ve-unknown-linux-gnu_COMPILER_RT_BUILD_PROFILE ON CACHE BOOL "") +set(RUNTIMES_ve-unknown-linux-gnu_COMPILER_RT_BUILD_CTX_PROFILE OFF CACHE BOOL "") set(RUNTIMES_ve-unknown-linux-gnu_COMPILER_RT_BUILD_MEMPROF OFF CACHE BOOL "") set(RUNTIMES_ve-unknown-linux-gnu_COMPILER_RT_BUILD_ORC OFF CACHE BOOL "") set(RUNTIMES_ve-unknown-linux-gnu_COMPILER_RT_BUILD_GWP_ASAN OFF CACHE BOOL "") diff --git a/clang/docs/OpenMPSupport.rst b/clang/docs/OpenMPSupport.rst index f8146bc365e8333d1e16389b162139386aa8c743..5e63b2c0f0be6ba7a986060d68a153461a694f22 100644 --- a/clang/docs/OpenMPSupport.rst +++ b/clang/docs/OpenMPSupport.rst @@ -310,7 +310,9 @@ implementation. +------------------------------+--------------------------------------------------------------+--------------------------+-----------------------------------------------------------------------+ | misc | dispatch construct and function variant argument adjustment | :part:`worked on` | D99537, D99679 | +------------------------------+--------------------------------------------------------------+--------------------------+-----------------------------------------------------------------------+ -| misc | assume and assumes directives | :part:`worked on` | | +| misc | assumes directives | :part:`worked on` | | ++------------------------------+--------------------------------------------------------------+--------------------------+-----------------------------------------------------------------------+ +| misc | assume directive | :part:`worked on` | | +------------------------------+--------------------------------------------------------------+--------------------------+-----------------------------------------------------------------------+ | misc | nothing directive | :good:`done` | D123286 | +------------------------------+--------------------------------------------------------------+--------------------------+-----------------------------------------------------------------------+ diff --git a/clang/docs/ReleaseNotes.rst b/clang/docs/ReleaseNotes.rst index d1f7293a842bb684c1f881d0fb60f4926a191716..92563262cc6737f11e2dbbe55675b63b68450347 100644 --- a/clang/docs/ReleaseNotes.rst +++ b/clang/docs/ReleaseNotes.rst @@ -90,6 +90,11 @@ C++ Language Changes -------------------- - Implemented ``_BitInt`` literal suffixes ``__wb`` or ``__WB`` as a Clang extension with ``unsigned`` modifiers also allowed. (#GH85223). +C++14 Feature Support +^^^^^^^^^^^^^^^^^^^^^ +- Sized deallocation is enabled by default in C++14 onwards. The user may specify + ``-fno-sized-deallocation`` to disable it if there are some regressions. + C++20 Feature Support ^^^^^^^^^^^^^^^^^^^^^ @@ -207,6 +212,16 @@ Non-comprehensive list of changes in this release - ``__typeof_unqual__`` is available in all C modes as an extension, which behaves like ``typeof_unqual`` from C23, similar to ``__typeof__`` and ``typeof``. + +* Shared libraries linked with either the ``-ffast-math``, ``-Ofast``, or + ``-funsafe-math-optimizations`` flags will no longer enable flush-to-zero + floating-point mode by default. This decision can be overridden with use of + ``-mdaz-ftz``. This behavior now matches GCC's behavior. + (`#57589 `_) + +* ``-fdenormal-fp-math=preserve-sign`` is no longer implied by ``-ffast-math`` + on x86 systems. + New Compiler Flags ------------------ - ``-fsanitize=implicit-bitfield-conversion`` checks implicit truncation and @@ -415,6 +430,9 @@ Bug Fixes in This Version operator. Fixes (#GH83267). +- Fix crash on ill-formed partial specialization with CRTP. + Fixes (#GH89374). + - Clang now correctly generates overloads for bit-precise integer types for builtin operators in C++. Fixes #GH82998. @@ -557,11 +575,12 @@ Bug Fixes to C++ Support - Fix a crash in requires expression with templated base class member function. Fixes (#GH84020). - Fix a crash caused by defined struct in a type alias template when the structure has fields with dependent type. Fixes (#GH75221). -- Fix placement new initializes typedef array with correct size. Fixes (#GH41441). - Fix the Itanium mangling of lambdas defined in a member of a local class (#GH88906) - Fixed a crash when trying to evaluate a user-defined ``static_assert`` message whose ``size()`` function returns a large or negative value. Fixes (#GH89407). - Fixed a use-after-free bug in parsing of type constraints with default arguments that involve lambdas. (#GH67235) +- Fixed bug in which the body of a consteval lambda within a template was not parsed as within an + immediate function context. Bug Fixes to AST Handling ^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -614,6 +633,9 @@ Arm and AArch64 Support * Arm Cortex-A78AE (cortex-a78ae). * Arm Cortex-A520AE (cortex-a520ae). * Arm Cortex-A720AE (cortex-a720ae). + * Arm Neoverse-N3 (neoverse-n3). + * Arm Neoverse-V3 (neoverse-v3). + * Arm Neoverse-V3AE (neoverse-v3ae). Android Support ^^^^^^^^^^^^^^^ @@ -708,6 +730,9 @@ clang-format libclang -------- +- ``clang_getSpellingLocation`` now correctly resolves macro expansions; that + is, it returns the spelling location instead of the expansion location. + Static Analyzer --------------- diff --git a/clang/docs/UsersManual.rst b/clang/docs/UsersManual.rst index c464bc3a69adc51c1f59db5245f1fc077aed4a11..d0326f01d251e02ea2e44ef671d5b548ff034768 100644 --- a/clang/docs/UsersManual.rst +++ b/clang/docs/UsersManual.rst @@ -1506,7 +1506,8 @@ floating point semantic models: precise (the default), strict, and fast. * ``-ffp-contract=fast`` - Note: ``-ffast-math`` causes ``crtfastmath.o`` to be linked with code. See + Note: ``-ffast-math`` causes ``crtfastmath.o`` to be linked with code unless + ``-shared`` or ``-mno-daz-ftz`` is present. See :ref:`crtfastmath.o` for more details. .. option:: -fno-fast-math @@ -1560,7 +1561,8 @@ floating point semantic models: precise (the default), strict, and fast. ``-ffp-contract``. Note: ``-fno-fast-math`` implies ``-fdenormal-fp-math=ieee``. - ``-fno-fast-math`` causes ``crtfastmath.o`` to not be linked with code. + ``-fno-fast-math`` causes ``crtfastmath.o`` to not be linked with code + unless ``-mdaz-ftz`` is present. .. option:: -fdenormal-fp-math= @@ -1938,10 +1940,13 @@ by using ``#pragma STDC FENV_ROUND`` with a value other than ``FE_DYNAMIC``. A note about ``crtfastmath.o`` ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ -``-ffast-math`` and ``-funsafe-math-optimizations`` cause ``crtfastmath.o`` to be -automatically linked, which adds a static constructor that sets the FTZ/DAZ +``-ffast-math`` and ``-funsafe-math-optimizations`` without the ``-shared`` +option cause ``crtfastmath.o`` to be +automatically linked, which adds a static constructor that sets the FTZ/DAZ bits in MXCSR, affecting not only the current compilation unit but all static -and shared libraries included in the program. +and shared libraries included in the program. This decision can be overridden +by using either the flag ``-mdaz-ftz`` or ``-mno-daz-ftz`` to respectively +link or not link ``crtfastmath.o``. .. _FLT_EVAL_METHOD: @@ -4921,6 +4926,9 @@ directory. Using the example installation above, this would mean passing If the user links the program with the ``clang`` or ``clang-cl`` drivers, the driver will pass this flag for them. +The auto-linking can be disabled with -fno-rtlib-defaultlib. If that flag is +used, pass the complete flag to required libraries as described for ASan below. + If the linker cannot find the appropriate library, it will emit an error like this:: diff --git a/clang/include/clang-c/Index.h b/clang/include/clang-c/Index.h index 7a8bd985a91fc00b2c3a6c488aca5030fc211c8d..365b607c741179e94146e57d3909e164857a9960 100644 --- a/clang/include/clang-c/Index.h +++ b/clang/include/clang-c/Index.h @@ -1644,8 +1644,9 @@ enum CXCursorKind { CXCursor_ObjCSelfExpr = 146, /** OpenMP 5.0 [2.1.5, Array Section]. + * OpenACC 3.3 [2.7.1, Data Specification for Data Clauses (Sub Arrays)] */ - CXCursor_OMPArraySectionExpr = 147, + CXCursor_ArraySectionExpr = 147, /** Represents an @available(...) check. */ diff --git a/clang/include/clang/AST/ASTContext.h b/clang/include/clang/AST/ASTContext.h index d5ed20ff50157d611ba643c9bdf6e2a5302a68de..6dbd06251ddad69d94ba95c5f57b061e775968cf 100644 --- a/clang/include/clang/AST/ASTContext.h +++ b/clang/include/clang/AST/ASTContext.h @@ -455,7 +455,7 @@ class ASTContext : public RefCountedBase { /// initialization of another module). struct PerModuleInitializers { llvm::SmallVector Initializers; - llvm::SmallVector LazyInitializers; + llvm::SmallVector LazyInitializers; void resolve(ASTContext &Ctx); }; @@ -1059,7 +1059,7 @@ public: /// or an ImportDecl nominating another module that has initializers. void addModuleInitializer(Module *M, Decl *Init); - void addLazyModuleInitializers(Module *M, ArrayRef IDs); + void addLazyModuleInitializers(Module *M, ArrayRef IDs); /// Get the initializations to perform when importing a module, if any. ArrayRef getModuleInitializers(Module *M); @@ -1127,7 +1127,8 @@ public: CanQualType OCLSamplerTy, OCLEventTy, OCLClkEventTy; CanQualType OCLQueueTy, OCLReserveIDTy; CanQualType IncompleteMatrixIdxTy; - CanQualType OMPArraySectionTy, OMPArrayShapingTy, OMPIteratorTy; + CanQualType ArraySectionTy; + CanQualType OMPArrayShapingTy, OMPIteratorTy; #define EXT_OPAQUE_TYPE(ExtType, Id, Ext) \ CanQualType Id##Ty; #include "clang/Basic/OpenCLExtensionTypes.def" @@ -2196,6 +2197,16 @@ public: return getQualifiedType(type.getUnqualifiedType(), Qs); } + /// \brief Return a type with the given __ptrauth qualifier. + QualType getPointerAuthType(QualType Ty, PointerAuthQualifier PointerAuth) { + assert(!Ty.getPointerAuth()); + assert(PointerAuth); + + Qualifiers Qs; + Qs.setPointerAuth(PointerAuth); + return getQualifiedType(Ty, Qs); + } + unsigned char getFixedPointScale(QualType Ty) const; unsigned char getFixedPointIBits(QualType Ty) const; llvm::FixedPointSemantics getFixedPointSemantics(QualType Ty) const; diff --git a/clang/include/clang/AST/AbstractBasicReader.h b/clang/include/clang/AST/AbstractBasicReader.h index 1f2797cc701458947ba3fa6f240dbb95cc67e326..ab036f1d445acc5c56a8a1e0f3b1eb3b7ea65a44 100644 --- a/clang/include/clang/AST/AbstractBasicReader.h +++ b/clang/include/clang/AST/AbstractBasicReader.h @@ -213,9 +213,9 @@ public: } Qualifiers readQualifiers() { - static_assert(sizeof(Qualifiers().getAsOpaqueValue()) <= sizeof(uint32_t), + static_assert(sizeof(Qualifiers().getAsOpaqueValue()) <= sizeof(uint64_t), "update this if the value size changes"); - uint32_t value = asImpl().readUInt32(); + uint64_t value = asImpl().readUInt64(); return Qualifiers::fromOpaqueValue(value); } diff --git a/clang/include/clang/AST/AbstractBasicWriter.h b/clang/include/clang/AST/AbstractBasicWriter.h index 07afa388de2c178bf63c276b1f0a2daa77821807..8e42fcaad1d388ecab9bb76c9082655fbcb750fc 100644 --- a/clang/include/clang/AST/AbstractBasicWriter.h +++ b/clang/include/clang/AST/AbstractBasicWriter.h @@ -196,9 +196,9 @@ public: } void writeQualifiers(Qualifiers value) { - static_assert(sizeof(value.getAsOpaqueValue()) <= sizeof(uint32_t), + static_assert(sizeof(value.getAsOpaqueValue()) <= sizeof(uint64_t), "update this if the value size changes"); - asImpl().writeUInt32(value.getAsOpaqueValue()); + asImpl().writeUInt64(value.getAsOpaqueValue()); } void writeExceptionSpecInfo( diff --git a/clang/include/clang/AST/BuiltinTypes.def b/clang/include/clang/AST/BuiltinTypes.def index c04f6f6f1271916bc93d5d818c2680958962c119..0a36fdc5d9c0f7ee7f12405d7bf04f2fd7aef666 100644 --- a/clang/include/clang/AST/BuiltinTypes.def +++ b/clang/include/clang/AST/BuiltinTypes.def @@ -320,7 +320,7 @@ PLACEHOLDER_TYPE(ARCUnbridgedCast, ARCUnbridgedCastTy) PLACEHOLDER_TYPE(IncompleteMatrixIdx, IncompleteMatrixIdxTy) // A placeholder type for OpenMP array sections. -PLACEHOLDER_TYPE(OMPArraySection, OMPArraySectionTy) +PLACEHOLDER_TYPE(ArraySection, ArraySectionTy) // A placeholder type for OpenMP array shaping operation. PLACEHOLDER_TYPE(OMPArrayShaping, OMPArrayShapingTy) diff --git a/clang/include/clang/AST/ComputeDependence.h b/clang/include/clang/AST/ComputeDependence.h index 7abf9141237dc87206548a7fc2a0bb639e436496..6d3a51c379f9df335bd0e7b084d532fe5ae4ad94 100644 --- a/clang/include/clang/AST/ComputeDependence.h +++ b/clang/include/clang/AST/ComputeDependence.h @@ -94,7 +94,7 @@ class DesignatedInitExpr; class ParenListExpr; class PseudoObjectExpr; class AtomicExpr; -class OMPArraySectionExpr; +class ArraySectionExpr; class OMPArrayShapingExpr; class OMPIteratorExpr; class ObjCArrayLiteral; @@ -189,7 +189,7 @@ ExprDependence computeDependence(ParenListExpr *E); ExprDependence computeDependence(PseudoObjectExpr *E); ExprDependence computeDependence(AtomicExpr *E); -ExprDependence computeDependence(OMPArraySectionExpr *E); +ExprDependence computeDependence(ArraySectionExpr *E); ExprDependence computeDependence(OMPArrayShapingExpr *E); ExprDependence computeDependence(OMPIteratorExpr *E); diff --git a/clang/include/clang/AST/Decl.h b/clang/include/clang/AST/Decl.h index 8b121896d66d158d06be1c317d7d1e1698782bc5..a53c27a99a8c3645c48c8ff2554e0ebf67cd38f1 100644 --- a/clang/include/clang/AST/Decl.h +++ b/clang/include/clang/AST/Decl.h @@ -157,7 +157,7 @@ public: SourceLocation CommentLoc, PragmaMSCommentKind CommentKind, StringRef Arg); - static PragmaCommentDecl *CreateDeserialized(ASTContext &C, DeclID ID, + static PragmaCommentDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID, unsigned ArgSize); PragmaMSCommentKind getCommentKind() const { return CommentKind; } @@ -192,7 +192,7 @@ public: SourceLocation Loc, StringRef Name, StringRef Value); static PragmaDetectMismatchDecl * - CreateDeserialized(ASTContext &C, DeclID ID, unsigned NameValueSize); + CreateDeserialized(ASTContext &C, GlobalDeclID ID, unsigned NameValueSize); StringRef getName() const { return getTrailingObjects(); } StringRef getValue() const { return getTrailingObjects() + ValueStart; } @@ -518,7 +518,7 @@ public: static LabelDecl *Create(ASTContext &C, DeclContext *DC, SourceLocation IdentL, IdentifierInfo *II, SourceLocation GnuLabelL); - static LabelDecl *CreateDeserialized(ASTContext &C, DeclID ID); + static LabelDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID); LabelStmt *getStmt() const { return TheStmt; } void setStmt(LabelStmt *T) { TheStmt = T; } @@ -581,7 +581,7 @@ public: IdentifierInfo *Id, NamespaceDecl *PrevDecl, bool Nested); - static NamespaceDecl *CreateDeserialized(ASTContext &C, DeclID ID); + static NamespaceDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID); using redecl_range = redeclarable_base::redecl_range; using redecl_iterator = redeclarable_base::redecl_iterator; @@ -1146,7 +1146,7 @@ public: const IdentifierInfo *Id, QualType T, TypeSourceInfo *TInfo, StorageClass S); - static VarDecl *CreateDeserialized(ASTContext &C, DeclID ID); + static VarDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID); SourceRange getSourceRange() const override LLVM_READONLY; @@ -1728,7 +1728,7 @@ public: static ImplicitParamDecl *Create(ASTContext &C, QualType T, ImplicitParamKind ParamKind); - static ImplicitParamDecl *CreateDeserialized(ASTContext &C, DeclID ID); + static ImplicitParamDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID); ImplicitParamDecl(ASTContext &C, DeclContext *DC, SourceLocation IdLoc, const IdentifierInfo *Id, QualType Type, @@ -1782,7 +1782,7 @@ public: TypeSourceInfo *TInfo, StorageClass S, Expr *DefArg); - static ParmVarDecl *CreateDeserialized(ASTContext &C, DeclID ID); + static ParmVarDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID); SourceRange getSourceRange() const override LLVM_READONLY; @@ -2178,7 +2178,7 @@ public: bool hasWrittenPrototype, ConstexprSpecKind ConstexprKind, Expr *TrailingRequiresClause); - static FunctionDecl *CreateDeserialized(ASTContext &C, DeclID ID); + static FunctionDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID); DeclarationNameInfo getNameInfo() const { return DeclarationNameInfo(getDeclName(), getLocation(), DNLoc); @@ -3136,7 +3136,7 @@ public: TypeSourceInfo *TInfo, Expr *BW, bool Mutable, InClassInitStyle InitStyle); - static FieldDecl *CreateDeserialized(ASTContext &C, DeclID ID); + static FieldDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID); /// Returns the index of this field within its record, /// as appropriate for passing to ASTRecordLayout::getFieldOffset. @@ -3311,7 +3311,7 @@ public: SourceLocation L, IdentifierInfo *Id, QualType T, Expr *E, const llvm::APSInt &V); - static EnumConstantDecl *CreateDeserialized(ASTContext &C, DeclID ID); + static EnumConstantDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID); const Expr *getInitExpr() const { return (const Expr*) Init; } Expr *getInitExpr() { return (Expr*) Init; } @@ -3357,7 +3357,7 @@ public: QualType T, llvm::MutableArrayRef CH); - static IndirectFieldDecl *CreateDeserialized(ASTContext &C, DeclID ID); + static IndirectFieldDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID); using chain_iterator = ArrayRef::const_iterator; @@ -3542,7 +3542,7 @@ public: static TypedefDecl *Create(ASTContext &C, DeclContext *DC, SourceLocation StartLoc, SourceLocation IdLoc, const IdentifierInfo *Id, TypeSourceInfo *TInfo); - static TypedefDecl *CreateDeserialized(ASTContext &C, DeclID ID); + static TypedefDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID); SourceRange getSourceRange() const override LLVM_READONLY; @@ -3567,7 +3567,7 @@ public: static TypeAliasDecl *Create(ASTContext &C, DeclContext *DC, SourceLocation StartLoc, SourceLocation IdLoc, const IdentifierInfo *Id, TypeSourceInfo *TInfo); - static TypeAliasDecl *CreateDeserialized(ASTContext &C, DeclID ID); + static TypeAliasDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID); SourceRange getSourceRange() const override LLVM_READONLY; @@ -3977,7 +3977,7 @@ public: IdentifierInfo *Id, EnumDecl *PrevDecl, bool IsScoped, bool IsScopedUsingClassTag, bool IsFixed); - static EnumDecl *CreateDeserialized(ASTContext &C, DeclID ID); + static EnumDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID); /// Overrides to provide correct range when there's an enum-base specifier /// with forward declarations. @@ -4182,7 +4182,7 @@ public: static RecordDecl *Create(const ASTContext &C, TagKind TK, DeclContext *DC, SourceLocation StartLoc, SourceLocation IdLoc, IdentifierInfo *Id, RecordDecl* PrevDecl = nullptr); - static RecordDecl *CreateDeserialized(const ASTContext &C, DeclID ID); + static RecordDecl *CreateDeserialized(const ASTContext &C, GlobalDeclID ID); RecordDecl *getPreviousDecl() { return cast_or_null( @@ -4433,7 +4433,7 @@ public: StringLiteral *Str, SourceLocation AsmLoc, SourceLocation RParenLoc); - static FileScopeAsmDecl *CreateDeserialized(ASTContext &C, DeclID ID); + static FileScopeAsmDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID); SourceLocation getAsmLoc() const { return getLocation(); } SourceLocation getRParenLoc() const { return RParenLoc; } @@ -4469,7 +4469,7 @@ class TopLevelStmtDecl : public Decl, public DeclContext { public: static TopLevelStmtDecl *Create(ASTContext &C, Stmt *Statement); - static TopLevelStmtDecl *CreateDeserialized(ASTContext &C, DeclID ID); + static TopLevelStmtDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID); SourceRange getSourceRange() const override LLVM_READONLY; Stmt *getStmt() { return Statement; } @@ -4563,7 +4563,7 @@ protected: public: static BlockDecl *Create(ASTContext &C, DeclContext *DC, SourceLocation L); - static BlockDecl *CreateDeserialized(ASTContext &C, DeclID ID); + static BlockDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID); SourceLocation getCaretLocation() const { return getLocation(); } @@ -4717,7 +4717,7 @@ public: static CapturedDecl *Create(ASTContext &C, DeclContext *DC, unsigned NumParams); - static CapturedDecl *CreateDeserialized(ASTContext &C, DeclID ID, + static CapturedDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID, unsigned NumParams); Stmt *getBody() const override; @@ -4851,7 +4851,7 @@ public: SourceLocation EndLoc); /// Create a new, deserialized module import declaration. - static ImportDecl *CreateDeserialized(ASTContext &C, DeclID ID, + static ImportDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID, unsigned NumLocations); /// Retrieve the module that was imported by the import declaration. @@ -4892,7 +4892,7 @@ private: public: static ExportDecl *Create(ASTContext &C, DeclContext *DC, SourceLocation ExportLoc); - static ExportDecl *CreateDeserialized(ASTContext &C, DeclID ID); + static ExportDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID); SourceLocation getExportLoc() const { return getLocation(); } SourceLocation getRBraceLoc() const { return RBraceLoc; } @@ -4931,7 +4931,7 @@ class EmptyDecl : public Decl { public: static EmptyDecl *Create(ASTContext &C, DeclContext *DC, SourceLocation L); - static EmptyDecl *CreateDeserialized(ASTContext &C, DeclID ID); + static EmptyDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID); static bool classof(const Decl *D) { return classofKind(D->getKind()); } static bool classofKind(Kind K) { return K == Empty; } @@ -4957,7 +4957,7 @@ public: bool CBuffer, SourceLocation KwLoc, IdentifierInfo *ID, SourceLocation IDLoc, SourceLocation LBrace); - static HLSLBufferDecl *CreateDeserialized(ASTContext &C, DeclID ID); + static HLSLBufferDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID); SourceRange getSourceRange() const override LLVM_READONLY { return SourceRange(getLocStart(), RBraceLoc); diff --git a/clang/include/clang/AST/DeclBase.h b/clang/include/clang/AST/DeclBase.h index d8cafc3d81526ef53ac6290fc6f03cae2acdf6f3..e43e812cd94558469ee5d6c53f6742dd89045e59 100644 --- a/clang/include/clang/AST/DeclBase.h +++ b/clang/include/clang/AST/DeclBase.h @@ -15,6 +15,7 @@ #include "clang/AST/ASTDumperUtils.h" #include "clang/AST/AttrIterator.h" +#include "clang/AST/DeclID.h" #include "clang/AST/DeclarationName.h" #include "clang/AST/SelectorLocationsKind.h" #include "clang/Basic/IdentifierTable.h" @@ -239,9 +240,6 @@ public: ModulePrivate }; - /// An ID number that refers to a declaration in an AST file. - using DeclID = uint32_t; - protected: /// The next declaration within the same lexical /// DeclContext. These pointers form the linked list that is @@ -361,7 +359,7 @@ protected: /// \param Ctx The context in which we will allocate memory. /// \param ID The global ID of the deserialized declaration. /// \param Extra The amount of extra space to allocate after the object. - void *operator new(std::size_t Size, const ASTContext &Ctx, DeclID ID, + void *operator new(std::size_t Size, const ASTContext &Ctx, GlobalDeclID ID, std::size_t Extra = 0); /// Allocate memory for a non-deserialized declaration. @@ -779,10 +777,10 @@ public: /// Retrieve the global declaration ID associated with this /// declaration, which specifies where this Decl was loaded from. - DeclID getGlobalID() const { + GlobalDeclID getGlobalID() const { if (isFromASTFile()) - return *((const DeclID *)this - 1); - return 0; + return (*((const GlobalDeclID *)this - 1)); + return GlobalDeclID(); } /// Retrieve the global ID of the module that owns this particular diff --git a/clang/include/clang/AST/DeclCXX.h b/clang/include/clang/AST/DeclCXX.h index a7644d2a19d2459c0a746a62cb1fc06f5fa5c2d5..fb52ac804849d87c91017bfd2b4381d9d55150aa 100644 --- a/clang/include/clang/AST/DeclCXX.h +++ b/clang/include/clang/AST/DeclCXX.h @@ -120,7 +120,7 @@ public: return new (C, DC) AccessSpecDecl(AS, DC, ASLoc, ColonLoc); } - static AccessSpecDecl *CreateDeserialized(ASTContext &C, DeclID ID); + static AccessSpecDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID); // Implement isa/cast/dyncast/etc. static bool classof(const Decl *D) { return classofKind(D->getKind()); } @@ -579,7 +579,8 @@ public: TypeSourceInfo *Info, SourceLocation Loc, unsigned DependencyKind, bool IsGeneric, LambdaCaptureDefault CaptureDefault); - static CXXRecordDecl *CreateDeserialized(const ASTContext &C, DeclID ID); + static CXXRecordDecl *CreateDeserialized(const ASTContext &C, + GlobalDeclID ID); bool isDynamicClass() const { return data().Polymorphic || data().NumVBases != 0; @@ -1980,7 +1981,8 @@ public: CXXConstructorDecl *Ctor = nullptr, DeductionCandidate Kind = DeductionCandidate::Normal); - static CXXDeductionGuideDecl *CreateDeserialized(ASTContext &C, DeclID ID); + static CXXDeductionGuideDecl *CreateDeserialized(ASTContext &C, + GlobalDeclID ID); ExplicitSpecifier getExplicitSpecifier() { return ExplicitSpec; } const ExplicitSpecifier getExplicitSpecifier() const { return ExplicitSpec; } @@ -2035,7 +2037,8 @@ public: static RequiresExprBodyDecl *Create(ASTContext &C, DeclContext *DC, SourceLocation StartLoc); - static RequiresExprBodyDecl *CreateDeserialized(ASTContext &C, DeclID ID); + static RequiresExprBodyDecl *CreateDeserialized(ASTContext &C, + GlobalDeclID ID); // Implement isa/cast/dyncast/etc. static bool classof(const Decl *D) { return classofKind(D->getKind()); } @@ -2078,7 +2081,7 @@ public: ConstexprSpecKind ConstexprKind, SourceLocation EndLocation, Expr *TrailingRequiresClause = nullptr); - static CXXMethodDecl *CreateDeserialized(ASTContext &C, DeclID ID); + static CXXMethodDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID); bool isStatic() const; bool isInstance() const { return !isStatic(); } @@ -2579,7 +2582,7 @@ public: friend class ASTDeclWriter; friend TrailingObjects; - static CXXConstructorDecl *CreateDeserialized(ASTContext &C, DeclID ID, + static CXXConstructorDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID, uint64_t AllocKind); static CXXConstructorDecl * Create(ASTContext &C, CXXRecordDecl *RD, SourceLocation StartLoc, @@ -2822,7 +2825,7 @@ public: bool UsesFPIntrin, bool isInline, bool isImplicitlyDeclared, ConstexprSpecKind ConstexprKind, Expr *TrailingRequiresClause = nullptr); - static CXXDestructorDecl *CreateDeserialized(ASTContext & C, DeclID ID); + static CXXDestructorDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID); void setOperatorDelete(FunctionDecl *OD, Expr *ThisArg); @@ -2881,7 +2884,7 @@ public: bool UsesFPIntrin, bool isInline, ExplicitSpecifier ES, ConstexprSpecKind ConstexprKind, SourceLocation EndLocation, Expr *TrailingRequiresClause = nullptr); - static CXXConversionDecl *CreateDeserialized(ASTContext &C, DeclID ID); + static CXXConversionDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID); ExplicitSpecifier getExplicitSpecifier() { return getCanonicalDecl()->ExplicitSpec; @@ -2948,7 +2951,7 @@ public: SourceLocation ExternLoc, SourceLocation LangLoc, LinkageSpecLanguageIDs Lang, bool HasBraces); - static LinkageSpecDecl *CreateDeserialized(ASTContext &C, DeclID ID); + static LinkageSpecDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID); /// Return the language specified by this linkage specification. LinkageSpecLanguageIDs getLanguage() const { @@ -3096,7 +3099,7 @@ public: SourceLocation IdentLoc, NamedDecl *Nominated, DeclContext *CommonAncestor); - static UsingDirectiveDecl *CreateDeserialized(ASTContext &C, DeclID ID); + static UsingDirectiveDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID); SourceRange getSourceRange() const override LLVM_READONLY { return SourceRange(UsingLoc, getLocation()); @@ -3157,7 +3160,7 @@ public: SourceLocation IdentLoc, NamedDecl *Namespace); - static NamespaceAliasDecl *CreateDeserialized(ASTContext &C, DeclID ID); + static NamespaceAliasDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID); using redecl_range = redeclarable_base::redecl_range; using redecl_iterator = redeclarable_base::redecl_iterator; @@ -3254,7 +3257,7 @@ public: LifetimeExtendedTemporaryDecl(Temp, EDec, Mangling); } static LifetimeExtendedTemporaryDecl *CreateDeserialized(ASTContext &C, - DeclID ID) { + GlobalDeclID ID) { return new (C, ID) LifetimeExtendedTemporaryDecl(EmptyShell{}); } @@ -3357,7 +3360,7 @@ public: UsingShadowDecl(UsingShadow, C, DC, Loc, Name, Introducer, Target); } - static UsingShadowDecl *CreateDeserialized(ASTContext &C, DeclID ID); + static UsingShadowDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID); using redecl_range = redeclarable_base::redecl_range; using redecl_iterator = redeclarable_base::redecl_iterator; @@ -3566,7 +3569,7 @@ public: const DeclarationNameInfo &NameInfo, bool HasTypenameKeyword); - static UsingDecl *CreateDeserialized(ASTContext &C, DeclID ID); + static UsingDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID); SourceRange getSourceRange() const override LLVM_READONLY; @@ -3645,7 +3648,7 @@ public: UsingDecl *Using, NamedDecl *Target, bool IsVirtual); static ConstructorUsingShadowDecl *CreateDeserialized(ASTContext &C, - DeclID ID); + GlobalDeclID ID); /// Override the UsingShadowDecl's getIntroducer, returning the UsingDecl that /// introduced this. @@ -3757,7 +3760,7 @@ public: SourceLocation UsingL, SourceLocation EnumL, SourceLocation NameL, TypeSourceInfo *EnumType); - static UsingEnumDecl *CreateDeserialized(ASTContext &C, DeclID ID); + static UsingEnumDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID); SourceRange getSourceRange() const override LLVM_READONLY; @@ -3830,7 +3833,7 @@ public: NamedDecl *InstantiatedFrom, ArrayRef UsingDecls); - static UsingPackDecl *CreateDeserialized(ASTContext &C, DeclID ID, + static UsingPackDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID, unsigned NumExpansions); SourceRange getSourceRange() const override LLVM_READONLY { @@ -3923,8 +3926,8 @@ public: NestedNameSpecifierLoc QualifierLoc, const DeclarationNameInfo &NameInfo, SourceLocation EllipsisLoc); - static UnresolvedUsingValueDecl * - CreateDeserialized(ASTContext &C, DeclID ID); + static UnresolvedUsingValueDecl *CreateDeserialized(ASTContext &C, + GlobalDeclID ID); SourceRange getSourceRange() const override LLVM_READONLY; @@ -4014,8 +4017,8 @@ public: SourceLocation TargetNameLoc, DeclarationName TargetName, SourceLocation EllipsisLoc); - static UnresolvedUsingTypenameDecl * - CreateDeserialized(ASTContext &C, DeclID ID); + static UnresolvedUsingTypenameDecl *CreateDeserialized(ASTContext &C, + GlobalDeclID ID); /// Retrieves the canonical declaration of this declaration. UnresolvedUsingTypenameDecl *getCanonicalDecl() override { @@ -4045,7 +4048,7 @@ public: SourceLocation Loc, DeclarationName Name); static UnresolvedUsingIfExistsDecl *CreateDeserialized(ASTContext &Ctx, - DeclID ID); + GlobalDeclID ID); static bool classof(const Decl *D) { return classofKind(D->getKind()); } static bool classofKind(Kind K) { return K == Decl::UnresolvedUsingIfExists; } @@ -4073,7 +4076,7 @@ public: SourceLocation StaticAssertLoc, Expr *AssertExpr, Expr *Message, SourceLocation RParenLoc, bool Failed); - static StaticAssertDecl *CreateDeserialized(ASTContext &C, DeclID ID); + static StaticAssertDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID); Expr *getAssertExpr() { return AssertExprAndFailed.getPointer(); } const Expr *getAssertExpr() const { return AssertExprAndFailed.getPointer(); } @@ -4120,7 +4123,7 @@ public: static BindingDecl *Create(ASTContext &C, DeclContext *DC, SourceLocation IdLoc, IdentifierInfo *Id); - static BindingDecl *CreateDeserialized(ASTContext &C, DeclID ID); + static BindingDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID); /// Get the expression to which this declaration is bound. This may be null /// in two different cases: while parsing the initializer for the @@ -4189,7 +4192,7 @@ public: QualType T, TypeSourceInfo *TInfo, StorageClass S, ArrayRef Bindings); - static DecompositionDecl *CreateDeserialized(ASTContext &C, DeclID ID, + static DecompositionDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID, unsigned NumBindings); ArrayRef bindings() const { @@ -4246,7 +4249,7 @@ public: SourceLocation L, DeclarationName N, QualType T, TypeSourceInfo *TInfo, SourceLocation StartL, IdentifierInfo *Getter, IdentifierInfo *Setter); - static MSPropertyDecl *CreateDeserialized(ASTContext &C, DeclID ID); + static MSPropertyDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID); static bool classof(const Decl *D) { return D->getKind() == MSProperty; } @@ -4300,7 +4303,7 @@ private: MSGuidDecl(DeclContext *DC, QualType T, Parts P); static MSGuidDecl *Create(const ASTContext &C, QualType T, Parts P); - static MSGuidDecl *CreateDeserialized(ASTContext &C, DeclID ID); + static MSGuidDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID); // Only ASTContext::getMSGuidDecl and deserialization create these. friend class ASTContext; @@ -4353,7 +4356,7 @@ class UnnamedGlobalConstantDecl : public ValueDecl, static UnnamedGlobalConstantDecl *Create(const ASTContext &C, QualType T, const APValue &APVal); static UnnamedGlobalConstantDecl *CreateDeserialized(ASTContext &C, - DeclID ID); + GlobalDeclID ID); // Only ASTContext::getUnnamedGlobalConstantDecl and deserialization create // these. diff --git a/clang/include/clang/AST/DeclFriend.h b/clang/include/clang/AST/DeclFriend.h index b56627a5337d63a80af5b4ad2856aad5c1be2998..9789282f351a55c07e242598489aeb2a9b8b4e56 100644 --- a/clang/include/clang/AST/DeclFriend.h +++ b/clang/include/clang/AST/DeclFriend.h @@ -112,7 +112,7 @@ public: Create(ASTContext &C, DeclContext *DC, SourceLocation L, FriendUnion Friend_, SourceLocation FriendL, ArrayRef FriendTypeTPLists = std::nullopt); - static FriendDecl *CreateDeserialized(ASTContext &C, DeclID ID, + static FriendDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID, unsigned FriendTypeNumTPLists); /// If this friend declaration names an (untemplated but possibly diff --git a/clang/include/clang/AST/DeclID.h b/clang/include/clang/AST/DeclID.h new file mode 100644 index 0000000000000000000000000000000000000000..614ba06b63860cdd13f7c1f2761c40231ca39275 --- /dev/null +++ b/clang/include/clang/AST/DeclID.h @@ -0,0 +1,227 @@ +//===--- DeclID.h - ID number for deserialized declarations ----*- C++ -*-===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// +// +// This file defines DeclID class family to describe the deserialized +// declarations. The DeclID is widely used in AST via LazyDeclPtr, or calls to +// `ExternalASTSource::getExternalDecl`. It will be helpful for type safety to +// require the use of `DeclID` to explicit. +// +//===----------------------------------------------------------------------===// + +#ifndef LLVM_CLANG_AST_DECLID_H +#define LLVM_CLANG_AST_DECLID_H + +#include "llvm/ADT/DenseMapInfo.h" +#include "llvm/ADT/iterator.h" + +namespace clang { + +/// Predefined declaration IDs. +/// +/// These declaration IDs correspond to predefined declarations in the AST +/// context, such as the NULL declaration ID. Such declarations are never +/// actually serialized, since they will be built by the AST context when +/// it is created. +enum PredefinedDeclIDs { + /// The NULL declaration. + PREDEF_DECL_NULL_ID = 0, + + /// The translation unit. + PREDEF_DECL_TRANSLATION_UNIT_ID = 1, + + /// The Objective-C 'id' type. + PREDEF_DECL_OBJC_ID_ID = 2, + + /// The Objective-C 'SEL' type. + PREDEF_DECL_OBJC_SEL_ID = 3, + + /// The Objective-C 'Class' type. + PREDEF_DECL_OBJC_CLASS_ID = 4, + + /// The Objective-C 'Protocol' type. + PREDEF_DECL_OBJC_PROTOCOL_ID = 5, + + /// The signed 128-bit integer type. + PREDEF_DECL_INT_128_ID = 6, + + /// The unsigned 128-bit integer type. + PREDEF_DECL_UNSIGNED_INT_128_ID = 7, + + /// The internal 'instancetype' typedef. + PREDEF_DECL_OBJC_INSTANCETYPE_ID = 8, + + /// The internal '__builtin_va_list' typedef. + PREDEF_DECL_BUILTIN_VA_LIST_ID = 9, + + /// The internal '__va_list_tag' struct, if any. + PREDEF_DECL_VA_LIST_TAG = 10, + + /// The internal '__builtin_ms_va_list' typedef. + PREDEF_DECL_BUILTIN_MS_VA_LIST_ID = 11, + + /// The predeclared '_GUID' struct. + PREDEF_DECL_BUILTIN_MS_GUID_ID = 12, + + /// The extern "C" context. + PREDEF_DECL_EXTERN_C_CONTEXT_ID = 13, + + /// The internal '__make_integer_seq' template. + PREDEF_DECL_MAKE_INTEGER_SEQ_ID = 14, + + /// The internal '__NSConstantString' typedef. + PREDEF_DECL_CF_CONSTANT_STRING_ID = 15, + + /// The internal '__NSConstantString' tag type. + PREDEF_DECL_CF_CONSTANT_STRING_TAG_ID = 16, + + /// The internal '__type_pack_element' template. + PREDEF_DECL_TYPE_PACK_ELEMENT_ID = 17, +}; + +/// The number of declaration IDs that are predefined. +/// +/// For more information about predefined declarations, see the +/// \c PredefinedDeclIDs type and the PREDEF_DECL_*_ID constants. +const unsigned int NUM_PREDEF_DECL_IDS = 18; + +/// GlobalDeclID means DeclID in the current ASTContext and LocalDeclID means +/// DeclID specific to a certain ModuleFile. Specially, in ASTWriter, the +/// LocalDeclID to the ModuleFile been writting is equal to the GlobalDeclID. +/// Outside the serializer, all the DeclID been used should be GlobalDeclID. +/// We can translate a LocalDeclID to the GlobalDeclID by +/// `ASTReader::getGlobalDeclID()`. + +class DeclIDBase { +public: + /// An ID number that refers to a declaration in an AST file. + /// + /// The ID numbers of declarations are consecutive (in order of + /// discovery), with values below NUM_PREDEF_DECL_IDS being reserved. + /// At the start of a chain of precompiled headers, declaration ID 1 is + /// used for the translation unit declaration. + /// + /// DeclID should only be used directly in serialization. All other users + /// should use LocalDeclID or GlobalDeclID. + using DeclID = uint32_t; + +protected: + DeclIDBase() : ID(PREDEF_DECL_NULL_ID) {} + explicit DeclIDBase(DeclID ID) : ID(ID) {} + +public: + DeclID get() const { return ID; } + + explicit operator DeclID() const { return ID; } + + explicit operator PredefinedDeclIDs() const { return (PredefinedDeclIDs)ID; } + + bool isValid() const { return ID != PREDEF_DECL_NULL_ID; } + + bool isInvalid() const { return ID == PREDEF_DECL_NULL_ID; } + + friend bool operator==(const DeclIDBase &LHS, const DeclIDBase &RHS) { + return LHS.ID == RHS.ID; + } + friend bool operator!=(const DeclIDBase &LHS, const DeclIDBase &RHS) { + return LHS.ID != RHS.ID; + } + // We may sort the decl ID. + friend bool operator<(const DeclIDBase &LHS, const DeclIDBase &RHS) { + return LHS.ID < RHS.ID; + } + friend bool operator>(const DeclIDBase &LHS, const DeclIDBase &RHS) { + return LHS.ID > RHS.ID; + } + friend bool operator<=(const DeclIDBase &LHS, const DeclIDBase &RHS) { + return LHS.ID <= RHS.ID; + } + friend bool operator>=(const DeclIDBase &LHS, const DeclIDBase &RHS) { + return LHS.ID >= RHS.ID; + } + +protected: + DeclID ID; +}; + +class LocalDeclID : public DeclIDBase { + using Base = DeclIDBase; + +public: + LocalDeclID() : Base() {} + LocalDeclID(PredefinedDeclIDs ID) : Base(ID) {} + explicit LocalDeclID(DeclID ID) : Base(ID) {} + + LocalDeclID &operator++() { + ++ID; + return *this; + } + + LocalDeclID operator++(int) { + LocalDeclID Ret = *this; + ++(*this); + return Ret; + } +}; + +class GlobalDeclID : public DeclIDBase { + using Base = DeclIDBase; + +public: + GlobalDeclID() : Base() {} + explicit GlobalDeclID(DeclID ID) : Base(ID) {} + + // For DeclIDIterator to be able to convert a GlobalDeclID + // to a LocalDeclID. + explicit operator LocalDeclID() const { return LocalDeclID(this->ID); } +}; + +/// A helper iterator adaptor to convert the iterators to +/// `SmallVector` to the iterators to `SmallVector`. +template +class DeclIDIterator + : public llvm::iterator_adaptor_base, + const FromTy *, + std::forward_iterator_tag, ToTy> { +public: + DeclIDIterator() : DeclIDIterator::iterator_adaptor_base(nullptr) {} + + DeclIDIterator(const FromTy *ID) + : DeclIDIterator::iterator_adaptor_base(ID) {} + + ToTy operator*() const { return ToTy(*this->I); } + + bool operator==(const DeclIDIterator &RHS) const { return this->I == RHS.I; } +}; + +} // namespace clang + +namespace llvm { +template <> struct DenseMapInfo { + using GlobalDeclID = clang::GlobalDeclID; + using DeclID = GlobalDeclID::DeclID; + + static GlobalDeclID getEmptyKey() { + return GlobalDeclID(DenseMapInfo::getEmptyKey()); + } + + static GlobalDeclID getTombstoneKey() { + return GlobalDeclID(DenseMapInfo::getTombstoneKey()); + } + + static unsigned getHashValue(const GlobalDeclID &Key) { + return DenseMapInfo::getHashValue(Key.get()); + } + + static bool isEqual(const GlobalDeclID &L, const GlobalDeclID &R) { + return L == R; + } +}; + +} // namespace llvm + +#endif diff --git a/clang/include/clang/AST/DeclObjC.h b/clang/include/clang/AST/DeclObjC.h index 7780afa6f1cf5c11b286b39613cc18c21293630b..d2cc61ca19f8a5796a7a499c0780de95a0b92a6c 100644 --- a/clang/include/clang/AST/DeclObjC.h +++ b/clang/include/clang/AST/DeclObjC.h @@ -236,7 +236,7 @@ public: ObjCImplementationControl impControl = ObjCImplementationControl::None, bool HasRelatedResultType = false); - static ObjCMethodDecl *CreateDeserialized(ASTContext &C, DeclID ID); + static ObjCMethodDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID); ObjCMethodDecl *getCanonicalDecl() override; const ObjCMethodDecl *getCanonicalDecl() const { @@ -614,7 +614,8 @@ public: IdentifierInfo *name, SourceLocation colonLoc, TypeSourceInfo *boundInfo); - static ObjCTypeParamDecl *CreateDeserialized(ASTContext &ctx, DeclID ID); + static ObjCTypeParamDecl *CreateDeserialized(ASTContext &ctx, + GlobalDeclID ID); SourceRange getSourceRange() const override LLVM_READONLY; @@ -789,7 +790,7 @@ public: TypeSourceInfo *TSI, PropertyControl propControl = None); - static ObjCPropertyDecl *CreateDeserialized(ASTContext &C, DeclID ID); + static ObjCPropertyDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID); SourceLocation getAtLoc() const { return AtLoc; } void setAtLoc(SourceLocation L) { AtLoc = L; } @@ -1279,7 +1280,8 @@ public: ObjCInterfaceDecl *PrevDecl, SourceLocation ClassLoc = SourceLocation(), bool isInternal = false); - static ObjCInterfaceDecl *CreateDeserialized(const ASTContext &C, DeclID ID); + static ObjCInterfaceDecl *CreateDeserialized(const ASTContext &C, + GlobalDeclID ID); /// Retrieve the type parameters of this class. /// @@ -1969,7 +1971,7 @@ public: TypeSourceInfo *TInfo, AccessControl ac, Expr *BW = nullptr, bool synthesized = false); - static ObjCIvarDecl *CreateDeserialized(ASTContext &C, DeclID ID); + static ObjCIvarDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID); /// Return the class interface that this ivar is logically contained /// in; this is either the interface where the ivar was declared, or the @@ -2039,7 +2041,8 @@ public: SourceLocation IdLoc, IdentifierInfo *Id, QualType T, Expr *BW); - static ObjCAtDefsFieldDecl *CreateDeserialized(ASTContext &C, DeclID ID); + static ObjCAtDefsFieldDecl *CreateDeserialized(ASTContext &C, + GlobalDeclID ID); // Implement isa/cast/dyncast/etc. static bool classof(const Decl *D) { return classofKind(D->getKind()); } @@ -2142,7 +2145,7 @@ public: SourceLocation atStartLoc, ObjCProtocolDecl *PrevDecl); - static ObjCProtocolDecl *CreateDeserialized(ASTContext &C, DeclID ID); + static ObjCProtocolDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID); const ObjCProtocolList &getReferencedProtocols() const { assert(hasDefinition() && "No definition available!"); @@ -2361,7 +2364,7 @@ public: ObjCTypeParamList *typeParamList, SourceLocation IvarLBraceLoc = SourceLocation(), SourceLocation IvarRBraceLoc = SourceLocation()); - static ObjCCategoryDecl *CreateDeserialized(ASTContext &C, DeclID ID); + static ObjCCategoryDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID); ObjCInterfaceDecl *getClassInterface() { return ClassInterface; } const ObjCInterfaceDecl *getClassInterface() const { return ClassInterface; } @@ -2558,7 +2561,8 @@ public: Create(ASTContext &C, DeclContext *DC, const IdentifierInfo *Id, ObjCInterfaceDecl *classInterface, SourceLocation nameLoc, SourceLocation atStartLoc, SourceLocation CategoryNameLoc); - static ObjCCategoryImplDecl *CreateDeserialized(ASTContext &C, DeclID ID); + static ObjCCategoryImplDecl *CreateDeserialized(ASTContext &C, + GlobalDeclID ID); ObjCCategoryDecl *getCategoryDecl() const; @@ -2640,7 +2644,8 @@ public: SourceLocation IvarLBraceLoc=SourceLocation(), SourceLocation IvarRBraceLoc=SourceLocation()); - static ObjCImplementationDecl *CreateDeserialized(ASTContext &C, DeclID ID); + static ObjCImplementationDecl *CreateDeserialized(ASTContext &C, + GlobalDeclID ID); /// init_iterator - Iterates through the ivar initializer list. using init_iterator = CXXCtorInitializer **; @@ -2780,7 +2785,7 @@ public: ObjCInterfaceDecl* aliasedClass); static ObjCCompatibleAliasDecl *CreateDeserialized(ASTContext &C, - DeclID ID); + GlobalDeclID ID); const ObjCInterfaceDecl *getClassInterface() const { return AliasedClass; } ObjCInterfaceDecl *getClassInterface() { return AliasedClass; } @@ -2851,7 +2856,8 @@ public: ObjCIvarDecl *ivarDecl, SourceLocation ivarLoc); - static ObjCPropertyImplDecl *CreateDeserialized(ASTContext &C, DeclID ID); + static ObjCPropertyImplDecl *CreateDeserialized(ASTContext &C, + GlobalDeclID ID); SourceRange getSourceRange() const override LLVM_READONLY; diff --git a/clang/include/clang/AST/DeclOpenMP.h b/clang/include/clang/AST/DeclOpenMP.h index c7ede7f2157fef7676cb6bf068761c49602479d9..e542c3c8e66b0f28a4de617c302c60542cee632e 100644 --- a/clang/include/clang/AST/DeclOpenMP.h +++ b/clang/include/clang/AST/DeclOpenMP.h @@ -59,7 +59,7 @@ protected: } template - static T *createEmptyDirective(const ASTContext &C, unsigned ID, + static T *createEmptyDirective(const ASTContext &C, GlobalDeclID ID, unsigned NumClauses, unsigned NumChildren, Params &&... P) { auto *Inst = new (C, ID, size(NumClauses, NumChildren)) @@ -133,7 +133,7 @@ public: SourceLocation L, ArrayRef VL); static OMPThreadPrivateDecl *CreateDeserialized(ASTContext &C, - DeclID ID, unsigned N); + GlobalDeclID ID, unsigned N); typedef MutableArrayRef::iterator varlist_iterator; typedef ArrayRef::iterator varlist_const_iterator; @@ -214,7 +214,7 @@ public: QualType T, OMPDeclareReductionDecl *PrevDeclInScope); /// Create deserialized declare reduction node. static OMPDeclareReductionDecl *CreateDeserialized(ASTContext &C, - DeclID ID); + GlobalDeclID ID); /// Get combiner expression of the declare reduction construct. Expr *getCombiner() { return Combiner; } @@ -318,8 +318,8 @@ public: ArrayRef Clauses, OMPDeclareMapperDecl *PrevDeclInScope); /// Creates deserialized declare mapper node. - static OMPDeclareMapperDecl *CreateDeserialized(ASTContext &C, DeclID ID, - unsigned N); + static OMPDeclareMapperDecl *CreateDeserialized(ASTContext &C, + GlobalDeclID ID, unsigned N); using clauselist_iterator = MutableArrayRef::iterator; using clauselist_const_iterator = ArrayRef::iterator; @@ -397,7 +397,8 @@ public: IdentifierInfo *Id, QualType T, SourceLocation StartLoc); - static OMPCapturedExprDecl *CreateDeserialized(ASTContext &C, DeclID ID); + static OMPCapturedExprDecl *CreateDeserialized(ASTContext &C, + GlobalDeclID ID); SourceRange getSourceRange() const override LLVM_READONLY; @@ -427,7 +428,7 @@ public: static OMPRequiresDecl *Create(ASTContext &C, DeclContext *DC, SourceLocation L, ArrayRef CL); /// Create deserialized requires node. - static OMPRequiresDecl *CreateDeserialized(ASTContext &C, DeclID ID, + static OMPRequiresDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID, unsigned N); using clauselist_iterator = MutableArrayRef::iterator; @@ -495,7 +496,7 @@ public: static OMPAllocateDecl *Create(ASTContext &C, DeclContext *DC, SourceLocation L, ArrayRef VL, ArrayRef CL); - static OMPAllocateDecl *CreateDeserialized(ASTContext &C, DeclID ID, + static OMPAllocateDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID, unsigned NVars, unsigned NClauses); typedef MutableArrayRef::iterator varlist_iterator; diff --git a/clang/include/clang/AST/DeclTemplate.h b/clang/include/clang/AST/DeclTemplate.h index 231bda44a9fcfdfbcfc532cb0894040dc6332492..3ee03eebdb8ca45d48358b8e52d2cce85553c5bf 100644 --- a/clang/include/clang/AST/DeclTemplate.h +++ b/clang/include/clang/AST/DeclTemplate.h @@ -797,7 +797,7 @@ protected: /// /// The first value in the array is the number of specializations/partial /// specializations that follow. - Decl::DeclID *LazySpecializations = nullptr; + GlobalDeclID *LazySpecializations = nullptr; /// The set of "injected" template arguments used within this /// template. @@ -1087,7 +1087,8 @@ public: NamedDecl *Decl); /// Create an empty function template node. - static FunctionTemplateDecl *CreateDeserialized(ASTContext &C, DeclID ID); + static FunctionTemplateDecl *CreateDeserialized(ASTContext &C, + GlobalDeclID ID); // Implement isa/cast/dyncast support static bool classof(const Decl *D) { return classofKind(D->getKind()); } @@ -1204,9 +1205,9 @@ public: bool Typename, bool ParameterPack, bool HasTypeConstraint = false, std::optional NumExpanded = std::nullopt); static TemplateTypeParmDecl *CreateDeserialized(const ASTContext &C, - DeclID ID); + GlobalDeclID ID); static TemplateTypeParmDecl *CreateDeserialized(const ASTContext &C, - DeclID ID, + GlobalDeclID ID, bool HasTypeConstraint); /// Whether this template type parameter was declared with @@ -1413,11 +1414,10 @@ public: QualType T, TypeSourceInfo *TInfo, ArrayRef ExpandedTypes, ArrayRef ExpandedTInfos); + static NonTypeTemplateParmDecl * + CreateDeserialized(ASTContext &C, GlobalDeclID ID, bool HasTypeConstraint); static NonTypeTemplateParmDecl *CreateDeserialized(ASTContext &C, - DeclID ID, - bool HasTypeConstraint); - static NonTypeTemplateParmDecl *CreateDeserialized(ASTContext &C, - DeclID ID, + GlobalDeclID ID, unsigned NumExpandedTypes, bool HasTypeConstraint); @@ -1632,10 +1632,9 @@ public: ArrayRef Expansions); static TemplateTemplateParmDecl *CreateDeserialized(ASTContext &C, - DeclID ID); - static TemplateTemplateParmDecl *CreateDeserialized(ASTContext &C, - DeclID ID, - unsigned NumExpansions); + GlobalDeclID ID); + static TemplateTemplateParmDecl * + CreateDeserialized(ASTContext &C, GlobalDeclID ID, unsigned NumExpansions); using TemplateParmPosition::getDepth; using TemplateParmPosition::setDepth; @@ -1857,8 +1856,8 @@ public: ClassTemplateDecl *SpecializedTemplate, ArrayRef Args, ClassTemplateSpecializationDecl *PrevDecl); - static ClassTemplateSpecializationDecl * - CreateDeserialized(ASTContext &C, DeclID ID); + static ClassTemplateSpecializationDecl *CreateDeserialized(ASTContext &C, + GlobalDeclID ID); void getNameForDiagnostic(raw_ostream &OS, const PrintingPolicy &Policy, bool Qualified) const override; @@ -2110,7 +2109,7 @@ public: ClassTemplatePartialSpecializationDecl *PrevDecl); static ClassTemplatePartialSpecializationDecl * - CreateDeserialized(ASTContext &C, DeclID ID); + CreateDeserialized(ASTContext &C, GlobalDeclID ID); ClassTemplatePartialSpecializationDecl *getMostRecentDecl() { return cast( @@ -2306,7 +2305,7 @@ public: NamedDecl *Decl); /// Create an empty class template node. - static ClassTemplateDecl *CreateDeserialized(ASTContext &C, DeclID ID); + static ClassTemplateDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID); /// Return the specialization with the provided arguments if it exists, /// otherwise return the insertion point. @@ -2472,7 +2471,7 @@ public: MutableArrayRef Params, FriendUnion Friend, SourceLocation FriendLoc); - static FriendTemplateDecl *CreateDeserialized(ASTContext &C, DeclID ID); + static FriendTemplateDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID); /// If this friend declaration names a templated type (or /// a dependent member type of a templated type), return that @@ -2573,7 +2572,8 @@ public: NamedDecl *Decl); /// Create an empty alias template node. - static TypeAliasTemplateDecl *CreateDeserialized(ASTContext &C, DeclID ID); + static TypeAliasTemplateDecl *CreateDeserialized(ASTContext &C, + GlobalDeclID ID); // Implement isa/cast/dyncast support static bool classof(const Decl *D) { return classofKind(D->getKind()); } @@ -2670,7 +2670,7 @@ public: TypeSourceInfo *TInfo, StorageClass S, ArrayRef Args); static VarTemplateSpecializationDecl *CreateDeserialized(ASTContext &C, - DeclID ID); + GlobalDeclID ID); void getNameForDiagnostic(raw_ostream &OS, const PrintingPolicy &Policy, bool Qualified) const override; @@ -2900,8 +2900,8 @@ public: TypeSourceInfo *TInfo, StorageClass S, ArrayRef Args, const TemplateArgumentListInfo &ArgInfos); - static VarTemplatePartialSpecializationDecl *CreateDeserialized(ASTContext &C, - DeclID ID); + static VarTemplatePartialSpecializationDecl * + CreateDeserialized(ASTContext &C, GlobalDeclID ID); VarTemplatePartialSpecializationDecl *getMostRecentDecl() { return cast( @@ -3078,7 +3078,7 @@ public: VarDecl *Decl); /// Create an empty variable template node. - static VarTemplateDecl *CreateDeserialized(ASTContext &C, DeclID ID); + static VarTemplateDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID); /// Return the specialization with the provided arguments if it exists, /// otherwise return the insertion point. @@ -3183,7 +3183,7 @@ public: SourceLocation L, DeclarationName Name, TemplateParameterList *Params, Expr *ConstraintExpr); - static ConceptDecl *CreateDeserialized(ASTContext &C, DeclID ID); + static ConceptDecl *CreateDeserialized(ASTContext &C, GlobalDeclID ID); Expr *getConstraintExpr() const { return ConstraintExpr; @@ -3232,7 +3232,7 @@ public: Create(const ASTContext &C, DeclContext *DC, SourceLocation SL, ArrayRef ConvertedArgs); static ImplicitConceptSpecializationDecl * - CreateDeserialized(const ASTContext &C, DeclID ID, + CreateDeserialized(const ASTContext &C, GlobalDeclID ID, unsigned NumTemplateArgs); ArrayRef getTemplateArguments() const { @@ -3275,7 +3275,7 @@ private: static TemplateParamObjectDecl *Create(const ASTContext &C, QualType T, const APValue &V); static TemplateParamObjectDecl *CreateDeserialized(ASTContext &C, - DeclID ID); + GlobalDeclID ID); /// Only ASTContext::getTemplateParamObjectDecl and deserialization /// create these. diff --git a/clang/include/clang/AST/Expr.h b/clang/include/clang/AST/Expr.h index 2bfefeabc348bee1cc399a43bfd8aa057a18ec3d..f2bf667636dc9b5d63864130240af4c01cfbc3ff 100644 --- a/clang/include/clang/AST/Expr.h +++ b/clang/include/clang/AST/Expr.h @@ -6610,6 +6610,275 @@ public: }; +/// This class represents BOTH the OpenMP Array Section and OpenACC 'subarray', +/// with a boolean differentiator. +/// OpenMP 5.0 [2.1.5, Array Sections]. +/// To specify an array section in an OpenMP construct, array subscript +/// expressions are extended with the following syntax: +/// \code +/// [ lower-bound : length : stride ] +/// [ lower-bound : length : ] +/// [ lower-bound : length ] +/// [ lower-bound : : stride ] +/// [ lower-bound : : ] +/// [ lower-bound : ] +/// [ : length : stride ] +/// [ : length : ] +/// [ : length ] +/// [ : : stride ] +/// [ : : ] +/// [ : ] +/// \endcode +/// The array section must be a subset of the original array. +/// Array sections are allowed on multidimensional arrays. Base language array +/// subscript expressions can be used to specify length-one dimensions of +/// multidimensional array sections. +/// Each of the lower-bound, length, and stride expressions if specified must be +/// an integral type expressions of the base language. When evaluated +/// they represent a set of integer values as follows: +/// \code +/// { lower-bound, lower-bound + stride, lower-bound + 2 * stride,... , +/// lower-bound + ((length - 1) * stride) } +/// \endcode +/// The lower-bound and length must evaluate to non-negative integers. +/// The stride must evaluate to a positive integer. +/// When the size of the array dimension is not known, the length must be +/// specified explicitly. +/// When the stride is absent it defaults to 1. +/// When the length is absent it defaults to ⌈(size − lower-bound)/stride⌉, +/// where size is the size of the array dimension. When the lower-bound is +/// absent it defaults to 0. +/// +/// +/// OpenACC 3.3 [2.7.1 Data Specification in Data Clauses] +/// In C and C++, a subarray is an array name followed by an extended array +/// range specification in brackets, with start and length, such as +/// +/// AA[2:n] +/// +/// If the lower bound is missing, zero is used. If the length is missing and +/// the array has known size, the size of the array is used; otherwise the +/// length is required. The subarray AA[2:n] means elements AA[2], AA[3], . . . +/// , AA[2+n-1]. In C and C++, a two dimensional array may be declared in at +/// least four ways: +/// +/// -Statically-sized array: float AA[100][200]; +/// -Pointer to statically sized rows: typedef float row[200]; row* BB; +/// -Statically-sized array of pointers: float* CC[200]; +/// -Pointer to pointers: float** DD; +/// +/// Each dimension may be statically sized, or a pointer to dynamically +/// allocated memory. Each of these may be included in a data clause using +/// subarray notation to specify a rectangular array: +/// +/// -AA[2:n][0:200] +/// -BB[2:n][0:m] +/// -CC[2:n][0:m] +/// -DD[2:n][0:m] +/// +/// Multidimensional rectangular subarrays in C and C++ may be specified for any +/// array with any combination of statically-sized or dynamically-allocated +/// dimensions. For statically sized dimensions, all dimensions except the first +/// must specify the whole extent to preserve the contiguous data restriction, +/// discussed below. For dynamically allocated dimensions, the implementation +/// will allocate pointers in device memory corresponding to the pointers in +/// local memory and will fill in those pointers as appropriate. +/// +/// In Fortran, a subarray is an array name followed by a comma-separated list +/// of range specifications in parentheses, with lower and upper bound +/// subscripts, such as +/// +/// arr(1:high,low:100) +/// +/// If either the lower or upper bounds are missing, the declared or allocated +/// bounds of the array, if known, are used. All dimensions except the last must +/// specify the whole extent, to preserve the contiguous data restriction, +/// discussed below. +/// +/// Restrictions +/// +/// -In Fortran, the upper bound for the last dimension of an assumed-size dummy +/// array must be specified. +/// +/// -In C and C++, the length for dynamically allocated dimensions of an array +/// must be explicitly specified. +/// +/// -In C and C++, modifying pointers in pointer arrays during the data +/// lifetime, either on the host or on the device, may result in undefined +/// behavior. +/// +/// -If a subarray appears in a data clause, the implementation may choose to +/// allocate memory for only that subarray on the accelerator. +/// +/// -In Fortran, array pointers may appear, but pointer association is not +/// preserved in device memory. +/// +/// -Any array or subarray in a data clause, including Fortran array pointers, +/// must be a contiguous section of memory, except for dynamic multidimensional +/// C arrays. +/// +/// -In C and C++, if a variable or array of composite type appears, all the +/// data members of the struct or class are allocated and copied, as +/// appropriate. If a composite member is a pointer type, the data addressed by +/// that pointer are not implicitly copied. +/// +/// -In Fortran, if a variable or array of composite type appears, all the +/// members of that derived type are allocated and copied, as appropriate. If +/// any member has the allocatable or pointer attribute, the data accessed +/// through that member are not copied. +/// +/// -If an expression is used in a subscript or subarray expression in a clause +/// on a data construct, the same value is used when copying data at the end of +/// the data region, even if the values of variables in the expression change +/// during the data region. +class ArraySectionExpr : public Expr { + friend class ASTStmtReader; + friend class ASTStmtWriter; + +public: + enum ArraySectionType { OMPArraySection, OpenACCArraySection }; + +private: + enum { + BASE, + LOWER_BOUND, + LENGTH, + STRIDE, + END_EXPR, + OPENACC_END_EXPR = STRIDE + }; + + ArraySectionType ASType = OMPArraySection; + Stmt *SubExprs[END_EXPR] = {nullptr}; + SourceLocation ColonLocFirst; + SourceLocation ColonLocSecond; + SourceLocation RBracketLoc; + +public: + // Constructor for OMP array sections, which include a 'stride'. + ArraySectionExpr(Expr *Base, Expr *LowerBound, Expr *Length, Expr *Stride, + QualType Type, ExprValueKind VK, ExprObjectKind OK, + SourceLocation ColonLocFirst, SourceLocation ColonLocSecond, + SourceLocation RBracketLoc) + : Expr(ArraySectionExprClass, Type, VK, OK), ASType(OMPArraySection), + ColonLocFirst(ColonLocFirst), ColonLocSecond(ColonLocSecond), + RBracketLoc(RBracketLoc) { + setBase(Base); + setLowerBound(LowerBound); + setLength(Length); + setStride(Stride); + setDependence(computeDependence(this)); + } + + // Constructor for OpenACC sub-arrays, which do not permit a 'stride'. + ArraySectionExpr(Expr *Base, Expr *LowerBound, Expr *Length, QualType Type, + ExprValueKind VK, ExprObjectKind OK, SourceLocation ColonLoc, + SourceLocation RBracketLoc) + : Expr(ArraySectionExprClass, Type, VK, OK), ASType(OpenACCArraySection), + ColonLocFirst(ColonLoc), RBracketLoc(RBracketLoc) { + setBase(Base); + setLowerBound(LowerBound); + setLength(Length); + setDependence(computeDependence(this)); + } + + /// Create an empty array section expression. + explicit ArraySectionExpr(EmptyShell Shell) + : Expr(ArraySectionExprClass, Shell) {} + + /// Return original type of the base expression for array section. + static QualType getBaseOriginalType(const Expr *Base); + + static bool classof(const Stmt *T) { + return T->getStmtClass() == ArraySectionExprClass; + } + + bool isOMPArraySection() const { return ASType == OMPArraySection; } + bool isOpenACCArraySection() const { return ASType == OpenACCArraySection; } + + /// Get base of the array section. + Expr *getBase() { return cast(SubExprs[BASE]); } + const Expr *getBase() const { return cast(SubExprs[BASE]); } + + /// Get lower bound of array section. + Expr *getLowerBound() { return cast_or_null(SubExprs[LOWER_BOUND]); } + const Expr *getLowerBound() const { + return cast_or_null(SubExprs[LOWER_BOUND]); + } + + /// Get length of array section. + Expr *getLength() { return cast_or_null(SubExprs[LENGTH]); } + const Expr *getLength() const { return cast_or_null(SubExprs[LENGTH]); } + + /// Get stride of array section. + Expr *getStride() { + assert(ASType != OpenACCArraySection && + "Stride not valid in OpenACC subarrays"); + return cast_or_null(SubExprs[STRIDE]); + } + + const Expr *getStride() const { + assert(ASType != OpenACCArraySection && + "Stride not valid in OpenACC subarrays"); + return cast_or_null(SubExprs[STRIDE]); + } + + SourceLocation getBeginLoc() const LLVM_READONLY { + return getBase()->getBeginLoc(); + } + SourceLocation getEndLoc() const LLVM_READONLY { return RBracketLoc; } + + SourceLocation getColonLocFirst() const { return ColonLocFirst; } + SourceLocation getColonLocSecond() const { + assert(ASType != OpenACCArraySection && + "second colon for stride not valid in OpenACC subarrays"); + return ColonLocSecond; + } + SourceLocation getRBracketLoc() const { return RBracketLoc; } + + SourceLocation getExprLoc() const LLVM_READONLY { + return getBase()->getExprLoc(); + } + + child_range children() { + return child_range( + &SubExprs[BASE], + &SubExprs[ASType == OMPArraySection ? END_EXPR : OPENACC_END_EXPR]); + } + + const_child_range children() const { + return const_child_range( + &SubExprs[BASE], + &SubExprs[ASType == OMPArraySection ? END_EXPR : OPENACC_END_EXPR]); + } + +private: + /// Set base of the array section. + void setBase(Expr *E) { SubExprs[BASE] = E; } + + /// Set lower bound of the array section. + void setLowerBound(Expr *E) { SubExprs[LOWER_BOUND] = E; } + + /// Set length of the array section. + void setLength(Expr *E) { SubExprs[LENGTH] = E; } + + /// Set length of the array section. + void setStride(Expr *E) { + assert(ASType != OpenACCArraySection && + "Stride not valid in OpenACC subarrays"); + SubExprs[STRIDE] = E; + } + + void setColonLocFirst(SourceLocation L) { ColonLocFirst = L; } + + void setColonLocSecond(SourceLocation L) { + assert(ASType != OpenACCArraySection && + "second colon for stride not valid in OpenACC subarrays"); + ColonLocSecond = L; + } + void setRBracketLoc(SourceLocation L) { RBracketLoc = L; } +}; + /// Frontend produces RecoveryExprs on semantic errors that prevent creating /// other well-formed expressions. E.g. when type-checking of a binary operator /// fails, we cannot produce a BinaryOperator expression. Instead, we can choose diff --git a/clang/include/clang/AST/ExprOpenMP.h b/clang/include/clang/AST/ExprOpenMP.h index be5b1f3fdd112f1008891aa3abcfc7854ff32a19..54a0c203f656c3585ef440c8aea0fbfac404a787 100644 --- a/clang/include/clang/AST/ExprOpenMP.h +++ b/clang/include/clang/AST/ExprOpenMP.h @@ -17,130 +17,6 @@ #include "clang/AST/Expr.h" namespace clang { -/// OpenMP 5.0 [2.1.5, Array Sections]. -/// To specify an array section in an OpenMP construct, array subscript -/// expressions are extended with the following syntax: -/// \code -/// [ lower-bound : length : stride ] -/// [ lower-bound : length : ] -/// [ lower-bound : length ] -/// [ lower-bound : : stride ] -/// [ lower-bound : : ] -/// [ lower-bound : ] -/// [ : length : stride ] -/// [ : length : ] -/// [ : length ] -/// [ : : stride ] -/// [ : : ] -/// [ : ] -/// \endcode -/// The array section must be a subset of the original array. -/// Array sections are allowed on multidimensional arrays. Base language array -/// subscript expressions can be used to specify length-one dimensions of -/// multidimensional array sections. -/// Each of the lower-bound, length, and stride expressions if specified must be -/// an integral type expressions of the base language. When evaluated -/// they represent a set of integer values as follows: -/// \code -/// { lower-bound, lower-bound + stride, lower-bound + 2 * stride,... , -/// lower-bound + ((length - 1) * stride) } -/// \endcode -/// The lower-bound and length must evaluate to non-negative integers. -/// The stride must evaluate to a positive integer. -/// When the size of the array dimension is not known, the length must be -/// specified explicitly. -/// When the stride is absent it defaults to 1. -/// When the length is absent it defaults to ⌈(size − lower-bound)/stride⌉, -/// where size is the size of the array dimension. When the lower-bound is -/// absent it defaults to 0. -class OMPArraySectionExpr : public Expr { - enum { BASE, LOWER_BOUND, LENGTH, STRIDE, END_EXPR }; - Stmt *SubExprs[END_EXPR]; - SourceLocation ColonLocFirst; - SourceLocation ColonLocSecond; - SourceLocation RBracketLoc; - -public: - OMPArraySectionExpr(Expr *Base, Expr *LowerBound, Expr *Length, Expr *Stride, - QualType Type, ExprValueKind VK, ExprObjectKind OK, - SourceLocation ColonLocFirst, - SourceLocation ColonLocSecond, SourceLocation RBracketLoc) - : Expr(OMPArraySectionExprClass, Type, VK, OK), - ColonLocFirst(ColonLocFirst), ColonLocSecond(ColonLocSecond), - RBracketLoc(RBracketLoc) { - SubExprs[BASE] = Base; - SubExprs[LOWER_BOUND] = LowerBound; - SubExprs[LENGTH] = Length; - SubExprs[STRIDE] = Stride; - setDependence(computeDependence(this)); - } - - /// Create an empty array section expression. - explicit OMPArraySectionExpr(EmptyShell Shell) - : Expr(OMPArraySectionExprClass, Shell) {} - - /// An array section can be written only as Base[LowerBound:Length]. - - /// Get base of the array section. - Expr *getBase() { return cast(SubExprs[BASE]); } - const Expr *getBase() const { return cast(SubExprs[BASE]); } - /// Set base of the array section. - void setBase(Expr *E) { SubExprs[BASE] = E; } - - /// Return original type of the base expression for array section. - static QualType getBaseOriginalType(const Expr *Base); - - /// Get lower bound of array section. - Expr *getLowerBound() { return cast_or_null(SubExprs[LOWER_BOUND]); } - const Expr *getLowerBound() const { - return cast_or_null(SubExprs[LOWER_BOUND]); - } - /// Set lower bound of the array section. - void setLowerBound(Expr *E) { SubExprs[LOWER_BOUND] = E; } - - /// Get length of array section. - Expr *getLength() { return cast_or_null(SubExprs[LENGTH]); } - const Expr *getLength() const { return cast_or_null(SubExprs[LENGTH]); } - /// Set length of the array section. - void setLength(Expr *E) { SubExprs[LENGTH] = E; } - - /// Get stride of array section. - Expr *getStride() { return cast_or_null(SubExprs[STRIDE]); } - const Expr *getStride() const { return cast_or_null(SubExprs[STRIDE]); } - /// Set length of the array section. - void setStride(Expr *E) { SubExprs[STRIDE] = E; } - - SourceLocation getBeginLoc() const LLVM_READONLY { - return getBase()->getBeginLoc(); - } - SourceLocation getEndLoc() const LLVM_READONLY { return RBracketLoc; } - - SourceLocation getColonLocFirst() const { return ColonLocFirst; } - void setColonLocFirst(SourceLocation L) { ColonLocFirst = L; } - - SourceLocation getColonLocSecond() const { return ColonLocSecond; } - void setColonLocSecond(SourceLocation L) { ColonLocSecond = L; } - - SourceLocation getRBracketLoc() const { return RBracketLoc; } - void setRBracketLoc(SourceLocation L) { RBracketLoc = L; } - - SourceLocation getExprLoc() const LLVM_READONLY { - return getBase()->getExprLoc(); - } - - static bool classof(const Stmt *T) { - return T->getStmtClass() == OMPArraySectionExprClass; - } - - child_range children() { - return child_range(&SubExprs[BASE], &SubExprs[END_EXPR]); - } - - const_child_range children() const { - return const_child_range(&SubExprs[BASE], &SubExprs[END_EXPR]); - } -}; - /// An explicit cast in C or a C-style cast in C++, which uses the syntax /// ([s1][s2]...[sn])expr. For example: @c ([3][3])f. class OMPArrayShapingExpr final diff --git a/clang/include/clang/AST/ExternalASTSource.h b/clang/include/clang/AST/ExternalASTSource.h index eee8d6b6c6ef115e2e9c44d8aca7ee714f58ea6f..385c32edbae0fdba3218d0711bee53fa3f72bd68 100644 --- a/clang/include/clang/AST/ExternalASTSource.h +++ b/clang/include/clang/AST/ExternalASTSource.h @@ -99,7 +99,7 @@ public: /// passes back decl sets as VisibleDeclaration objects. /// /// The default implementation of this method is a no-op. - virtual Decl *GetExternalDecl(Decl::DeclID ID); + virtual Decl *GetExternalDecl(GlobalDeclID ID); /// Resolve a selector ID into a selector. /// @@ -375,7 +375,7 @@ public: if (isOffset()) { assert(Source && "Cannot deserialize a lazy pointer without an AST source"); - Ptr = reinterpret_cast((Source->*Get)(Ptr >> 1)); + Ptr = reinterpret_cast((Source->*Get)(OffsT(Ptr >> 1))); } return reinterpret_cast(Ptr); } @@ -579,7 +579,7 @@ using LazyDeclStmtPtr = /// A lazy pointer to a declaration. using LazyDeclPtr = - LazyOffsetPtr; + LazyOffsetPtr; /// A lazy pointer to a set of CXXCtorInitializers. using LazyCXXCtorInitializersPtr = diff --git a/clang/include/clang/AST/RecursiveASTVisitor.h b/clang/include/clang/AST/RecursiveASTVisitor.h index 7eb92e304a3856bcdbc70bb9733e108389df3778..f9b145b4e86a5579dc13760ecce791468620c681 100644 --- a/clang/include/clang/AST/RecursiveASTVisitor.h +++ b/clang/include/clang/AST/RecursiveASTVisitor.h @@ -2740,7 +2740,7 @@ DEF_TRAVERSE_STMT(CXXMemberCallExpr, {}) DEF_TRAVERSE_STMT(AddrLabelExpr, {}) DEF_TRAVERSE_STMT(ArraySubscriptExpr, {}) DEF_TRAVERSE_STMT(MatrixSubscriptExpr, {}) -DEF_TRAVERSE_STMT(OMPArraySectionExpr, {}) +DEF_TRAVERSE_STMT(ArraySectionExpr, {}) DEF_TRAVERSE_STMT(OMPArrayShapingExpr, {}) DEF_TRAVERSE_STMT(OMPIteratorExpr, {}) diff --git a/clang/include/clang/AST/Type.h b/clang/include/clang/AST/Type.h index 99f45d518c7960fab956a317719a6870a2c8fdf4..dff02d4861b3dbd5272b9c238a8d4604b58d4ab9 100644 --- a/clang/include/clang/AST/Type.h +++ b/clang/include/clang/AST/Type.h @@ -25,8 +25,10 @@ #include "clang/Basic/Diagnostic.h" #include "clang/Basic/ExceptionSpecificationType.h" #include "clang/Basic/LLVM.h" +#include "clang/Basic/LangOptions.h" #include "clang/Basic/Linkage.h" #include "clang/Basic/PartialDiagnostic.h" +#include "clang/Basic/PointerAuthOptions.h" #include "clang/Basic/SourceLocation.h" #include "clang/Basic/Specifiers.h" #include "clang/Basic/Visibility.h" @@ -139,6 +141,174 @@ using CanQualType = CanQual; #define TYPE(Class, Base) class Class##Type; #include "clang/AST/TypeNodes.inc" +/// Pointer-authentication qualifiers. +class PointerAuthQualifier { + enum : uint32_t { + EnabledShift = 0, + EnabledBits = 1, + EnabledMask = 1 << EnabledShift, + AddressDiscriminatedShift = EnabledShift + EnabledBits, + AddressDiscriminatedBits = 1, + AddressDiscriminatedMask = 1 << AddressDiscriminatedShift, + AuthenticationModeShift = + AddressDiscriminatedShift + AddressDiscriminatedBits, + AuthenticationModeBits = 2, + AuthenticationModeMask = ((1 << AuthenticationModeBits) - 1) + << AuthenticationModeShift, + IsaPointerShift = AuthenticationModeShift + AuthenticationModeBits, + IsaPointerBits = 1, + IsaPointerMask = ((1 << IsaPointerBits) - 1) << IsaPointerShift, + AuthenticatesNullValuesShift = IsaPointerShift + IsaPointerBits, + AuthenticatesNullValuesBits = 1, + AuthenticatesNullValuesMask = ((1 << AuthenticatesNullValuesBits) - 1) + << AuthenticatesNullValuesShift, + KeyShift = AuthenticatesNullValuesShift + AuthenticatesNullValuesBits, + KeyBits = 10, + KeyMask = ((1 << KeyBits) - 1) << KeyShift, + DiscriminatorShift = KeyShift + KeyBits, + DiscriminatorBits = 16, + DiscriminatorMask = ((1u << DiscriminatorBits) - 1) << DiscriminatorShift, + }; + + // bits: |0 |1 |2..3 |4 | + // |Enabled|Address|AuthenticationMode|ISA pointer| + // bits: |5 |6..15| 16...31 | + // |AuthenticatesNull|Key |Discriminator| + uint32_t Data = 0; + + // The following static assertions check that each of the 32 bits is present + // exactly in one of the constants. + static_assert((EnabledBits + AddressDiscriminatedBits + + AuthenticationModeBits + IsaPointerBits + + AuthenticatesNullValuesBits + KeyBits + DiscriminatorBits) == + 32, + "PointerAuthQualifier should be exactly 32 bits"); + static_assert((EnabledMask + AddressDiscriminatedMask + + AuthenticationModeMask + IsaPointerMask + + AuthenticatesNullValuesMask + KeyMask + DiscriminatorMask) == + 0xFFFFFFFF, + "All masks should cover the entire bits"); + static_assert((EnabledMask ^ AddressDiscriminatedMask ^ + AuthenticationModeMask ^ IsaPointerMask ^ + AuthenticatesNullValuesMask ^ KeyMask ^ DiscriminatorMask) == + 0xFFFFFFFF, + "All masks should cover the entire bits"); + + PointerAuthQualifier(unsigned Key, bool IsAddressDiscriminated, + unsigned ExtraDiscriminator, + PointerAuthenticationMode AuthenticationMode, + bool IsIsaPointer, bool AuthenticatesNullValues) + : Data(EnabledMask | + (IsAddressDiscriminated + ? llvm::to_underlying(AddressDiscriminatedMask) + : 0) | + (Key << KeyShift) | + (llvm::to_underlying(AuthenticationMode) + << AuthenticationModeShift) | + (ExtraDiscriminator << DiscriminatorShift) | + (IsIsaPointer << IsaPointerShift) | + (AuthenticatesNullValues << AuthenticatesNullValuesShift)) { + assert(Key <= KeyNoneInternal); + assert(ExtraDiscriminator <= MaxDiscriminator); + assert((Data == 0) == + (getAuthenticationMode() == PointerAuthenticationMode::None)); + } + +public: + enum { + KeyNoneInternal = (1u << KeyBits) - 1, + + /// The maximum supported pointer-authentication key. + MaxKey = KeyNoneInternal - 1, + + /// The maximum supported pointer-authentication discriminator. + MaxDiscriminator = (1u << DiscriminatorBits) - 1 + }; + +public: + PointerAuthQualifier() = default; + + static PointerAuthQualifier + Create(unsigned Key, bool IsAddressDiscriminated, unsigned ExtraDiscriminator, + PointerAuthenticationMode AuthenticationMode, bool IsIsaPointer, + bool AuthenticatesNullValues) { + if (Key == PointerAuthKeyNone) + Key = KeyNoneInternal; + assert(Key <= KeyNoneInternal && "out-of-range key value"); + return PointerAuthQualifier(Key, IsAddressDiscriminated, ExtraDiscriminator, + AuthenticationMode, IsIsaPointer, + AuthenticatesNullValues); + } + + bool isPresent() const { + assert((Data == 0) == + (getAuthenticationMode() == PointerAuthenticationMode::None)); + return Data != 0; + } + + explicit operator bool() const { return isPresent(); } + + unsigned getKey() const { + assert(isPresent()); + return (Data & KeyMask) >> KeyShift; + } + + bool hasKeyNone() const { return isPresent() && getKey() == KeyNoneInternal; } + + bool isAddressDiscriminated() const { + assert(isPresent()); + return (Data & AddressDiscriminatedMask) >> AddressDiscriminatedShift; + } + + unsigned getExtraDiscriminator() const { + assert(isPresent()); + return (Data >> DiscriminatorShift); + } + + PointerAuthenticationMode getAuthenticationMode() const { + return PointerAuthenticationMode((Data & AuthenticationModeMask) >> + AuthenticationModeShift); + } + + bool isIsaPointer() const { + assert(isPresent()); + return (Data & IsaPointerMask) >> IsaPointerShift; + } + + bool authenticatesNullValues() const { + assert(isPresent()); + return (Data & AuthenticatesNullValuesMask) >> AuthenticatesNullValuesShift; + } + + PointerAuthQualifier withoutKeyNone() const { + return hasKeyNone() ? PointerAuthQualifier() : *this; + } + + friend bool operator==(PointerAuthQualifier Lhs, PointerAuthQualifier Rhs) { + return Lhs.Data == Rhs.Data; + } + friend bool operator!=(PointerAuthQualifier Lhs, PointerAuthQualifier Rhs) { + return Lhs.Data != Rhs.Data; + } + + bool isEquivalent(PointerAuthQualifier Other) const { + return withoutKeyNone() == Other.withoutKeyNone(); + } + + uint32_t getAsOpaqueValue() const { return Data; } + + // Deserialize pointer-auth qualifiers from an opaque representation. + static PointerAuthQualifier fromOpaqueValue(uint32_t Opaque) { + PointerAuthQualifier Result; + Result.Data = Opaque; + assert((Result.Data == 0) == + (Result.getAuthenticationMode() == PointerAuthenticationMode::None)); + return Result; + } + + void Profile(llvm::FoldingSetNodeID &ID) const { ID.AddInteger(Data); } +}; + /// The collection of all-type qualifiers we support. /// Clang supports five independent qualifiers: /// * C99: const, volatile, and restrict @@ -147,8 +317,9 @@ using CanQualType = CanQual; /// * Objective C: the GC attributes (none, weak, or strong) class Qualifiers { public: - enum TQ { // NOTE: These flags must be kept in sync with DeclSpec::TQ. - Const = 0x1, + enum TQ : uint64_t { + // NOTE: These flags must be kept in sync with DeclSpec::TQ. + Const = 0x1, Restrict = 0x2, Volatile = 0x4, CVRMask = Const | Volatile | Restrict @@ -182,7 +353,7 @@ public: OCL_Autoreleasing }; - enum { + enum : uint64_t { /// The maximum supported address space number. /// 23 bits should be enough for anyone. MaxAddressSpace = 0x7fffffu, @@ -197,16 +368,25 @@ public: /// Returns the common set of qualifiers while removing them from /// the given sets. static Qualifiers removeCommonQualifiers(Qualifiers &L, Qualifiers &R) { + Qualifiers Q; + PointerAuthQualifier LPtrAuth = L.getPointerAuth(); + if (LPtrAuth.isPresent() && + LPtrAuth.getKey() != PointerAuthQualifier::KeyNoneInternal && + LPtrAuth == R.getPointerAuth()) { + Q.setPointerAuth(LPtrAuth); + PointerAuthQualifier Empty; + L.setPointerAuth(Empty); + R.setPointerAuth(Empty); + } + // If both are only CVR-qualified, bit operations are sufficient. if (!(L.Mask & ~CVRMask) && !(R.Mask & ~CVRMask)) { - Qualifiers Q; Q.Mask = L.Mask & R.Mask; L.Mask &= ~Q.Mask; R.Mask &= ~Q.Mask; return Q; } - Qualifiers Q; unsigned CommonCRV = L.getCVRQualifiers() & R.getCVRQualifiers(); Q.addCVRQualifiers(CommonCRV); L.removeCVRQualifiers(CommonCRV); @@ -251,16 +431,14 @@ public: } // Deserialize qualifiers from an opaque representation. - static Qualifiers fromOpaqueValue(unsigned opaque) { + static Qualifiers fromOpaqueValue(uint64_t opaque) { Qualifiers Qs; Qs.Mask = opaque; return Qs; } // Serialize these qualifiers into an opaque representation. - unsigned getAsOpaqueValue() const { - return Mask; - } + uint64_t getAsOpaqueValue() const { return Mask; } bool hasConst() const { return Mask & Const; } bool hasOnlyConst() const { return Mask == Const; } @@ -407,6 +585,20 @@ public: setAddressSpace(space); } + bool hasPointerAuth() const { return Mask & PtrAuthMask; } + PointerAuthQualifier getPointerAuth() const { + return PointerAuthQualifier::fromOpaqueValue(Mask >> PtrAuthShift); + } + void setPointerAuth(PointerAuthQualifier Q) { + Mask = (Mask & ~PtrAuthMask) | + (uint64_t(Q.getAsOpaqueValue()) << PtrAuthShift); + } + void removePointerAuth() { Mask &= ~PtrAuthMask; } + void addPointerAuth(PointerAuthQualifier Q) { + assert(Q.isPresent()); + setPointerAuth(Q); + } + // Fast qualifiers are those that can be allocated directly // on a QualType object. bool hasFastQualifiers() const { return getFastQualifiers(); } @@ -454,6 +646,8 @@ public: addObjCGCAttr(Q.getObjCGCAttr()); if (Q.hasObjCLifetime()) addObjCLifetime(Q.getObjCLifetime()); + if (Q.hasPointerAuth()) + addPointerAuth(Q.getPointerAuth()); } } @@ -471,6 +665,8 @@ public: removeObjCLifetime(); if (getAddressSpace() == Q.getAddressSpace()) removeAddressSpace(); + if (getPointerAuth() == Q.getPointerAuth()) + removePointerAuth(); } } @@ -483,6 +679,8 @@ public: !hasObjCGCAttr() || !qs.hasObjCGCAttr()); assert(getObjCLifetime() == qs.getObjCLifetime() || !hasObjCLifetime() || !qs.hasObjCLifetime()); + assert(!hasPointerAuth() || !qs.hasPointerAuth() || + getPointerAuth() == qs.getPointerAuth()); Mask |= qs.Mask; } @@ -536,6 +734,8 @@ public: // be changed. (getObjCGCAttr() == other.getObjCGCAttr() || !hasObjCGCAttr() || !other.hasObjCGCAttr()) && + // Pointer-auth qualifiers must match exactly. + getPointerAuth() == other.getPointerAuth() && // ObjC lifetime qualifiers must match exactly. getObjCLifetime() == other.getObjCLifetime() && // CVR qualifiers may subset. @@ -605,24 +805,26 @@ public: void print(raw_ostream &OS, const PrintingPolicy &Policy, bool appendSpaceIfNonEmpty = false) const; - void Profile(llvm::FoldingSetNodeID &ID) const { - ID.AddInteger(Mask); - } + void Profile(llvm::FoldingSetNodeID &ID) const { ID.AddInteger(Mask); } private: - // bits: |0 1 2|3|4 .. 5|6 .. 8|9 ... 31| - // |C R V|U|GCAttr|Lifetime|AddressSpace| - uint32_t Mask = 0; - - static const uint32_t UMask = 0x8; - static const uint32_t UShift = 3; - static const uint32_t GCAttrMask = 0x30; - static const uint32_t GCAttrShift = 4; - static const uint32_t LifetimeMask = 0x1C0; - static const uint32_t LifetimeShift = 6; - static const uint32_t AddressSpaceMask = + // bits: |0 1 2|3|4 .. 5|6 .. 8|9 ... 31|32 ... 63| + // |C R V|U|GCAttr|Lifetime|AddressSpace| PtrAuth | + uint64_t Mask = 0; + static_assert(sizeof(PointerAuthQualifier) == sizeof(uint32_t), + "PointerAuthQualifier must be 32 bits"); + + static constexpr uint64_t UMask = 0x8; + static constexpr uint64_t UShift = 3; + static constexpr uint64_t GCAttrMask = 0x30; + static constexpr uint64_t GCAttrShift = 4; + static constexpr uint64_t LifetimeMask = 0x1C0; + static constexpr uint64_t LifetimeShift = 6; + static constexpr uint64_t AddressSpaceMask = ~(CVRMask | UMask | GCAttrMask | LifetimeMask); - static const uint32_t AddressSpaceShift = 9; + static constexpr uint64_t AddressSpaceShift = 9; + static constexpr uint64_t PtrAuthShift = 32; + static constexpr uint64_t PtrAuthMask = uint64_t(0xffffffff) << PtrAuthShift; }; class QualifiersAndAtomic { @@ -1242,6 +1444,10 @@ public: // true when Type is objc's weak and weak is enabled but ARC isn't. bool isNonWeakInMRRWithObjCWeak(const ASTContext &Context) const; + PointerAuthQualifier getPointerAuth() const { + return getQualifiers().getPointerAuth(); + } + enum PrimitiveDefaultInitializeKind { /// The type does not fall into any of the following categories. Note that /// this case is zero-valued so that values of this enum can be used as a diff --git a/clang/include/clang/Basic/DiagnosticFrontendKinds.td b/clang/include/clang/Basic/DiagnosticFrontendKinds.td index 14b08d4927ec5e264ac9bb73cf8f07ebc4eb1cc2..fcffadacc8e631ebbd7b3d54368b02a50c815b29 100644 --- a/clang/include/clang/Basic/DiagnosticFrontendKinds.td +++ b/clang/include/clang/Basic/DiagnosticFrontendKinds.td @@ -370,4 +370,7 @@ def warn_missing_symbol_graph_dir : Warning< "Missing symbol graph output directory, defaulting to working directory">, InGroup; +def err_ast_action_on_llvm_ir : Error< + "cannot apply AST actions to LLVM IR file '%0'">, + DefaultFatal; } diff --git a/clang/include/clang/Basic/DiagnosticSemaKinds.td b/clang/include/clang/Basic/DiagnosticSemaKinds.td index 63e951daec7477679802ad24842eb33f2652c4f4..fdca82934cb4dcf0b78130377f846d60b24eb987 100644 --- a/clang/include/clang/Basic/DiagnosticSemaKinds.td +++ b/clang/include/clang/Basic/DiagnosticSemaKinds.td @@ -3755,14 +3755,12 @@ def err_sme_definition_using_za_in_non_sme_target : Error< def err_sme_definition_using_zt0_in_non_sme2_target : Error< "function using ZT0 state requires 'sme2'">; def warn_sme_streaming_pass_return_vl_to_non_streaming : Warning< - "passing a VL-dependent argument to/from a function that has a different" - " streaming-mode. The streaming and non-streaming vector lengths may be" - " different">, + "%select{returning|passing}0 a VL-dependent argument %select{from|to}0 a function with a different" + " streaming-mode is undefined behaviour when the streaming and non-streaming vector lengths are different at runtime">, InGroup, DefaultIgnore; def warn_sme_locally_streaming_has_vl_args_returns : Warning< - "passing/returning a VL-dependent argument to/from a __arm_locally_streaming" - " function. The streaming and non-streaming vector" - " lengths may be different">, + "%select{returning|passing}0 a VL-dependent argument %select{from|to}0 a locally streaming function is undefined" + " behaviour when the streaming and non-streaming vector lengths are different at runtime">, InGroup, DefaultIgnore; def err_conflicting_attributes_arm_state : Error< "conflicting attributes for state '%0'">; @@ -11163,7 +11161,7 @@ def err_omp_declare_mapper_redefinition : Error< "redefinition of user-defined mapper for type %0 with name %1">; def err_omp_invalid_mapper: Error< "cannot find a valid user-defined mapper for type %0 with name %1">; -def err_omp_array_section_use : Error<"OpenMP array section is not allowed here">; +def err_array_section_use : Error<"%select{OpenACC sub-array|OpenMP array section}0 is not allowed here">; def err_omp_array_shaping_use : Error<"OpenMP array shaping operation is not allowed here">; def err_omp_iterator_use : Error<"OpenMP iterator is not allowed here">; def err_omp_typecheck_section_value : Error< diff --git a/clang/include/clang/Basic/FileManager.h b/clang/include/clang/Basic/FileManager.h index 2245fd78bfc9f0c77479dbcb07b192de48d59129..8b4206e52cd482bc10ce449a176c447b1dcb0218 100644 --- a/clang/include/clang/Basic/FileManager.h +++ b/clang/include/clang/Basic/FileManager.h @@ -114,6 +114,12 @@ class FileManager : public RefCountedBase { /// unsigned NextFileUID; + /// Statistics gathered during the lifetime of the FileManager. + unsigned NumDirLookups = 0; + unsigned NumFileLookups = 0; + unsigned NumDirCacheMisses = 0; + unsigned NumFileCacheMisses = 0; + // Caching. std::unique_ptr StatCache; @@ -341,6 +347,10 @@ private: public: void PrintStats() const; + + /// Import statistics from a child FileManager and add them to this current + /// FileManager. + void AddStats(const FileManager &Other); }; } // end namespace clang diff --git a/clang/include/clang/Basic/LangOptions.h b/clang/include/clang/Basic/LangOptions.h index ae4715921d166595cfe899e54527736ac9051cf7..e2a2aa71b880b3b8a366c1363e3784e8d2e42b67 100644 --- a/clang/include/clang/Basic/LangOptions.h +++ b/clang/include/clang/Basic/LangOptions.h @@ -57,6 +57,13 @@ enum class ShaderStage { Invalid, }; +enum class PointerAuthenticationMode : unsigned { + None, + Strip, + SignAndStrip, + SignAndAuth +}; + /// Bitfields of LangOptions, split out from LangOptions in order to ensure that /// this large collection of bitfields is a trivial class type. class LangOptionsBase { diff --git a/clang/include/clang/Basic/PointerAuthOptions.h b/clang/include/clang/Basic/PointerAuthOptions.h new file mode 100644 index 0000000000000000000000000000000000000000..e5cdcc31ebfb70d2c55f9d717bd24996f5c1b169 --- /dev/null +++ b/clang/include/clang/Basic/PointerAuthOptions.h @@ -0,0 +1,23 @@ +//===--- PointerAuthOptions.h -----------------------------------*- C++ -*-===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// +// +// This file defines options for configuring pointer-auth technologies +// like ARMv8.3. +// +//===----------------------------------------------------------------------===// + +#ifndef LLVM_CLANG_BASIC_POINTERAUTHOPTIONS_H +#define LLVM_CLANG_BASIC_POINTERAUTHOPTIONS_H + +namespace clang { + +constexpr unsigned PointerAuthKeyNone = -1; + +} // end namespace clang + +#endif diff --git a/clang/include/clang/Basic/StmtNodes.td b/clang/include/clang/Basic/StmtNodes.td index b4e3ae573b95e62af4fae5529bc8d1e52bbcf88c..305f19daa4a9238fff2d9a755fb163da2ff06dfc 100644 --- a/clang/include/clang/Basic/StmtNodes.td +++ b/clang/include/clang/Basic/StmtNodes.td @@ -71,7 +71,7 @@ def OffsetOfExpr : StmtNode; def UnaryExprOrTypeTraitExpr : StmtNode; def ArraySubscriptExpr : StmtNode; def MatrixSubscriptExpr : StmtNode; -def OMPArraySectionExpr : StmtNode; +def ArraySectionExpr : StmtNode; def OMPIteratorExpr : StmtNode; def CallExpr : StmtNode; def MemberExpr : StmtNode; diff --git a/clang/include/clang/Basic/arm_sve.td b/clang/include/clang/Basic/arm_sve.td index 6cc249837d3f3d42414331ee5a0bf3f0e9c36bee..15340ebb62b365d1ea8d7a40811097a49aaa5e26 100644 --- a/clang/include/clang/Basic/arm_sve.td +++ b/clang/include/clang/Basic/arm_sve.td @@ -1961,19 +1961,20 @@ def SVPSEL_D : SInst<"svpsel_lane_b64", "PPPm", "Pl", MergeNone, "", [IsStreamin // Standalone sve2.1 builtins let TargetGuard = "sve2p1" in { -def SVORQV : SInst<"svorqv[_{d}]", "{Pd", "csilUcUsUiUl", MergeNone, "aarch64_sve_orqv", [IsReductionQV]>; -def SVEORQV : SInst<"sveorqv[_{d}]", "{Pd", "csilUcUsUiUl", MergeNone, "aarch64_sve_eorqv", [IsReductionQV]>; -def SVADDQV : SInst<"svaddqv[_{d}]", "{Pd", "hfdcsilUcUsUiUl", MergeNone, "aarch64_sve_addqv", [IsReductionQV]>; -def SVANDQV : SInst<"svandqv[_{d}]", "{Pd", "csilUcUsUiUl", MergeNone, "aarch64_sve_andqv", [IsReductionQV]>; -def SVSMAXQV : SInst<"svmaxqv[_{d}]", "{Pd", "csil", MergeNone, "aarch64_sve_smaxqv", [IsReductionQV]>; -def SVUMAXQV : SInst<"svmaxqv[_{d}]", "{Pd", "UcUsUiUl", MergeNone, "aarch64_sve_umaxqv", [IsReductionQV]>; -def SVSMINQV : SInst<"svminqv[_{d}]", "{Pd", "csil", MergeNone, "aarch64_sve_sminqv", [IsReductionQV]>; -def SVUMINQV : SInst<"svminqv[_{d}]", "{Pd", "UcUsUiUl", MergeNone, "aarch64_sve_uminqv", [IsReductionQV]>; - -def SVFMAXNMQV: SInst<"svmaxnmqv[_{d}]", "{Pd", "hfd", MergeNone, "aarch64_sve_fmaxnmqv", [IsReductionQV]>; -def SVFMINNMQV: SInst<"svminnmqv[_{d}]", "{Pd", "hfd", MergeNone, "aarch64_sve_fminnmqv", [IsReductionQV]>; -def SVFMAXQV: SInst<"svmaxqv[_{d}]", "{Pd", "hfd", MergeNone, "aarch64_sve_fmaxqv", [IsReductionQV]>; -def SVFMINQV: SInst<"svminqv[_{d}]", "{Pd", "hfd", MergeNone, "aarch64_sve_fminqv", [IsReductionQV]>; +def SVORQV : SInst<"svorqv[_{d}]", "{Pd", "csilUcUsUiUl", MergeNone, "aarch64_sve_orqv", [IsReductionQV]>; +def SVEORQV : SInst<"sveorqv[_{d}]", "{Pd", "csilUcUsUiUl", MergeNone, "aarch64_sve_eorqv", [IsReductionQV]>; +def SVADDQV : SInst<"svaddqv[_{d}]", "{Pd", "csilUcUsUiUl", MergeNone, "aarch64_sve_addqv", [IsReductionQV]>; +def SVANDQV : SInst<"svandqv[_{d}]", "{Pd", "csilUcUsUiUl", MergeNone, "aarch64_sve_andqv", [IsReductionQV]>; +def SVSMAXQV : SInst<"svmaxqv[_{d}]", "{Pd", "csil", MergeNone, "aarch64_sve_smaxqv", [IsReductionQV]>; +def SVUMAXQV : SInst<"svmaxqv[_{d}]", "{Pd", "UcUsUiUl", MergeNone, "aarch64_sve_umaxqv", [IsReductionQV]>; +def SVSMINQV : SInst<"svminqv[_{d}]", "{Pd", "csil", MergeNone, "aarch64_sve_sminqv", [IsReductionQV]>; +def SVUMINQV : SInst<"svminqv[_{d}]", "{Pd", "UcUsUiUl", MergeNone, "aarch64_sve_uminqv", [IsReductionQV]>; + +def SVFADDQV : SInst<"svaddqv[_{d}]", "{Pd", "hfd", MergeNone, "aarch64_sve_faddqv", [IsReductionQV]>; +def SVFMAXNMQV : SInst<"svmaxnmqv[_{d}]", "{Pd", "hfd", MergeNone, "aarch64_sve_fmaxnmqv", [IsReductionQV]>; +def SVFMINNMQV : SInst<"svminnmqv[_{d}]", "{Pd", "hfd", MergeNone, "aarch64_sve_fminnmqv", [IsReductionQV]>; +def SVFMAXQV : SInst<"svmaxqv[_{d}]", "{Pd", "hfd", MergeNone, "aarch64_sve_fmaxqv", [IsReductionQV]>; +def SVFMINQV : SInst<"svminqv[_{d}]", "{Pd", "hfd", MergeNone, "aarch64_sve_fminqv", [IsReductionQV]>; } let TargetGuard = "sve2p1|sme2" in { diff --git a/clang/include/clang/Basic/riscv_vector.td b/clang/include/clang/Basic/riscv_vector.td index 76ed544f3b2bb1f2e0176932098b732613ec1b7a..cca4367751b92b0812c6e16bc084d64aceea641e 100644 --- a/clang/include/clang/Basic/riscv_vector.td +++ b/clang/include/clang/Basic/riscv_vector.td @@ -14,14 +14,14 @@ include "riscv_vector_common.td" -defvar TypeList = ["c","s","i","l","x","f","d"]; +defvar TypeList = ["c","s","i","l","x","f","d","y"]; defvar EEWList = [["8", "(Log2EEW:3)"], ["16", "(Log2EEW:4)"], ["32", "(Log2EEW:5)"], ["64", "(Log2EEW:6)"]]; class IsFloat { - bit val = !or(!eq(type, "x"), !eq(type, "f"), !eq(type, "d")); + bit val = !or(!eq(type, "x"), !eq(type, "f"), !eq(type, "d"), !eq(type, "y")); } let SupportOverloading = false, @@ -118,7 +118,8 @@ multiclass RVVIndexedLoad { defvar eew_type = eew_list[1]; let Name = op # eew # "_v", IRName = op, MaskedIRName = op # "_mask", RequiredFeatures = !if(!eq(type, "x"), ["Zvfhmin"], - []) in { + !if(!eq(type, "y"), ["Zvfbfmin"], + [])) in { def: RVVOutOp1Builtin<"v", "vPCe" # eew_type # "Uv", type>; if !not(IsFloat.val) then { def: RVVOutOp1Builtin<"Uv", "UvPCUe" # eew_type # "Uv", type>; @@ -129,7 +130,8 @@ multiclass RVVIndexedLoad { defvar eew64_type = "(Log2EEW:6)"; let Name = op # eew64 # "_v", IRName = op, MaskedIRName = op # "_mask", RequiredFeatures = !if(!eq(type, "x"), ["Zvfhmin", "RV64"], - ["RV64"]) in { + !if(!eq(type, "y"), ["Zvfbfmin", "RV64"], + ["RV64"])) in { def: RVVOutOp1Builtin<"v", "vPCe" # eew64_type # "Uv", type>; if !not(IsFloat.val) then { def: RVVOutOp1Builtin<"Uv", "UvPCUe" # eew64_type # "Uv", type>; @@ -223,7 +225,8 @@ multiclass RVVIndexedStore { defvar eew_type = eew_list[1]; let Name = op # eew # "_v", IRName = op, MaskedIRName = op # "_mask", RequiredFeatures = !if(!eq(type, "x"), ["Zvfhmin"], - []) in { + !if(!eq(type, "y"), ["Zvfbfmin"], + [])) in { def : RVVBuiltin<"v", "0Pe" # eew_type # "Uvv", type>; if !not(IsFloat.val) then { def : RVVBuiltin<"Uv", "0PUe" # eew_type # "UvUv", type>; @@ -234,7 +237,8 @@ multiclass RVVIndexedStore { defvar eew64_type = "(Log2EEW:6)"; let Name = op # eew64 # "_v", IRName = op, MaskedIRName = op # "_mask", RequiredFeatures = !if(!eq(type, "x"), ["Zvfhmin", "RV64"], - ["RV64"]) in { + !if(!eq(type, "y"), ["Zvfbfmin", "RV64"], + ["RV64"])) in { def : RVVBuiltin<"v", "0Pe" # eew64_type # "Uvv", type>; if !not(IsFloat.val) then { def : RVVBuiltin<"Uv", "0PUe" # eew64_type # "UvUv", type>; @@ -358,6 +362,10 @@ multiclass RVVNonTupleVCreateBuiltin src_lmul_list> { def vcreate # src_v # dst_v : RVVBuiltin; + let RequiredFeatures = ["Zvfbfmin"] in + def vcreate_bf16 # src_v # dst_v : RVVBuiltin; defvar src_uv = FixedVString.V; defvar src_us = FixedVString.S; @@ -683,6 +691,8 @@ defm vle8: RVVVLEBuiltin<["c"]>; defm vle16: RVVVLEBuiltin<["s"]>; let Name = "vle16_v", RequiredFeatures = ["Zvfhmin"] in defm vle16_h: RVVVLEBuiltin<["x"]>; +let Name = "vle16_v", RequiredFeatures = ["Zvfbfmin"] in + defm vle16_bf16 : RVVVLEBuiltin<["y"]>; defm vle32: RVVVLEBuiltin<["i","f"]>; defm vle64: RVVVLEBuiltin<["l","d"]>; @@ -691,6 +701,8 @@ defm vse8 : RVVVSEBuiltin<["c"]>; defm vse16: RVVVSEBuiltin<["s"]>; let Name = "vse16_v", RequiredFeatures = ["Zvfhmin"] in defm vse16_h: RVVVSEBuiltin<["x"]>; +let Name = "vse16_v", RequiredFeatures = ["Zvfbfmin"] in + defm vse16_bf16: RVVVSEBuiltin<["y"]>; defm vse32: RVVVSEBuiltin<["i","f"]>; defm vse64: RVVVSEBuiltin<["l","d"]>; @@ -699,6 +711,8 @@ defm vlse8: RVVVLSEBuiltin<["c"]>; defm vlse16: RVVVLSEBuiltin<["s"]>; let Name = "vlse16_v", RequiredFeatures = ["Zvfhmin"] in defm vlse16_h: RVVVLSEBuiltin<["x"]>; +let Name = "vlse16_v", RequiredFeatures = ["Zvfbfmin"] in + defm vlse16_bf16: RVVVLSEBuiltin<["y"]>; defm vlse32: RVVVLSEBuiltin<["i","f"]>; defm vlse64: RVVVLSEBuiltin<["l","d"]>; @@ -706,6 +720,8 @@ defm vsse8 : RVVVSSEBuiltin<["c"]>; defm vsse16: RVVVSSEBuiltin<["s"]>; let Name = "vsse16_v", RequiredFeatures = ["Zvfhmin"] in defm vsse16_h: RVVVSSEBuiltin<["x"]>; +let Name = "vsse16_v", RequiredFeatures = ["Zvfbfmin"] in + defm vsse16_bf: RVVVSSEBuiltin<["y"]>; defm vsse32: RVVVSSEBuiltin<["i","f"]>; defm vsse64: RVVVSSEBuiltin<["l","d"]>; @@ -721,6 +737,8 @@ defm vle8ff: RVVVLEFFBuiltin<["c"]>; defm vle16ff: RVVVLEFFBuiltin<["s"]>; let Name = "vle16ff_v", RequiredFeatures = ["Zvfhmin"] in defm vle16ff: RVVVLEFFBuiltin<["x"]>; +let Name = "vle16ff_v", RequiredFeatures = ["Zvfbfmin"] in + defm vle16ff: RVVVLEFFBuiltin<["y"]>; defm vle32ff: RVVVLEFFBuiltin<["i", "f"]>; defm vle64ff: RVVVLEFFBuiltin<["l", "d"]>; @@ -732,14 +750,16 @@ multiclass RVVUnitStridedSegLoadTuple { !eq(type, "l") : "64", !eq(type, "x") : "16", !eq(type, "f") : "32", - !eq(type, "d") : "64"); + !eq(type, "d") : "64", + !eq(type, "y") : "16"); foreach nf = NFList in { let Name = op # nf # "e" # eew # "_v", IRName = op # nf, MaskedIRName = op # nf # "_mask", NF = nf, RequiredFeatures = !if(!eq(type, "x"), ["Zvfhmin"], - []), + !if(!eq(type, "y"), ["Zvfbfmin"], + [])), ManualCodegen = [{ { llvm::Type *ElementVectorType = cast(ResultType)->elements()[0]; @@ -793,7 +813,8 @@ multiclass RVVUnitStridedSegStoreTuple { !eq(type, "l") : "64", !eq(type, "x") : "16", !eq(type, "f") : "32", - !eq(type, "d") : "64"); + !eq(type, "d") : "64", + !eq(type, "y") : "16"); foreach nf = NFList in { let Name = op # nf # "e" # eew # "_v", IRName = op # nf, @@ -801,7 +822,8 @@ multiclass RVVUnitStridedSegStoreTuple { NF = nf, HasMaskedOffOperand = false, RequiredFeatures = !if(!eq(type, "x"), ["Zvfhmin"], - []), + !if(!eq(type, "y"), ["Zvfbfmin"], + [])), ManualCodegen = [{ { // Masked @@ -846,14 +868,16 @@ multiclass RVVUnitStridedSegLoadFFTuple { !eq(type, "l") : "64", !eq(type, "x") : "16", !eq(type, "f") : "32", - !eq(type, "d") : "64"); + !eq(type, "d") : "64", + !eq(type, "y") : "16"); foreach nf = NFList in { let Name = op # nf # "e" # eew # "ff_v", IRName = op # nf # "ff", MaskedIRName = op # nf # "ff_mask", NF = nf, RequiredFeatures = !if(!eq(type, "x"), ["Zvfhmin"], - []), + !if(!eq(type, "y"), ["Zvfbfmin"], + [])), ManualCodegen = [{ { llvm::Type *ElementVectorType = cast(ResultType)->elements()[0]; @@ -921,14 +945,16 @@ multiclass RVVStridedSegLoadTuple { !eq(type, "l") : "64", !eq(type, "x") : "16", !eq(type, "f") : "32", - !eq(type, "d") : "64"); + !eq(type, "d") : "64", + !eq(type, "y") : "16"); foreach nf = NFList in { let Name = op # nf # "e" # eew # "_v", IRName = op # nf, MaskedIRName = op # nf # "_mask", NF = nf, RequiredFeatures = !if(!eq(type, "x"), ["Zvfhmin"], - []), + !if(!eq(type, "y"), ["Zvfbfmin"], + [])), ManualCodegen = [{ { llvm::Type *ElementVectorType = cast(ResultType)->elements()[0]; @@ -983,7 +1009,8 @@ multiclass RVVStridedSegStoreTuple { !eq(type, "l") : "64", !eq(type, "x") : "16", !eq(type, "f") : "32", - !eq(type, "d") : "64"); + !eq(type, "d") : "64", + !eq(type, "y") : "16"); foreach nf = NFList in { let Name = op # nf # "e" # eew # "_v", IRName = op # nf, @@ -992,7 +1019,8 @@ multiclass RVVStridedSegStoreTuple { HasMaskedOffOperand = false, MaskedPolicyScheme = NonePolicy, RequiredFeatures = !if(!eq(type, "x"), ["Zvfhmin"], - []), + !if(!eq(type, "y"), ["Zvfbfmin"], + [])), ManualCodegen = [{ { // Masked @@ -1041,7 +1069,8 @@ multiclass RVVIndexedSegLoadTuple { MaskedIRName = op # nf # "_mask", NF = nf, RequiredFeatures = !if(!eq(type, "x"), ["Zvfhmin"], - []), + !if(!eq(type, "y"), ["Zvfbfmin"], + [])), ManualCodegen = [{ { llvm::Type *ElementVectorType = cast(ResultType)->elements()[0]; @@ -1104,7 +1133,8 @@ multiclass RVVIndexedSegStoreTuple { HasMaskedOffOperand = false, MaskedPolicyScheme = NonePolicy, RequiredFeatures = !if(!eq(type, "x"), ["Zvfhmin"], - []), + !if(!eq(type, "y"), ["Zvfbfmin"], + [])), ManualCodegen = [{ { // Masked @@ -2308,6 +2338,12 @@ let HasMasked = false, HasVL = false, IRName = "" in { def vreinterpret_h_i : RVVBuiltin<"vFv", "Fvv", "s", "Fv">; def vreinterpret_h_u : RVVBuiltin<"UvFv", "FvUv", "s", "Fv">; } + let RequiredFeatures = ["Zvfbfmin"] in { + def vreinterpret_i_bf16 : RVVBuiltin<"vIv", "Ivv", "y", "Iv">; + def vreinterpret_u_bf16 : RVVBuiltin<"vUv", "Uvv", "y", "Uv">; + def vreinterpret_bf16_i : RVVBuiltin<"Ivv", "vIv", "y", "v">; + def vreinterpret_bf16_u : RVVBuiltin<"Uvv", "vUv", "y", "v">; + } // Reinterpret between different SEW under the same LMUL foreach dst_sew = ["(FixedSEW:8)", "(FixedSEW:16)", "(FixedSEW:32)", @@ -2372,12 +2408,16 @@ let HasMasked = false, HasVL = false, IRName = "" in { return llvm::PoisonValue::get(ResultType); }] in { def vundefined : RVVBuiltin<"v", "v", "csilxfd">; + let RequiredFeatures = ["Zvfbfmin"] in + def vundefined_bf16 : RVVBuiltin<"v", "v", "y">; def vundefined_u : RVVBuiltin<"Uv", "Uv", "csil">; foreach nf = NFList in { let NF = nf in { defvar T = "(Tuple:" # nf # ")"; def : RVVBuiltin; + let RequiredFeatures = ["Zvfbfmin"] in + def : RVVBuiltin; def : RVVBuiltin; } } @@ -2396,6 +2436,9 @@ let HasMasked = false, HasVL = false, IRName = "" in { "(SFixedLog2LMUL:0)", "(SFixedLog2LMUL:1)", "(SFixedLog2LMUL:2)"] in { def vlmul_trunc # dst_lmul : RVVBuiltin<"v" # dst_lmul # "v", dst_lmul # "vv", "csilxfd", dst_lmul # "v">; + let RequiredFeatures = ["Zvfbfmin"] in + def vlmul_trunc_bf16 # dst_lmul : RVVBuiltin<"v" # dst_lmul # "v", + dst_lmul # "vv", "y", dst_lmul # "v">; def vlmul_trunc_u # dst_lmul : RVVBuiltin<"Uv" # dst_lmul # "Uv", dst_lmul # "UvUv", "csil", dst_lmul # "Uv">; } @@ -2414,6 +2457,9 @@ let HasMasked = false, HasVL = false, IRName = "" in { "(LFixedLog2LMUL:1)", "(LFixedLog2LMUL:2)", "(LFixedLog2LMUL:3)"] in { def vlmul_ext # dst_lmul : RVVBuiltin<"v" # dst_lmul # "v", dst_lmul # "vv", "csilxfd", dst_lmul # "v">; + let RequiredFeatures = ["Zvfbfmin"] in + def vlmul_ext_bf16 # dst_lmul : RVVBuiltin<"v" # dst_lmul # "v", + dst_lmul # "vv", "y", dst_lmul # "v">; def vlmul_ext_u # dst_lmul : RVVBuiltin<"Uv" # dst_lmul # "Uv", dst_lmul # "UvUv", "csil", dst_lmul # "Uv">; } @@ -2441,12 +2487,12 @@ let HasMasked = false, HasVL = false, IRName = "" in { } }] in { foreach dst_lmul = ["(SFixedLog2LMUL:0)", "(SFixedLog2LMUL:1)", "(SFixedLog2LMUL:2)"] in { - def : RVVBuiltin<"v" # dst_lmul # "v", dst_lmul # "vvKz", "csilxfd", dst_lmul # "v">; + def : RVVBuiltin<"v" # dst_lmul # "v", dst_lmul # "vvKz", "csilxfdy", dst_lmul # "v">; def : RVVBuiltin<"Uv" # dst_lmul # "Uv", dst_lmul # "UvUvKz", "csil", dst_lmul # "Uv">; } foreach nf = NFList in { defvar T = "(Tuple:" # nf # ")"; - def : RVVBuiltin; + def : RVVBuiltin; def : RVVBuiltin; } } @@ -2474,11 +2520,15 @@ let HasMasked = false, HasVL = false, IRName = "" in { }] in { foreach dst_lmul = ["(LFixedLog2LMUL:1)", "(LFixedLog2LMUL:2)", "(LFixedLog2LMUL:3)"] in { def : RVVBuiltin<"v" # dst_lmul # "v", dst_lmul # "v" # dst_lmul # "vKzv", "csilxfd">; + let RequiredFeatures = ["Zvfbfmin"] in + def : RVVBuiltin<"v" # dst_lmul # "v", dst_lmul # "v" # dst_lmul # "vKzv", "y">; def : RVVBuiltin<"Uv" # dst_lmul # "Uv", dst_lmul # "Uv" # dst_lmul #"UvKzUv", "csil">; } foreach nf = NFList in { defvar T = "(Tuple:" # nf # ")"; def : RVVBuiltin<"v" # T # "v", T # "v" # T # "vKzv", "csilxfd">; + let RequiredFeatures = ["Zvfbfmin"] in + def : RVVBuiltin<"v" # T # "v", T # "v" # T # "vKzv", "y">; def : RVVBuiltin<"Uv" # T # "Uv", T # "Uv" # T # "UvKzUv", "csil">; } } @@ -2523,7 +2573,9 @@ let HasMasked = false, HasVL = false, IRName = "" in { defvar T = "(Tuple:" # nf # ")"; defvar V = VString.S; defvar UV = VString.S; - def : RVVBuiltin; + def : RVVBuiltin; + let RequiredFeatures = ["Zvfbfmin"] in + def : RVVBuiltin; def : RVVBuiltin; } } @@ -2549,8 +2601,7 @@ multiclass RVVOutBuiltinSetZvk { if HasVS then { foreach vs2_lmul = ["(SEFixedLog2LMUL:-1)", "(SEFixedLog2LMUL:0)", - "(SEFixedLog2LMUL:1)", "(SEFixedLog2LMUL:2)", - "(SEFixedLog2LMUL:3)"] in { + "(SEFixedLog2LMUL:1)", "(SEFixedLog2LMUL:2)"] in { defvar name = NAME # !if(!eq(NAME, "vaesz"), "", "_vs"); let OverloadedName = name, IRName = NAME # "_vs", Name = NAME # "_vs", IntrinsicTypes = [-1, 1] in diff --git a/clang/include/clang/CIR/CMakeLists.txt b/clang/include/clang/CIR/CMakeLists.txt index e69de29bb2d1d6434b8b29ae775ad8c2e48c5391..f8d6f407a03d02358be081c96682e8736385b53c 100644 --- a/clang/include/clang/CIR/CMakeLists.txt +++ b/clang/include/clang/CIR/CMakeLists.txt @@ -0,0 +1,6 @@ +set(MLIR_INCLUDE_DIR ${LLVM_MAIN_SRC_DIR}/../mlir/include ) # --includedir +set(MLIR_TABLEGEN_OUTPUT_DIR ${CMAKE_BINARY_DIR}/tools/mlir/include) +include_directories(${MLIR_INCLUDE_DIR}) +include_directories(${MLIR_TABLEGEN_OUTPUT_DIR}) + +add_subdirectory(Dialect) diff --git a/clang/include/clang/CIR/Dialect/CMakeLists.txt b/clang/include/clang/CIR/Dialect/CMakeLists.txt new file mode 100644 index 0000000000000000000000000000000000000000..f33061b2d87cffc48b072763eb55d349e9070aba --- /dev/null +++ b/clang/include/clang/CIR/Dialect/CMakeLists.txt @@ -0,0 +1 @@ +add_subdirectory(IR) diff --git a/clang/include/clang/CIR/Dialect/IR/CIRDialect.h b/clang/include/clang/CIR/Dialect/IR/CIRDialect.h new file mode 100644 index 0000000000000000000000000000000000000000..d53e5d1663d62a478d74a7f5624b9d0a75314003 --- /dev/null +++ b/clang/include/clang/CIR/Dialect/IR/CIRDialect.h @@ -0,0 +1,16 @@ +//===- CIRDialect.h - CIR dialect -------------------------------*- C++ -*-===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// +// +// This file declares the CIR dialect. +// +//===----------------------------------------------------------------------===// + +#ifndef LLVM_CLANG_CIR_DIALECT_IR_CIRDIALECT_H +#define LLVM_CLANG_CIR_DIALECT_IR_CIRDIALECT_H + +#endif // LLVM_CLANG_CIR_DIALECT_IR_CIRDIALECT_H diff --git a/clang/include/clang/CIR/Dialect/IR/CIRDialect.td b/clang/include/clang/CIR/Dialect/IR/CIRDialect.td new file mode 100644 index 0000000000000000000000000000000000000000..69d6e9774942b9dfb0eb85793dafb63c0b89baf3 --- /dev/null +++ b/clang/include/clang/CIR/Dialect/IR/CIRDialect.td @@ -0,0 +1,44 @@ +//===- CIRDialect.td - CIR dialect -------------------------*- tablegen -*-===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// +// +// This file declares the CIR dialect. +// +//===----------------------------------------------------------------------===// + +#ifndef LLVM_CLANG_CIR_DIALECT_IR_CIRDIALECT +#define LLVM_CLANG_CIR_DIALECT_IR_CIRDIALECT + +include "mlir/IR/OpBase.td" + +def CIR_Dialect : Dialect { + let name = "cir"; + + // A short one-line summary of our dialect. + let summary = "A high-level dialect for analyzing and optimizing Clang " + "supported languages"; + + let cppNamespace = "::mlir::cir"; + + let useDefaultAttributePrinterParser = 0; + let useDefaultTypePrinterParser = 0; + + let extraClassDeclaration = [{ + void registerAttributes(); + void registerTypes(); + + Type parseType(DialectAsmParser &parser) const override; + void printType(Type type, DialectAsmPrinter &printer) const override; + + Attribute parseAttribute(DialectAsmParser &parser, + Type type) const override; + + void printAttribute(Attribute attr, DialectAsmPrinter &os) const override; + }]; +} + +#endif // LLVM_CLANG_CIR_DIALECT_IR_CIRDIALECT diff --git a/clang/include/clang/CIR/Dialect/IR/CIROps.td b/clang/include/clang/CIR/Dialect/IR/CIROps.td new file mode 100644 index 0000000000000000000000000000000000000000..7311c8db783e061705e3745ca266d87aa379c2db --- /dev/null +++ b/clang/include/clang/CIR/Dialect/IR/CIROps.td @@ -0,0 +1,19 @@ +//===-- CIROps.td - CIR dialect definition -----------------*- tablegen -*-===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// +/// +/// \file +/// Definition of the CIR dialect +/// +//===----------------------------------------------------------------------===// + +#ifndef LLVM_CLANG_CIR_DIALECT_IR_CIROPS +#define LLVM_CLANG_CIR_DIALECT_IR_CIROPS + +include "clang/CIR/Dialect/IR/CIRDialect.td" + +#endif // LLVM_CLANG_CIR_DIALECT_IR_CIROPS diff --git a/clang/include/clang/CIR/Dialect/IR/CMakeLists.txt b/clang/include/clang/CIR/Dialect/IR/CMakeLists.txt new file mode 100644 index 0000000000000000000000000000000000000000..28ae30dab8dfb23a75751a885cf6795eaa2ee217 --- /dev/null +++ b/clang/include/clang/CIR/Dialect/IR/CMakeLists.txt @@ -0,0 +1,16 @@ +# This replicates part of the add_mlir_dialect cmake function from MLIR that +# cannot be used here. This happens because it expects to be run inside MLIR +# directory which is not the case for CIR (and also FIR, both have similar +# workarounds). + +# Equivalent to add_mlir_dialect(CIROps cir) +set(LLVM_TARGET_DEFINITIONS CIROps.td) +mlir_tablegen(CIROps.h.inc -gen-op-decls) +mlir_tablegen(CIROps.cpp.inc -gen-op-defs) +mlir_tablegen(CIROpsTypes.h.inc -gen-typedef-decls) +mlir_tablegen(CIROpsTypes.cpp.inc -gen-typedef-defs) +mlir_tablegen(CIROpsDialect.h.inc -gen-dialect-decls) +mlir_tablegen(CIROpsDialect.cpp.inc -gen-dialect-defs) +add_public_tablegen_target(MLIRCIROpsIncGen) +add_dependencies(mlir-headers MLIRCIROpsIncGen) + diff --git a/clang/include/clang/Driver/Options.td b/clang/include/clang/Driver/Options.td index 3c55aceecdde38bf895cb59672e30f502dc3388a..5a6526b0592f7ba40ffad7c95bbc4914bcc21f43 100644 --- a/clang/include/clang/Driver/Options.td +++ b/clang/include/clang/Driver/Options.td @@ -603,6 +603,7 @@ class MarshallingInfoVisibility // Key paths that are constant during parsing of options with the same key path prefix. defvar cplusplus = LangOpts<"CPlusPlus">; defvar cpp11 = LangOpts<"CPlusPlus11">; +defvar cpp14 = LangOpts<"CPlusPlus14">; defvar cpp17 = LangOpts<"CPlusPlus17">; defvar cpp20 = LangOpts<"CPlusPlus20">; defvar c99 = LangOpts<"C99">; @@ -2615,6 +2616,11 @@ defm protect_parens : BoolFOption<"protect-parens", "floating-point expressions are evaluated">, NegFlag>; +defm daz_ftz : SimpleMFlag<"daz-ftz", + "Globally set", "Do not globally set", + " the denormals-are-zero (DAZ) and flush-to-zero (FTZ) bits in the " + "floating-point control register on program startup">; + def ffor_scope : Flag<["-"], "ffor-scope">, Group; def fno_for_scope : Flag<["-"], "fno-for-scope">, Group; @@ -3365,10 +3371,9 @@ defm relaxed_template_template_args : BoolFOption<"relaxed-template-template-arg "Enable C++17 relaxed template template argument matching">, NegFlag>; defm sized_deallocation : BoolFOption<"sized-deallocation", - LangOpts<"SizedDeallocation">, DefaultFalse, - PosFlag, - NegFlag>; + LangOpts<"SizedDeallocation">, Default, + PosFlag, + NegFlag, BothFlags<[], [ClangOption, CC1Option]>>; defm aligned_allocation : BoolFOption<"aligned-allocation", LangOpts<"AlignedAllocation">, Default, PosFlag, @@ -5508,6 +5513,14 @@ def fno_rtlib_add_rpath: Flag<["-"], "fno-rtlib-add-rpath">, Visibility<[ClangOption, FlangOption]>, HelpText<"Do not add -rpath with architecture-specific resource directory to the linker flags. " "When --hip-link is specified, do not add -rpath with HIP runtime library directory to the linker flags">; +def frtlib_defaultlib : Flag<["-"], "frtlib-defaultlib">, + Visibility<[ClangOption, CLOption]>, + Group, + HelpText<"On Windows, emit /defaultlib: directives to link compiler-rt libraries (default)">; +def fno_rtlib_defaultlib : Flag<["-"], "fno-rtlib-defaultlib">, + Visibility<[ClangOption, CLOption]>, + Group, + HelpText<"On Windows, do not emit /defaultlib: directives to link compiler-rt libraries">; def offload_add_rpath: Flag<["--"], "offload-add-rpath">, Flags<[NoArgumentUnused]>, Alias; diff --git a/clang/include/clang/ExtractAPI/API.h b/clang/include/clang/ExtractAPI/API.h index 92cacf65c7d64e585d00687d0121d071e3c6ca0d..d323e1668a72b1718ab62e24f139a6304b93cbdb 100644 --- a/clang/include/clang/ExtractAPI/API.h +++ b/clang/include/clang/ExtractAPI/API.h @@ -208,20 +208,20 @@ struct APIRecord { RK_ClassTemplate, RK_ClassTemplateSpecialization, RK_ClassTemplatePartialSpecialization, - RK_LastRecordContext, - RK_GlobalFunction, - RK_GlobalFunctionTemplate, - RK_GlobalFunctionTemplateSpecialization, + RK_StructField, + RK_UnionField, + RK_CXXField, + RK_StaticField, + RK_CXXFieldTemplate, RK_GlobalVariable, RK_GlobalVariableTemplate, RK_GlobalVariableTemplateSpecialization, RK_GlobalVariableTemplatePartialSpecialization, + RK_LastRecordContext, + RK_GlobalFunction, + RK_GlobalFunctionTemplate, + RK_GlobalFunctionTemplateSpecialization, RK_EnumConstant, - RK_StructField, - RK_UnionField, - RK_StaticField, - RK_CXXField, - RK_CXXFieldTemplate, RK_Concept, RK_CXXStaticMethod, RK_CXXInstanceMethod, @@ -321,6 +321,10 @@ public: RecordContext(APIRecord::RecordKind Kind) : Kind(Kind) {} + /// Append \p Other children chain into ours and empty out Other's record + /// chain. + void stealRecordChain(RecordContext &Other); + APIRecord::RecordKind getKind() const { return Kind; } struct record_iterator { @@ -370,6 +374,7 @@ private: APIRecord::RecordKind Kind; mutable APIRecord *First = nullptr; mutable APIRecord *Last = nullptr; + bool IsWellFormed() const; protected: friend class APISet; @@ -475,7 +480,7 @@ struct GlobalFunctionTemplateSpecializationRecord : GlobalFunctionRecord { }; /// This holds information associated with global functions. -struct GlobalVariableRecord : APIRecord { +struct GlobalVariableRecord : APIRecord, RecordContext { GlobalVariableRecord(StringRef USR, StringRef Name, SymbolReference Parent, PresumedLoc Loc, AvailabilityInfo Availability, LinkageInfo Linkage, const DocComment &Comment, @@ -483,23 +488,28 @@ struct GlobalVariableRecord : APIRecord { DeclarationFragments SubHeading, bool IsFromSystemHeader) : APIRecord(RK_GlobalVariable, USR, Name, Parent, Loc, std::move(Availability), Linkage, Comment, Declaration, - SubHeading, IsFromSystemHeader) {} + SubHeading, IsFromSystemHeader), + RecordContext(RK_GlobalVariable) {} GlobalVariableRecord(RecordKind Kind, StringRef USR, StringRef Name, - SymbolReference Parent, - - PresumedLoc Loc, AvailabilityInfo Availability, - LinkageInfo Linkage, const DocComment &Comment, + SymbolReference Parent, PresumedLoc Loc, + AvailabilityInfo Availability, LinkageInfo Linkage, + const DocComment &Comment, DeclarationFragments Declaration, DeclarationFragments SubHeading, bool IsFromSystemHeader) : APIRecord(Kind, USR, Name, Parent, Loc, std::move(Availability), Linkage, Comment, Declaration, SubHeading, - IsFromSystemHeader) {} + IsFromSystemHeader), + RecordContext(Kind) {} static bool classof(const APIRecord *Record) { return classofKind(Record->getKind()); } - static bool classofKind(RecordKind K) { return K == RK_GlobalVariable; } + static bool classofKind(RecordKind K) { + return K == RK_GlobalVariable || K == RK_GlobalVariableTemplate || + K == RK_GlobalVariableTemplateSpecialization || + K == RK_GlobalVariableTemplatePartialSpecialization; + } private: virtual void anchor(); @@ -591,20 +601,47 @@ private: virtual void anchor(); }; +struct TagRecord : APIRecord, RecordContext { + TagRecord(RecordKind Kind, StringRef USR, StringRef Name, + SymbolReference Parent, PresumedLoc Loc, + AvailabilityInfo Availability, const DocComment &Comment, + DeclarationFragments Declaration, DeclarationFragments SubHeading, + bool IsFromSystemHeader, bool IsEmbeddedInVarDeclarator, + AccessControl Access = AccessControl()) + : APIRecord(Kind, USR, Name, Parent, Loc, std::move(Availability), + LinkageInfo::none(), Comment, Declaration, SubHeading, + IsFromSystemHeader, std::move(Access)), + RecordContext(Kind), + IsEmbeddedInVarDeclarator(IsEmbeddedInVarDeclarator){}; + + static bool classof(const APIRecord *Record) { + return classofKind(Record->getKind()); + } + static bool classofKind(RecordKind K) { + return K == RK_Struct || K == RK_Union || K == RK_Enum; + } + + bool IsEmbeddedInVarDeclarator; + + virtual ~TagRecord() = 0; +}; + /// This holds information associated with enums. -struct EnumRecord : APIRecord, RecordContext { +struct EnumRecord : TagRecord { EnumRecord(StringRef USR, StringRef Name, SymbolReference Parent, PresumedLoc Loc, AvailabilityInfo Availability, const DocComment &Comment, DeclarationFragments Declaration, - DeclarationFragments SubHeading, bool IsFromSystemHeader) - : APIRecord(RK_Enum, USR, Name, Parent, Loc, std::move(Availability), - LinkageInfo::none(), Comment, Declaration, SubHeading, - IsFromSystemHeader), - RecordContext(RK_Enum) {} + DeclarationFragments SubHeading, bool IsFromSystemHeader, + bool IsEmbeddedInVarDeclarator, + AccessControl Access = AccessControl()) + : TagRecord(RK_Enum, USR, Name, Parent, Loc, std::move(Availability), + Comment, Declaration, SubHeading, IsFromSystemHeader, + IsEmbeddedInVarDeclarator, std::move(Access)) {} static bool classof(const APIRecord *Record) { return classofKind(Record->getKind()); } + static bool classofKind(RecordKind K) { return K == RK_Enum; } private: @@ -612,7 +649,7 @@ private: }; /// This holds information associated with struct or union fields fields. -struct RecordFieldRecord : APIRecord { +struct RecordFieldRecord : APIRecord, RecordContext { RecordFieldRecord(RecordKind Kind, StringRef USR, StringRef Name, SymbolReference Parent, PresumedLoc Loc, AvailabilityInfo Availability, const DocComment &Comment, @@ -620,7 +657,8 @@ struct RecordFieldRecord : APIRecord { DeclarationFragments SubHeading, bool IsFromSystemHeader) : APIRecord(Kind, USR, Name, Parent, Loc, std::move(Availability), LinkageInfo::none(), Comment, Declaration, SubHeading, - IsFromSystemHeader) {} + IsFromSystemHeader), + RecordContext(Kind) {} static bool classof(const APIRecord *Record) { return classofKind(Record->getKind()); @@ -633,16 +671,17 @@ struct RecordFieldRecord : APIRecord { }; /// This holds information associated with structs and unions. -struct RecordRecord : APIRecord, RecordContext { +struct RecordRecord : TagRecord { RecordRecord(RecordKind Kind, StringRef USR, StringRef Name, SymbolReference Parent, PresumedLoc Loc, AvailabilityInfo Availability, const DocComment &Comment, DeclarationFragments Declaration, - DeclarationFragments SubHeading, bool IsFromSystemHeader) - : APIRecord(Kind, USR, Name, Parent, Loc, std::move(Availability), - LinkageInfo::none(), Comment, Declaration, SubHeading, - IsFromSystemHeader), - RecordContext(Kind) {} + DeclarationFragments SubHeading, bool IsFromSystemHeader, + bool IsEmbeddedInVarDeclarator, + AccessControl Access = AccessControl()) + : TagRecord(Kind, USR, Name, Parent, Loc, std::move(Availability), + Comment, Declaration, SubHeading, IsFromSystemHeader, + IsEmbeddedInVarDeclarator, std::move(Access)) {} static bool classof(const APIRecord *Record) { return classofKind(Record->getKind()); @@ -651,6 +690,8 @@ struct RecordRecord : APIRecord, RecordContext { return K == RK_Struct || K == RK_Union; } + bool isAnonymousWithNoTypedef() { return Name.empty(); } + virtual ~RecordRecord() = 0; }; @@ -676,9 +717,11 @@ struct StructRecord : RecordRecord { StructRecord(StringRef USR, StringRef Name, SymbolReference Parent, PresumedLoc Loc, AvailabilityInfo Availability, const DocComment &Comment, DeclarationFragments Declaration, - DeclarationFragments SubHeading, bool IsFromSystemHeader) + DeclarationFragments SubHeading, bool IsFromSystemHeader, + bool IsEmbeddedInVarDeclarator) : RecordRecord(RK_Struct, USR, Name, Parent, Loc, std::move(Availability), - Comment, Declaration, SubHeading, IsFromSystemHeader) {} + Comment, Declaration, SubHeading, IsFromSystemHeader, + IsEmbeddedInVarDeclarator) {} static bool classof(const APIRecord *Record) { return classofKind(Record->getKind()); @@ -711,9 +754,11 @@ struct UnionRecord : RecordRecord { UnionRecord(StringRef USR, StringRef Name, SymbolReference Parent, PresumedLoc Loc, AvailabilityInfo Availability, const DocComment &Comment, DeclarationFragments Declaration, - DeclarationFragments SubHeading, bool IsFromSystemHeader) + DeclarationFragments SubHeading, bool IsFromSystemHeader, + bool IsEmbeddedInVarDeclarator) : RecordRecord(RK_Union, USR, Name, Parent, Loc, std::move(Availability), - Comment, Declaration, SubHeading, IsFromSystemHeader) {} + Comment, Declaration, SubHeading, IsFromSystemHeader, + IsEmbeddedInVarDeclarator) {} static bool classof(const APIRecord *Record) { return classofKind(Record->getKind()); @@ -724,7 +769,7 @@ private: virtual void anchor(); }; -struct CXXFieldRecord : APIRecord { +struct CXXFieldRecord : APIRecord, RecordContext { CXXFieldRecord(StringRef USR, StringRef Name, SymbolReference Parent, PresumedLoc Loc, AvailabilityInfo Availability, const DocComment &Comment, DeclarationFragments Declaration, @@ -732,7 +777,8 @@ struct CXXFieldRecord : APIRecord { bool IsFromSystemHeader) : APIRecord(RK_CXXField, USR, Name, Parent, Loc, std::move(Availability), LinkageInfo::none(), Comment, Declaration, SubHeading, - IsFromSystemHeader, std::move(Access)) {} + IsFromSystemHeader, std::move(Access)), + RecordContext(RK_CXXField) {} CXXFieldRecord(RecordKind Kind, StringRef USR, StringRef Name, SymbolReference Parent, PresumedLoc Loc, @@ -742,7 +788,8 @@ struct CXXFieldRecord : APIRecord { bool IsFromSystemHeader) : APIRecord(Kind, USR, Name, Parent, Loc, std::move(Availability), LinkageInfo::none(), Comment, Declaration, SubHeading, - IsFromSystemHeader, std::move(Access)) {} + IsFromSystemHeader, std::move(Access)), + RecordContext(Kind) {} static bool classof(const APIRecord *Record) { return classofKind(Record->getKind()); @@ -1118,18 +1165,18 @@ struct ObjCContainerRecord : APIRecord, RecordContext { virtual ~ObjCContainerRecord() = 0; }; -struct CXXClassRecord : APIRecord, RecordContext { +struct CXXClassRecord : RecordRecord { SmallVector Bases; CXXClassRecord(StringRef USR, StringRef Name, SymbolReference Parent, PresumedLoc Loc, AvailabilityInfo Availability, const DocComment &Comment, DeclarationFragments Declaration, DeclarationFragments SubHeading, RecordKind Kind, - AccessControl Access, bool IsFromSystemHeader) - : APIRecord(Kind, USR, Name, Parent, Loc, std::move(Availability), - LinkageInfo::none(), Comment, Declaration, SubHeading, - IsFromSystemHeader, std::move(Access)), - RecordContext(Kind) {} + AccessControl Access, bool IsFromSystemHeader, + bool IsEmbeddedInVarDeclarator = false) + : RecordRecord(Kind, USR, Name, Parent, Loc, std::move(Availability), + Comment, Declaration, SubHeading, IsFromSystemHeader, + IsEmbeddedInVarDeclarator, std::move(Access)) {} static bool classof(const APIRecord *Record) { return classofKind(Record->getKind()); diff --git a/clang/include/clang/ExtractAPI/APIRecords.inc b/clang/include/clang/ExtractAPI/APIRecords.inc index 15fee809656d9a4b5e50ba7b1f8c2ff88978128e..4cda4ef2f9be63f14b4922f09bd08ab0cafd3889 100644 --- a/clang/include/clang/ExtractAPI/APIRecords.inc +++ b/clang/include/clang/ExtractAPI/APIRecords.inc @@ -35,10 +35,11 @@ CONCRETE_RECORD(GlobalVariableTemplateSpecializationRecord, CONCRETE_RECORD(GlobalVariableTemplatePartialSpecializationRecord, GlobalVariableRecord, RK_GlobalVariableTemplatePartialSpecialization) +ABSTRACT_RECORD(TagRecord, APIRecord) CONCRETE_RECORD(EnumConstantRecord, APIRecord, RK_EnumConstant) -CONCRETE_RECORD(EnumRecord, APIRecord, RK_Enum) +CONCRETE_RECORD(EnumRecord, TagRecord, RK_Enum) ABSTRACT_RECORD(RecordFieldRecord, APIRecord) -ABSTRACT_RECORD(RecordRecord, APIRecord) +ABSTRACT_RECORD(RecordRecord, TagRecord) CONCRETE_RECORD(StructFieldRecord, RecordFieldRecord, RK_StructField) CONCRETE_RECORD(StructRecord, APIRecord, RK_Struct) CONCRETE_RECORD(UnionFieldRecord, RecordFieldRecord, RK_UnionField) @@ -99,5 +100,16 @@ RECORD_CONTEXT(ClassTemplateSpecializationRecord, RK_ClassTemplateSpecialization) RECORD_CONTEXT(ClassTemplatePartialSpecializationRecord, RK_ClassTemplatePartialSpecialization) +RECORD_CONTEXT(StructFieldRecord, RK_StructField) +RECORD_CONTEXT(UnionFieldRecord, RK_UnionField) +RECORD_CONTEXT(CXXFieldRecord, RK_CXXField) +RECORD_CONTEXT(StaticFieldRecord, RK_StaticField) +RECORD_CONTEXT(CXXFieldTemplateRecord, RK_CXXFieldTemplate) +RECORD_CONTEXT(GlobalVariableRecord, RK_GlobalVariable) +RECORD_CONTEXT(GlobalVariableTemplateRecord, RK_GlobalVariableTemplate) +RECORD_CONTEXT(GlobalVariableTemplateSpecializationRecord, + RK_GlobalVariableTemplateSpecialization) +RECORD_CONTEXT(GlobalVariableTemplatePartialSpecializationRecord, + RK_GlobalVariableTemplatePartialSpecialization) #undef RECORD_CONTEXT diff --git a/clang/include/clang/ExtractAPI/DeclarationFragments.h b/clang/include/clang/ExtractAPI/DeclarationFragments.h index 94392c185165951c39adad41cd402f83cd30119c..535da90b98284ba54f868eb4ea92d594da68c1f7 100644 --- a/clang/include/clang/ExtractAPI/DeclarationFragments.h +++ b/clang/include/clang/ExtractAPI/DeclarationFragments.h @@ -27,6 +27,8 @@ #include "clang/AST/TypeLoc.h" #include "clang/Basic/Specifiers.h" #include "clang/Lex/MacroInfo.h" +#include +#include #include namespace clang { @@ -113,28 +115,26 @@ public: ConstFragmentIterator cend() const { return Fragments.cend(); } - // Add a new Fragment at an arbitrary offset. - DeclarationFragments &insert(FragmentIterator It, StringRef Spelling, - FragmentKind Kind, - StringRef PreciseIdentifier = "", - const Decl *Declaration = nullptr) { - Fragments.insert(It, - Fragment(Spelling, Kind, PreciseIdentifier, Declaration)); - return *this; + /// Prepend another DeclarationFragments to the beginning. + /// + /// \returns a reference to the DeclarationFragments object itself after + /// appending to chain up consecutive operations. + DeclarationFragments &prepend(DeclarationFragments Other) { + return insert(begin(), std::move(Other)); } - DeclarationFragments &insert(FragmentIterator It, - DeclarationFragments &&Other) { - Fragments.insert(It, std::make_move_iterator(Other.Fragments.begin()), - std::make_move_iterator(Other.Fragments.end())); - Other.Fragments.clear(); - return *this; + /// Append another DeclarationFragments to the end. + /// + /// \returns a reference to the DeclarationFragments object itself after + /// appending to chain up consecutive operations. + DeclarationFragments &append(DeclarationFragments Other) { + return insert(end(), std::move(Other)); } /// Append a new Fragment to the end of the Fragments. /// /// \returns a reference to the DeclarationFragments object itself after - /// appending to chain up consecutive appends. + /// appending to chain up consecutive operations. DeclarationFragments &append(StringRef Spelling, FragmentKind Kind, StringRef PreciseIdentifier = "", const Decl *Declaration = nullptr) { @@ -149,18 +149,48 @@ public: return *this; } - /// Append another DeclarationFragments to the end. - /// - /// Note: \p Other is moved from and cannot be used after a call to this - /// method. + /// Inserts another DeclarationFragments at \p It. /// /// \returns a reference to the DeclarationFragments object itself after - /// appending to chain up consecutive appends. - DeclarationFragments &append(DeclarationFragments &&Other) { - Fragments.insert(Fragments.end(), - std::make_move_iterator(Other.Fragments.begin()), - std::make_move_iterator(Other.Fragments.end())); - Other.Fragments.clear(); + /// appending to chain up consecutive operations. + DeclarationFragments &insert(FragmentIterator It, + DeclarationFragments Other) { + if (Other.Fragments.empty()) + return *this; + + if (Fragments.empty()) { + Fragments = std::move(Other.Fragments); + return *this; + } + + const auto &OtherFrags = Other.Fragments; + auto ToInsertBegin = std::make_move_iterator(Other.begin()); + auto ToInsertEnd = std::make_move_iterator(Other.end()); + + // If we aren't inserting at the end let's make sure that we merge their + // last fragment with It if both are text fragments. + if (It != end() && It->Kind == FragmentKind::Text && + OtherFrags.back().Kind == FragmentKind::Text) { + auto &TheirBackSpelling = OtherFrags.back().Spelling; + It->Spelling.reserve(It->Spelling.size() + TheirBackSpelling.size()); + It->Spelling.insert(It->Spelling.begin(), TheirBackSpelling.begin(), + TheirBackSpelling.end()); + --ToInsertEnd; + } + + // If we aren't inserting at the beginning we want to merge their first + // fragment with the fragment before It if both are text fragments. + if (It != begin() && std::prev(It)->Kind == FragmentKind::Text && + OtherFrags.front().Kind == FragmentKind::Text) { + auto PrevIt = std::prev(It); + auto &TheirFrontSpelling = OtherFrags.front().Spelling; + PrevIt->Spelling.reserve(PrevIt->Spelling.size() + + TheirFrontSpelling.size()); + PrevIt->Spelling.append(TheirFrontSpelling); + ++ToInsertBegin; + } + + Fragments.insert(It, ToInsertBegin, ToInsertEnd); return *this; } @@ -177,13 +207,13 @@ public: /// Append a text Fragment of a space character. /// /// \returns a reference to the DeclarationFragments object itself after - /// appending to chain up consecutive appends. + /// appending to chain up consecutive operations. DeclarationFragments &appendSpace(); /// Append a text Fragment of a semicolon character. /// /// \returns a reference to the DeclarationFragments object itself after - /// appending to chain up consecutive appends. + /// appending to chain up consecutive operations. DeclarationFragments &appendSemicolon(); /// Removes a trailing semicolon character if present. diff --git a/clang/include/clang/ExtractAPI/ExtractAPIVisitor.h b/clang/include/clang/ExtractAPI/ExtractAPIVisitor.h index 4cb866892b5d00d10c7a3f70c2174b35f103563b..97cc457ea2a9263c8ce4b5910fc85b56a0c98755 100644 --- a/clang/include/clang/ExtractAPI/ExtractAPIVisitor.h +++ b/clang/include/clang/ExtractAPI/ExtractAPIVisitor.h @@ -224,6 +224,29 @@ protected: return API.createSymbolReference(Name, USR, getOwningModuleName(D)); } + + bool isEmbeddedInVarDeclarator(const TagDecl &D) { + return D.getName().empty() && getTypedefName(&D).empty() && + D.isEmbeddedInDeclarator(); + } + + void maybeMergeWithAnonymousTag(const DeclaratorDecl &D, + RecordContext *NewRecordContext) { + if (!NewRecordContext) + return; + auto *Tag = D.getType()->getAsTagDecl(); + SmallString<128> TagUSR; + clang::index::generateUSRForDecl(Tag, TagUSR); + if (auto *Record = llvm::dyn_cast_if_present( + API.findRecordForUSR(TagUSR))) { + if (Record->IsEmbeddedInVarDeclarator) { + NewRecordContext->stealRecordChain(*Record); + auto *NewRecord = cast(NewRecordContext); + if (NewRecord->Comment.empty()) + NewRecord->Comment = Record->Comment; + } + } + } }; template @@ -273,12 +296,18 @@ bool ExtractAPIVisitorBase::VisitVarDecl(const VarDecl *Decl) { USR, Name, createHierarchyInformationForDecl(*Decl), Loc, AvailabilityInfo::createFromDecl(Decl), Linkage, Comment, Declaration, SubHeading, Access, isInSystemHeader(Decl)); - } else + } else { // Add the global variable record to the API set. - API.createRecord( + auto *NewRecord = API.createRecord( USR, Name, createHierarchyInformationForDecl(*Decl), Loc, AvailabilityInfo::createFromDecl(Decl), Linkage, Comment, Declaration, SubHeading, isInSystemHeader(Decl)); + + // If this global variable has a non typedef'd anonymous tag type let's + // pretend the type's child records are under us in the hierarchy. + maybeMergeWithAnonymousTag(*Decl, NewRecord); + } + return true; } @@ -364,7 +393,7 @@ bool ExtractAPIVisitorBase::VisitEnumDecl(const EnumDecl *Decl) { if (Name.empty()) { llvm::raw_svector_ostream OS(QualifiedNameBuffer); Decl->printQualifiedName(OS); - Name = QualifiedNameBuffer.str(); + Name = QualifiedNameBuffer; } SmallString<128> USR; @@ -385,7 +414,7 @@ bool ExtractAPIVisitorBase::VisitEnumDecl(const EnumDecl *Decl) { auto *ER = API.createRecord( USR, Name, createHierarchyInformationForDecl(*Decl), Loc, AvailabilityInfo::createFromDecl(Decl), Comment, Declaration, SubHeading, - isInSystemHeader(Decl)); + isInSystemHeader(Decl), isEmbeddedInVarDeclarator(*Decl)); // Now collect information about the enumerators in this enum. getDerivedExtractAPIVisitor().recordEnumConstants(ER, Decl->enumerators()); @@ -510,16 +539,10 @@ bool ExtractAPIVisitorBase::VisitRecordDecl(const RecordDecl *Decl) { if (!getDerivedExtractAPIVisitor().shouldDeclBeIncluded(Decl)) return true; - SmallString<128> QualifiedNameBuffer; // Collect symbol information. StringRef Name = Decl->getName(); if (Name.empty()) Name = getTypedefName(Decl); - if (Name.empty()) { - llvm::raw_svector_ostream OS(QualifiedNameBuffer); - Decl->printQualifiedName(OS); - Name = QualifiedNameBuffer.str(); - } SmallString<128> USR; index::generateUSRForDecl(Decl, USR); @@ -541,12 +564,12 @@ bool ExtractAPIVisitorBase::VisitRecordDecl(const RecordDecl *Decl) { API.createRecord( USR, Name, createHierarchyInformationForDecl(*Decl), Loc, AvailabilityInfo::createFromDecl(Decl), Comment, Declaration, - SubHeading, isInSystemHeader(Decl)); + SubHeading, isInSystemHeader(Decl), isEmbeddedInVarDeclarator(*Decl)); else API.createRecord( USR, Name, createHierarchyInformationForDecl(*Decl), Loc, AvailabilityInfo::createFromDecl(Decl), Comment, Declaration, - SubHeading, isInSystemHeader(Decl)); + SubHeading, isInSystemHeader(Decl), isEmbeddedInVarDeclarator(*Decl)); return true; } @@ -559,6 +582,9 @@ bool ExtractAPIVisitorBase::VisitCXXRecordDecl( return true; StringRef Name = Decl->getName(); + if (Name.empty()) + Name = getTypedefName(Decl); + SmallString<128> USR; index::generateUSRForDecl(Decl, USR); PresumedLoc Loc = @@ -585,8 +611,7 @@ bool ExtractAPIVisitorBase::VisitCXXRecordDecl( CXXClassRecord *Record; if (Decl->getDescribedClassTemplate()) { // Inject template fragments before class fragments. - Declaration.insert( - Declaration.begin(), + Declaration.prepend( DeclarationFragmentsBuilder::getFragmentsForRedeclarableTemplate( Decl->getDescribedClassTemplate())); Record = API.createRecord( @@ -598,7 +623,8 @@ bool ExtractAPIVisitorBase::VisitCXXRecordDecl( Record = API.createRecord( USR, Name, createHierarchyInformationForDecl(*Decl), Loc, AvailabilityInfo::createFromDecl(Decl), Comment, Declaration, - SubHeading, Kind, Access, isInSystemHeader(Decl)); + SubHeading, Kind, Access, isInSystemHeader(Decl), + isEmbeddedInVarDeclarator(*Decl)); Record->Bases = getBases(Decl); @@ -1075,18 +1101,17 @@ bool ExtractAPIVisitorBase::VisitTypedefNameDecl( // If the underlying type was defined as part of the typedef modify it's // fragments directly and pretend the typedef doesn't exist. if (auto *TagDecl = Decl->getUnderlyingType()->getAsTagDecl()) { - if (TagDecl->getName() == Decl->getName() && - TagDecl->isEmbeddedInDeclarator() && TagDecl->isCompleteDefinition()) { + if (TagDecl->isEmbeddedInDeclarator() && TagDecl->isCompleteDefinition() && + Decl->getName() == TagDecl->getName()) { SmallString<128> TagUSR; index::generateUSRForDecl(TagDecl, TagUSR); if (auto *Record = API.findRecordForUSR(TagUSR)) { DeclarationFragments LeadingFragments; LeadingFragments.append("typedef", - DeclarationFragments::FragmentKind::Keyword, "", - nullptr); + DeclarationFragments::FragmentKind::Keyword); LeadingFragments.appendSpace(); Record->Declaration.removeTrailingSemicolon() - .insert(Record->Declaration.begin(), std::move(LeadingFragments)) + .prepend(std::move(LeadingFragments)) .append(" { ... } ", DeclarationFragments::FragmentKind::Text) .append(Name, DeclarationFragments::FragmentKind::Identifier) .appendSemicolon(); @@ -1221,26 +1246,31 @@ bool ExtractAPIVisitorBase::VisitFieldDecl(const FieldDecl *Decl) { DeclarationFragments SubHeading = DeclarationFragmentsBuilder::getSubHeading(Decl); + RecordContext *NewRecord = nullptr; if (isa(Decl->getDeclContext())) { AccessControl Access = DeclarationFragmentsBuilder::getAccessControl(Decl); - API.createRecord( + NewRecord = API.createRecord( USR, Name, createHierarchyInformationForDecl(*Decl), Loc, AvailabilityInfo::createFromDecl(Decl), Comment, Declaration, SubHeading, Access, isInSystemHeader(Decl)); } else if (auto *RD = dyn_cast(Decl->getDeclContext())) { if (RD->isUnion()) - API.createRecord( + NewRecord = API.createRecord( USR, Name, createHierarchyInformationForDecl(*Decl), Loc, AvailabilityInfo::createFromDecl(Decl), Comment, Declaration, SubHeading, isInSystemHeader(Decl)); else - API.createRecord( + NewRecord = API.createRecord( USR, Name, createHierarchyInformationForDecl(*Decl), Loc, AvailabilityInfo::createFromDecl(Decl), Comment, Declaration, SubHeading, isInSystemHeader(Decl)); } + // If this field has a non typedef'd anonymous tag type let's pretend the + // type's child records are under us in the hierarchy. + maybeMergeWithAnonymousTag(*Decl, NewRecord); + return true; } diff --git a/clang/include/clang/Frontend/ASTUnit.h b/clang/include/clang/Frontend/ASTUnit.h index a2c1b25dd224768fa38aeae466da1f0919bcfe4f..080844893c13c9503663a9ed7b8805a67ec20940 100644 --- a/clang/include/clang/Frontend/ASTUnit.h +++ b/clang/include/clang/Frontend/ASTUnit.h @@ -241,7 +241,7 @@ private: /// A list of the serialization ID numbers for each of the top-level /// declarations parsed within the precompiled preamble. - std::vector TopLevelDeclsInPreamble; + std::vector TopLevelDeclsInPreamble; /// Whether we should be caching code-completion results. bool ShouldCacheCodeCompletionResults : 1; diff --git a/clang/include/clang/Frontend/MultiplexConsumer.h b/clang/include/clang/Frontend/MultiplexConsumer.h index 7f8d2858b3863eb71018e5dfca54c5efbf1fdce9..f29c8e92fded0cebb77329fc8cd4f3583992bb7c 100644 --- a/clang/include/clang/Frontend/MultiplexConsumer.h +++ b/clang/include/clang/Frontend/MultiplexConsumer.h @@ -35,7 +35,7 @@ public: void IdentifierRead(serialization::IdentID ID, IdentifierInfo *II) override; void MacroRead(serialization::MacroID ID, MacroInfo *MI) override; void TypeRead(serialization::TypeIdx Idx, QualType T) override; - void DeclRead(serialization::DeclID ID, const Decl *D) override; + void DeclRead(GlobalDeclID ID, const Decl *D) override; void SelectorRead(serialization::SelectorID iD, Selector Sel) override; void MacroDefinitionRead(serialization::PreprocessedEntityID, MacroDefinitionRecord *MD) override; diff --git a/clang/include/clang/Lex/HeaderSearch.h b/clang/include/clang/Lex/HeaderSearch.h index c5f90ef4cb3682a35f0869f81ff3f5a433ca396f..5ac63dddd4d4eaeb8a3db65fef5715da99add5e3 100644 --- a/clang/include/clang/Lex/HeaderSearch.h +++ b/clang/include/clang/Lex/HeaderSearch.h @@ -56,6 +56,12 @@ class TargetInfo; /// The preprocessor keeps track of this information for each /// file that is \#included. struct HeaderFileInfo { + // TODO: Whether the file was included is not a property of the file itself. + // It's a preprocessor state, move it there. + /// True if this file has been included (or imported) **locally**. + LLVM_PREFERRED_TYPE(bool) + unsigned IsLocallyIncluded : 1; + // TODO: Whether the file was imported is not a property of the file itself. // It's a preprocessor state, move it there. /// True if this is a \#import'd file. @@ -135,10 +141,10 @@ struct HeaderFileInfo { StringRef Framework; HeaderFileInfo() - : isImport(false), isPragmaOnce(false), DirInfo(SrcMgr::C_User), - External(false), isModuleHeader(false), isTextualModuleHeader(false), - isCompilingModuleHeader(false), Resolved(false), - IndexHeaderMapHeader(false), IsValid(false) {} + : IsLocallyIncluded(false), isImport(false), isPragmaOnce(false), + DirInfo(SrcMgr::C_User), External(false), isModuleHeader(false), + isTextualModuleHeader(false), isCompilingModuleHeader(false), + Resolved(false), IndexHeaderMapHeader(false), IsValid(false) {} /// Retrieve the controlling macro for this header file, if /// any. diff --git a/clang/include/clang/Sema/MultiplexExternalSemaSource.h b/clang/include/clang/Sema/MultiplexExternalSemaSource.h index 993c9b1daa309b5fe8998cebd935a852b31ec737..238fb398b7d12930becba1be738f44e7470024f8 100644 --- a/clang/include/clang/Sema/MultiplexExternalSemaSource.h +++ b/clang/include/clang/Sema/MultiplexExternalSemaSource.h @@ -65,7 +65,7 @@ public: /// Resolve a declaration ID into a declaration, potentially /// building a new declaration. - Decl *GetExternalDecl(Decl::DeclID ID) override; + Decl *GetExternalDecl(GlobalDeclID ID) override; /// Complete the redeclaration chain if it's been extended since the /// previous generation of the AST source. diff --git a/clang/include/clang/Sema/SemaOpenACC.h b/clang/include/clang/Sema/SemaOpenACC.h index ea28617f79b81b65df7d5cc63050a55a07003adb..da19503c2902fd270817f049bab819bd574919ce 100644 --- a/clang/include/clang/Sema/SemaOpenACC.h +++ b/clang/include/clang/Sema/SemaOpenACC.h @@ -193,6 +193,12 @@ public: /// conversions and diagnostics to 'int'. ExprResult ActOnIntExpr(OpenACCDirectiveKind DK, OpenACCClauseKind CK, SourceLocation Loc, Expr *IntExpr); + + /// Checks and creates an Array Section used in an OpenACC construct/clause. + ExprResult ActOnArraySectionExpr(Expr *Base, SourceLocation LBLoc, + Expr *LowerBound, + SourceLocation ColonLocFirst, Expr *Length, + SourceLocation RBLoc); }; } // namespace clang diff --git a/clang/include/clang/Serialization/ASTBitCodes.h b/clang/include/clang/Serialization/ASTBitCodes.h index dcfa4ac0c1967797b8425ba53fd96fbe0e297edb..a8df5a0bda085092308105bfef680032e28dc5e2 100644 --- a/clang/include/clang/Serialization/ASTBitCodes.h +++ b/clang/include/clang/Serialization/ASTBitCodes.h @@ -17,6 +17,7 @@ #ifndef LLVM_CLANG_SERIALIZATION_ASTBITCODES_H #define LLVM_CLANG_SERIALIZATION_ASTBITCODES_H +#include "clang/AST/DeclID.h" #include "clang/AST/DeclarationName.h" #include "clang/AST/Type.h" #include "clang/Basic/IdentifierTable.h" @@ -59,91 +60,9 @@ const unsigned VERSION_MINOR = 1; /// and start at 1. 0 is reserved for NULL. using IdentifierID = uint32_t; -/// An ID number that refers to a declaration in an AST file. -/// -/// The ID numbers of declarations are consecutive (in order of -/// discovery), with values below NUM_PREDEF_DECL_IDS being reserved. -/// At the start of a chain of precompiled headers, declaration ID 1 is -/// used for the translation unit declaration. -/// -/// FIXME: Merge with Decl::DeclID -using DeclID = uint32_t; - -class LocalDeclID { -public: - explicit LocalDeclID(DeclID ID) : ID(ID) {} - - DeclID get() const { return ID; } - -private: - DeclID ID; -}; - -/// Wrapper class for DeclID. This is helpful to not mix the use of LocalDeclID -/// and GlobalDeclID to improve the type safety. -class GlobalDeclID { -public: - GlobalDeclID() : ID(0) {} - explicit GlobalDeclID(DeclID ID) : ID(ID) {} - - DeclID get() const { return ID; } - - explicit operator DeclID() const { return ID; } - - friend bool operator==(const GlobalDeclID &LHS, const GlobalDeclID &RHS) { - return LHS.ID == RHS.ID; - } - friend bool operator!=(const GlobalDeclID &LHS, const GlobalDeclID &RHS) { - return LHS.ID != RHS.ID; - } - // We may sort the global decl ID. - friend bool operator<(const GlobalDeclID &LHS, const GlobalDeclID &RHS) { - return LHS.ID < RHS.ID; - } - friend bool operator>(const GlobalDeclID &LHS, const GlobalDeclID &RHS) { - return LHS.ID > RHS.ID; - } - friend bool operator<=(const GlobalDeclID &LHS, const GlobalDeclID &RHS) { - return LHS.ID <= RHS.ID; - } - friend bool operator>=(const GlobalDeclID &LHS, const GlobalDeclID &RHS) { - return LHS.ID >= RHS.ID; - } - -private: - DeclID ID; -}; - -/// A helper iterator adaptor to convert the iterators to `SmallVector` -/// to the iterators to `SmallVector`. -class GlobalDeclIDIterator - : public llvm::iterator_adaptor_base { -public: - GlobalDeclIDIterator() : iterator_adaptor_base(nullptr) {} - - GlobalDeclIDIterator(const DeclID *ID) : iterator_adaptor_base(ID) {} - - value_type operator*() const { return GlobalDeclID(*I); } - - bool operator==(const GlobalDeclIDIterator &RHS) const { return I == RHS.I; } -}; - -/// A helper iterator adaptor to convert the iterators to -/// `SmallVector` to the iterators to `SmallVector`. -class DeclIDIterator - : public llvm::iterator_adaptor_base { -public: - DeclIDIterator() : iterator_adaptor_base(nullptr) {} - - DeclIDIterator(const GlobalDeclID *ID) : iterator_adaptor_base(ID) {} - - value_type operator*() const { return DeclID(*I); } - - bool operator==(const DeclIDIterator &RHS) const { return I == RHS.I; } -}; +/// An ID number that refers to a declaration in an AST file. See the comments +/// in DeclIDBase for details. +using DeclID = DeclIDBase::DeclID; /// An ID number that refers to a type in an AST file. /// @@ -1054,8 +973,8 @@ enum PredefinedTypeIDs { /// OpenCL reserve_id type. PREDEF_TYPE_RESERVE_ID_ID = 41, - /// The placeholder type for OpenMP array section. - PREDEF_TYPE_OMP_ARRAY_SECTION = 42, + /// The placeholder type for an array section. + PREDEF_TYPE_ARRAY_SECTION = 42, /// The '__float128' type PREDEF_TYPE_FLOAT128_ID = 43, @@ -1238,74 +1157,6 @@ enum SpecialTypeIDs { /// The number of special type IDs. const unsigned NumSpecialTypeIDs = 8; -/// Predefined declaration IDs. -/// -/// These declaration IDs correspond to predefined declarations in the AST -/// context, such as the NULL declaration ID. Such declarations are never -/// actually serialized, since they will be built by the AST context when -/// it is created. -enum PredefinedDeclIDs { - /// The NULL declaration. - PREDEF_DECL_NULL_ID = 0, - - /// The translation unit. - PREDEF_DECL_TRANSLATION_UNIT_ID = 1, - - /// The Objective-C 'id' type. - PREDEF_DECL_OBJC_ID_ID = 2, - - /// The Objective-C 'SEL' type. - PREDEF_DECL_OBJC_SEL_ID = 3, - - /// The Objective-C 'Class' type. - PREDEF_DECL_OBJC_CLASS_ID = 4, - - /// The Objective-C 'Protocol' type. - PREDEF_DECL_OBJC_PROTOCOL_ID = 5, - - /// The signed 128-bit integer type. - PREDEF_DECL_INT_128_ID = 6, - - /// The unsigned 128-bit integer type. - PREDEF_DECL_UNSIGNED_INT_128_ID = 7, - - /// The internal 'instancetype' typedef. - PREDEF_DECL_OBJC_INSTANCETYPE_ID = 8, - - /// The internal '__builtin_va_list' typedef. - PREDEF_DECL_BUILTIN_VA_LIST_ID = 9, - - /// The internal '__va_list_tag' struct, if any. - PREDEF_DECL_VA_LIST_TAG = 10, - - /// The internal '__builtin_ms_va_list' typedef. - PREDEF_DECL_BUILTIN_MS_VA_LIST_ID = 11, - - /// The predeclared '_GUID' struct. - PREDEF_DECL_BUILTIN_MS_GUID_ID = 12, - - /// The extern "C" context. - PREDEF_DECL_EXTERN_C_CONTEXT_ID = 13, - - /// The internal '__make_integer_seq' template. - PREDEF_DECL_MAKE_INTEGER_SEQ_ID = 14, - - /// The internal '__NSConstantString' typedef. - PREDEF_DECL_CF_CONSTANT_STRING_ID = 15, - - /// The internal '__NSConstantString' tag type. - PREDEF_DECL_CF_CONSTANT_STRING_TAG_ID = 16, - - /// The internal '__type_pack_element' template. - PREDEF_DECL_TYPE_PACK_ELEMENT_ID = 17, -}; - -/// The number of declaration IDs that are predefined. -/// -/// For more information about predefined declarations, see the -/// \c PredefinedDeclIDs type and the PREDEF_DECL_*_ID constants. -const unsigned int NUM_PREDEF_DECL_IDS = 18; - /// Record of updates for a declaration that was modified after /// being deserialized. This can occur within DECLTYPES_BLOCK_ID. const unsigned int DECL_UPDATES = 49; @@ -2075,7 +1926,7 @@ enum StmtCode { STMT_OMP_TARGET_TEAMS_GENERIC_LOOP_DIRECTIVE, STMT_OMP_PARALLEL_GENERIC_LOOP_DIRECTIVE, STMT_OMP_TARGET_PARALLEL_GENERIC_LOOP_DIRECTIVE, - EXPR_OMP_ARRAY_SECTION, + EXPR_ARRAY_SECTION, EXPR_OMP_ARRAY_SHAPING, EXPR_OMP_ITERATOR, @@ -2132,7 +1983,7 @@ enum CleanupObjectKind { COK_Block, COK_CompoundLiteral }; /// Describes the categories of an Objective-C class. struct ObjCCategoriesInfo { // The ID of the definition - DeclID DefinitionID; + LocalDeclID DefinitionID; // Offset into the array of category lists. unsigned Offset; @@ -2231,27 +2082,6 @@ template <> struct DenseMapInfo { } }; -template <> struct DenseMapInfo { - using DeclID = clang::serialization::DeclID; - using GlobalDeclID = clang::serialization::GlobalDeclID; - - static GlobalDeclID getEmptyKey() { - return GlobalDeclID(DenseMapInfo::getEmptyKey()); - } - - static GlobalDeclID getTombstoneKey() { - return GlobalDeclID(DenseMapInfo::getTombstoneKey()); - } - - static unsigned getHashValue(const GlobalDeclID &Key) { - return DenseMapInfo::getHashValue(Key.get()); - } - - static bool isEqual(const GlobalDeclID &L, const GlobalDeclID &R) { - return L == R; - } -}; - } // namespace llvm #endif // LLVM_CLANG_SERIALIZATION_ASTBITCODES_H diff --git a/clang/include/clang/Serialization/ASTDeserializationListener.h b/clang/include/clang/Serialization/ASTDeserializationListener.h index f3a01a4b9731580c7b8e9eb056ea7ffc5cfa6af9..3ab7f1a91843b5c87afb91f64582323a3a107117 100644 --- a/clang/include/clang/Serialization/ASTDeserializationListener.h +++ b/clang/include/clang/Serialization/ASTDeserializationListener.h @@ -44,7 +44,7 @@ public: /// unqualified. virtual void TypeRead(serialization::TypeIdx Idx, QualType T) { } /// A decl was deserialized from the AST file. - virtual void DeclRead(serialization::DeclID ID, const Decl *D) { } + virtual void DeclRead(GlobalDeclID ID, const Decl *D) {} /// A selector was read from the AST file. virtual void SelectorRead(serialization::SelectorID iD, Selector Sel) {} /// A macro definition was read from the AST file. diff --git a/clang/include/clang/Serialization/ASTReader.h b/clang/include/clang/Serialization/ASTReader.h index ed917aa1642293154f6e61d42a9f44579cf15629..64f1ebc117b327047c942f164702cbeccfbc490d 100644 --- a/clang/include/clang/Serialization/ASTReader.h +++ b/clang/include/clang/Serialization/ASTReader.h @@ -501,10 +501,7 @@ private: /// = I + 1 has already been loaded. llvm::PagedVector DeclsLoaded; - static_assert(std::is_same_v); - - using GlobalDeclMapType = - ContinuousRangeMap; + using GlobalDeclMapType = ContinuousRangeMap; /// Mapping from global declaration IDs to the module in which the /// declaration resides. @@ -512,16 +509,15 @@ private: using FileOffset = std::pair; using FileOffsetsTy = SmallVector; - using DeclUpdateOffsetsMap = - llvm::DenseMap; + using DeclUpdateOffsetsMap = llvm::DenseMap; /// Declarations that have modifications residing in a later file /// in the chain. DeclUpdateOffsetsMap DeclUpdateOffsets; - using DelayedNamespaceOffsetMapTy = llvm::DenseMap< - serialization::GlobalDeclID, - std::pair>; + using DelayedNamespaceOffsetMapTy = + llvm::DenseMap>; /// Mapping from global declaration IDs to the lexical and visible block /// offset for delayed namespace in reduced BMI. @@ -535,13 +531,12 @@ private: struct PendingUpdateRecord { Decl *D; - serialization::GlobalDeclID ID; + GlobalDeclID ID; // Whether the declaration was just deserialized. bool JustLoaded; - PendingUpdateRecord(serialization::GlobalDeclID ID, Decl *D, - bool JustLoaded) + PendingUpdateRecord(GlobalDeclID ID, Decl *D, bool JustLoaded) : D(D), ID(ID), JustLoaded(JustLoaded) {} }; @@ -594,10 +589,10 @@ private: struct FileDeclsInfo { ModuleFile *Mod = nullptr; - ArrayRef Decls; + ArrayRef Decls; FileDeclsInfo() = default; - FileDeclsInfo(ModuleFile *Mod, ArrayRef Decls) + FileDeclsInfo(ModuleFile *Mod, ArrayRef Decls) : Mod(Mod), Decls(Decls) {} }; @@ -635,8 +630,7 @@ private: /// Updates to the visible declarations of declaration contexts that /// haven't been loaded yet. - llvm::DenseMap - PendingVisibleUpdates; + llvm::DenseMap PendingVisibleUpdates; /// The set of C++ or Objective-C classes that have forward /// declarations that have not yet been linked to their definitions. @@ -662,8 +656,7 @@ private: /// Read the record that describes the visible contents of a DC. bool ReadVisibleDeclContextStorage(ModuleFile &M, llvm::BitstreamCursor &Cursor, - uint64_t Offset, - serialization::GlobalDeclID ID); + uint64_t Offset, GlobalDeclID ID); /// A vector containing identifiers that have already been /// loaded. @@ -816,14 +809,14 @@ private: /// This contains the data loaded from all EAGERLY_DESERIALIZED_DECLS blocks /// in the chain. The referenced declarations are deserialized and passed to /// the consumer eagerly. - SmallVector EagerlyDeserializedDecls; + SmallVector EagerlyDeserializedDecls; /// The IDs of all tentative definitions stored in the chain. /// /// Sema keeps track of all tentative definitions in a TU because it has to /// complete them and pass them on to CodeGen. Thus, tentative definitions in /// the PCH chain must be eagerly deserialized. - SmallVector TentativeDefinitions; + SmallVector TentativeDefinitions; /// The IDs of all CXXRecordDecls stored in the chain whose VTables are /// used. @@ -831,7 +824,7 @@ private: /// CodeGen has to emit VTables for these records, so they have to be eagerly /// deserialized. struct VTableUse { - serialization::GlobalDeclID ID; + GlobalDeclID ID; SourceLocation::UIntTy RawLoc; bool Used; }; @@ -844,7 +837,7 @@ private: /// instantiation where the first value is the ID of the decl and the second /// is the instantiation location. struct PendingInstantiation { - serialization::GlobalDeclID ID; + GlobalDeclID ID; SourceLocation::UIntTy RawLoc; }; SmallVector PendingInstantiations; @@ -857,11 +850,11 @@ private: /// A snapshot of Sema's unused file-scoped variable tracking, for /// generating warnings. - SmallVector UnusedFileScopedDecls; + SmallVector UnusedFileScopedDecls; /// A list of all the delegating constructors we've seen, to diagnose /// cycles. - SmallVector DelegatingCtorDecls; + SmallVector DelegatingCtorDecls; /// Method selectors used in a @selector expression. Used for /// implementation of -Wselector. @@ -874,7 +867,7 @@ private: /// The IDs of type aliases for ext_vectors that exist in the chain. /// /// Used by Sema for finding sugared names for ext_vectors in diagnostics. - SmallVector ExtVectorDecls; + SmallVector ExtVectorDecls; //@} @@ -885,7 +878,7 @@ private: /// The IDs of all potentially unused typedef names in the chain. /// /// Sema tracks these to emit warnings. - SmallVector UnusedLocalTypedefNameCandidates; + SmallVector UnusedLocalTypedefNameCandidates; /// Our current depth in #pragma cuda force_host_device begin/end /// macros. @@ -894,7 +887,7 @@ private: /// The IDs of the declarations Sema stores directly. /// /// Sema tracks a few important decls, such as namespace std, directly. - SmallVector SemaDeclRefs; + SmallVector SemaDeclRefs; /// The IDs of the types ASTContext stores directly. /// @@ -905,7 +898,7 @@ private: /// /// The AST context tracks a few important decls, currently cudaConfigureCall, /// directly. - SmallVector CUDASpecialDeclRefs; + SmallVector CUDASpecialDeclRefs; /// The floating point pragma option settings. SmallVector FPPragmaOptions; @@ -954,12 +947,12 @@ private: llvm::DenseMap> OpenCLDeclExtMap; /// A list of the namespaces we've seen. - SmallVector KnownNamespaces; + SmallVector KnownNamespaces; /// A list of undefined decls with internal linkage followed by the /// SourceLocation of a matching ODR-use. struct UndefinedButUsedDecl { - serialization::GlobalDeclID ID; + GlobalDeclID ID; SourceLocation::UIntTy RawLoc; }; SmallVector UndefinedButUsed; @@ -974,8 +967,7 @@ private: /// The IDs of all decls to be checked for deferred diags. /// /// Sema tracks these to emit deferred diags. - llvm::SmallSetVector - DeclsToCheckForDeferredDiags; + llvm::SmallSetVector DeclsToCheckForDeferredDiags; private: struct ImportedSubmodule { @@ -1112,7 +1104,7 @@ private: /// /// The declarations on the identifier chain for these identifiers will be /// loaded once the recursive loading has completed. - llvm::MapVector> + llvm::MapVector> PendingIdentifierInfos; /// The set of lookup results that we have faked in order to support @@ -1157,8 +1149,8 @@ private: /// been loaded but its DeclContext was not set yet. struct PendingDeclContextInfo { Decl *D; - serialization::GlobalDeclID SemaDC; - serialization::GlobalDeclID LexicalDC; + GlobalDeclID SemaDC; + GlobalDeclID LexicalDC; }; /// The set of Decls that have been loaded but their DeclContexts are @@ -1239,8 +1231,7 @@ private: /// module is loaded. SmallVector ObjCClassesLoaded; - using KeyDeclsMap = - llvm::DenseMap>; + using KeyDeclsMap = llvm::DenseMap>; /// A mapping from canonical declarations to the set of global /// declaration IDs for key declaration that have been merged with that @@ -1449,7 +1440,7 @@ private: QualType readTypeRecord(unsigned Index); RecordLocation TypeCursorForIndex(unsigned Index); void LoadedDecl(unsigned Index, Decl *D); - Decl *ReadDeclRecord(serialization::GlobalDeclID ID); + Decl *ReadDeclRecord(GlobalDeclID ID); void markIncompleteDeclChain(Decl *D); /// Returns the most recent declaration of a declaration (which must be @@ -1457,11 +1448,10 @@ private: /// merged into its redecl chain. Decl *getMostRecentExistingDecl(Decl *D); - RecordLocation DeclCursorForID(serialization::GlobalDeclID ID, - SourceLocation &Location); + RecordLocation DeclCursorForID(GlobalDeclID ID, SourceLocation &Location); void loadDeclUpdateRecords(PendingUpdateRecord &Record); void loadPendingDeclChain(Decl *D, uint64_t LocalOffset); - void loadObjCCategories(serialization::GlobalDeclID ID, ObjCInterfaceDecl *D, + void loadObjCCategories(GlobalDeclID ID, ObjCInterfaceDecl *D, unsigned PreviousGeneration = 0); RecordLocation getLocalBitOffset(uint64_t GlobalOffset); @@ -1496,11 +1486,10 @@ private: unsigned ClientLoadCapabilities); public: - class ModuleDeclIterator - : public llvm::iterator_adaptor_base< - ModuleDeclIterator, const serialization::LocalDeclID *, - std::random_access_iterator_tag, const Decl *, ptrdiff_t, - const Decl *, const Decl *> { + class ModuleDeclIterator : public llvm::iterator_adaptor_base< + ModuleDeclIterator, const LocalDeclID *, + std::random_access_iterator_tag, const Decl *, + ptrdiff_t, const Decl *, const Decl *> { ASTReader *Reader = nullptr; ModuleFile *Mod = nullptr; @@ -1508,7 +1497,7 @@ public: ModuleDeclIterator() : iterator_adaptor_base(nullptr) {} ModuleDeclIterator(ASTReader *Reader, ModuleFile *Mod, - const serialization::LocalDeclID *Pos) + const LocalDeclID *Pos) : iterator_adaptor_base(Pos), Reader(Reader), Mod(Mod) {} value_type operator*() const { @@ -1536,9 +1525,8 @@ private: void pushExternalDeclIntoScope(NamedDecl *D, DeclarationName Name); - void addPendingDeclContextInfo(Decl *D, - serialization::GlobalDeclID SemaDC, - serialization::GlobalDeclID LexicalDC) { + void addPendingDeclContextInfo(Decl *D, GlobalDeclID SemaDC, + GlobalDeclID LexicalDC) { assert(D); PendingDeclContextInfo Info = { D, SemaDC, LexicalDC }; PendingDeclContextInfos.push_back(Info); @@ -1916,38 +1904,36 @@ public: /// Map from a local declaration ID within a given module to a /// global declaration ID. - serialization::GlobalDeclID - getGlobalDeclID(ModuleFile &F, serialization::LocalDeclID LocalID) const; + GlobalDeclID getGlobalDeclID(ModuleFile &F, LocalDeclID LocalID) const; /// Returns true if global DeclID \p ID originated from module \p M. - bool isDeclIDFromModule(serialization::GlobalDeclID ID, ModuleFile &M) const; + bool isDeclIDFromModule(GlobalDeclID ID, ModuleFile &M) const; /// Retrieve the module file that owns the given declaration, or NULL /// if the declaration is not from a module file. ModuleFile *getOwningModuleFile(const Decl *D); /// Returns the source location for the decl \p ID. - SourceLocation getSourceLocationForDeclID(serialization::GlobalDeclID ID); + SourceLocation getSourceLocationForDeclID(GlobalDeclID ID); /// Resolve a declaration ID into a declaration, potentially /// building a new declaration. - Decl *GetDecl(serialization::GlobalDeclID ID); - Decl *GetExternalDecl(Decl::DeclID ID) override; + Decl *GetDecl(GlobalDeclID ID); + Decl *GetExternalDecl(GlobalDeclID ID) override; /// Resolve a declaration ID into a declaration. Return 0 if it's not /// been loaded yet. - Decl *GetExistingDecl(serialization::GlobalDeclID ID); + Decl *GetExistingDecl(GlobalDeclID ID); /// Reads a declaration with the given local ID in the given module. - Decl *GetLocalDecl(ModuleFile &F, serialization::LocalDeclID LocalID) { + Decl *GetLocalDecl(ModuleFile &F, LocalDeclID LocalID) { return GetDecl(getGlobalDeclID(F, LocalID)); } /// Reads a declaration with the given local ID in the given module. /// /// \returns The requested declaration, casted to the given return type. - template - T *GetLocalDeclAs(ModuleFile &F, serialization::LocalDeclID LocalID) { + template T *GetLocalDeclAs(ModuleFile &F, LocalDeclID LocalID) { return cast_or_null(GetLocalDecl(F, LocalID)); } @@ -1956,16 +1942,15 @@ public: /// /// \returns the global ID of the given declaration as known in the given /// module file. - serialization::DeclID - mapGlobalIDToModuleFileGlobalID(ModuleFile &M, - serialization::GlobalDeclID GlobalID); + LocalDeclID mapGlobalIDToModuleFileGlobalID(ModuleFile &M, + GlobalDeclID GlobalID); /// Reads a declaration ID from the given position in a record in the /// given module. /// /// \returns The declaration ID read from the record, adjusted to a global ID. - serialization::GlobalDeclID - ReadDeclID(ModuleFile &F, const RecordData &Record, unsigned &Idx); + GlobalDeclID ReadDeclID(ModuleFile &F, const RecordData &Record, + unsigned &Idx); /// Reads a declaration from the given position in a record in the /// given module. @@ -2139,10 +2124,9 @@ public: void LoadSelector(Selector Sel); void SetIdentifierInfo(unsigned ID, IdentifierInfo *II); - void SetGloballyVisibleDecls( - IdentifierInfo *II, - const SmallVectorImpl &DeclIDs, - SmallVectorImpl *Decls = nullptr); + void SetGloballyVisibleDecls(IdentifierInfo *II, + const SmallVectorImpl &DeclIDs, + SmallVectorImpl *Decls = nullptr); /// Report a diagnostic. DiagnosticBuilder Diag(unsigned DiagID) const; @@ -2383,7 +2367,7 @@ public: // Contains the IDs for declarations that were requested before we have // access to a Sema object. - SmallVector PreloadedDeclIDs; + SmallVector PreloadedDeclIDs; /// Retrieve the semantic analysis object used to analyze the /// translation unit in which the precompiled header is being diff --git a/clang/include/clang/Serialization/ASTRecordReader.h b/clang/include/clang/Serialization/ASTRecordReader.h index 9eaf50a76d52f4c6f5ec33a65c4385855cda80c4..06b80f266a9441639796bea1f55b882fb46d4a0a 100644 --- a/clang/include/clang/Serialization/ASTRecordReader.h +++ b/clang/include/clang/Serialization/ASTRecordReader.h @@ -136,7 +136,7 @@ public: /// Reads a declaration with the given local ID in the given module. /// /// \returns The requested declaration, casted to the given return type. - template T *GetLocalDeclAs(serialization::LocalDeclID LocalID) { + template T *GetLocalDeclAs(LocalDeclID LocalID) { return cast_or_null(Reader->GetLocalDecl(*F, LocalID)); } @@ -182,9 +182,7 @@ public: /// Reads a declaration ID from the given position in this record. /// /// \returns The declaration ID read from the record, adjusted to a global ID. - serialization::GlobalDeclID readDeclID() { - return Reader->ReadDeclID(*F, Record, Idx); - } + GlobalDeclID readDeclID() { return Reader->ReadDeclID(*F, Record, Idx); } /// Reads a declaration from the given position in a record in the /// given module, advancing Idx. diff --git a/clang/include/clang/Serialization/ASTWriter.h b/clang/include/clang/Serialization/ASTWriter.h index 13b4ad4ad2953dba072d56eec9ff2c033cfb8a45..6c45b7348b8552c53a21eeff39f52e9f39edd687 100644 --- a/clang/include/clang/Serialization/ASTWriter.h +++ b/clang/include/clang/Serialization/ASTWriter.h @@ -212,10 +212,10 @@ private: llvm::SmallVector DelayedNamespace; /// The first ID number we can use for our own declarations. - serialization::DeclID FirstDeclID = serialization::NUM_PREDEF_DECL_IDS; + LocalDeclID FirstDeclID = LocalDeclID(clang::NUM_PREDEF_DECL_IDS); /// The decl ID that will be assigned to the next new decl. - serialization::DeclID NextDeclID = FirstDeclID; + LocalDeclID NextDeclID = FirstDeclID; /// Map that provides the ID numbers of each declaration within /// the output stream, as well as those deserialized from a chained PCH. @@ -223,7 +223,7 @@ private: /// The ID numbers of declarations are consecutive (in order of /// discovery) and start at 2. 1 is reserved for the translation /// unit, while 0 is reserved for NULL. - llvm::DenseMap DeclIDs; + llvm::DenseMap DeclIDs; /// Offset of each declaration in the bitstream, indexed by /// the declaration's ID. @@ -233,9 +233,8 @@ private: /// are relative to this value. uint64_t DeclTypesBlockStartOffset = 0; - /// Sorted (by file offset) vector of pairs of file offset/DeclID. - using LocDeclIDsTy = - SmallVector, 64>; + /// Sorted (by file offset) vector of pairs of file offset/LocalDeclID. + using LocDeclIDsTy = SmallVector, 64>; struct DeclIDInFileInfo { LocDeclIDsTy DeclIDs; @@ -250,7 +249,7 @@ private: /// that it contains. FileDeclIDsTy FileDeclIDs; - void associateDeclWithFile(const Decl *D, serialization::DeclID); + void associateDeclWithFile(const Decl *D, LocalDeclID); /// The first ID number we can use for our own types. serialization::TypeID FirstTypeID = serialization::NUM_PREDEF_TYPE_IDS; @@ -421,8 +420,8 @@ private: /// headers. The declarations themselves are stored as declaration /// IDs, since they will be written out to an EAGERLY_DESERIALIZED_DECLS /// record. - SmallVector EagerlyDeserializedDecls; - SmallVector ModularCodegenDecls; + RecordData EagerlyDeserializedDecls; + RecordData ModularCodegenDecls; /// DeclContexts that have received extensions since their serialized /// form. @@ -709,7 +708,7 @@ public: return false; auto I = DeclIDs.find(D); return (I == DeclIDs.end() || - I->second >= serialization::NUM_PREDEF_DECL_IDS); + I->second.get() >= clang::NUM_PREDEF_DECL_IDS); }; /// Emit a reference to a declaration. @@ -717,12 +716,13 @@ public: // Emit a reference to a declaration if the declaration was emitted. void AddEmittedDeclRef(const Decl *D, RecordDataImpl &Record); - /// Force a declaration to be emitted and get its ID. - serialization::DeclID GetDeclRef(const Decl *D); + /// Force a declaration to be emitted and get its local ID to the module file + /// been writing. + LocalDeclID GetDeclRef(const Decl *D); - /// Determine the declaration ID of an already-emitted + /// Determine the local declaration ID of an already-emitted /// declaration. - serialization::DeclID getDeclID(const Decl *D); + LocalDeclID getDeclID(const Decl *D); /// Whether or not the declaration got emitted. If not, it wouldn't be /// emitted. diff --git a/clang/include/clang/Serialization/ModuleFile.h b/clang/include/clang/Serialization/ModuleFile.h index 492c35dceb08d4f08b3ddbeab49b7976b4e1ecdb..25f644e76edb1a4ce15551aa81293e7a49df8821 100644 --- a/clang/include/clang/Serialization/ModuleFile.h +++ b/clang/include/clang/Serialization/ModuleFile.h @@ -474,7 +474,7 @@ public: llvm::DenseMap GlobalToLocalDeclIDs; /// Array of file-level DeclIDs sorted by file. - const serialization::LocalDeclID *FileSortedDecls = nullptr; + const LocalDeclID *FileSortedDecls = nullptr; unsigned NumFileSortedDecls = 0; /// Array of category list location information within this diff --git a/clang/include/clang/StaticAnalyzer/Core/PathSensitive/Store.h b/clang/include/clang/StaticAnalyzer/Core/PathSensitive/Store.h index fac0c04ae2caab5b1abae8d9cd6889dcbd343996..ef23b160a3c03291be9f5fcd7e97ecd0840dc368 100644 --- a/clang/include/clang/StaticAnalyzer/Core/PathSensitive/Store.h +++ b/clang/include/clang/StaticAnalyzer/Core/PathSensitive/Store.h @@ -225,15 +225,11 @@ public: /// invalidated. This should include any regions explicitly invalidated /// even if they do not currently have bindings. Pass \c NULL if this /// information will not be used. - virtual StoreRef invalidateRegions(Store store, - ArrayRef Values, - const Expr *E, unsigned Count, - const LocationContext *LCtx, - const CallEvent *Call, - InvalidatedSymbols &IS, - RegionAndSymbolInvalidationTraits &ITraits, - InvalidatedRegions *InvalidatedTopLevel, - InvalidatedRegions *Invalidated) = 0; + virtual StoreRef invalidateRegions( + Store store, ArrayRef Values, const Expr *Ex, unsigned Count, + const LocationContext *LCtx, const CallEvent *Call, + InvalidatedSymbols &IS, RegionAndSymbolInvalidationTraits &ITraits, + InvalidatedRegions *TopLevelRegions, InvalidatedRegions *Invalidated) = 0; /// enterStackFrame - Let the StoreManager to do something when execution /// engine is about to execute into a callee. diff --git a/clang/include/clang/Support/RISCVVIntrinsicUtils.h b/clang/include/clang/Support/RISCVVIntrinsicUtils.h index ef9d6c15724b68856f8ed99e7be0e4af4338da43..97493bae5656e90695f42a513ef27820d06e0453 100644 --- a/clang/include/clang/Support/RISCVVIntrinsicUtils.h +++ b/clang/include/clang/Support/RISCVVIntrinsicUtils.h @@ -502,7 +502,8 @@ enum RVVRequire : uint32_t { RVV_REQ_Zvksed = 1 << 14, RVV_REQ_Zvksh = 1 << 15, RVV_REQ_Zvfbfwma = 1 << 16, - RVV_REQ_Experimental = 1 << 17, + RVV_REQ_Zvfbfmin = 1 << 17, + RVV_REQ_Experimental = 1 << 18, LLVM_MARK_AS_BITMASK_ENUM(RVV_REQ_Experimental) }; diff --git a/clang/lib/AST/ASTContext.cpp b/clang/lib/AST/ASTContext.cpp index 0f894c623beeeaf44dc2a1e52ccd9dc48315830d..cbf4932aff9a6b9ad6f5b24e8d74d0aafa25f29f 100644 --- a/clang/lib/AST/ASTContext.cpp +++ b/clang/lib/AST/ASTContext.cpp @@ -1084,7 +1084,7 @@ void ASTContext::addModuleInitializer(Module *M, Decl *D) { } void ASTContext::addLazyModuleInitializers(Module *M, - ArrayRef IDs) { + ArrayRef IDs) { auto *&Inits = ModuleInitializers[M]; if (!Inits) Inits = new (*this) PerModuleInitializers; @@ -1321,16 +1321,14 @@ void ASTContext::InitBuiltinTypes(const TargetInfo &Target, // Placeholder type for OMP array sections. if (LangOpts.OpenMP) { - InitBuiltinType(OMPArraySectionTy, BuiltinType::OMPArraySection); + InitBuiltinType(ArraySectionTy, BuiltinType::ArraySection); InitBuiltinType(OMPArrayShapingTy, BuiltinType::OMPArrayShaping); InitBuiltinType(OMPIteratorTy, BuiltinType::OMPIterator); } - // Placeholder type for OpenACC array sections. - if (LangOpts.OpenACC) { - // FIXME: Once we implement OpenACC array sections in Sema, this will either - // be combined with the OpenMP type, or given its own type. In the meantime, - // just use the OpenMP type so that parsing can work. - InitBuiltinType(OMPArraySectionTy, BuiltinType::OMPArraySection); + // Placeholder type for OpenACC array sections, if we are ALSO in OMP mode, + // don't bother, as we're just using the same type as OMP. + if (LangOpts.OpenACC && !LangOpts.OpenMP) { + InitBuiltinType(ArraySectionTy, BuiltinType::ArraySection); } if (LangOpts.MatrixTypes) InitBuiltinType(IncompleteMatrixIdxTy, BuiltinType::IncompleteMatrixIdx); diff --git a/clang/lib/AST/ComputeDependence.cpp b/clang/lib/AST/ComputeDependence.cpp index 5ec3013fabba9ae4868d8faef7989a1ae0c648f0..bad8e75b2f878c25b47170ae6f31f3e11b8a098e 100644 --- a/clang/lib/AST/ComputeDependence.cpp +++ b/clang/lib/AST/ComputeDependence.cpp @@ -443,12 +443,17 @@ ExprDependence clang::computeDependence(ObjCIndirectCopyRestoreExpr *E) { return E->getSubExpr()->getDependence(); } -ExprDependence clang::computeDependence(OMPArraySectionExpr *E) { +ExprDependence clang::computeDependence(ArraySectionExpr *E) { auto D = E->getBase()->getDependence(); if (auto *LB = E->getLowerBound()) D |= LB->getDependence(); if (auto *Len = E->getLength()) D |= Len->getDependence(); + + if (E->isOMPArraySection()) { + if (auto *Stride = E->getStride()) + D |= Stride->getDependence(); + } return D; } diff --git a/clang/lib/AST/Decl.cpp b/clang/lib/AST/Decl.cpp index 474e0ccde5bbf793369028e9fee2a2d6660032f1..e7e95c16b6978637f1dbdeb57191ea59366b396f 100644 --- a/clang/lib/AST/Decl.cpp +++ b/clang/lib/AST/Decl.cpp @@ -2151,7 +2151,7 @@ VarDecl *VarDecl::Create(ASTContext &C, DeclContext *DC, SourceLocation StartL, return new (C, DC) VarDecl(Var, C, DC, StartL, IdL, Id, T, TInfo, S); } -VarDecl *VarDecl::CreateDeserialized(ASTContext &C, Decl::DeclID ID) { +VarDecl *VarDecl::CreateDeserialized(ASTContext &C, GlobalDeclID ID) { return new (C, ID) VarDecl(Var, C, nullptr, SourceLocation(), SourceLocation(), nullptr, QualType(), nullptr, SC_None); @@ -2929,7 +2929,7 @@ QualType ParmVarDecl::getOriginalType() const { return T; } -ParmVarDecl *ParmVarDecl::CreateDeserialized(ASTContext &C, Decl::DeclID ID) { +ParmVarDecl *ParmVarDecl::CreateDeserialized(ASTContext &C, GlobalDeclID ID) { return new (C, ID) ParmVarDecl(ParmVar, C, nullptr, SourceLocation(), SourceLocation(), nullptr, QualType(), nullptr, SC_None, nullptr); @@ -4553,7 +4553,7 @@ FieldDecl *FieldDecl::Create(const ASTContext &C, DeclContext *DC, BW, Mutable, InitStyle); } -FieldDecl *FieldDecl::CreateDeserialized(ASTContext &C, Decl::DeclID ID) { +FieldDecl *FieldDecl::CreateDeserialized(ASTContext &C, GlobalDeclID ID) { return new (C, ID) FieldDecl(Field, nullptr, SourceLocation(), SourceLocation(), nullptr, QualType(), nullptr, nullptr, false, ICIS_NoInit); @@ -4863,7 +4863,7 @@ EnumDecl *EnumDecl::Create(ASTContext &C, DeclContext *DC, return Enum; } -EnumDecl *EnumDecl::CreateDeserialized(ASTContext &C, Decl::DeclID ID) { +EnumDecl *EnumDecl::CreateDeserialized(ASTContext &C, GlobalDeclID ID) { EnumDecl *Enum = new (C, ID) EnumDecl(C, nullptr, SourceLocation(), SourceLocation(), nullptr, nullptr, false, false, false); @@ -5025,7 +5025,8 @@ RecordDecl *RecordDecl::Create(const ASTContext &C, TagKind TK, DeclContext *DC, return R; } -RecordDecl *RecordDecl::CreateDeserialized(const ASTContext &C, Decl::DeclID ID) { +RecordDecl *RecordDecl::CreateDeserialized(const ASTContext &C, + GlobalDeclID ID) { RecordDecl *R = new (C, ID) RecordDecl(Record, TagTypeKind::Struct, C, nullptr, SourceLocation(), SourceLocation(), nullptr, nullptr); @@ -5297,7 +5298,7 @@ PragmaCommentDecl *PragmaCommentDecl::Create(const ASTContext &C, } PragmaCommentDecl *PragmaCommentDecl::CreateDeserialized(ASTContext &C, - Decl::DeclID ID, + GlobalDeclID ID, unsigned ArgSize) { return new (C, ID, additionalSizeToAlloc(ArgSize + 1)) PragmaCommentDecl(nullptr, SourceLocation(), PCK_Unknown); @@ -5322,7 +5323,7 @@ PragmaDetectMismatchDecl::Create(const ASTContext &C, TranslationUnitDecl *DC, } PragmaDetectMismatchDecl * -PragmaDetectMismatchDecl::CreateDeserialized(ASTContext &C, Decl::DeclID ID, +PragmaDetectMismatchDecl::CreateDeserialized(ASTContext &C, GlobalDeclID ID, unsigned NameValueSize) { return new (C, ID, additionalSizeToAlloc(NameValueSize + 1)) PragmaDetectMismatchDecl(nullptr, SourceLocation(), 0); @@ -5349,7 +5350,7 @@ LabelDecl *LabelDecl::Create(ASTContext &C, DeclContext *DC, return new (C, DC) LabelDecl(DC, IdentL, II, nullptr, GnuLabelL); } -LabelDecl *LabelDecl::CreateDeserialized(ASTContext &C, Decl::DeclID ID) { +LabelDecl *LabelDecl::CreateDeserialized(ASTContext &C, GlobalDeclID ID) { return new (C, ID) LabelDecl(nullptr, SourceLocation(), nullptr, nullptr, SourceLocation()); } @@ -5390,7 +5391,7 @@ ImplicitParamDecl *ImplicitParamDecl::Create(ASTContext &C, QualType Type, } ImplicitParamDecl *ImplicitParamDecl::CreateDeserialized(ASTContext &C, - Decl::DeclID ID) { + GlobalDeclID ID) { return new (C, ID) ImplicitParamDecl(C, QualType(), ImplicitParamKind::Other); } @@ -5408,7 +5409,7 @@ FunctionDecl::Create(ASTContext &C, DeclContext *DC, SourceLocation StartLoc, return New; } -FunctionDecl *FunctionDecl::CreateDeserialized(ASTContext &C, Decl::DeclID ID) { +FunctionDecl *FunctionDecl::CreateDeserialized(ASTContext &C, GlobalDeclID ID) { return new (C, ID) FunctionDecl( Function, C, nullptr, SourceLocation(), DeclarationNameInfo(), QualType(), nullptr, SC_None, false, false, ConstexprSpecKind::Unspecified, nullptr); @@ -5418,7 +5419,7 @@ BlockDecl *BlockDecl::Create(ASTContext &C, DeclContext *DC, SourceLocation L) { return new (C, DC) BlockDecl(DC, L); } -BlockDecl *BlockDecl::CreateDeserialized(ASTContext &C, Decl::DeclID ID) { +BlockDecl *BlockDecl::CreateDeserialized(ASTContext &C, GlobalDeclID ID) { return new (C, ID) BlockDecl(nullptr, SourceLocation()); } @@ -5432,7 +5433,7 @@ CapturedDecl *CapturedDecl::Create(ASTContext &C, DeclContext *DC, CapturedDecl(DC, NumParams); } -CapturedDecl *CapturedDecl::CreateDeserialized(ASTContext &C, Decl::DeclID ID, +CapturedDecl *CapturedDecl::CreateDeserialized(ASTContext &C, GlobalDeclID ID, unsigned NumParams) { return new (C, ID, additionalSizeToAlloc(NumParams)) CapturedDecl(nullptr, NumParams); @@ -5458,8 +5459,8 @@ EnumConstantDecl *EnumConstantDecl::Create(ASTContext &C, EnumDecl *CD, return new (C, CD) EnumConstantDecl(C, CD, L, Id, T, E, V); } -EnumConstantDecl * -EnumConstantDecl::CreateDeserialized(ASTContext &C, Decl::DeclID ID) { +EnumConstantDecl *EnumConstantDecl::CreateDeserialized(ASTContext &C, + GlobalDeclID ID) { return new (C, ID) EnumConstantDecl(C, nullptr, SourceLocation(), nullptr, QualType(), nullptr, llvm::APSInt()); } @@ -5486,7 +5487,7 @@ IndirectFieldDecl::Create(ASTContext &C, DeclContext *DC, SourceLocation L, } IndirectFieldDecl *IndirectFieldDecl::CreateDeserialized(ASTContext &C, - Decl::DeclID ID) { + GlobalDeclID ID) { return new (C, ID) IndirectFieldDecl(C, nullptr, SourceLocation(), DeclarationName(), QualType(), std::nullopt); @@ -5547,7 +5548,7 @@ bool TypedefNameDecl::isTransparentTagSlow() const { return isTransparent; } -TypedefDecl *TypedefDecl::CreateDeserialized(ASTContext &C, Decl::DeclID ID) { +TypedefDecl *TypedefDecl::CreateDeserialized(ASTContext &C, GlobalDeclID ID) { return new (C, ID) TypedefDecl(C, nullptr, SourceLocation(), SourceLocation(), nullptr, nullptr); } @@ -5560,7 +5561,8 @@ TypeAliasDecl *TypeAliasDecl::Create(ASTContext &C, DeclContext *DC, return new (C, DC) TypeAliasDecl(C, DC, StartLoc, IdLoc, Id, TInfo); } -TypeAliasDecl *TypeAliasDecl::CreateDeserialized(ASTContext &C, Decl::DeclID ID) { +TypeAliasDecl *TypeAliasDecl::CreateDeserialized(ASTContext &C, + GlobalDeclID ID) { return new (C, ID) TypeAliasDecl(C, nullptr, SourceLocation(), SourceLocation(), nullptr, nullptr); } @@ -5591,7 +5593,7 @@ FileScopeAsmDecl *FileScopeAsmDecl::Create(ASTContext &C, DeclContext *DC, } FileScopeAsmDecl *FileScopeAsmDecl::CreateDeserialized(ASTContext &C, - Decl::DeclID ID) { + GlobalDeclID ID) { return new (C, ID) FileScopeAsmDecl(nullptr, nullptr, SourceLocation(), SourceLocation()); } @@ -5609,7 +5611,7 @@ TopLevelStmtDecl *TopLevelStmtDecl::Create(ASTContext &C, Stmt *Statement) { } TopLevelStmtDecl *TopLevelStmtDecl::CreateDeserialized(ASTContext &C, - Decl::DeclID ID) { + GlobalDeclID ID) { return new (C, ID) TopLevelStmtDecl(/*DC=*/nullptr, SourceLocation(), /*S=*/nullptr); } @@ -5630,7 +5632,7 @@ EmptyDecl *EmptyDecl::Create(ASTContext &C, DeclContext *DC, SourceLocation L) { return new (C, DC) EmptyDecl(DC, L); } -EmptyDecl *EmptyDecl::CreateDeserialized(ASTContext &C, Decl::DeclID ID) { +EmptyDecl *EmptyDecl::CreateDeserialized(ASTContext &C, GlobalDeclID ID) { return new (C, ID) EmptyDecl(nullptr, SourceLocation()); } @@ -5663,7 +5665,8 @@ HLSLBufferDecl *HLSLBufferDecl::Create(ASTContext &C, return Result; } -HLSLBufferDecl *HLSLBufferDecl::CreateDeserialized(ASTContext &C, Decl::DeclID ID) { +HLSLBufferDecl *HLSLBufferDecl::CreateDeserialized(ASTContext &C, + GlobalDeclID ID) { return new (C, ID) HLSLBufferDecl(nullptr, false, SourceLocation(), nullptr, SourceLocation(), SourceLocation()); } @@ -5719,7 +5722,7 @@ ImportDecl *ImportDecl::CreateImplicit(ASTContext &C, DeclContext *DC, return Import; } -ImportDecl *ImportDecl::CreateDeserialized(ASTContext &C, Decl::DeclID ID, +ImportDecl *ImportDecl::CreateDeserialized(ASTContext &C, GlobalDeclID ID, unsigned NumLocations) { return new (C, ID, additionalSizeToAlloc(NumLocations)) ImportDecl(EmptyShell()); @@ -5752,6 +5755,6 @@ ExportDecl *ExportDecl::Create(ASTContext &C, DeclContext *DC, return new (C, DC) ExportDecl(DC, ExportLoc); } -ExportDecl *ExportDecl::CreateDeserialized(ASTContext &C, Decl::DeclID ID) { +ExportDecl *ExportDecl::CreateDeserialized(ASTContext &C, GlobalDeclID ID) { return new (C, ID) ExportDecl(nullptr, SourceLocation()); } diff --git a/clang/lib/AST/DeclBase.cpp b/clang/lib/AST/DeclBase.cpp index 7cb6b31c541fd373662921cc8e46de533d9c16f7..c33babf8d1df3b2fd9580084ef6eb8c62ca208f2 100644 --- a/clang/lib/AST/DeclBase.cpp +++ b/clang/lib/AST/DeclBase.cpp @@ -71,7 +71,7 @@ void Decl::updateOutOfDate(IdentifierInfo &II) const { #include "clang/AST/DeclNodes.inc" void *Decl::operator new(std::size_t Size, const ASTContext &Context, - Decl::DeclID ID, std::size_t Extra) { + GlobalDeclID ID, std::size_t Extra) { // Allocate an extra 8 bytes worth of storage, which ensures that the // resulting pointer will still be 8-byte aligned. static_assert(sizeof(unsigned) * 2 >= alignof(Decl), @@ -85,7 +85,7 @@ void *Decl::operator new(std::size_t Size, const ASTContext &Context, PrefixPtr[0] = 0; // Store the global declaration ID in the second 4 bytes. - PrefixPtr[1] = ID; + PrefixPtr[1] = ID.get(); return Result; } diff --git a/clang/lib/AST/DeclCXX.cpp b/clang/lib/AST/DeclCXX.cpp index 426c5262051094b23d83023eacd2b0ac31abba65..75c441293d62e2038743e7b2f218c70082a5b665 100644 --- a/clang/lib/AST/DeclCXX.cpp +++ b/clang/lib/AST/DeclCXX.cpp @@ -57,7 +57,8 @@ using namespace clang; void AccessSpecDecl::anchor() {} -AccessSpecDecl *AccessSpecDecl::CreateDeserialized(ASTContext &C, Decl::DeclID ID) { +AccessSpecDecl *AccessSpecDecl::CreateDeserialized(ASTContext &C, + GlobalDeclID ID) { return new (C, ID) AccessSpecDecl(EmptyShell()); } @@ -68,7 +69,7 @@ void LazyASTUnresolvedSet::getFromExternalSource(ASTContext &C) const { for (ASTUnresolvedSet::iterator I = Impl.begin(); I != Impl.end(); ++I) I.setDecl(cast(Source->GetExternalDecl( - reinterpret_cast(I.getDecl()) >> 2))); + GlobalDeclID(reinterpret_cast(I.getDecl()) >> 2)))); Impl.Decls.setLazy(false); } @@ -160,8 +161,8 @@ CXXRecordDecl::CreateLambda(const ASTContext &C, DeclContext *DC, return R; } -CXXRecordDecl * -CXXRecordDecl::CreateDeserialized(const ASTContext &C, Decl::DeclID ID) { +CXXRecordDecl *CXXRecordDecl::CreateDeserialized(const ASTContext &C, + GlobalDeclID ID) { auto *R = new (C, ID) CXXRecordDecl(CXXRecord, TagTypeKind::Struct, C, nullptr, SourceLocation(), SourceLocation(), nullptr, nullptr); @@ -2162,8 +2163,8 @@ CXXDeductionGuideDecl *CXXDeductionGuideDecl::Create( TInfo, EndLocation, Ctor, Kind); } -CXXDeductionGuideDecl *CXXDeductionGuideDecl::CreateDeserialized(ASTContext &C, - Decl::DeclID ID) { +CXXDeductionGuideDecl * +CXXDeductionGuideDecl::CreateDeserialized(ASTContext &C, GlobalDeclID ID) { return new (C, ID) CXXDeductionGuideDecl( C, nullptr, SourceLocation(), ExplicitSpecifier(), DeclarationNameInfo(), QualType(), nullptr, SourceLocation(), nullptr, @@ -2175,8 +2176,8 @@ RequiresExprBodyDecl *RequiresExprBodyDecl::Create( return new (C, DC) RequiresExprBodyDecl(C, DC, StartLoc); } -RequiresExprBodyDecl *RequiresExprBodyDecl::CreateDeserialized(ASTContext &C, - Decl::DeclID ID) { +RequiresExprBodyDecl * +RequiresExprBodyDecl::CreateDeserialized(ASTContext &C, GlobalDeclID ID) { return new (C, ID) RequiresExprBodyDecl(C, nullptr, SourceLocation()); } @@ -2281,7 +2282,8 @@ CXXMethodDecl::Create(ASTContext &C, CXXRecordDecl *RD, SourceLocation StartLoc, isInline, ConstexprKind, EndLocation, TrailingRequiresClause); } -CXXMethodDecl *CXXMethodDecl::CreateDeserialized(ASTContext &C, Decl::DeclID ID) { +CXXMethodDecl *CXXMethodDecl::CreateDeserialized(ASTContext &C, + GlobalDeclID ID) { return new (C, ID) CXXMethodDecl( CXXMethod, C, nullptr, SourceLocation(), DeclarationNameInfo(), QualType(), nullptr, SC_None, false, false, @@ -2699,7 +2701,7 @@ CXXConstructorDecl::CXXConstructorDecl( void CXXConstructorDecl::anchor() {} CXXConstructorDecl *CXXConstructorDecl::CreateDeserialized(ASTContext &C, - Decl::DeclID ID, + GlobalDeclID ID, uint64_t AllocKind) { bool hasTrailingExplicit = static_cast(AllocKind & TAKHasTailExplicit); bool isInheritingConstructor = @@ -2845,8 +2847,8 @@ bool CXXConstructorDecl::isSpecializationCopyingObject() const { void CXXDestructorDecl::anchor() {} -CXXDestructorDecl * -CXXDestructorDecl::CreateDeserialized(ASTContext &C, Decl::DeclID ID) { +CXXDestructorDecl *CXXDestructorDecl::CreateDeserialized(ASTContext &C, + GlobalDeclID ID) { return new (C, ID) CXXDestructorDecl( C, nullptr, SourceLocation(), DeclarationNameInfo(), QualType(), nullptr, false, false, false, ConstexprSpecKind::Unspecified, nullptr); @@ -2877,8 +2879,8 @@ void CXXDestructorDecl::setOperatorDelete(FunctionDecl *OD, Expr *ThisArg) { void CXXConversionDecl::anchor() {} -CXXConversionDecl * -CXXConversionDecl::CreateDeserialized(ASTContext &C, Decl::DeclID ID) { +CXXConversionDecl *CXXConversionDecl::CreateDeserialized(ASTContext &C, + GlobalDeclID ID) { return new (C, ID) CXXConversionDecl( C, nullptr, SourceLocation(), DeclarationNameInfo(), QualType(), nullptr, false, false, ExplicitSpecifier(), ConstexprSpecKind::Unspecified, @@ -2924,7 +2926,7 @@ LinkageSpecDecl *LinkageSpecDecl::Create(ASTContext &C, DeclContext *DC, } LinkageSpecDecl *LinkageSpecDecl::CreateDeserialized(ASTContext &C, - Decl::DeclID ID) { + GlobalDeclID ID) { return new (C, ID) LinkageSpecDecl(nullptr, SourceLocation(), SourceLocation(), LinkageSpecLanguageIDs::C, false); @@ -2946,7 +2948,7 @@ UsingDirectiveDecl *UsingDirectiveDecl::Create(ASTContext &C, DeclContext *DC, } UsingDirectiveDecl *UsingDirectiveDecl::CreateDeserialized(ASTContext &C, - Decl::DeclID ID) { + GlobalDeclID ID) { return new (C, ID) UsingDirectiveDecl(nullptr, SourceLocation(), SourceLocation(), NestedNameSpecifierLoc(), @@ -2985,7 +2987,8 @@ NamespaceDecl *NamespaceDecl::Create(ASTContext &C, DeclContext *DC, NamespaceDecl(C, DC, Inline, StartLoc, IdLoc, Id, PrevDecl, Nested); } -NamespaceDecl *NamespaceDecl::CreateDeserialized(ASTContext &C, Decl::DeclID ID) { +NamespaceDecl *NamespaceDecl::CreateDeserialized(ASTContext &C, + GlobalDeclID ID) { return new (C, ID) NamespaceDecl(C, nullptr, false, SourceLocation(), SourceLocation(), nullptr, nullptr, false); } @@ -3046,8 +3049,8 @@ NamespaceAliasDecl *NamespaceAliasDecl::Create(ASTContext &C, DeclContext *DC, QualifierLoc, IdentLoc, Namespace); } -NamespaceAliasDecl * -NamespaceAliasDecl::CreateDeserialized(ASTContext &C, Decl::DeclID ID) { +NamespaceAliasDecl *NamespaceAliasDecl::CreateDeserialized(ASTContext &C, + GlobalDeclID ID) { return new (C, ID) NamespaceAliasDecl(C, nullptr, SourceLocation(), SourceLocation(), nullptr, NestedNameSpecifierLoc(), @@ -3102,8 +3105,8 @@ UsingShadowDecl::UsingShadowDecl(Kind K, ASTContext &C, EmptyShell Empty) : NamedDecl(K, nullptr, SourceLocation(), DeclarationName()), redeclarable_base(C) {} -UsingShadowDecl * -UsingShadowDecl::CreateDeserialized(ASTContext &C, Decl::DeclID ID) { +UsingShadowDecl *UsingShadowDecl::CreateDeserialized(ASTContext &C, + GlobalDeclID ID) { return new (C, ID) UsingShadowDecl(UsingShadow, C, EmptyShell()); } @@ -3126,7 +3129,7 @@ ConstructorUsingShadowDecl::Create(ASTContext &C, DeclContext *DC, } ConstructorUsingShadowDecl * -ConstructorUsingShadowDecl::CreateDeserialized(ASTContext &C, Decl::DeclID ID) { +ConstructorUsingShadowDecl::CreateDeserialized(ASTContext &C, GlobalDeclID ID) { return new (C, ID) ConstructorUsingShadowDecl(C, EmptyShell()); } @@ -3174,7 +3177,7 @@ UsingDecl *UsingDecl::Create(ASTContext &C, DeclContext *DC, SourceLocation UL, return new (C, DC) UsingDecl(DC, UL, QualifierLoc, NameInfo, HasTypename); } -UsingDecl *UsingDecl::CreateDeserialized(ASTContext &C, Decl::DeclID ID) { +UsingDecl *UsingDecl::CreateDeserialized(ASTContext &C, GlobalDeclID ID) { return new (C, ID) UsingDecl(nullptr, SourceLocation(), NestedNameSpecifierLoc(), DeclarationNameInfo(), false); @@ -3198,7 +3201,8 @@ UsingEnumDecl *UsingEnumDecl::Create(ASTContext &C, DeclContext *DC, UsingEnumDecl(DC, EnumType->getType()->getAsTagDecl()->getDeclName(), UL, EL, NL, EnumType); } -UsingEnumDecl *UsingEnumDecl::CreateDeserialized(ASTContext &C, Decl::DeclID ID) { +UsingEnumDecl *UsingEnumDecl::CreateDeserialized(ASTContext &C, + GlobalDeclID ID) { return new (C, ID) UsingEnumDecl(nullptr, DeclarationName(), SourceLocation(), SourceLocation(), SourceLocation(), nullptr); @@ -3217,7 +3221,7 @@ UsingPackDecl *UsingPackDecl::Create(ASTContext &C, DeclContext *DC, return new (C, DC, Extra) UsingPackDecl(DC, InstantiatedFrom, UsingDecls); } -UsingPackDecl *UsingPackDecl::CreateDeserialized(ASTContext &C, Decl::DeclID ID, +UsingPackDecl *UsingPackDecl::CreateDeserialized(ASTContext &C, GlobalDeclID ID, unsigned NumExpansions) { size_t Extra = additionalSizeToAlloc(NumExpansions); auto *Result = @@ -3243,7 +3247,7 @@ UnresolvedUsingValueDecl::Create(ASTContext &C, DeclContext *DC, } UnresolvedUsingValueDecl * -UnresolvedUsingValueDecl::CreateDeserialized(ASTContext &C, Decl::DeclID ID) { +UnresolvedUsingValueDecl::CreateDeserialized(ASTContext &C, GlobalDeclID ID) { return new (C, ID) UnresolvedUsingValueDecl(nullptr, QualType(), SourceLocation(), NestedNameSpecifierLoc(), @@ -3273,7 +3277,8 @@ UnresolvedUsingTypenameDecl::Create(ASTContext &C, DeclContext *DC, } UnresolvedUsingTypenameDecl * -UnresolvedUsingTypenameDecl::CreateDeserialized(ASTContext &C, Decl::DeclID ID) { +UnresolvedUsingTypenameDecl::CreateDeserialized(ASTContext &C, + GlobalDeclID ID) { return new (C, ID) UnresolvedUsingTypenameDecl( nullptr, SourceLocation(), SourceLocation(), NestedNameSpecifierLoc(), SourceLocation(), nullptr, SourceLocation()); @@ -3286,7 +3291,8 @@ UnresolvedUsingIfExistsDecl::Create(ASTContext &Ctx, DeclContext *DC, } UnresolvedUsingIfExistsDecl * -UnresolvedUsingIfExistsDecl::CreateDeserialized(ASTContext &Ctx, Decl::DeclID ID) { +UnresolvedUsingIfExistsDecl::CreateDeserialized(ASTContext &Ctx, + GlobalDeclID ID) { return new (Ctx, ID) UnresolvedUsingIfExistsDecl(nullptr, SourceLocation(), DeclarationName()); } @@ -3310,7 +3316,7 @@ StaticAssertDecl *StaticAssertDecl::Create(ASTContext &C, DeclContext *DC, } StaticAssertDecl *StaticAssertDecl::CreateDeserialized(ASTContext &C, - Decl::DeclID ID) { + GlobalDeclID ID) { return new (C, ID) StaticAssertDecl(nullptr, SourceLocation(), nullptr, nullptr, SourceLocation(), false); } @@ -3332,7 +3338,7 @@ BindingDecl *BindingDecl::Create(ASTContext &C, DeclContext *DC, return new (C, DC) BindingDecl(DC, IdLoc, Id); } -BindingDecl *BindingDecl::CreateDeserialized(ASTContext &C, Decl::DeclID ID) { +BindingDecl *BindingDecl::CreateDeserialized(ASTContext &C, GlobalDeclID ID) { return new (C, ID) BindingDecl(nullptr, SourceLocation(), nullptr); } @@ -3363,7 +3369,7 @@ DecompositionDecl *DecompositionDecl::Create(ASTContext &C, DeclContext *DC, } DecompositionDecl *DecompositionDecl::CreateDeserialized(ASTContext &C, - Decl::DeclID ID, + GlobalDeclID ID, unsigned NumBindings) { size_t Extra = additionalSizeToAlloc(NumBindings); auto *Result = new (C, ID, Extra) @@ -3402,7 +3408,7 @@ MSPropertyDecl *MSPropertyDecl::Create(ASTContext &C, DeclContext *DC, } MSPropertyDecl *MSPropertyDecl::CreateDeserialized(ASTContext &C, - Decl::DeclID ID) { + GlobalDeclID ID) { return new (C, ID) MSPropertyDecl(nullptr, SourceLocation(), DeclarationName(), QualType(), nullptr, SourceLocation(), nullptr, nullptr); @@ -3419,7 +3425,7 @@ MSGuidDecl *MSGuidDecl::Create(const ASTContext &C, QualType T, Parts P) { return new (C, DC) MSGuidDecl(DC, T, P); } -MSGuidDecl *MSGuidDecl::CreateDeserialized(ASTContext &C, Decl::DeclID ID) { +MSGuidDecl *MSGuidDecl::CreateDeserialized(ASTContext &C, GlobalDeclID ID) { return new (C, ID) MSGuidDecl(nullptr, QualType(), Parts()); } @@ -3529,7 +3535,7 @@ UnnamedGlobalConstantDecl::Create(const ASTContext &C, QualType T, } UnnamedGlobalConstantDecl * -UnnamedGlobalConstantDecl::CreateDeserialized(ASTContext &C, Decl::DeclID ID) { +UnnamedGlobalConstantDecl::CreateDeserialized(ASTContext &C, GlobalDeclID ID) { return new (C, ID) UnnamedGlobalConstantDecl(C, nullptr, QualType(), APValue()); } diff --git a/clang/lib/AST/DeclFriend.cpp b/clang/lib/AST/DeclFriend.cpp index 1fabf8aa80c2bdb66fca9e368f4d6f95a147038d..04b9b93699f36cebc9bfe7d72198eac8d03e09b4 100644 --- a/clang/lib/AST/DeclFriend.cpp +++ b/clang/lib/AST/DeclFriend.cpp @@ -62,7 +62,7 @@ FriendDecl *FriendDecl::Create(ASTContext &C, DeclContext *DC, return FD; } -FriendDecl *FriendDecl::CreateDeserialized(ASTContext &C, Decl::DeclID ID, +FriendDecl *FriendDecl::CreateDeserialized(ASTContext &C, GlobalDeclID ID, unsigned FriendTypeNumTPLists) { std::size_t Extra = additionalSizeToAlloc(FriendTypeNumTPLists); diff --git a/clang/lib/AST/DeclObjC.cpp b/clang/lib/AST/DeclObjC.cpp index d4275eea058212976f056a3f72874d144e15f11f..83062b0e68878d4e42d6b68d808e1e1eea852bc4 100644 --- a/clang/lib/AST/DeclObjC.cpp +++ b/clang/lib/AST/DeclObjC.cpp @@ -862,7 +862,8 @@ ObjCMethodDecl *ObjCMethodDecl::Create( isImplicitlyDeclared, isDefined, impControl, HasRelatedResultType); } -ObjCMethodDecl *ObjCMethodDecl::CreateDeserialized(ASTContext &C, Decl::DeclID ID) { +ObjCMethodDecl *ObjCMethodDecl::CreateDeserialized(ASTContext &C, + GlobalDeclID ID) { return new (C, ID) ObjCMethodDecl(SourceLocation(), SourceLocation(), Selector(), QualType(), nullptr, nullptr); } @@ -1486,7 +1487,7 @@ ObjCTypeParamDecl *ObjCTypeParamDecl::Create(ASTContext &ctx, DeclContext *dc, } ObjCTypeParamDecl *ObjCTypeParamDecl::CreateDeserialized(ASTContext &ctx, - Decl::DeclID ID) { + GlobalDeclID ID) { return new (ctx, ID) ObjCTypeParamDecl(ctx, nullptr, ObjCTypeParamVariance::Invariant, SourceLocation(), 0, SourceLocation(), @@ -1551,7 +1552,7 @@ ObjCInterfaceDecl *ObjCInterfaceDecl::Create( } ObjCInterfaceDecl *ObjCInterfaceDecl::CreateDeserialized(const ASTContext &C, - Decl::DeclID ID) { + GlobalDeclID ID) { auto *Result = new (C, ID) ObjCInterfaceDecl(C, nullptr, SourceLocation(), nullptr, nullptr, SourceLocation(), nullptr, false); @@ -1865,7 +1866,7 @@ ObjCIvarDecl *ObjCIvarDecl::Create(ASTContext &C, ObjCContainerDecl *DC, synthesized); } -ObjCIvarDecl *ObjCIvarDecl::CreateDeserialized(ASTContext &C, Decl::DeclID ID) { +ObjCIvarDecl *ObjCIvarDecl::CreateDeserialized(ASTContext &C, GlobalDeclID ID) { return new (C, ID) ObjCIvarDecl(nullptr, SourceLocation(), SourceLocation(), nullptr, QualType(), nullptr, ObjCIvarDecl::None, nullptr, false); @@ -1914,7 +1915,7 @@ ObjCAtDefsFieldDecl } ObjCAtDefsFieldDecl *ObjCAtDefsFieldDecl::CreateDeserialized(ASTContext &C, - Decl::DeclID ID) { + GlobalDeclID ID) { return new (C, ID) ObjCAtDefsFieldDecl(nullptr, SourceLocation(), SourceLocation(), nullptr, QualType(), nullptr); @@ -1949,7 +1950,7 @@ ObjCProtocolDecl *ObjCProtocolDecl::Create(ASTContext &C, DeclContext *DC, } ObjCProtocolDecl *ObjCProtocolDecl::CreateDeserialized(ASTContext &C, - Decl::DeclID ID) { + GlobalDeclID ID) { ObjCProtocolDecl *Result = new (C, ID) ObjCProtocolDecl(C, nullptr, nullptr, SourceLocation(), SourceLocation(), nullptr); @@ -2148,7 +2149,7 @@ ObjCCategoryDecl *ObjCCategoryDecl::Create( } ObjCCategoryDecl *ObjCCategoryDecl::CreateDeserialized(ASTContext &C, - Decl::DeclID ID) { + GlobalDeclID ID) { return new (C, ID) ObjCCategoryDecl(nullptr, SourceLocation(), SourceLocation(), SourceLocation(), nullptr, nullptr, nullptr); @@ -2188,8 +2189,8 @@ ObjCCategoryImplDecl *ObjCCategoryImplDecl::Create( atStartLoc, CategoryNameLoc); } -ObjCCategoryImplDecl *ObjCCategoryImplDecl::CreateDeserialized(ASTContext &C, - Decl::DeclID ID) { +ObjCCategoryImplDecl * +ObjCCategoryImplDecl::CreateDeserialized(ASTContext &C, GlobalDeclID ID) { return new (C, ID) ObjCCategoryImplDecl(nullptr, nullptr, nullptr, SourceLocation(), SourceLocation(), SourceLocation()); @@ -2296,7 +2297,7 @@ ObjCImplementationDecl::Create(ASTContext &C, DeclContext *DC, } ObjCImplementationDecl * -ObjCImplementationDecl::CreateDeserialized(ASTContext &C, Decl::DeclID ID) { +ObjCImplementationDecl::CreateDeserialized(ASTContext &C, GlobalDeclID ID) { return new (C, ID) ObjCImplementationDecl(nullptr, nullptr, nullptr, SourceLocation(), SourceLocation()); } @@ -2339,7 +2340,7 @@ ObjCCompatibleAliasDecl::Create(ASTContext &C, DeclContext *DC, } ObjCCompatibleAliasDecl * -ObjCCompatibleAliasDecl::CreateDeserialized(ASTContext &C, Decl::DeclID ID) { +ObjCCompatibleAliasDecl::CreateDeserialized(ASTContext &C, GlobalDeclID ID) { return new (C, ID) ObjCCompatibleAliasDecl(nullptr, SourceLocation(), nullptr, nullptr); } @@ -2360,7 +2361,7 @@ ObjCPropertyDecl::Create(ASTContext &C, DeclContext *DC, SourceLocation L, } ObjCPropertyDecl *ObjCPropertyDecl::CreateDeserialized(ASTContext &C, - Decl::DeclID ID) { + GlobalDeclID ID) { return new (C, ID) ObjCPropertyDecl(nullptr, SourceLocation(), nullptr, SourceLocation(), SourceLocation(), QualType(), nullptr, None); @@ -2392,8 +2393,8 @@ ObjCPropertyImplDecl *ObjCPropertyImplDecl::Create(ASTContext &C, ivarLoc); } -ObjCPropertyImplDecl *ObjCPropertyImplDecl::CreateDeserialized(ASTContext &C, - Decl::DeclID ID) { +ObjCPropertyImplDecl * +ObjCPropertyImplDecl::CreateDeserialized(ASTContext &C, GlobalDeclID ID) { return new (C, ID) ObjCPropertyImplDecl(nullptr, SourceLocation(), SourceLocation(), nullptr, Dynamic, nullptr, SourceLocation()); diff --git a/clang/lib/AST/DeclOpenMP.cpp b/clang/lib/AST/DeclOpenMP.cpp index b178a15aab5f282363b48a29bfa252c9c2a1783b..81ca48e60942d5a69c7d5a3f873459dae4a79afe 100644 --- a/clang/lib/AST/DeclOpenMP.cpp +++ b/clang/lib/AST/DeclOpenMP.cpp @@ -36,7 +36,7 @@ OMPThreadPrivateDecl *OMPThreadPrivateDecl::Create(ASTContext &C, } OMPThreadPrivateDecl *OMPThreadPrivateDecl::CreateDeserialized(ASTContext &C, - Decl::DeclID ID, + GlobalDeclID ID, unsigned N) { return OMPDeclarativeDirective::createEmptyDirective( C, ID, 0, N); @@ -63,7 +63,8 @@ OMPAllocateDecl *OMPAllocateDecl::Create(ASTContext &C, DeclContext *DC, return D; } -OMPAllocateDecl *OMPAllocateDecl::CreateDeserialized(ASTContext &C, Decl::DeclID ID, +OMPAllocateDecl *OMPAllocateDecl::CreateDeserialized(ASTContext &C, + GlobalDeclID ID, unsigned NVars, unsigned NClauses) { return OMPDeclarativeDirective::createEmptyDirective( @@ -89,7 +90,8 @@ OMPRequiresDecl *OMPRequiresDecl::Create(ASTContext &C, DeclContext *DC, L); } -OMPRequiresDecl *OMPRequiresDecl::CreateDeserialized(ASTContext &C, Decl::DeclID ID, +OMPRequiresDecl *OMPRequiresDecl::CreateDeserialized(ASTContext &C, + GlobalDeclID ID, unsigned N) { return OMPDeclarativeDirective::createEmptyDirective( C, ID, N, 0, SourceLocation()); @@ -117,7 +119,7 @@ OMPDeclareReductionDecl *OMPDeclareReductionDecl::Create( } OMPDeclareReductionDecl * -OMPDeclareReductionDecl::CreateDeserialized(ASTContext &C, Decl::DeclID ID) { +OMPDeclareReductionDecl::CreateDeserialized(ASTContext &C, GlobalDeclID ID) { return new (C, ID) OMPDeclareReductionDecl( OMPDeclareReduction, /*DC=*/nullptr, SourceLocation(), DeclarationName(), QualType(), /*PrevDeclInScope=*/nullptr); @@ -148,7 +150,7 @@ OMPDeclareMapperDecl *OMPDeclareMapperDecl::Create( } OMPDeclareMapperDecl *OMPDeclareMapperDecl::CreateDeserialized(ASTContext &C, - Decl::DeclID ID, + GlobalDeclID ID, unsigned N) { return OMPDeclarativeDirective::createEmptyDirective( C, ID, N, 1, SourceLocation(), DeclarationName(), QualType(), @@ -179,7 +181,7 @@ OMPCapturedExprDecl *OMPCapturedExprDecl::Create(ASTContext &C, DeclContext *DC, } OMPCapturedExprDecl *OMPCapturedExprDecl::CreateDeserialized(ASTContext &C, - Decl::DeclID ID) { + GlobalDeclID ID) { return new (C, ID) OMPCapturedExprDecl(C, nullptr, nullptr, QualType(), /*TInfo=*/nullptr, SourceLocation()); } diff --git a/clang/lib/AST/DeclTemplate.cpp b/clang/lib/AST/DeclTemplate.cpp index 67bb9e41e3e61e75d05baeeac4e102a9572a1de4..d27a30e0c5fce18b3c6d30e1fe10fd092e6cfed2 100644 --- a/clang/lib/AST/DeclTemplate.cpp +++ b/clang/lib/AST/DeclTemplate.cpp @@ -337,9 +337,10 @@ void RedeclarableTemplateDecl::loadLazySpecializationsImpl() const { CommonBase *CommonBasePtr = getMostRecentDecl()->getCommonPtr(); if (CommonBasePtr->LazySpecializations) { ASTContext &Context = getASTContext(); - Decl::DeclID *Specs = CommonBasePtr->LazySpecializations; + GlobalDeclID *Specs = CommonBasePtr->LazySpecializations; CommonBasePtr->LazySpecializations = nullptr; - for (uint32_t I = 0, N = *Specs++; I != N; ++I) + unsigned SpecSize = (*Specs++).get(); + for (unsigned I = 0; I != SpecSize; ++I) (void)Context.getExternalSource()->GetExternalDecl(Specs[I]); } } @@ -417,8 +418,8 @@ FunctionTemplateDecl::Create(ASTContext &C, DeclContext *DC, SourceLocation L, return TD; } -FunctionTemplateDecl *FunctionTemplateDecl::CreateDeserialized(ASTContext &C, - Decl::DeclID ID) { +FunctionTemplateDecl * +FunctionTemplateDecl::CreateDeserialized(ASTContext &C, GlobalDeclID ID) { return new (C, ID) FunctionTemplateDecl(C, nullptr, SourceLocation(), DeclarationName(), nullptr, nullptr); } @@ -503,7 +504,7 @@ ClassTemplateDecl *ClassTemplateDecl::Create(ASTContext &C, DeclContext *DC, } ClassTemplateDecl *ClassTemplateDecl::CreateDeserialized(ASTContext &C, - Decl::DeclID ID) { + GlobalDeclID ID) { return new (C, ID) ClassTemplateDecl(C, nullptr, SourceLocation(), DeclarationName(), nullptr, nullptr); } @@ -652,14 +653,14 @@ TemplateTypeParmDecl *TemplateTypeParmDecl::Create( } TemplateTypeParmDecl * -TemplateTypeParmDecl::CreateDeserialized(const ASTContext &C, Decl::DeclID ID) { +TemplateTypeParmDecl::CreateDeserialized(const ASTContext &C, GlobalDeclID ID) { return new (C, ID) TemplateTypeParmDecl(nullptr, SourceLocation(), SourceLocation(), nullptr, false, false, std::nullopt); } TemplateTypeParmDecl * -TemplateTypeParmDecl::CreateDeserialized(const ASTContext &C, Decl::DeclID ID, +TemplateTypeParmDecl::CreateDeserialized(const ASTContext &C, GlobalDeclID ID, bool HasTypeConstraint) { return new (C, ID, additionalSizeToAlloc(HasTypeConstraint ? 1 : 0)) @@ -759,7 +760,7 @@ NonTypeTemplateParmDecl *NonTypeTemplateParmDecl::Create( } NonTypeTemplateParmDecl * -NonTypeTemplateParmDecl::CreateDeserialized(ASTContext &C, Decl::DeclID ID, +NonTypeTemplateParmDecl::CreateDeserialized(ASTContext &C, GlobalDeclID ID, bool HasTypeConstraint) { return new (C, ID, additionalSizeToAlloc, @@ -770,7 +771,7 @@ NonTypeTemplateParmDecl::CreateDeserialized(ASTContext &C, Decl::DeclID ID, } NonTypeTemplateParmDecl * -NonTypeTemplateParmDecl::CreateDeserialized(ASTContext &C, Decl::DeclID ID, +NonTypeTemplateParmDecl::CreateDeserialized(ASTContext &C, GlobalDeclID ID, unsigned NumExpandedTypes, bool HasTypeConstraint) { auto *NTTP = @@ -836,13 +837,13 @@ TemplateTemplateParmDecl::Create(const ASTContext &C, DeclContext *DC, } TemplateTemplateParmDecl * -TemplateTemplateParmDecl::CreateDeserialized(ASTContext &C, Decl::DeclID ID) { +TemplateTemplateParmDecl::CreateDeserialized(ASTContext &C, GlobalDeclID ID) { return new (C, ID) TemplateTemplateParmDecl(nullptr, SourceLocation(), 0, 0, false, nullptr, false, nullptr); } TemplateTemplateParmDecl * -TemplateTemplateParmDecl::CreateDeserialized(ASTContext &C, Decl::DeclID ID, +TemplateTemplateParmDecl::CreateDeserialized(ASTContext &C, GlobalDeclID ID, unsigned NumExpansions) { auto *TTP = new (C, ID, additionalSizeToAlloc(NumExpansions)) @@ -949,7 +950,7 @@ ClassTemplateSpecializationDecl::Create(ASTContext &Context, TagKind TK, ClassTemplateSpecializationDecl * ClassTemplateSpecializationDecl::CreateDeserialized(ASTContext &C, - Decl::DeclID ID) { + GlobalDeclID ID) { auto *Result = new (C, ID) ClassTemplateSpecializationDecl(C, ClassTemplateSpecialization); Result->setMayHaveOutOfDateDef(false); @@ -1035,8 +1036,7 @@ ConceptDecl *ConceptDecl::Create(ASTContext &C, DeclContext *DC, return TD; } -ConceptDecl *ConceptDecl::CreateDeserialized(ASTContext &C, - Decl::DeclID ID) { +ConceptDecl *ConceptDecl::CreateDeserialized(ASTContext &C, GlobalDeclID ID) { ConceptDecl *Result = new (C, ID) ConceptDecl(nullptr, SourceLocation(), DeclarationName(), nullptr, nullptr); @@ -1070,7 +1070,7 @@ ImplicitConceptSpecializationDecl *ImplicitConceptSpecializationDecl::Create( ImplicitConceptSpecializationDecl * ImplicitConceptSpecializationDecl::CreateDeserialized( - const ASTContext &C, Decl::DeclID ID, unsigned NumTemplateArgs) { + const ASTContext &C, GlobalDeclID ID, unsigned NumTemplateArgs) { return new (C, ID, additionalSizeToAlloc(NumTemplateArgs)) ImplicitConceptSpecializationDecl(EmptyShell{}, NumTemplateArgs); } @@ -1133,7 +1133,7 @@ Create(ASTContext &Context, TagKind TK,DeclContext *DC, ClassTemplatePartialSpecializationDecl * ClassTemplatePartialSpecializationDecl::CreateDeserialized(ASTContext &C, - Decl::DeclID ID) { + GlobalDeclID ID) { auto *Result = new (C, ID) ClassTemplatePartialSpecializationDecl(C); Result->setMayHaveOutOfDateDef(false); return Result; @@ -1160,7 +1160,7 @@ FriendTemplateDecl::Create(ASTContext &Context, DeclContext *DC, } FriendTemplateDecl *FriendTemplateDecl::CreateDeserialized(ASTContext &C, - Decl::DeclID ID) { + GlobalDeclID ID) { return new (C, ID) FriendTemplateDecl(EmptyShell()); } @@ -1179,8 +1179,8 @@ TypeAliasTemplateDecl::Create(ASTContext &C, DeclContext *DC, SourceLocation L, return TD; } -TypeAliasTemplateDecl *TypeAliasTemplateDecl::CreateDeserialized(ASTContext &C, - Decl::DeclID ID) { +TypeAliasTemplateDecl * +TypeAliasTemplateDecl::CreateDeserialized(ASTContext &C, GlobalDeclID ID) { return new (C, ID) TypeAliasTemplateDecl(C, nullptr, SourceLocation(), DeclarationName(), nullptr, nullptr); } @@ -1218,7 +1218,7 @@ VarTemplateDecl *VarTemplateDecl::Create(ASTContext &C, DeclContext *DC, } VarTemplateDecl *VarTemplateDecl::CreateDeserialized(ASTContext &C, - Decl::DeclID ID) { + GlobalDeclID ID) { return new (C, ID) VarTemplateDecl(C, nullptr, SourceLocation(), DeclarationName(), nullptr, nullptr); } @@ -1340,7 +1340,8 @@ VarTemplateSpecializationDecl *VarTemplateSpecializationDecl::Create( } VarTemplateSpecializationDecl * -VarTemplateSpecializationDecl::CreateDeserialized(ASTContext &C, Decl::DeclID ID) { +VarTemplateSpecializationDecl::CreateDeserialized(ASTContext &C, + GlobalDeclID ID) { return new (C, ID) VarTemplateSpecializationDecl(VarTemplateSpecialization, C); } @@ -1432,7 +1433,7 @@ VarTemplatePartialSpecializationDecl::Create( VarTemplatePartialSpecializationDecl * VarTemplatePartialSpecializationDecl::CreateDeserialized(ASTContext &C, - Decl::DeclID ID) { + GlobalDeclID ID) { return new (C, ID) VarTemplatePartialSpecializationDecl(C); } @@ -1546,7 +1547,7 @@ TemplateParamObjectDecl *TemplateParamObjectDecl::Create(const ASTContext &C, } TemplateParamObjectDecl * -TemplateParamObjectDecl::CreateDeserialized(ASTContext &C, Decl::DeclID ID) { +TemplateParamObjectDecl::CreateDeserialized(ASTContext &C, GlobalDeclID ID) { auto *TPOD = new (C, ID) TemplateParamObjectDecl(nullptr, QualType(), APValue()); C.addDestruction(&TPOD->Value); return TPOD; diff --git a/clang/lib/AST/Expr.cpp b/clang/lib/AST/Expr.cpp index 9eec7edc9d1a3e16c02df045792be33f589f1011..63dcdb919c7117f1f727bf6ac020d6f400561af2 100644 --- a/clang/lib/AST/Expr.cpp +++ b/clang/lib/AST/Expr.cpp @@ -3680,7 +3680,7 @@ bool Expr::HasSideEffects(const ASTContext &Ctx, case ParenExprClass: case ArraySubscriptExprClass: case MatrixSubscriptExprClass: - case OMPArraySectionExprClass: + case ArraySectionExprClass: case OMPArrayShapingExprClass: case OMPIteratorExprClass: case MemberExprClass: @@ -5060,9 +5060,9 @@ QualType AtomicExpr::getValueType() const { return T; } -QualType OMPArraySectionExpr::getBaseOriginalType(const Expr *Base) { +QualType ArraySectionExpr::getBaseOriginalType(const Expr *Base) { unsigned ArraySectionCount = 0; - while (auto *OASE = dyn_cast(Base->IgnoreParens())) { + while (auto *OASE = dyn_cast(Base->IgnoreParens())) { Base = OASE->getBase(); ++ArraySectionCount; } diff --git a/clang/lib/AST/ExprClassification.cpp b/clang/lib/AST/ExprClassification.cpp index 7026fca8554ce9fa6b7f6cc6dd20f69e919fa153..2bb8f9aeedc7e245abdf1a2759bd336fc944d87a 100644 --- a/clang/lib/AST/ExprClassification.cpp +++ b/clang/lib/AST/ExprClassification.cpp @@ -145,7 +145,7 @@ static Cl::Kinds ClassifyInternal(ASTContext &Ctx, const Expr *E) { case Expr::FunctionParmPackExprClass: case Expr::MSPropertyRefExprClass: case Expr::MSPropertySubscriptExprClass: - case Expr::OMPArraySectionExprClass: + case Expr::ArraySectionExprClass: case Expr::OMPArrayShapingExprClass: case Expr::OMPIteratorExprClass: return Cl::CL_LValue; diff --git a/clang/lib/AST/ExprConstant.cpp b/clang/lib/AST/ExprConstant.cpp index de3c2a63913e94295d0a3007231b70e04c2318aa..ea3e7304a7423cfee4910724da431de9eab3c84c 100644 --- a/clang/lib/AST/ExprConstant.cpp +++ b/clang/lib/AST/ExprConstant.cpp @@ -16130,7 +16130,7 @@ static ICEDiag CheckICE(const Expr* E, const ASTContext &Ctx) { case Expr::StringLiteralClass: case Expr::ArraySubscriptExprClass: case Expr::MatrixSubscriptExprClass: - case Expr::OMPArraySectionExprClass: + case Expr::ArraySectionExprClass: case Expr::OMPArrayShapingExprClass: case Expr::OMPIteratorExprClass: case Expr::MemberExprClass: diff --git a/clang/lib/AST/ExternalASTSource.cpp b/clang/lib/AST/ExternalASTSource.cpp index 2e54d9f9af1c6d571c4f83566cb63f0ae7036d7c..e96a4749685115bd6d989d2ad07b159793ed5f62 100644 --- a/clang/lib/AST/ExternalASTSource.cpp +++ b/clang/lib/AST/ExternalASTSource.cpp @@ -68,7 +68,7 @@ bool ExternalASTSource::layoutRecordType( return false; } -Decl *ExternalASTSource::GetExternalDecl(Decl::DeclID ID) { return nullptr; } +Decl *ExternalASTSource::GetExternalDecl(GlobalDeclID ID) { return nullptr; } Selector ExternalASTSource::GetExternalSelector(uint32_t ID) { return Selector(); diff --git a/clang/lib/AST/Interp/ByteCodeExprGen.cpp b/clang/lib/AST/Interp/ByteCodeExprGen.cpp index 8cd0c198d9a844d6de48d284b4a4321bffbfd22a..588ffa55c11e614e0dc4ebb76eafaa234146f3c3 100644 --- a/clang/lib/AST/Interp/ByteCodeExprGen.cpp +++ b/clang/lib/AST/Interp/ByteCodeExprGen.cpp @@ -110,18 +110,37 @@ bool ByteCodeExprGen::VisitCastExpr(const CastExpr *CE) { if (!this->visit(SubExpr)) return false; - unsigned DerivedOffset = collectBaseOffset(getRecordTy(CE->getType()), - getRecordTy(SubExpr->getType())); + const auto extractRecordDecl = [](QualType Ty) -> const CXXRecordDecl * { + if (const auto *PT = dyn_cast(Ty)) + return PT->getPointeeType()->getAsCXXRecordDecl(); + return Ty->getAsCXXRecordDecl(); + }; + + // FIXME: We can express a series of non-virtual casts as a single + // GetPtrBasePop op. + QualType CurType = SubExpr->getType(); + for (const CXXBaseSpecifier *B : CE->path()) { + if (B->isVirtual()) { + if (!this->emitGetPtrVirtBasePop(extractRecordDecl(B->getType()), CE)) + return false; + CurType = B->getType(); + } else { + unsigned DerivedOffset = collectBaseOffset(B->getType(), CurType); + if (!this->emitGetPtrBasePop(DerivedOffset, CE)) + return false; + CurType = B->getType(); + } + } - return this->emitGetPtrBasePop(DerivedOffset, CE); + return true; } case CK_BaseToDerived: { if (!this->visit(SubExpr)) return false; - unsigned DerivedOffset = collectBaseOffset(getRecordTy(SubExpr->getType()), - getRecordTy(CE->getType())); + unsigned DerivedOffset = + collectBaseOffset(SubExpr->getType(), CE->getType()); return this->emitGetPtrDerivedPop(DerivedOffset, CE); } @@ -3529,35 +3548,17 @@ void ByteCodeExprGen::emitCleanup() { template unsigned -ByteCodeExprGen::collectBaseOffset(const RecordType *BaseType, - const RecordType *DerivedType) { - assert(BaseType); - assert(DerivedType); - const auto *FinalDecl = cast(BaseType->getDecl()); - const RecordDecl *CurDecl = DerivedType->getDecl(); - const Record *CurRecord = getRecord(CurDecl); - assert(CurDecl && FinalDecl); - - unsigned OffsetSum = 0; - for (;;) { - assert(CurRecord->getNumBases() > 0); - // One level up - for (const Record::Base &B : CurRecord->bases()) { - const auto *BaseDecl = cast(B.Decl); - - if (BaseDecl == FinalDecl || BaseDecl->isDerivedFrom(FinalDecl)) { - OffsetSum += B.Offset; - CurRecord = B.R; - CurDecl = BaseDecl; - break; - } - } - if (CurDecl == FinalDecl) - break; - } +ByteCodeExprGen::collectBaseOffset(const QualType BaseType, + const QualType DerivedType) { + const auto extractRecordDecl = [](QualType Ty) -> const CXXRecordDecl * { + if (const auto *PT = dyn_cast(Ty)) + return PT->getPointeeType()->getAsCXXRecordDecl(); + return Ty->getAsCXXRecordDecl(); + }; + const CXXRecordDecl *BaseDecl = extractRecordDecl(BaseType); + const CXXRecordDecl *DerivedDecl = extractRecordDecl(DerivedType); - assert(OffsetSum > 0); - return OffsetSum; + return Ctx.collectBaseOffset(BaseDecl, DerivedDecl); } /// Emit casts from a PrimType to another PrimType. diff --git a/clang/lib/AST/Interp/ByteCodeExprGen.h b/clang/lib/AST/Interp/ByteCodeExprGen.h index 7e9dc8631fc0d3aa4f428cf245bbf20269906a7f..4a57f76ae5b3729a7ec81e9b2f7665c2c09b76c1 100644 --- a/clang/lib/AST/Interp/ByteCodeExprGen.h +++ b/clang/lib/AST/Interp/ByteCodeExprGen.h @@ -283,8 +283,8 @@ private: bool emitRecordDestruction(const Record *R); bool emitDestruction(const Descriptor *Desc); - unsigned collectBaseOffset(const RecordType *BaseType, - const RecordType *DerivedType); + unsigned collectBaseOffset(const QualType BaseType, + const QualType DerivedType); protected: /// Variable to storage mapping. diff --git a/clang/lib/AST/Interp/ByteCodeStmtGen.cpp b/clang/lib/AST/Interp/ByteCodeStmtGen.cpp index 36dab6252ece67a4071ed3b338e28f9524a3db3e..ec2fe39a8aeae9faeca70bdae4a74b936571b49f 100644 --- a/clang/lib/AST/Interp/ByteCodeStmtGen.cpp +++ b/clang/lib/AST/Interp/ByteCodeStmtGen.cpp @@ -189,14 +189,23 @@ bool ByteCodeStmtGen::visitFunc(const FunctionDecl *F) { if (!emitFieldInitializer(F, F->Offset, InitExpr)) return false; } else if (const Type *Base = Init->getBaseClass()) { - // Base class initializer. - // Get This Base and call initializer on it. const auto *BaseDecl = Base->getAsCXXRecordDecl(); assert(BaseDecl); - const Record::Base *B = R->getBase(BaseDecl); - assert(B); - if (!this->emitGetPtrThisBase(B->Offset, InitExpr)) - return false; + + if (Init->isBaseVirtual()) { + assert(R->getVirtualBase(BaseDecl)); + if (!this->emitGetPtrThisVirtBase(BaseDecl, InitExpr)) + return false; + + } else { + // Base class initializer. + // Get This Base and call initializer on it. + const Record::Base *B = R->getBase(BaseDecl); + assert(B); + if (!this->emitGetPtrThisBase(B->Offset, InitExpr)) + return false; + } + if (!this->visitInitializer(InitExpr)) return false; if (!this->emitFinishInitPop(InitExpr)) diff --git a/clang/lib/AST/Interp/Context.cpp b/clang/lib/AST/Interp/Context.cpp index 274178837bf047d346ba7be09a6ac6ba159dbc92..d51a57e5e92eae17070b18116d16a1d59e9f486f 100644 --- a/clang/lib/AST/Interp/Context.cpp +++ b/clang/lib/AST/Interp/Context.cpp @@ -262,3 +262,36 @@ const Function *Context::getOrCreateFunction(const FunctionDecl *FD) { return Func; } + +unsigned Context::collectBaseOffset(const RecordDecl *BaseDecl, + const RecordDecl *DerivedDecl) const { + assert(BaseDecl); + assert(DerivedDecl); + const auto *FinalDecl = cast(BaseDecl); + const RecordDecl *CurDecl = DerivedDecl; + const Record *CurRecord = P->getOrCreateRecord(CurDecl); + assert(CurDecl && FinalDecl); + + unsigned OffsetSum = 0; + for (;;) { + assert(CurRecord->getNumBases() > 0); + // One level up + for (const Record::Base &B : CurRecord->bases()) { + const auto *BaseDecl = cast(B.Decl); + + if (BaseDecl == FinalDecl || BaseDecl->isDerivedFrom(FinalDecl)) { + OffsetSum += B.Offset; + CurRecord = B.R; + CurDecl = BaseDecl; + break; + } + } + if (CurDecl == FinalDecl) + break; + + // break; + } + + assert(OffsetSum > 0); + return OffsetSum; +} diff --git a/clang/lib/AST/Interp/Context.h b/clang/lib/AST/Interp/Context.h index 23c439ad8912a74839c8c93a788893247b913a15..360e9499d0844071e0ffe9b3c857c93a9800ada9 100644 --- a/clang/lib/AST/Interp/Context.h +++ b/clang/lib/AST/Interp/Context.h @@ -104,6 +104,9 @@ public: /// Returns the program. This is only needed for unittests. Program &getProgram() const { return *P.get(); } + unsigned collectBaseOffset(const RecordDecl *BaseDecl, + const RecordDecl *DerivedDecl) const; + private: /// Runs a function. bool Run(State &Parent, const Function *Func, APValue &Result); diff --git a/clang/lib/AST/Interp/Descriptor.cpp b/clang/lib/AST/Interp/Descriptor.cpp index a4ccc0236d292ce40665aaf2d37138e1e9831b86..954c58c8cb37162c1beb3335f39e9ac47baffc4c 100644 --- a/clang/lib/AST/Interp/Descriptor.cpp +++ b/clang/lib/AST/Interp/Descriptor.cpp @@ -136,28 +136,66 @@ static void moveArrayDesc(Block *B, const std::byte *Src, std::byte *Dst, } } +static void initField(Block *B, std::byte *Ptr, bool IsConst, bool IsMutable, + bool IsActive, const Descriptor *D, + unsigned FieldOffset) { + bool IsUnion = false; // FIXME + auto *Desc = reinterpret_cast(Ptr + FieldOffset) - 1; + Desc->Offset = FieldOffset; + Desc->Desc = D; + Desc->IsInitialized = D->IsArray; + Desc->IsBase = false; + Desc->IsActive = IsActive && !IsUnion; + Desc->IsConst = IsConst || D->IsConst; + Desc->IsFieldMutable = IsMutable || D->IsMutable; + + if (auto Fn = D->CtorFn) + Fn(B, Ptr + FieldOffset, Desc->IsConst, Desc->IsFieldMutable, + Desc->IsActive, D); +} + +static void initBase(Block *B, std::byte *Ptr, bool IsConst, bool IsMutable, + bool IsActive, const Descriptor *D, unsigned FieldOffset, + bool IsVirtualBase) { + assert(D); + assert(D->ElemRecord); + + bool IsUnion = D->ElemRecord->isUnion(); + auto *Desc = reinterpret_cast(Ptr + FieldOffset) - 1; + Desc->Offset = FieldOffset; + Desc->Desc = D; + Desc->IsInitialized = D->IsArray; + Desc->IsBase = true; + Desc->IsActive = IsActive && !IsUnion; + Desc->IsConst = IsConst || D->IsConst; + Desc->IsFieldMutable = IsMutable || D->IsMutable; + + for (const auto &V : D->ElemRecord->bases()) + initBase(B, Ptr + FieldOffset, IsConst, IsMutable, IsActive, V.Desc, + V.Offset, false); + for (const auto &F : D->ElemRecord->fields()) + initField(B, Ptr + FieldOffset, IsConst, IsMutable, IsActive, F.Desc, + F.Offset); + + // If this is initializing a virtual base, we do NOT want to consider its + // virtual bases, those are already flattened into the parent record when + // creating it. + if (IsVirtualBase) + return; + + for (const auto &V : D->ElemRecord->virtual_bases()) + initBase(B, Ptr + FieldOffset, IsConst, IsMutable, IsActive, V.Desc, + V.Offset, true); +} + static void ctorRecord(Block *B, std::byte *Ptr, bool IsConst, bool IsMutable, bool IsActive, const Descriptor *D) { - const bool IsUnion = D->ElemRecord->isUnion(); - auto CtorSub = [=](unsigned SubOff, const Descriptor *F, bool IsBase) { - auto *Desc = reinterpret_cast(Ptr + SubOff) - 1; - Desc->Offset = SubOff; - Desc->Desc = F; - Desc->IsInitialized = F->IsArray && !IsBase; - Desc->IsBase = IsBase; - Desc->IsActive = IsActive && !IsUnion; - Desc->IsConst = IsConst || F->IsConst; - Desc->IsFieldMutable = IsMutable || F->IsMutable; - if (auto Fn = F->CtorFn) - Fn(B, Ptr + SubOff, Desc->IsConst, Desc->IsFieldMutable, Desc->IsActive, - F); - }; - for (const auto &B : D->ElemRecord->bases()) - CtorSub(B.Offset, B.Desc, /*isBase=*/true); + for (const auto &V : D->ElemRecord->bases()) + initBase(B, Ptr, IsConst, IsMutable, IsActive, V.Desc, V.Offset, false); for (const auto &F : D->ElemRecord->fields()) - CtorSub(F.Offset, F.Desc, /*isBase=*/false); + initField(B, Ptr, IsConst, IsMutable, IsActive, F.Desc, F.Offset); for (const auto &V : D->ElemRecord->virtual_bases()) - CtorSub(V.Offset, V.Desc, /*isBase=*/true); + initBase(B, Ptr, IsConst, IsMutable, IsActive, V.Desc, V.Offset, true); } static void dtorRecord(Block *B, std::byte *Ptr, const Descriptor *D) { diff --git a/clang/lib/AST/Interp/Descriptor.h b/clang/lib/AST/Interp/Descriptor.h index c386fc8ac7b09d5030d1332e2d8dc227bba19a4c..cd20495c259c7d7e8db623aa014f59c79ec2ed5b 100644 --- a/clang/lib/AST/Interp/Descriptor.h +++ b/clang/lib/AST/Interp/Descriptor.h @@ -82,6 +82,9 @@ struct InlineDescriptor { InlineDescriptor(const Descriptor *D) : Offset(sizeof(InlineDescriptor)), IsConst(false), IsInitialized(false), IsBase(false), IsActive(false), IsFieldMutable(false), Desc(D) {} + + void dump() const { dump(llvm::errs()); } + void dump(llvm::raw_ostream &OS) const; }; /// Describes a memory block created by an allocation site. diff --git a/clang/lib/AST/Interp/Disasm.cpp b/clang/lib/AST/Interp/Disasm.cpp index d127f33223e802b993ac5ec5d8d37091f781008b..01cc88ea9a84593d0262cded21569169d5ebbce1 100644 --- a/clang/lib/AST/Interp/Disasm.cpp +++ b/clang/lib/AST/Interp/Disasm.cpp @@ -208,6 +208,25 @@ LLVM_DUMP_METHOD void Descriptor::dump(llvm::raw_ostream &OS) const { OS << " dummy"; } +LLVM_DUMP_METHOD void InlineDescriptor::dump(llvm::raw_ostream &OS) const { + { + ColorScope SC(OS, true, {llvm::raw_ostream::BLUE, true}); + OS << "InlineDescriptor " << (const void *)this << "\n"; + } + OS << "Offset: " << Offset << "\n"; + OS << "IsConst: " << IsConst << "\n"; + OS << "IsInitialized: " << IsInitialized << "\n"; + OS << "IsBase: " << IsBase << "\n"; + OS << "IsActive: " << IsActive << "\n"; + OS << "IsFieldMutable: " << IsFieldMutable << "\n"; + OS << "Desc: "; + if (Desc) + Desc->dump(OS); + else + OS << "nullptr"; + OS << "\n"; +} + LLVM_DUMP_METHOD void InterpFrame::dump(llvm::raw_ostream &OS, unsigned Indent) const { unsigned Spaces = Indent * 2; @@ -251,8 +270,6 @@ LLVM_DUMP_METHOD void Record::dump(llvm::raw_ostream &OS, unsigned Indentation, ++I; } - // FIXME: Virtual bases. - I = 0; for (const Record::Field &F : fields()) { OS.indent(Indent) << "- Field " << I << ": "; @@ -263,6 +280,14 @@ LLVM_DUMP_METHOD void Record::dump(llvm::raw_ostream &OS, unsigned Indentation, OS << ". Offset " << (Offset + F.Offset) << "\n"; ++I; } + + I = 0; + for (const Record::Base &B : virtual_bases()) { + OS.indent(Indent) << "- Virtual Base " << I << ". Offset " + << (Offset + B.Offset) << "\n"; + B.R->dump(OS, Indentation + 1, Offset + B.Offset); + ++I; + } } LLVM_DUMP_METHOD void Block::dump(llvm::raw_ostream &OS) const { diff --git a/clang/lib/AST/Interp/Interp.h b/clang/lib/AST/Interp/Interp.h index 9283f697c007098804c8486cc9f0c4d31635f846..9da0286deada175870c5174c940751af41b3d7f8 100644 --- a/clang/lib/AST/Interp/Interp.h +++ b/clang/lib/AST/Interp/Interp.h @@ -1355,20 +1355,26 @@ inline bool VirtBaseHelper(InterpState &S, CodePtr OpPC, const RecordDecl *Decl, while (Base.isBaseClass()) Base = Base.getBase(); - auto *Field = Base.getRecord()->getVirtualBase(Decl); - S.Stk.push(Base.atField(Field->Offset)); + const Record::Base *VirtBase = Base.getRecord()->getVirtualBase(Decl); + S.Stk.push(Base.atField(VirtBase->Offset)); return true; } -inline bool GetPtrVirtBase(InterpState &S, CodePtr OpPC, const RecordDecl *D) { +inline bool GetPtrVirtBasePop(InterpState &S, CodePtr OpPC, + const RecordDecl *D) { + assert(D); const Pointer &Ptr = S.Stk.pop(); if (!CheckNull(S, OpPC, Ptr, CSK_Base)) return false; + if (Ptr.isDummy()) // FIXME: Once we have type info for dummy pointers, this + // needs to go. + return false; return VirtBaseHelper(S, OpPC, D, Ptr); } inline bool GetPtrThisVirtBase(InterpState &S, CodePtr OpPC, const RecordDecl *D) { + assert(D); if (S.checkingPotentialConstantExpression()) return false; const Pointer &This = S.Current->getThis(); diff --git a/clang/lib/AST/Interp/Opcodes.td b/clang/lib/AST/Interp/Opcodes.td index 742785b28eb4d7131cd862b0dbad87a5495e75be..2a97b978b523251fa64c91c77310b5224681596b 100644 --- a/clang/lib/AST/Interp/Opcodes.td +++ b/clang/lib/AST/Interp/Opcodes.td @@ -336,7 +336,7 @@ def GetPtrDerivedPop : Opcode { } // [Pointer] -> [Pointer] -def GetPtrVirtBase : Opcode { +def GetPtrVirtBasePop : Opcode { // RecordDecl of base class. let Args = [ArgRecordDecl]; } diff --git a/clang/lib/AST/ItaniumMangle.cpp b/clang/lib/AST/ItaniumMangle.cpp index 106c69dd5beed718256fc003af4caee51f475909..ed9e6eeb36c75d1832a7b2cf3572baf0c6e700a0 100644 --- a/clang/lib/AST/ItaniumMangle.cpp +++ b/clang/lib/AST/ItaniumMangle.cpp @@ -4715,7 +4715,7 @@ recurse: case Expr::MSPropertySubscriptExprClass: case Expr::TypoExprClass: // This should no longer exist in the AST by now. case Expr::RecoveryExprClass: - case Expr::OMPArraySectionExprClass: + case Expr::ArraySectionExprClass: case Expr::OMPArrayShapingExprClass: case Expr::OMPIteratorExprClass: case Expr::CXXInheritedCtorInitExprClass: diff --git a/clang/lib/AST/NSAPI.cpp b/clang/lib/AST/NSAPI.cpp index ecc56c13fb757338751e5b7e60ae64d078924cb9..6f586173edb021ba365351eea9ffed220b7cf299 100644 --- a/clang/lib/AST/NSAPI.cpp +++ b/clang/lib/AST/NSAPI.cpp @@ -462,7 +462,7 @@ NSAPI::getNSNumberFactoryMethodKind(QualType T) const { case BuiltinType::PseudoObject: case BuiltinType::BuiltinFn: case BuiltinType::IncompleteMatrixIdx: - case BuiltinType::OMPArraySection: + case BuiltinType::ArraySection: case BuiltinType::OMPArrayShaping: case BuiltinType::OMPIterator: case BuiltinType::BFloat16: diff --git a/clang/lib/AST/StmtPrinter.cpp b/clang/lib/AST/StmtPrinter.cpp index 5855ab3141edcc7d89a27ca956a4e670e1f8c604..f010d36513a49e34bf6e7f4295bbb05a7bfb3577 100644 --- a/clang/lib/AST/StmtPrinter.cpp +++ b/clang/lib/AST/StmtPrinter.cpp @@ -1521,7 +1521,7 @@ void StmtPrinter::VisitMatrixSubscriptExpr(MatrixSubscriptExpr *Node) { OS << "]"; } -void StmtPrinter::VisitOMPArraySectionExpr(OMPArraySectionExpr *Node) { +void StmtPrinter::VisitArraySectionExpr(ArraySectionExpr *Node) { PrintExpr(Node->getBase()); OS << "["; if (Node->getLowerBound()) @@ -1531,7 +1531,7 @@ void StmtPrinter::VisitOMPArraySectionExpr(OMPArraySectionExpr *Node) { if (Node->getLength()) PrintExpr(Node->getLength()); } - if (Node->getColonLocSecond().isValid()) { + if (Node->isOMPArraySection() && Node->getColonLocSecond().isValid()) { OS << ":"; if (Node->getStride()) PrintExpr(Node->getStride()); diff --git a/clang/lib/AST/StmtProfile.cpp b/clang/lib/AST/StmtProfile.cpp index c81724f84dd9cee09aed44aa37b6819cd2d2b613..a95f5c6103e24dd49332611b32a44650fae7e303 100644 --- a/clang/lib/AST/StmtProfile.cpp +++ b/clang/lib/AST/StmtProfile.cpp @@ -1435,7 +1435,7 @@ void StmtProfiler::VisitMatrixSubscriptExpr(const MatrixSubscriptExpr *S) { VisitExpr(S); } -void StmtProfiler::VisitOMPArraySectionExpr(const OMPArraySectionExpr *S) { +void StmtProfiler::VisitArraySectionExpr(const ArraySectionExpr *S) { VisitExpr(S); } diff --git a/clang/lib/AST/Type.cpp b/clang/lib/AST/Type.cpp index cb22c91a12aa8911b9c487e7044f3032ef5c9654..8aaa6801d85b8b89cb81616de1fd754d8ec71eb7 100644 --- a/clang/lib/AST/Type.cpp +++ b/clang/lib/AST/Type.cpp @@ -3413,8 +3413,8 @@ StringRef BuiltinType::getName(const PrintingPolicy &Policy) const { return "reserve_id_t"; case IncompleteMatrixIdx: return ""; - case OMPArraySection: - return ""; + case ArraySection: + return ""; case OMPArrayShaping: return ""; case OMPIterator: @@ -4710,7 +4710,7 @@ bool Type::canHaveNullability(bool ResultIfUnknown) const { case BuiltinType::BuiltinFn: case BuiltinType::NullPtr: case BuiltinType::IncompleteMatrixIdx: - case BuiltinType::OMPArraySection: + case BuiltinType::ArraySection: case BuiltinType::OMPArrayShaping: case BuiltinType::OMPIterator: return false; diff --git a/clang/lib/AST/TypeLoc.cpp b/clang/lib/AST/TypeLoc.cpp index 21e152f6aea8a0e1cc03418c8a6e582b7dadafcf..ce45b47d5cfea5ea4395e7777f7da30d20bb39c7 100644 --- a/clang/lib/AST/TypeLoc.cpp +++ b/clang/lib/AST/TypeLoc.cpp @@ -429,7 +429,7 @@ TypeSpecifierType BuiltinTypeLoc::getWrittenTypeSpec() const { #include "clang/Basic/WebAssemblyReferenceTypes.def" case BuiltinType::BuiltinFn: case BuiltinType::IncompleteMatrixIdx: - case BuiltinType::OMPArraySection: + case BuiltinType::ArraySection: case BuiltinType::OMPArrayShaping: case BuiltinType::OMPIterator: return TST_unspecified; diff --git a/clang/lib/Analysis/FlowSensitive/ASTOps.cpp b/clang/lib/Analysis/FlowSensitive/ASTOps.cpp index 619bf772bba5eec46215759e62e197176e2d7718..bd1676583ecccdec2c1d262c4bba9c4d6e2878ae 100644 --- a/clang/lib/Analysis/FlowSensitive/ASTOps.cpp +++ b/clang/lib/Analysis/FlowSensitive/ASTOps.cpp @@ -33,12 +33,20 @@ namespace clang::dataflow { const Expr &ignoreCFGOmittedNodes(const Expr &E) { const Expr *Current = &E; - if (auto *EWC = dyn_cast(Current)) { - Current = EWC->getSubExpr(); + const Expr *Last = nullptr; + while (Current != Last) { + Last = Current; + if (auto *EWC = dyn_cast(Current)) { + Current = EWC->getSubExpr(); + assert(Current != nullptr); + } + if (auto *CE = dyn_cast(Current)) { + Current = CE->getSubExpr(); + assert(Current != nullptr); + } + Current = Current->IgnoreParens(); assert(Current != nullptr); } - Current = Current->IgnoreParens(); - assert(Current != nullptr); return *Current; } diff --git a/clang/lib/Analysis/FlowSensitive/DataflowEnvironment.cpp b/clang/lib/Analysis/FlowSensitive/DataflowEnvironment.cpp index 3cb656adcbdc0cfa5ba8fa15cc0223d1e03f1011..d79e734402892a65331ebac4208cef6c4518eb9f 100644 --- a/clang/lib/Analysis/FlowSensitive/DataflowEnvironment.cpp +++ b/clang/lib/Analysis/FlowSensitive/DataflowEnvironment.cpp @@ -157,7 +157,13 @@ static WidenResult widenDistinctValues(QualType Type, Value &Prev, Value &Current, Environment &CurrentEnv, Environment::ValueModel &Model) { // Boolean-model widening. - if (auto *PrevBool = dyn_cast(&Prev)) { + if (isa(Prev) && isa(Current)) { + // FIXME: Checking both values should be unnecessary, but we can currently + // end up with `BoolValue`s in integer-typed variables. See comment in + // `joinDistinctValues()` for details. + auto &PrevBool = cast(Prev); + auto &CurBool = cast(Current); + if (isa(Prev)) // Safe to return `Prev` here, because Top is never dependent on the // environment. @@ -166,13 +172,12 @@ static WidenResult widenDistinctValues(QualType Type, Value &Prev, // We may need to widen to Top, but before we do so, check whether both // values are implied to be either true or false in the current environment. // In that case, we can simply return a literal instead. - auto &CurBool = cast(Current); - bool TruePrev = PrevEnv.proves(PrevBool->formula()); + bool TruePrev = PrevEnv.proves(PrevBool.formula()); bool TrueCur = CurrentEnv.proves(CurBool.formula()); if (TruePrev && TrueCur) return {&CurrentEnv.getBoolLiteralValue(true), LatticeEffect::Unchanged}; if (!TruePrev && !TrueCur && - PrevEnv.proves(PrevEnv.arena().makeNot(PrevBool->formula())) && + PrevEnv.proves(PrevEnv.arena().makeNot(PrevBool.formula())) && CurrentEnv.proves(CurrentEnv.arena().makeNot(CurBool.formula()))) return {&CurrentEnv.getBoolLiteralValue(false), LatticeEffect::Unchanged}; @@ -333,6 +338,18 @@ public: } } + bool TraverseDecl(Decl *D) { + // Don't traverse nested record or function declarations. + // - We won't be analyzing code contained in these anyway + // - We don't model fields that are used only in these nested declaration, + // so trying to propagate a result object to initializers of such fields + // would cause an error. + if (isa_and_nonnull(D) || isa_and_nonnull(D)) + return true; + + return RecursiveASTVisitor::TraverseDecl(D); + } + bool TraverseBindingDecl(BindingDecl *BD) { // `RecursiveASTVisitor` doesn't traverse holding variables for // `BindingDecl`s by itself, so we need to tell it to. diff --git a/clang/lib/Analysis/FlowSensitive/Transfer.cpp b/clang/lib/Analysis/FlowSensitive/Transfer.cpp index 43fdfa5abcbb51fd3aaeb130156fc8fadc4be38b..fd224aeb79b15109c783484855809b8d963c05a9 100644 --- a/clang/lib/Analysis/FlowSensitive/Transfer.cpp +++ b/clang/lib/Analysis/FlowSensitive/Transfer.cpp @@ -41,7 +41,11 @@ namespace dataflow { const Environment *StmtToEnvMap::getEnvironment(const Stmt &S) const { auto BlockIt = ACFG.getStmtToBlock().find(&ignoreCFGOmittedNodes(S)); - assert(BlockIt != ACFG.getStmtToBlock().end()); + if (BlockIt == ACFG.getStmtToBlock().end()) { + assert(false); + // Return null to avoid dereferencing the end iterator in non-assert builds. + return nullptr; + } if (!ACFG.isBlockReachable(*BlockIt->getSecond())) return nullptr; if (BlockIt->getSecond()->getBlockID() == CurBlockID) diff --git a/clang/lib/Basic/FileManager.cpp b/clang/lib/Basic/FileManager.cpp index cd520a6375e07e5f0629dfeb0843f5d02d02444b..143c04309d0753d114c36120c689e4e6b7e36489 100644 --- a/clang/lib/Basic/FileManager.cpp +++ b/clang/lib/Basic/FileManager.cpp @@ -39,12 +39,6 @@ using namespace clang; #define DEBUG_TYPE "file-search" -ALWAYS_ENABLED_STATISTIC(NumDirLookups, "Number of directory lookups."); -ALWAYS_ENABLED_STATISTIC(NumFileLookups, "Number of file lookups."); -ALWAYS_ENABLED_STATISTIC(NumDirCacheMisses, - "Number of directory cache misses."); -ALWAYS_ENABLED_STATISTIC(NumFileCacheMisses, "Number of file cache misses."); - //===----------------------------------------------------------------------===// // Common logic. //===----------------------------------------------------------------------===// @@ -656,6 +650,14 @@ StringRef FileManager::getCanonicalName(const void *Entry, StringRef Name) { return CanonicalName; } +void FileManager::AddStats(const FileManager &Other) { + assert(&Other != this && "Collecting stats into the same FileManager"); + NumDirLookups += Other.NumDirLookups; + NumFileLookups += Other.NumFileLookups; + NumDirCacheMisses += Other.NumDirCacheMisses; + NumFileCacheMisses += Other.NumFileCacheMisses; +} + void FileManager::PrintStats() const { llvm::errs() << "\n*** File Manager Stats:\n"; llvm::errs() << UniqueRealFiles.size() << " real files found, " diff --git a/clang/lib/Basic/Targets/RISCV.h b/clang/lib/Basic/Targets/RISCV.h index 78580b5b1c1063cd5f39f44ca20dbafff121818a..9fa42e75bbfd147fcf73b9ef32c63eb70dfa97ed 100644 --- a/clang/lib/Basic/Targets/RISCV.h +++ b/clang/lib/Basic/Targets/RISCV.h @@ -16,7 +16,7 @@ #include "clang/Basic/TargetInfo.h" #include "clang/Basic/TargetOptions.h" #include "llvm/Support/Compiler.h" -#include "llvm/Support/RISCVISAInfo.h" +#include "llvm/TargetParser/RISCVISAInfo.h" #include "llvm/TargetParser/Triple.h" #include diff --git a/clang/lib/Basic/Targets/WebAssembly.cpp b/clang/lib/Basic/Targets/WebAssembly.cpp index f1c925d90cb649f562e54618d92b5c2c7ec57fc3..d473fd19086460ba508499e5bddad840a789912f 100644 --- a/clang/lib/Basic/Targets/WebAssembly.cpp +++ b/clang/lib/Basic/Targets/WebAssembly.cpp @@ -148,18 +148,18 @@ bool WebAssemblyTargetInfo::initFeatureMap( llvm::StringMap &Features, DiagnosticsEngine &Diags, StringRef CPU, const std::vector &FeaturesVec) const { if (CPU == "bleeding-edge") { - Features["nontrapping-fptoint"] = true; - Features["sign-ext"] = true; - Features["bulk-memory"] = true; Features["atomics"] = true; + Features["bulk-memory"] = true; + Features["multimemory"] = true; Features["mutable-globals"] = true; - Features["tail-call"] = true; + Features["nontrapping-fptoint"] = true; Features["reference-types"] = true; - Features["multimemory"] = true; + Features["sign-ext"] = true; + Features["tail-call"] = true; setSIMDLevel(Features, SIMD128, true); } else if (CPU == "generic") { - Features["sign-ext"] = true; Features["mutable-globals"] = true; + Features["sign-ext"] = true; } return TargetInfo::initFeatureMap(Features, Diags, CPU, FeaturesVec); diff --git a/clang/lib/CIR/CMakeLists.txt b/clang/lib/CIR/CMakeLists.txt index e69de29bb2d1d6434b8b29ae775ad8c2e48c5391..d2ff200e0da5f58fb304607c1fd9e568d6e3d7e2 100644 --- a/clang/lib/CIR/CMakeLists.txt +++ b/clang/lib/CIR/CMakeLists.txt @@ -0,0 +1,4 @@ +include_directories(${LLVM_MAIN_SRC_DIR}/../mlir/include) +include_directories(${CMAKE_BINARY_DIR}/tools/mlir/include) + +add_subdirectory(Dialect) diff --git a/clang/lib/CIR/Dialect/CMakeLists.txt b/clang/lib/CIR/Dialect/CMakeLists.txt new file mode 100644 index 0000000000000000000000000000000000000000..f33061b2d87cffc48b072763eb55d349e9070aba --- /dev/null +++ b/clang/lib/CIR/Dialect/CMakeLists.txt @@ -0,0 +1 @@ +add_subdirectory(IR) diff --git a/clang/lib/CIR/Dialect/IR/CIRDialect.cpp b/clang/lib/CIR/Dialect/IR/CIRDialect.cpp new file mode 100644 index 0000000000000000000000000000000000000000..c2829c3ff2af8cfcf29784ba48b65e3b20ffb142 --- /dev/null +++ b/clang/lib/CIR/Dialect/IR/CIRDialect.cpp @@ -0,0 +1,13 @@ +//===- CIRDialect.cpp - MLIR CIR ops implementation -----------------------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// +// +// This file implements the CIR dialect and its operations. +// +//===----------------------------------------------------------------------===// + +#include diff --git a/clang/lib/CIR/Dialect/IR/CMakeLists.txt b/clang/lib/CIR/Dialect/IR/CMakeLists.txt new file mode 100644 index 0000000000000000000000000000000000000000..0d7476b555705da5a565cb35427e1838f04ff84a --- /dev/null +++ b/clang/lib/CIR/Dialect/IR/CMakeLists.txt @@ -0,0 +1,3 @@ +add_clang_library(MLIRCIR + CIRDialect.cpp + ) diff --git a/clang/lib/CodeGen/CGBuiltin.cpp b/clang/lib/CodeGen/CGBuiltin.cpp index 7e5f2edfc732cce0c7d0cc309f94b69b71a61a76..d08ab5391489142031d839bd230bfe23023cdd8e 100644 --- a/clang/lib/CodeGen/CGBuiltin.cpp +++ b/clang/lib/CodeGen/CGBuiltin.cpp @@ -822,8 +822,9 @@ CodeGenFunction::evaluateOrEmitBuiltinObjectSize(const Expr *E, unsigned Type, return ConstantInt::get(ResType, ObjectSize, /*isSigned=*/true); } -const FieldDecl *CodeGenFunction::FindFlexibleArrayMemberField( - ASTContext &Ctx, const RecordDecl *RD, StringRef Name, uint64_t &Offset) { +const FieldDecl *CodeGenFunction::FindFlexibleArrayMemberFieldAndOffset( + ASTContext &Ctx, const RecordDecl *RD, const FieldDecl *FAMDecl, + uint64_t &Offset) { const LangOptions::StrictFlexArraysLevelKind StrictFlexArraysLevel = getLangOpts().getStrictFlexArraysLevel(); uint32_t FieldNo = 0; @@ -832,7 +833,7 @@ const FieldDecl *CodeGenFunction::FindFlexibleArrayMemberField( return nullptr; for (const FieldDecl *FD : RD->fields()) { - if ((Name.empty() || FD->getNameAsString() == Name) && + if ((!FAMDecl || FD == FAMDecl) && Decl::isFlexibleArrayMemberLike( Ctx, FD, FD->getType(), StrictFlexArraysLevel, /*IgnoreTemplateOrMacroSubstitution=*/true)) { @@ -843,8 +844,8 @@ const FieldDecl *CodeGenFunction::FindFlexibleArrayMemberField( QualType Ty = FD->getType(); if (Ty->isRecordType()) { - if (const FieldDecl *Field = FindFlexibleArrayMemberField( - Ctx, Ty->getAsRecordDecl(), Name, Offset)) { + if (const FieldDecl *Field = FindFlexibleArrayMemberFieldAndOffset( + Ctx, Ty->getAsRecordDecl(), FAMDecl, Offset)) { const ASTRecordLayout &Layout = Ctx.getASTRecordLayout(RD); Offset += Layout.getFieldOffset(FieldNo); return Field; @@ -930,12 +931,14 @@ CodeGenFunction::emitFlexibleArrayMemberSize(const Expr *E, unsigned Type, // Get the flexible array member Decl. const RecordDecl *OuterRD = nullptr; - std::string FAMName; + const FieldDecl *FAMDecl = nullptr; if (const auto *ME = dyn_cast(Base)) { // Check if \p Base is referencing the FAM itself. const ValueDecl *VD = ME->getMemberDecl(); OuterRD = VD->getDeclContext()->getOuterLexicalRecordContext(); - FAMName = VD->getNameAsString(); + FAMDecl = dyn_cast(VD); + if (!FAMDecl) + return nullptr; } else if (const auto *DRE = dyn_cast(Base)) { // Check if we're pointing to the whole struct. QualType Ty = DRE->getDecl()->getType(); @@ -974,9 +977,11 @@ CodeGenFunction::emitFlexibleArrayMemberSize(const Expr *E, unsigned Type, if (!OuterRD) return nullptr; + // We call FindFlexibleArrayMemberAndOffset even if FAMDecl is non-null to + // get its offset. uint64_t Offset = 0; - const FieldDecl *FAMDecl = - FindFlexibleArrayMemberField(Ctx, OuterRD, FAMName, Offset); + FAMDecl = + FindFlexibleArrayMemberFieldAndOffset(Ctx, OuterRD, FAMDecl, Offset); Offset = Ctx.toCharUnitsFromBits(Offset).getQuantity(); if (!FAMDecl || !FAMDecl->getType()->isCountAttributedType()) @@ -3623,7 +3628,7 @@ RValue CodeGenFunction::EmitBuiltinExpr(const GlobalDecl GD, unsigned BuiltinID, // frexpl instead of legalizing this type in the BE. if (&getTarget().getLongDoubleFormat() == &llvm::APFloat::PPCDoubleDouble()) break; - LLVM_FALLTHROUGH; + [[fallthrough]]; } case Builtin::BI__builtin_frexp: case Builtin::BI__builtin_frexpf: @@ -5361,7 +5366,7 @@ RValue CodeGenFunction::EmitBuiltinExpr(const GlobalDecl GD, unsigned BuiltinID, case Builtin::BI__builtin_ptrauth_auth_and_resign: if (Args[4]->getType()->isPointerTy()) Args[4] = Builder.CreatePtrToInt(Args[4], IntPtrTy); - LLVM_FALLTHROUGH; + [[fallthrough]]; case Builtin::BI__builtin_ptrauth_auth: case Builtin::BI__builtin_ptrauth_sign_unauthenticated: @@ -18845,7 +18850,7 @@ Value *CodeGenFunction::EmitAMDGPUBuiltinExpr(unsigned BuiltinID, case AMDGPU::BI__builtin_amdgcn_wmma_f16_16x16x16_f16_w32_gfx12: case AMDGPU::BI__builtin_amdgcn_wmma_f16_16x16x16_f16_w64_gfx12: AppendFalseForOpselArg = true; - LLVM_FALLTHROUGH; + [[fallthrough]]; case AMDGPU::BI__builtin_amdgcn_wmma_f16_16x16x16_f16_w32: case AMDGPU::BI__builtin_amdgcn_wmma_f16_16x16x16_f16_w64: ArgsForMatchingMatrixTypes = {2, 0}; // CD, AB @@ -18854,7 +18859,7 @@ Value *CodeGenFunction::EmitAMDGPUBuiltinExpr(unsigned BuiltinID, case AMDGPU::BI__builtin_amdgcn_wmma_bf16_16x16x16_bf16_w32_gfx12: case AMDGPU::BI__builtin_amdgcn_wmma_bf16_16x16x16_bf16_w64_gfx12: AppendFalseForOpselArg = true; - LLVM_FALLTHROUGH; + [[fallthrough]]; case AMDGPU::BI__builtin_amdgcn_wmma_bf16_16x16x16_bf16_w32: case AMDGPU::BI__builtin_amdgcn_wmma_bf16_16x16x16_bf16_w64: ArgsForMatchingMatrixTypes = {2, 0}; // CD, AB diff --git a/clang/lib/CodeGen/CGCall.cpp b/clang/lib/CodeGen/CGCall.cpp index 6c33cc17621f8961ae4cbfb7c3500a9f67e7ed0d..d2d92140b6b2a33e6376c265051b065f0e59f8c2 100644 --- a/clang/lib/CodeGen/CGCall.cpp +++ b/clang/lib/CodeGen/CGCall.cpp @@ -1585,6 +1585,11 @@ bool CodeGenModule::ReturnTypeUsesSRet(const CGFunctionInfo &FI) { return RI.isIndirect() || (RI.isInAlloca() && RI.getInAllocaSRet()); } +bool CodeGenModule::ReturnTypeHasInReg(const CGFunctionInfo &FI) { + const auto &RI = FI.getReturnInfo(); + return RI.getInReg(); +} + bool CodeGenModule::ReturnSlotInterferesWithArgs(const CGFunctionInfo &FI) { return ReturnTypeUsesSRet(FI) && getTargetCodeGenInfo().doesReturnSlotInterfereWithArgs(); diff --git a/clang/lib/CodeGen/CGCoroutine.cpp b/clang/lib/CodeGen/CGCoroutine.cpp index 93ca711f716fce5bec80f56f81e0f3749de5d3f8..567e85a02dc6126fdbf990b50e43743779b2a19e 100644 --- a/clang/lib/CodeGen/CGCoroutine.cpp +++ b/clang/lib/CodeGen/CGCoroutine.cpp @@ -413,10 +413,8 @@ llvm::Function * CodeGenFunction::generateAwaitSuspendWrapper(Twine const &CoroName, Twine const &SuspendPointName, CoroutineSuspendExpr const &S) { - std::string FuncName = "__await_suspend_wrapper_"; - FuncName += CoroName.str(); - FuncName += '_'; - FuncName += SuspendPointName.str(); + std::string FuncName = + (CoroName + ".__await_suspend_wrapper__" + SuspendPointName).str(); ASTContext &C = getContext(); diff --git a/clang/lib/CodeGen/CGDebugInfo.cpp b/clang/lib/CodeGen/CGDebugInfo.cpp index 539ded5cca5e1b406df7b1c860501d50620b686a..787db350487417c0013c42e0f4625968a677105b 100644 --- a/clang/lib/CodeGen/CGDebugInfo.cpp +++ b/clang/lib/CodeGen/CGDebugInfo.cpp @@ -1372,7 +1372,26 @@ llvm::DIType *CGDebugInfo::CreateType(const TemplateSpecializationType *Ty, SourceLocation Loc = AliasDecl->getLocation(); - if (CGM.getCodeGenOpts().DebugTemplateAlias) { + if (CGM.getCodeGenOpts().DebugTemplateAlias && + // The TemplateSpecializationType doesn't contain any instantiation + // information; dependent template arguments can't be resolved. For now, + // fall back to DW_TAG_typedefs for template aliases that are + // instantiation dependent, e.g.: + // ``` + // template + // using A = int; + // + // template + // struct S { + // using AA = A; // Instantiation dependent. + // AA aa; + // }; + // + // S<0> s; + // ``` + // S::AA's underlying type A is dependent on I so will be emitted as a + // DW_TAG_typedef. + !Ty->isInstantiationDependentType()) { auto ArgVector = ::GetTemplateArgs(TD, Ty); TemplateArgs Args = {TD->getTemplateParameters(), ArgVector}; diff --git a/clang/lib/CodeGen/CGExpr.cpp b/clang/lib/CodeGen/CGExpr.cpp index 931cb391342ea236224fbd9ba85a05edd356c09f..c94322f51e46cfa71e9310bfd69aac7ed2b25a68 100644 --- a/clang/lib/CodeGen/CGExpr.cpp +++ b/clang/lib/CodeGen/CGExpr.cpp @@ -1621,8 +1621,8 @@ LValue CodeGenFunction::EmitLValueHelper(const Expr *E, return EmitArraySubscriptExpr(cast(E)); case Expr::MatrixSubscriptExprClass: return EmitMatrixSubscriptExpr(cast(E)); - case Expr::OMPArraySectionExprClass: - return EmitOMPArraySectionExpr(cast(E)); + case Expr::ArraySectionExprClass: + return EmitArraySectionExpr(cast(E)); case Expr::ExtVectorElementExprClass: return EmitExtVectorElementExpr(cast(E)); case Expr::CXXThisExprClass: @@ -4363,8 +4363,8 @@ static Address emitOMPArraySectionBase(CodeGenFunction &CGF, const Expr *Base, QualType BaseTy, QualType ElTy, bool IsLowerBound) { LValue BaseLVal; - if (auto *ASE = dyn_cast(Base->IgnoreParenImpCasts())) { - BaseLVal = CGF.EmitOMPArraySectionExpr(ASE, IsLowerBound); + if (auto *ASE = dyn_cast(Base->IgnoreParenImpCasts())) { + BaseLVal = CGF.EmitArraySectionExpr(ASE, IsLowerBound); if (BaseTy->isArrayType()) { Address Addr = BaseLVal.getAddress(CGF); BaseInfo = BaseLVal.getBaseInfo(); @@ -4396,9 +4396,13 @@ static Address emitOMPArraySectionBase(CodeGenFunction &CGF, const Expr *Base, return CGF.EmitPointerWithAlignment(Base, &BaseInfo, &TBAAInfo); } -LValue CodeGenFunction::EmitOMPArraySectionExpr(const OMPArraySectionExpr *E, - bool IsLowerBound) { - QualType BaseTy = OMPArraySectionExpr::getBaseOriginalType(E->getBase()); +LValue CodeGenFunction::EmitArraySectionExpr(const ArraySectionExpr *E, + bool IsLowerBound) { + + assert(!E->isOpenACCArraySection() && + "OpenACC Array section codegen not implemented"); + + QualType BaseTy = ArraySectionExpr::getBaseOriginalType(E->getBase()); QualType ResultExprTy; if (auto *AT = getContext().getAsArrayType(BaseTy)) ResultExprTy = AT->getElementType(); diff --git a/clang/lib/CodeGen/CGObjCGNU.cpp b/clang/lib/CodeGen/CGObjCGNU.cpp index 4e7f777ba1d9160fd872c7a3466fcf2a438f12e2..43dd38659518d11616bd3abfe2d466aff0fc178a 100644 --- a/clang/lib/CodeGen/CGObjCGNU.cpp +++ b/clang/lib/CodeGen/CGObjCGNU.cpp @@ -2905,23 +2905,29 @@ CGObjCGNU::GenerateMessageSend(CodeGenFunction &CGF, break; case CodeGenOptions::Mixed: case CodeGenOptions::NonLegacy: + StringRef name = "objc_msgSend"; if (CGM.ReturnTypeUsesFPRet(ResultType)) { - imp = - CGM.CreateRuntimeFunction(llvm::FunctionType::get(IdTy, IdTy, true), - "objc_msgSend_fpret") - .getCallee(); + name = "objc_msgSend_fpret"; } else if (CGM.ReturnTypeUsesSRet(MSI.CallInfo)) { - // The actual types here don't matter - we're going to bitcast the - // function anyway - imp = - CGM.CreateRuntimeFunction(llvm::FunctionType::get(IdTy, IdTy, true), - "objc_msgSend_stret") - .getCallee(); - } else { - imp = CGM.CreateRuntimeFunction( - llvm::FunctionType::get(IdTy, IdTy, true), "objc_msgSend") - .getCallee(); + name = "objc_msgSend_stret"; + + // The address of the memory block is be passed in x8 for POD type, + // or in x0 for non-POD type (marked as inreg). + bool shouldCheckForInReg = + CGM.getContext() + .getTargetInfo() + .getTriple() + .isWindowsMSVCEnvironment() && + CGM.getContext().getTargetInfo().getTriple().isAArch64(); + if (shouldCheckForInReg && CGM.ReturnTypeHasInReg(MSI.CallInfo)) { + name = "objc_msgSend_stret2"; + } } + // The actual types here don't matter - we're going to bitcast the + // function anyway + imp = CGM.CreateRuntimeFunction(llvm::FunctionType::get(IdTy, IdTy, true), + name) + .getCallee(); } // Reset the receiver in case the lookup modified it diff --git a/clang/lib/CodeGen/CGOpenMPRuntime.cpp b/clang/lib/CodeGen/CGOpenMPRuntime.cpp index 2ae11e129c75e42b88df5ceae7d3d1c71c3a6339..e39c7c58d2780e5488a848bf97161b96bbd6732b 100644 --- a/clang/lib/CodeGen/CGOpenMPRuntime.cpp +++ b/clang/lib/CodeGen/CGOpenMPRuntime.cpp @@ -742,8 +742,8 @@ LValue ReductionCodeGen::emitSharedLValue(CodeGenFunction &CGF, const Expr *E) { LValue ReductionCodeGen::emitSharedLValueUB(CodeGenFunction &CGF, const Expr *E) { - if (const auto *OASE = dyn_cast(E)) - return CGF.EmitOMPArraySectionExpr(OASE, /*IsLowerBound=*/false); + if (const auto *OASE = dyn_cast(E)) + return CGF.EmitArraySectionExpr(OASE, /*IsLowerBound=*/false); return LValue(); } @@ -800,7 +800,7 @@ void ReductionCodeGen::emitSharedOrigLValue(CodeGenFunction &CGF, unsigned N) { void ReductionCodeGen::emitAggregateType(CodeGenFunction &CGF, unsigned N) { QualType PrivateType = getPrivateType(N); - bool AsArraySection = isa(ClausesData[N].Ref); + bool AsArraySection = isa(ClausesData[N].Ref); if (!PrivateType->isVariablyModifiedType()) { Sizes.emplace_back( CGF.getTypeSize(OrigAddresses[N].first.getType().getNonReferenceType()), @@ -941,9 +941,9 @@ static Address castToBase(CodeGenFunction &CGF, QualType BaseTy, QualType ElTy, static const VarDecl *getBaseDecl(const Expr *Ref, const DeclRefExpr *&DE) { const VarDecl *OrigVD = nullptr; - if (const auto *OASE = dyn_cast(Ref)) { + if (const auto *OASE = dyn_cast(Ref)) { const Expr *Base = OASE->getBase()->IgnoreParenImpCasts(); - while (const auto *TempOASE = dyn_cast(Base)) + while (const auto *TempOASE = dyn_cast(Base)) Base = TempOASE->getBase()->IgnoreParenImpCasts(); while (const auto *TempASE = dyn_cast(Base)) Base = TempASE->getBase()->IgnoreParenImpCasts(); @@ -3570,9 +3570,8 @@ getPointerAndSize(CodeGenFunction &CGF, const Expr *E) { SizeVal = CGF.Builder.CreateNUWMul(SizeVal, Sz); } } else if (const auto *ASE = - dyn_cast(E->IgnoreParenImpCasts())) { - LValue UpAddrLVal = - CGF.EmitOMPArraySectionExpr(ASE, /*IsLowerBound=*/false); + dyn_cast(E->IgnoreParenImpCasts())) { + LValue UpAddrLVal = CGF.EmitArraySectionExpr(ASE, /*IsLowerBound=*/false); Address UpAddrAddress = UpAddrLVal.getAddress(CGF); llvm::Value *UpAddr = CGF.Builder.CreateConstGEP1_32( UpAddrAddress.getElementType(), UpAddrAddress.emitRawPointer(CGF), @@ -6672,8 +6671,8 @@ private: // Given that an array section is considered a built-in type, we need to // do the calculation based on the length of the section instead of relying // on CGF.getTypeSize(E->getType()). - if (const auto *OAE = dyn_cast(E)) { - QualType BaseTy = OMPArraySectionExpr::getBaseOriginalType( + if (const auto *OAE = dyn_cast(E)) { + QualType BaseTy = ArraySectionExpr::getBaseOriginalType( OAE->getBase()->IgnoreParenImpCasts()) .getCanonicalType(); @@ -6779,7 +6778,7 @@ private: /// Return true if the provided expression is a final array section. A /// final array section, is one whose length can't be proved to be one. bool isFinalArraySectionExpression(const Expr *E) const { - const auto *OASE = dyn_cast(E); + const auto *OASE = dyn_cast(E); // It is not an array section and therefore not a unity-size one. if (!OASE) @@ -6795,7 +6794,7 @@ private: // for this dimension. Also, we should always expect a length if the // base type is pointer. if (!Length) { - QualType BaseQTy = OMPArraySectionExpr::getBaseOriginalType( + QualType BaseQTy = ArraySectionExpr::getBaseOriginalType( OASE->getBase()->IgnoreParenImpCasts()) .getCanonicalType(); if (const auto *ATy = dyn_cast(BaseQTy.getTypePtr())) @@ -7027,7 +7026,7 @@ private: Address BP = Address::invalid(); const Expr *AssocExpr = I->getAssociatedExpression(); const auto *AE = dyn_cast(AssocExpr); - const auto *OASE = dyn_cast(AssocExpr); + const auto *OASE = dyn_cast(AssocExpr); const auto *OAShE = dyn_cast(AssocExpr); if (isa(AssocExpr)) { @@ -7179,14 +7178,14 @@ private: // special treatment for array sections given that they are built-in // types. const auto *OASE = - dyn_cast(I->getAssociatedExpression()); + dyn_cast(I->getAssociatedExpression()); const auto *OAShE = dyn_cast(I->getAssociatedExpression()); const auto *UO = dyn_cast(I->getAssociatedExpression()); const auto *BO = dyn_cast(I->getAssociatedExpression()); bool IsPointer = OAShE || - (OASE && OMPArraySectionExpr::getBaseOriginalType(OASE) + (OASE && ArraySectionExpr::getBaseOriginalType(OASE) .getCanonicalType() ->isAnyPointerType()) || I->getAssociatedExpression()->getType()->isAnyPointerType(); @@ -7207,7 +7206,7 @@ private: assert((Next == CE || isa(Next->getAssociatedExpression()) || isa(Next->getAssociatedExpression()) || - isa(Next->getAssociatedExpression()) || + isa(Next->getAssociatedExpression()) || isa(Next->getAssociatedExpression()) || isa(Next->getAssociatedExpression()) || isa(Next->getAssociatedExpression())) && @@ -7439,7 +7438,7 @@ private: PartialStruct.LowestElem = {FieldIndex, LowestElem}; if (IsFinalArraySection) { Address HB = - CGF.EmitOMPArraySectionExpr(OASE, /*IsLowerBound=*/false) + CGF.EmitArraySectionExpr(OASE, /*IsLowerBound=*/false) .getAddress(CGF); PartialStruct.HighestElem = {FieldIndex, HB}; } else { @@ -7452,7 +7451,7 @@ private: } else if (FieldIndex > PartialStruct.HighestElem.first) { if (IsFinalArraySection) { Address HB = - CGF.EmitOMPArraySectionExpr(OASE, /*IsLowerBound=*/false) + CGF.EmitArraySectionExpr(OASE, /*IsLowerBound=*/false) .getAddress(CGF); PartialStruct.HighestElem = {FieldIndex, HB}; } else { @@ -7510,12 +7509,12 @@ private: for (const OMPClauseMappableExprCommon::MappableComponent &Component : Components) { const Expr *AssocExpr = Component.getAssociatedExpression(); - const auto *OASE = dyn_cast(AssocExpr); + const auto *OASE = dyn_cast(AssocExpr); if (!OASE) continue; - QualType Ty = OMPArraySectionExpr::getBaseOriginalType(OASE->getBase()); + QualType Ty = ArraySectionExpr::getBaseOriginalType(OASE->getBase()); auto *CAT = Context.getAsConstantArrayType(Ty); auto *VAT = Context.getAsVariableArrayType(Ty); @@ -7589,7 +7588,7 @@ private: continue; } - const auto *OASE = dyn_cast(AssocExpr); + const auto *OASE = dyn_cast(AssocExpr); if (!OASE) continue; @@ -8780,7 +8779,7 @@ static ValueDecl *getDeclFromThisExpr(const Expr *E) { if (!E) return nullptr; - if (const auto *OASE = dyn_cast(E->IgnoreParenCasts())) + if (const auto *OASE = dyn_cast(E->IgnoreParenCasts())) if (const MemberExpr *ME = dyn_cast(OASE->getBase()->IgnoreParenImpCasts())) return ME->getMemberDecl(); diff --git a/clang/lib/CodeGen/CGOpenMPRuntimeGPU.cpp b/clang/lib/CodeGen/CGOpenMPRuntimeGPU.cpp index eb716520e5ff562754f645acf3e7198f0de5da25..87496c8e488c679b1ffb74d00d87a04eedf41a9b 100644 --- a/clang/lib/CodeGen/CGOpenMPRuntimeGPU.cpp +++ b/clang/lib/CodeGen/CGOpenMPRuntimeGPU.cpp @@ -92,9 +92,9 @@ static const ValueDecl *getPrivateItem(const Expr *RefExpr) { while (const auto *TempASE = dyn_cast(Base)) Base = TempASE->getBase()->IgnoreParenImpCasts(); RefExpr = Base; - } else if (auto *OASE = dyn_cast(RefExpr)) { + } else if (auto *OASE = dyn_cast(RefExpr)) { const Expr *Base = OASE->getBase()->IgnoreParenImpCasts(); - while (const auto *TempOASE = dyn_cast(Base)) + while (const auto *TempOASE = dyn_cast(Base)) Base = TempOASE->getBase()->IgnoreParenImpCasts(); while (const auto *TempASE = dyn_cast(Base)) Base = TempASE->getBase()->IgnoreParenImpCasts(); diff --git a/clang/lib/CodeGen/CGStmtOpenMP.cpp b/clang/lib/CodeGen/CGStmtOpenMP.cpp index a0a8a07c76ba16528fea5c39459684d7ee37a74c..ef3aa3a8e0dc619fd3b0f95e654ccb812cd5b573 100644 --- a/clang/lib/CodeGen/CGStmtOpenMP.cpp +++ b/clang/lib/CodeGen/CGStmtOpenMP.cpp @@ -1256,7 +1256,7 @@ void CodeGenFunction::EmitOMPReductionClauseInit( const auto *LHSVD = cast(cast(*ILHS)->getDecl()); const auto *RHSVD = cast(cast(*IRHS)->getDecl()); QualType Type = PrivateVD->getType(); - bool isaOMPArraySectionExpr = isa(IRef); + bool isaOMPArraySectionExpr = isa(IRef); if (isaOMPArraySectionExpr && Type->isVariablyModifiedType()) { // Store the address of the original variable associated with the LHS // implicit variable. @@ -7289,7 +7289,7 @@ void CodeGenFunction::EmitOMPUseDevicePtrClause( static const VarDecl *getBaseDecl(const Expr *Ref) { const Expr *Base = Ref->IgnoreParenImpCasts(); - while (const auto *OASE = dyn_cast(Base)) + while (const auto *OASE = dyn_cast(Base)) Base = OASE->getBase()->IgnoreParenImpCasts(); while (const auto *ASE = dyn_cast(Base)) Base = ASE->getBase()->IgnoreParenImpCasts(); diff --git a/clang/lib/CodeGen/CodeGenFunction.h b/clang/lib/CodeGen/CodeGenFunction.h index ff1873325d409fe758ddc1665d597b6ae2d0accc..33fb7a41912b520bf29b33b0cfed754e14aaf727 100644 --- a/clang/lib/CodeGen/CodeGenFunction.h +++ b/clang/lib/CodeGen/CodeGenFunction.h @@ -3204,12 +3204,12 @@ public: llvm::Value *Index, QualType IndexType, QualType IndexedType, bool Accessed); - // Find a struct's flexible array member. It may be embedded inside multiple - // sub-structs, but must still be the last field. - const FieldDecl *FindFlexibleArrayMemberField(ASTContext &Ctx, - const RecordDecl *RD, - StringRef Name, - uint64_t &Offset); + // Find a struct's flexible array member and get its offset. It may be + // embedded inside multiple sub-structs, but must still be the last field. + const FieldDecl * + FindFlexibleArrayMemberFieldAndOffset(ASTContext &Ctx, const RecordDecl *RD, + const FieldDecl *FAMDecl, + uint64_t &Offset); /// Find the FieldDecl specified in a FAM's "counted_by" attribute. Returns /// \p nullptr if either the attribute or the field doesn't exist. @@ -4169,8 +4169,8 @@ public: LValue EmitArraySubscriptExpr(const ArraySubscriptExpr *E, bool Accessed = false); LValue EmitMatrixSubscriptExpr(const MatrixSubscriptExpr *E); - LValue EmitOMPArraySectionExpr(const OMPArraySectionExpr *E, - bool IsLowerBound = true); + LValue EmitArraySectionExpr(const ArraySectionExpr *E, + bool IsLowerBound = true); LValue EmitExtVectorElementExpr(const ExtVectorElementExpr *E); LValue EmitMemberExpr(const MemberExpr *E); LValue EmitObjCIsaExpr(const ObjCIsaExpr *E); diff --git a/clang/lib/CodeGen/CodeGenModule.cpp b/clang/lib/CodeGen/CodeGenModule.cpp index 0c447b20cef40d6098b2c742a632ddeaf4ba64b3..d085e735ecb443a1bc59f9dea2ba4ae319ac56ae 100644 --- a/clang/lib/CodeGen/CodeGenModule.cpp +++ b/clang/lib/CodeGen/CodeGenModule.cpp @@ -68,9 +68,9 @@ #include "llvm/Support/CommandLine.h" #include "llvm/Support/ConvertUTF.h" #include "llvm/Support/ErrorHandling.h" -#include "llvm/Support/RISCVISAInfo.h" #include "llvm/Support/TimeProfiler.h" #include "llvm/Support/xxhash.h" +#include "llvm/TargetParser/RISCVISAInfo.h" #include "llvm/TargetParser/Triple.h" #include "llvm/TargetParser/X86TargetParser.h" #include diff --git a/clang/lib/CodeGen/CodeGenModule.h b/clang/lib/CodeGen/CodeGenModule.h index 1cc447765e2c977cec62df9b7aaa54c44e20ebc4..be43a18fc60856b6e9fb0f79e89112f4948b8aec 100644 --- a/clang/lib/CodeGen/CodeGenModule.h +++ b/clang/lib/CodeGen/CodeGenModule.h @@ -1241,6 +1241,9 @@ public: /// Return true iff the given type uses 'sret' when used as a return type. bool ReturnTypeUsesSRet(const CGFunctionInfo &FI); + /// Return true iff the given type has `inreg` set. + bool ReturnTypeHasInReg(const CGFunctionInfo &FI); + /// Return true iff the given type uses an argument slot when 'sret' is used /// as a return type. bool ReturnSlotInterferesWithArgs(const CGFunctionInfo &FI); diff --git a/clang/lib/CodeGen/CodeGenTypes.cpp b/clang/lib/CodeGen/CodeGenTypes.cpp index 1568b6e6275b9dee1c65a56f872f2897c24cba0f..e8d75eda029e6653a3d46218020a7bab6d425cdb 100644 --- a/clang/lib/CodeGen/CodeGenTypes.cpp +++ b/clang/lib/CodeGen/CodeGenTypes.cpp @@ -409,7 +409,7 @@ llvm::Type *CodeGenTypes::ConvertType(QualType T) { break; case BuiltinType::LongDouble: LongDoubleReferenced = true; - LLVM_FALLTHROUGH; + [[fallthrough]]; case BuiltinType::BFloat16: case BuiltinType::Float: case BuiltinType::Double: diff --git a/clang/lib/Driver/Driver.cpp b/clang/lib/Driver/Driver.cpp index 0da92001e08c2701481b697ab3a30d7be6913bd7..76b7b9fdfb4f9b0cc8a82c1f69d534443b483fcc 100644 --- a/clang/lib/Driver/Driver.cpp +++ b/clang/lib/Driver/Driver.cpp @@ -87,12 +87,12 @@ #include "llvm/Support/PrettyStackTrace.h" #include "llvm/Support/Process.h" #include "llvm/Support/Program.h" -#include "llvm/Support/RISCVISAInfo.h" #include "llvm/Support/Regex.h" #include "llvm/Support/StringSaver.h" #include "llvm/Support/VirtualFileSystem.h" #include "llvm/Support/raw_ostream.h" #include "llvm/TargetParser/Host.h" +#include "llvm/TargetParser/RISCVISAInfo.h" #include // ::getenv #include #include diff --git a/clang/lib/Driver/SanitizerArgs.cpp b/clang/lib/Driver/SanitizerArgs.cpp index 8bfe9f02a091d17a01c3c4c4fd48d38c50a25dca..6a4f2548c0bffaf98e4488b3a138dc9f78f833b5 100644 --- a/clang/lib/Driver/SanitizerArgs.cpp +++ b/clang/lib/Driver/SanitizerArgs.cpp @@ -1192,7 +1192,9 @@ void SanitizerArgs::addArgs(const ToolChain &TC, const llvm::opt::ArgList &Args, BinaryMetadataIgnorelistFiles); } - if (TC.getTriple().isOSWindows() && needsUbsanRt()) { + if (TC.getTriple().isOSWindows() && needsUbsanRt() && + Args.hasFlag(options::OPT_frtlib_defaultlib, + options::OPT_fno_rtlib_defaultlib, true)) { // Instruct the code generator to embed linker directives in the object file // that cause the required runtime libraries to be linked. CmdArgs.push_back( @@ -1203,7 +1205,9 @@ void SanitizerArgs::addArgs(const ToolChain &TC, const llvm::opt::ArgList &Args, "--dependent-lib=" + TC.getCompilerRTBasename(Args, "ubsan_standalone_cxx"))); } - if (TC.getTriple().isOSWindows() && needsStatsRt()) { + if (TC.getTriple().isOSWindows() && needsStatsRt() && + Args.hasFlag(options::OPT_frtlib_defaultlib, + options::OPT_fno_rtlib_defaultlib, true)) { CmdArgs.push_back(Args.MakeArgString( "--dependent-lib=" + TC.getCompilerRTBasename(Args, "stats_client"))); diff --git a/clang/lib/Driver/ToolChain.cpp b/clang/lib/Driver/ToolChain.cpp index 237092ed07e5dcf09dd90974d7a634d4cfecb507..341d6202a9ca3c69c608097d1497b5bf63fcb75d 100644 --- a/clang/lib/Driver/ToolChain.cpp +++ b/clang/lib/Driver/ToolChain.cpp @@ -1307,9 +1307,14 @@ void ToolChain::AddCCKextLibArgs(const ArgList &Args, bool ToolChain::isFastMathRuntimeAvailable(const ArgList &Args, std::string &Path) const { + // Don't implicitly link in mode-changing libraries in a shared library, since + // this can have very deleterious effects. See the various links from + // https://github.com/llvm/llvm-project/issues/57589 for more information. + bool Default = !Args.hasArgNoClaim(options::OPT_shared); + // Do not check for -fno-fast-math or -fno-unsafe-math when -Ofast passed // (to keep the linker options consistent with gcc and clang itself). - if (!isOptimizationLevelFast(Args)) { + if (Default && !isOptimizationLevelFast(Args)) { // Check if -ffast-math or -funsafe-math. Arg *A = Args.getLastArg(options::OPT_ffast_math, options::OPT_fno_fast_math, @@ -1318,8 +1323,14 @@ bool ToolChain::isFastMathRuntimeAvailable(const ArgList &Args, if (!A || A->getOption().getID() == options::OPT_fno_fast_math || A->getOption().getID() == options::OPT_fno_unsafe_math_optimizations) - return false; + Default = false; } + + // Whatever decision came as a result of the above implicit settings, either + // -mdaz-ftz or -mno-daz-ftz is capable of overriding it. + if (!Args.hasFlag(options::OPT_mdaz_ftz, options::OPT_mno_daz_ftz, Default)) + return false; + // If crtfastmath.o exists add it to the arguments. Path = GetFilePath("crtfastmath.o"); return (Path != "crtfastmath.o"); // Not found. diff --git a/clang/lib/Driver/ToolChains/AIX.cpp b/clang/lib/Driver/ToolChains/AIX.cpp index c1b350893b3744ae818aef707591eacec1e6904c..aab98506adb96f0a86f0389b01ca92515312ddd3 100644 --- a/clang/lib/Driver/ToolChains/AIX.cpp +++ b/clang/lib/Driver/ToolChains/AIX.cpp @@ -376,9 +376,7 @@ void AIX::AddOpenMPIncludeArgs(const ArgList &DriverArgs, addSystemInclude(DriverArgs, CC1Args, PathOpenMP.str()); break; case Driver::OMPRT_IOMP5: - LLVM_FALLTHROUGH; case Driver::OMPRT_GOMP: - LLVM_FALLTHROUGH; case Driver::OMPRT_Unknown: // Unknown / unsupported include paths. break; diff --git a/clang/lib/Driver/ToolChains/AMDGPU.cpp b/clang/lib/Driver/ToolChains/AMDGPU.cpp index 4e6362a0f40632246ae10abc6512d703332164f0..07965b487ea79be0618244e140eda5d8a747cd68 100644 --- a/clang/lib/Driver/ToolChains/AMDGPU.cpp +++ b/clang/lib/Driver/ToolChains/AMDGPU.cpp @@ -617,8 +617,7 @@ void amdgpu::Linker::ConstructJob(Compilation &C, const JobAction &JA, const InputInfoList &Inputs, const ArgList &Args, const char *LinkingOutput) const { - - std::string Linker = getToolChain().GetProgramPath(getShortName()); + std::string Linker = getToolChain().GetLinkerPath(); ArgStringList CmdArgs; CmdArgs.push_back("--no-undefined"); CmdArgs.push_back("-shared"); diff --git a/clang/lib/Driver/ToolChains/Arch/RISCV.cpp b/clang/lib/Driver/ToolChains/Arch/RISCV.cpp index 96b3cc3bb8ffb1620afb43ca88f17e44827931a7..2e2bce8494672fe0e29086fbf768de1d3c256b31 100644 --- a/clang/lib/Driver/ToolChains/Arch/RISCV.cpp +++ b/clang/lib/Driver/ToolChains/Arch/RISCV.cpp @@ -15,9 +15,9 @@ #include "clang/Driver/Options.h" #include "llvm/Option/ArgList.h" #include "llvm/Support/Error.h" -#include "llvm/Support/RISCVISAInfo.h" #include "llvm/Support/raw_ostream.h" #include "llvm/TargetParser/Host.h" +#include "llvm/TargetParser/RISCVISAInfo.h" #include "llvm/TargetParser/RISCVTargetParser.h" using namespace clang::driver; diff --git a/clang/lib/Driver/ToolChains/Clang.cpp b/clang/lib/Driver/ToolChains/Clang.cpp index 5894a48e0e378bc89ab0feb3b0235959c66b9ae3..f4fe7422cba6303a23c77bcc54998c62979bf858 100644 --- a/clang/lib/Driver/ToolChains/Clang.cpp +++ b/clang/lib/Driver/ToolChains/Clang.cpp @@ -54,11 +54,11 @@ #include "llvm/Support/FileSystem.h" #include "llvm/Support/Path.h" #include "llvm/Support/Process.h" -#include "llvm/Support/RISCVISAInfo.h" #include "llvm/Support/YAMLParser.h" #include "llvm/TargetParser/ARMTargetParserCommon.h" #include "llvm/TargetParser/Host.h" #include "llvm/TargetParser/LoongArchTargetParser.h" +#include "llvm/TargetParser/RISCVISAInfo.h" #include "llvm/TargetParser/RISCVTargetParser.h" #include @@ -637,7 +637,9 @@ static void addPGOAndCoverageFlags(const ToolChain &TC, Compilation &C, ProfileGenerateArg->getValue())); // The default is to use Clang Instrumentation. CmdArgs.push_back("-fprofile-instrument=clang"); - if (TC.getTriple().isWindowsMSVCEnvironment()) { + if (TC.getTriple().isWindowsMSVCEnvironment() && + Args.hasFlag(options::OPT_frtlib_defaultlib, + options::OPT_fno_rtlib_defaultlib, true)) { // Add dependent lib for clang_rt.profile CmdArgs.push_back(Args.MakeArgString( "--dependent-lib=" + TC.getCompilerRTBasename(Args, "profile"))); @@ -656,7 +658,9 @@ static void addPGOAndCoverageFlags(const ToolChain &TC, Compilation &C, CmdArgs.push_back("-fprofile-instrument=csllvm"); } if (PGOGenArg) { - if (TC.getTriple().isWindowsMSVCEnvironment()) { + if (TC.getTriple().isWindowsMSVCEnvironment() && + Args.hasFlag(options::OPT_frtlib_defaultlib, + options::OPT_fno_rtlib_defaultlib, true)) { // Add dependent lib for clang_rt.profile CmdArgs.push_back(Args.MakeArgString( "--dependent-lib=" + TC.getCompilerRTBasename(Args, "profile"))); @@ -831,46 +835,6 @@ static void addPGOAndCoverageFlags(const ToolChain &TC, Compilation &C, } } -/// Check whether the given input tree contains any compilation actions. -static bool ContainsCompileAction(const Action *A) { - if (isa(A) || isa(A)) - return true; - - return llvm::any_of(A->inputs(), ContainsCompileAction); -} - -/// Check if -relax-all should be passed to the internal assembler. -/// This is done by default when compiling non-assembler source with -O0. -static bool UseRelaxAll(Compilation &C, const ArgList &Args) { - bool RelaxDefault = true; - - if (Arg *A = Args.getLastArg(options::OPT_O_Group)) - RelaxDefault = A->getOption().matches(options::OPT_O0); - - // RISC-V requires an indirect jump for offsets larger than 1MiB. This cannot - // be done by assembler branch relaxation as it needs a free temporary - // register. Because of this, branch relaxation is handled by a MachineIR - // pass before the assembler. Forcing assembler branch relaxation for -O0 - // makes the MachineIR branch relaxation inaccurate and it will miss cases - // where an indirect branch is necessary. To avoid this issue we are - // sacrificing the compile time improvement of using -mrelax-all for -O0. - if (C.getDefaultToolChain().getTriple().isRISCV()) - RelaxDefault = false; - - if (RelaxDefault) { - RelaxDefault = false; - for (const auto &Act : C.getActions()) { - if (ContainsCompileAction(Act)) { - RelaxDefault = true; - break; - } - } - } - - return Args.hasFlag(options::OPT_mrelax_all, options::OPT_mno_relax_all, - RelaxDefault); -} - static void RenderDebugEnablingArgs(const ArgList &Args, ArgStringList &CmdArgs, llvm::codegenoptions::DebugInfoKind DebugInfoKind, @@ -2468,8 +2432,16 @@ static void CollectArgsForIntegratedAssembler(Compilation &C, const ArgList &Args, ArgStringList &CmdArgs, const Driver &D) { - if (UseRelaxAll(C, Args)) - CmdArgs.push_back("-mrelax-all"); + // Default to -mno-relax-all. + // + // Note: RISC-V requires an indirect jump for offsets larger than 1MiB. This + // cannot be done by assembler branch relaxation as it needs a free temporary + // register. Because of this, branch relaxation is handled by a MachineIR pass + // before the assembler. Forcing assembler branch relaxation for -O0 makes the + // MachineIR branch relaxation inaccurate and it will miss cases where an + // indirect branch is necessary. + Args.addOptInFlag(CmdArgs, options::OPT_mrelax_all, + options::OPT_mno_relax_all); // Only default to -mincremental-linker-compatible if we think we are // targeting the MSVC linker. @@ -7290,10 +7262,15 @@ void Clang::ConstructJob(Compilation &C, const JobAction &JA, Args.addOptInFlag(CmdArgs, options::OPT_frelaxed_template_template_args, options::OPT_fno_relaxed_template_template_args); - // -fsized-deallocation is off by default, as it is an ABI-breaking change for - // most platforms. - Args.addOptInFlag(CmdArgs, options::OPT_fsized_deallocation, - options::OPT_fno_sized_deallocation); + // -fsized-deallocation is on by default in C++14 onwards and otherwise off + // by default. + if (Arg *A = Args.getLastArg(options::OPT_fsized_deallocation, + options::OPT_fno_sized_deallocation)) { + if (A->getOption().matches(options::OPT_fno_sized_deallocation)) + CmdArgs.push_back("-fno-sized-deallocation"); + else + CmdArgs.push_back("-fsized-deallocation"); + } // -faligned-allocation is on by default in C++17 onwards and otherwise off // by default. diff --git a/clang/lib/Driver/ToolChains/Darwin.cpp b/clang/lib/Driver/ToolChains/Darwin.cpp index caf6c4a444fdcec76007c09ffc73c15bc4d3002c..593b403a1e3f057e82c5f7ce42f9963c1057f228 100644 --- a/clang/lib/Driver/ToolChains/Darwin.cpp +++ b/clang/lib/Driver/ToolChains/Darwin.cpp @@ -2912,9 +2912,54 @@ static bool sdkSupportsBuiltinModules(const Darwin::DarwinPlatformKind &TargetPl } } -void Darwin::addClangTargetOptions(const llvm::opt::ArgList &DriverArgs, - llvm::opt::ArgStringList &CC1Args, - Action::OffloadKind DeviceOffloadKind) const { +static inline llvm::VersionTuple +sizedDeallocMinVersion(llvm::Triple::OSType OS) { + switch (OS) { + default: + break; + case llvm::Triple::Darwin: + case llvm::Triple::MacOSX: // Earliest supporting version is 10.12. + return llvm::VersionTuple(10U, 12U); + case llvm::Triple::IOS: + case llvm::Triple::TvOS: // Earliest supporting version is 10.0.0. + return llvm::VersionTuple(10U); + case llvm::Triple::WatchOS: // Earliest supporting version is 3.0.0. + return llvm::VersionTuple(3U); + } + + llvm_unreachable("Unexpected OS"); +} + +bool Darwin::isSizedDeallocationUnavailable() const { + llvm::Triple::OSType OS; + + if (isTargetMacCatalyst()) + return TargetVersion < sizedDeallocMinVersion(llvm::Triple::MacOSX); + switch (TargetPlatform) { + case MacOS: // Earlier than 10.12. + OS = llvm::Triple::MacOSX; + break; + case IPhoneOS: + OS = llvm::Triple::IOS; + break; + case TvOS: // Earlier than 10.0. + OS = llvm::Triple::TvOS; + break; + case WatchOS: // Earlier than 3.0. + OS = llvm::Triple::WatchOS; + break; + case DriverKit: + case XROS: + // Always available. + return false; + } + + return TargetVersion < sizedDeallocMinVersion(OS); +} + +void Darwin::addClangTargetOptions( + const llvm::opt::ArgList &DriverArgs, llvm::opt::ArgStringList &CC1Args, + Action::OffloadKind DeviceOffloadKind) const { // Pass "-faligned-alloc-unavailable" only when the user hasn't manually // enabled or disabled aligned allocations. if (!DriverArgs.hasArgNoClaim(options::OPT_faligned_allocation, @@ -2922,6 +2967,13 @@ void Darwin::addClangTargetOptions(const llvm::opt::ArgList &DriverArgs, isAlignedAllocationUnavailable()) CC1Args.push_back("-faligned-alloc-unavailable"); + // Pass "-fno-sized-deallocation" only when the user hasn't manually enabled + // or disabled sized deallocations. + if (!DriverArgs.hasArgNoClaim(options::OPT_fsized_deallocation, + options::OPT_fno_sized_deallocation) && + isSizedDeallocationUnavailable()) + CC1Args.push_back("-fno-sized-deallocation"); + addClangCC1ASTargetOptions(DriverArgs, CC1Args); // Enable compatibility mode for NSItemProviderCompletionHandler in diff --git a/clang/lib/Driver/ToolChains/Darwin.h b/clang/lib/Driver/ToolChains/Darwin.h index 10d4b69e5d5f10dacd40442f20930ca0aeca719f..b45279ecedeb250af0c123007745221e17509e7d 100644 --- a/clang/lib/Driver/ToolChains/Darwin.h +++ b/clang/lib/Driver/ToolChains/Darwin.h @@ -511,6 +511,10 @@ protected: /// targeting. bool isAlignedAllocationUnavailable() const; + /// Return true if c++14 sized deallocation functions are not implemented in + /// the c++ standard library of the deployment target we are targeting. + bool isSizedDeallocationUnavailable() const; + void addClangTargetOptions(const llvm::opt::ArgList &DriverArgs, llvm::opt::ArgStringList &CC1Args, Action::OffloadKind DeviceOffloadKind) const override; diff --git a/clang/lib/Driver/ToolChains/Flang.cpp b/clang/lib/Driver/ToolChains/Flang.cpp index abe0b931676005c00de472e432051db124f6785d..6d93c1f3d7034a02dd8beed312e7b0457ba67bd6 100644 --- a/clang/lib/Driver/ToolChains/Flang.cpp +++ b/clang/lib/Driver/ToolChains/Flang.cpp @@ -15,7 +15,7 @@ #include "llvm/Frontend/Debug/Options.h" #include "llvm/Support/FileSystem.h" #include "llvm/Support/Path.h" -#include "llvm/Support/RISCVISAInfo.h" +#include "llvm/TargetParser/RISCVISAInfo.h" #include "llvm/TargetParser/RISCVTargetParser.h" #include diff --git a/clang/lib/Driver/ToolChains/Gnu.cpp b/clang/lib/Driver/ToolChains/Gnu.cpp index dedbfac6cb25d26b67587d4ed273597366f1296d..f55b8bf48c13f781a69eaf464b60123618bd022b 100644 --- a/clang/lib/Driver/ToolChains/Gnu.cpp +++ b/clang/lib/Driver/ToolChains/Gnu.cpp @@ -30,8 +30,8 @@ #include "llvm/Option/ArgList.h" #include "llvm/Support/CodeGen.h" #include "llvm/Support/Path.h" -#include "llvm/Support/RISCVISAInfo.h" #include "llvm/Support/VirtualFileSystem.h" +#include "llvm/TargetParser/RISCVISAInfo.h" #include "llvm/TargetParser/TargetParser.h" #include diff --git a/clang/lib/Driver/ToolChains/Linux.cpp b/clang/lib/Driver/ToolChains/Linux.cpp index fb65881061effc3abc4f88028b48f889f8bab1ae..db2c20d7b461d0a782ce6b4dd5a498903cc5e204 100644 --- a/clang/lib/Driver/ToolChains/Linux.cpp +++ b/clang/lib/Driver/ToolChains/Linux.cpp @@ -842,25 +842,6 @@ void Linux::addProfileRTLibs(const llvm::opt::ArgList &Args, ToolChain::addProfileRTLibs(Args, CmdArgs); } -llvm::DenormalMode -Linux::getDefaultDenormalModeForType(const llvm::opt::ArgList &DriverArgs, - const JobAction &JA, - const llvm::fltSemantics *FPType) const { - switch (getTriple().getArch()) { - case llvm::Triple::x86: - case llvm::Triple::x86_64: { - std::string Unused; - // DAZ and FTZ are turned on in crtfastmath.o - if (!DriverArgs.hasArg(options::OPT_nostdlib, options::OPT_nostartfiles) && - isFastMathRuntimeAvailable(DriverArgs, Unused)) - return llvm::DenormalMode::getPreserveSign(); - return llvm::DenormalMode::getIEEE(); - } - default: - return llvm::DenormalMode::getIEEE(); - } -} - void Linux::addExtraOpts(llvm::opt::ArgStringList &CmdArgs) const { for (const auto &Opt : ExtraOpts) CmdArgs.push_back(Opt.c_str()); diff --git a/clang/lib/Driver/ToolChains/Linux.h b/clang/lib/Driver/ToolChains/Linux.h index 524391743090ba386cc55a50a039a6be31ebf3a1..2d9e674e50a630325659166d5e9eeb9dc4912cdc 100644 --- a/clang/lib/Driver/ToolChains/Linux.h +++ b/clang/lib/Driver/ToolChains/Linux.h @@ -59,10 +59,6 @@ public: std::vector ExtraOpts; - llvm::DenormalMode getDefaultDenormalModeForType( - const llvm::opt::ArgList &DriverArgs, const JobAction &JA, - const llvm::fltSemantics *FPType = nullptr) const override; - const char *getDefaultLinker() const override; protected: diff --git a/clang/lib/Driver/ToolChains/ZOS.cpp b/clang/lib/Driver/ToolChains/ZOS.cpp index d5fc7b8ef562a66870c15838cbd2ff60d90127a7..074e0556ecd2ad2a60bba85539ad58bcd1d49965 100644 --- a/clang/lib/Driver/ToolChains/ZOS.cpp +++ b/clang/lib/Driver/ToolChains/ZOS.cpp @@ -36,6 +36,12 @@ void ZOS::addClangTargetOptions(const ArgList &DriverArgs, if (!DriverArgs.hasArgNoClaim(options::OPT_faligned_allocation, options::OPT_fno_aligned_allocation)) CC1Args.push_back("-faligned-alloc-unavailable"); + + // Pass "-fno-sized-deallocation" only when the user hasn't manually enabled + // or disabled sized deallocations. + if (!DriverArgs.hasArgNoClaim(options::OPT_fsized_deallocation, + options::OPT_fno_sized_deallocation)) + CC1Args.push_back("-fno-sized-deallocation"); } void zos::Assembler::ConstructJob(Compilation &C, const JobAction &JA, diff --git a/clang/lib/ExtractAPI/API.cpp b/clang/lib/ExtractAPI/API.cpp index 5a62c5deb240836aeeb4c73d54b7c3faa371db16..96bef967d8591a248f384e330fa7948d3e3269fb 100644 --- a/clang/lib/ExtractAPI/API.cpp +++ b/clang/lib/ExtractAPI/API.cpp @@ -54,7 +54,28 @@ RecordContext *APIRecord::castToRecordContext(const APIRecord *Record) { } } +bool RecordContext::IsWellFormed() const { + // Check that First and Last are both null or both non-null. + return (First == nullptr) == (Last == nullptr); +} + +void RecordContext::stealRecordChain(RecordContext &Other) { + assert(IsWellFormed()); + // If we don't have an empty chain append Other's chain into ours. + if (First) + Last->NextInContext = Other.First; + else + First = Other.First; + + Last = Other.Last; + + // Delete Other's chain to ensure we don't accidentally traverse it. + Other.First = nullptr; + Other.Last = nullptr; +} + void RecordContext::addToRecordChain(APIRecord *Record) const { + assert(IsWellFormed()); if (!First) { First = Record; Last = Record; @@ -95,6 +116,7 @@ SymbolReference APISet::createSymbolReference(StringRef Name, StringRef USR, } APIRecord::~APIRecord() {} +TagRecord::~TagRecord() {} RecordRecord::~RecordRecord() {} RecordFieldRecord::~RecordFieldRecord() {} ObjCContainerRecord::~ObjCContainerRecord() {} diff --git a/clang/lib/ExtractAPI/DeclarationFragments.cpp b/clang/lib/ExtractAPI/DeclarationFragments.cpp index 0a243120b7c0e35c409ca7a70a269d2a7ff0ac08..9bf7950888dbb2566fad2c6765695967d1ad58c9 100644 --- a/clang/lib/ExtractAPI/DeclarationFragments.cpp +++ b/clang/lib/ExtractAPI/DeclarationFragments.cpp @@ -396,7 +396,8 @@ DeclarationFragments DeclarationFragmentsBuilder::getFragmentsForType( const TagDecl *Decl = TagTy->getDecl(); // Anonymous decl, skip this fragment. if (Decl->getName().empty()) - return Fragments; + return Fragments.append("{ ... }", + DeclarationFragments::FragmentKind::Text); SmallString<128> TagUSR; clang::index::generateUSRForDecl(Decl, TagUSR); return Fragments.append(Decl->getName(), @@ -743,11 +744,16 @@ DeclarationFragmentsBuilder::getFragmentsForEnum(const EnumDecl *EnumDecl) { QualType IntegerType = EnumDecl->getIntegerType(); if (!IntegerType.isNull()) - Fragments.append(": ", DeclarationFragments::FragmentKind::Text) + Fragments.appendSpace() + .append(": ", DeclarationFragments::FragmentKind::Text) .append( getFragmentsForType(IntegerType, EnumDecl->getASTContext(), After)) .append(std::move(After)); + if (EnumDecl->getName().empty()) + Fragments.appendSpace().append("{ ... }", + DeclarationFragments::FragmentKind::Text); + return Fragments.appendSemicolon(); } @@ -778,9 +784,12 @@ DeclarationFragments DeclarationFragmentsBuilder::getFragmentsForRecordDecl( else Fragments.append("struct", DeclarationFragments::FragmentKind::Keyword); + Fragments.appendSpace(); if (!Record->getName().empty()) - Fragments.appendSpace().append( - Record->getName(), DeclarationFragments::FragmentKind::Identifier); + Fragments.append(Record->getName(), + DeclarationFragments::FragmentKind::Identifier); + else + Fragments.append("{ ... }", DeclarationFragments::FragmentKind::Text); return Fragments.appendSemicolon(); } diff --git a/clang/lib/ExtractAPI/Serialization/SymbolGraphSerializer.cpp b/clang/lib/ExtractAPI/Serialization/SymbolGraphSerializer.cpp index 8b1dcb4a4144f4044a1f7f8e7c3cb6204c2834a1..34278b5d40c4221931624b7efc2164edeb5d11a3 100644 --- a/clang/lib/ExtractAPI/Serialization/SymbolGraphSerializer.cpp +++ b/clang/lib/ExtractAPI/Serialization/SymbolGraphSerializer.cpp @@ -667,6 +667,14 @@ bool SymbolGraphSerializer::shouldSkip(const APIRecord *Record) const { if (Record->Availability.isUnconditionallyUnavailable()) return true; + // Filter out symbols without a name as we can generate correct symbol graphs + // for them. In practice these are anonymous record types that aren't attached + // to a declaration. + if (auto *Tag = dyn_cast(Record)) { + if (Tag->IsEmbeddedInVarDeclarator) + return true; + } + // Filter out symbols prefixed with an underscored as they are understood to // be symbols clients should not use. if (Record->Name.starts_with("_")) diff --git a/clang/lib/Format/Format.cpp b/clang/lib/Format/Format.cpp index ccb2c9190e2eff0bdb551c3ecb95dde3c987639d..c8d8ec3afbd990c8f4618a6b5f36cf115f8c2e56 100644 --- a/clang/lib/Format/Format.cpp +++ b/clang/lib/Format/Format.cpp @@ -807,7 +807,6 @@ template <> struct MappingTraits { FormatStyle PredefinedStyle; if (getPredefinedStyle(StyleName, Style.Language, &PredefinedStyle) && Style == PredefinedStyle) { - IO.mapOptional("# BasedOnStyle", StyleName); BasedOnStyle = StyleName; break; } @@ -3117,6 +3116,7 @@ static void sortCppIncludes(const FormatStyle &Style, return; } + const auto OldCursor = Cursor ? *Cursor : 0; std::string result; for (unsigned Index : Indices) { if (!result.empty()) { @@ -3140,6 +3140,8 @@ static void sortCppIncludes(const FormatStyle &Style, // the entire range of blocks. Otherwise, no replacement is generated. if (replaceCRLF(result) == replaceCRLF(std::string(Code.substr( IncludesBeginOffset, IncludesBlockSize)))) { + if (Cursor) + *Cursor = OldCursor; return; } diff --git a/clang/lib/Format/UnwrappedLineParser.cpp b/clang/lib/Format/UnwrappedLineParser.cpp index 603268f771ac5226165ba33e30c0c97918c11c4a..3a263955a6a8fef805a83e48ce8b77672fb32b0e 100644 --- a/clang/lib/Format/UnwrappedLineParser.cpp +++ b/clang/lib/Format/UnwrappedLineParser.cpp @@ -534,11 +534,11 @@ void UnwrappedLineParser::calculateBraceTypes(bool ExpectClassBody) { case tok::r_brace: if (LBraceStack.empty()) break; - if (LBraceStack.back().Tok->is(BK_Unknown)) { + if (auto *LBrace = LBraceStack.back().Tok; LBrace->is(BK_Unknown)) { bool ProbablyBracedList = false; if (Style.Language == FormatStyle::LK_Proto) { ProbablyBracedList = NextTok->isOneOf(tok::comma, tok::r_square); - } else { + } else if (LBrace->isNot(TT_EnumLBrace)) { // Using OriginalColumn to distinguish between ObjC methods and // binary operators is a bit hacky. bool NextIsObjCMethod = NextTok->isOneOf(tok::plus, tok::minus) && @@ -552,7 +552,7 @@ void UnwrappedLineParser::calculateBraceTypes(bool ExpectClassBody) { // If we already marked the opening brace as braced list, the closing // must also be part of it. - ProbablyBracedList = LBraceStack.back().Tok->is(TT_BracedListLBrace); + ProbablyBracedList = LBrace->is(TT_BracedListLBrace); ProbablyBracedList = ProbablyBracedList || (Style.isJavaScript() && @@ -608,13 +608,9 @@ void UnwrappedLineParser::calculateBraceTypes(bool ExpectClassBody) { ProbablyBracedList = true; } } - if (ProbablyBracedList) { - Tok->setBlockKind(BK_BracedInit); - LBraceStack.back().Tok->setBlockKind(BK_BracedInit); - } else { - Tok->setBlockKind(BK_Block); - LBraceStack.back().Tok->setBlockKind(BK_Block); - } + const auto BlockKind = ProbablyBracedList ? BK_BracedInit : BK_Block; + Tok->setBlockKind(BlockKind); + LBrace->setBlockKind(BlockKind); } LBraceStack.pop_back(); break; @@ -819,8 +815,11 @@ FormatToken *UnwrappedLineParser::parseBlock(bool MustBeDeclaration, return IfLBrace; } - if (FormatTok->is(tok::r_brace) && Tok->is(TT_NamespaceLBrace)) - FormatTok->setFinalizedType(TT_NamespaceRBrace); + if (FormatTok->is(tok::r_brace)) { + FormatTok->setBlockKind(BK_Block); + if (Tok->is(TT_NamespaceLBrace)) + FormatTok->setFinalizedType(TT_NamespaceRBrace); + } const bool IsFunctionRBrace = FormatTok->is(tok::r_brace) && Tok->is(TT_FunctionLBrace); @@ -2415,6 +2414,7 @@ bool UnwrappedLineParser::tryToParseChildBlock() { } bool UnwrappedLineParser::parseBracedList(bool IsAngleBracket, bool IsEnum) { + assert(!IsAngleBracket || !IsEnum); bool HasError = false; // FIXME: Once we have an expression parser in the UnwrappedLineParser, @@ -2437,8 +2437,11 @@ bool UnwrappedLineParser::parseBracedList(bool IsAngleBracket, bool IsEnum) { } } if (FormatTok->is(IsAngleBracket ? tok::greater : tok::r_brace)) { - if (IsEnum && !Style.AllowShortEnumsOnASingleLine) - addUnwrappedLine(); + if (IsEnum) { + FormatTok->setBlockKind(BK_Block); + if (!Style.AllowShortEnumsOnASingleLine) + addUnwrappedLine(); + } nextToken(); return !HasError; } @@ -3910,6 +3913,8 @@ void UnwrappedLineParser::parseRecord(bool ParseAsExpr) { const FormatToken &InitialToken = *FormatTok; nextToken(); + const FormatToken *ClassName = nullptr; + bool IsDerived = false; auto IsNonMacroIdentifier = [](const FormatToken *Tok) { return Tok->is(tok::identifier) && Tok->TokenText != Tok->TokenText.upper(); }; @@ -3934,15 +3939,35 @@ void UnwrappedLineParser::parseRecord(bool ParseAsExpr) { } if (FormatTok->is(tok::l_square) && handleCppAttributes()) continue; + const auto *Previous = FormatTok; nextToken(); - // We can have macros in between 'class' and the class name. - if (!IsNonMacroIdentifier(FormatTok->Previous) && - FormatTok->is(tok::l_paren)) { - parseParens(); + switch (FormatTok->Tok.getKind()) { + case tok::l_paren: + // We can have macros in between 'class' and the class name. + if (!IsNonMacroIdentifier(Previous)) + parseParens(); + break; + case tok::coloncolon: + break; + default: + if (!ClassName && Previous->is(tok::identifier)) + ClassName = Previous; } } + auto IsListInitialization = [&] { + if (!ClassName || IsDerived) + return false; + assert(FormatTok->is(tok::l_brace)); + const auto *Prev = FormatTok->getPreviousNonComment(); + assert(Prev); + return Prev != ClassName && Prev->is(tok::identifier) && + Prev->isNot(Keywords.kw_final) && tryToParseBracedList(); + }; + if (FormatTok->isOneOf(tok::colon, tok::less)) { + if (FormatTok->is(tok::colon)) + IsDerived = true; int AngleNestingLevel = 0; do { if (FormatTok->is(tok::less)) @@ -3955,6 +3980,8 @@ void UnwrappedLineParser::parseRecord(bool ParseAsExpr) { break; } if (FormatTok->is(tok::l_brace)) { + if (AngleNestingLevel == 0 && IsListInitialization()) + return; calculateBraceTypes(/*ExpectClassBody=*/true); if (!tryToParseBracedList()) break; @@ -3999,6 +4026,8 @@ void UnwrappedLineParser::parseRecord(bool ParseAsExpr) { } }; if (FormatTok->is(tok::l_brace)) { + if (IsListInitialization()) + return; auto [OpenBraceType, ClosingBraceType] = GetBraceTypes(InitialToken); FormatTok->setFinalizedType(OpenBraceType); if (ParseAsExpr) { diff --git a/clang/lib/Frontend/ASTUnit.cpp b/clang/lib/Frontend/ASTUnit.cpp index 3610a08831e79a9fe0206941f4b59d2bab2fd56d..1b93588553a276507dc14d36a67ba7f666a77afc 100644 --- a/clang/lib/Frontend/ASTUnit.cpp +++ b/clang/lib/Frontend/ASTUnit.cpp @@ -1067,7 +1067,7 @@ public: std::vector takeTopLevelDecls() { return std::move(TopLevelDecls); } - std::vector takeTopLevelDeclIDs() { + std::vector takeTopLevelDeclIDs() { return std::move(TopLevelDeclIDs); } @@ -1101,7 +1101,7 @@ public: private: unsigned Hash = 0; std::vector TopLevelDecls; - std::vector TopLevelDeclIDs; + std::vector TopLevelDeclIDs; llvm::SmallVector PreambleDiags; }; @@ -1467,11 +1467,12 @@ void ASTUnit::RealizeTopLevelDeclsFromPreamble() { std::vector Resolved; Resolved.reserve(TopLevelDeclsInPreamble.size()); - ExternalASTSource &Source = *getASTContext().getExternalSource(); + // The module file of the preamble. + serialization::ModuleFile &MF = Reader->getModuleManager().getPrimaryModule(); for (const auto TopLevelDecl : TopLevelDeclsInPreamble) { // Resolve the declaration ID to an actual declaration, possibly // deserializing the declaration in the process. - if (Decl *D = Source.GetExternalDecl(TopLevelDecl)) + if (Decl *D = Reader->GetDecl(Reader->getGlobalDeclID(MF, TopLevelDecl))) Resolved.push_back(D); } TopLevelDeclsInPreamble.clear(); diff --git a/clang/lib/Frontend/CompilerInstance.cpp b/clang/lib/Frontend/CompilerInstance.cpp index 6e3baf8386441593bd767ce2260bd1b107be3e6c..66a45b888f15cc736b11aeba5ee02cac93742ba1 100644 --- a/clang/lib/Frontend/CompilerInstance.cpp +++ b/clang/lib/Frontend/CompilerInstance.cpp @@ -1293,6 +1293,10 @@ compileModuleImpl(CompilerInstance &ImportingInstance, SourceLocation ImportLoc, diag::remark_module_build_done) << ModuleName; + // Propagate the statistics to the parent FileManager. + if (!FrontendOpts.ModulesShareFileManager) + ImportingInstance.getFileManager().AddStats(Instance.getFileManager()); + if (Crashed) { // Clear the ASTConsumer if it hasn't been already, in case it owns streams // that must be closed before clearing output files. diff --git a/clang/lib/Frontend/FrontendAction.cpp b/clang/lib/Frontend/FrontendAction.cpp index b7c9967316f0b82ff2b211315d1be87a05d6340c..9ae7664b4b49d435dc8ea3ed90e6b89f7ac90678 100644 --- a/clang/lib/Frontend/FrontendAction.cpp +++ b/clang/lib/Frontend/FrontendAction.cpp @@ -80,7 +80,7 @@ public: if (Previous) Previous->TypeRead(Idx, T); } - void DeclRead(serialization::DeclID ID, const Decl *D) override { + void DeclRead(GlobalDeclID ID, const Decl *D) override { if (Previous) Previous->DeclRead(ID, D); } @@ -102,7 +102,7 @@ public: bool DeletePrevious) : DelegatingDeserializationListener(Previous, DeletePrevious) {} - void DeclRead(serialization::DeclID ID, const Decl *D) override { + void DeclRead(GlobalDeclID ID, const Decl *D) override { llvm::outs() << "PCH DECL: " << D->getDeclKindName(); if (const NamedDecl *ND = dyn_cast(D)) { llvm::outs() << " - "; @@ -128,7 +128,7 @@ public: : DelegatingDeserializationListener(Previous, DeletePrevious), Ctx(Ctx), NamesToCheck(NamesToCheck) {} - void DeclRead(serialization::DeclID ID, const Decl *D) override { + void DeclRead(GlobalDeclID ID, const Decl *D) override { if (const NamedDecl *ND = dyn_cast(D)) if (NamesToCheck.find(ND->getNameAsString()) != NamesToCheck.end()) { unsigned DiagID @@ -757,8 +757,11 @@ bool FrontendAction::BeginSourceFile(CompilerInstance &CI, // IR files bypass the rest of initialization. if (Input.getKind().getLanguage() == Language::LLVM_IR) { - assert(hasIRSupport() && - "This action does not have IR file support!"); + if (!hasIRSupport()) { + CI.getDiagnostics().Report(diag::err_ast_action_on_llvm_ir) + << Input.getFile(); + return false; + } // Inform the diagnostic client we are processing a source file. CI.getDiagnosticClient().BeginSourceFile(CI.getLangOpts(), nullptr); diff --git a/clang/lib/Frontend/InitPreprocessor.cpp b/clang/lib/Frontend/InitPreprocessor.cpp index 4f44c3b7b89d4d860ad3815fb77c23557fcb1b37..6bdd734e8a275281af27c00b1ee295e4fbd909fa 100644 --- a/clang/lib/Frontend/InitPreprocessor.cpp +++ b/clang/lib/Frontend/InitPreprocessor.cpp @@ -389,8 +389,7 @@ static void InitializeStandardPredefinedMacros(const TargetInfo &TI, Twine((unsigned)LangOpts.getHLSLVersion())); if (LangOpts.NativeHalfType) - Builder.defineMacro("__HLSL_ENABLE_16_BIT", - Twine((unsigned)LangOpts.getHLSLVersion())); + Builder.defineMacro("__HLSL_ENABLE_16_BIT", "1"); // Shader target information // "enums" for shader stages diff --git a/clang/lib/Frontend/MultiplexConsumer.cpp b/clang/lib/Frontend/MultiplexConsumer.cpp index 744ea70cc24def6442cdd1c306ab43334daa6862..c74bfd86195fec275b875c50b747d907fdfbd164 100644 --- a/clang/lib/Frontend/MultiplexConsumer.cpp +++ b/clang/lib/Frontend/MultiplexConsumer.cpp @@ -52,8 +52,8 @@ void MultiplexASTDeserializationListener::TypeRead( Listeners[i]->TypeRead(Idx, T); } -void MultiplexASTDeserializationListener::DeclRead( - serialization::DeclID ID, const Decl *D) { +void MultiplexASTDeserializationListener::DeclRead(GlobalDeclID ID, + const Decl *D) { for (size_t i = 0, e = Listeners.size(); i != e; ++i) Listeners[i]->DeclRead(ID, D); } diff --git a/clang/lib/Headers/cpuid.h b/clang/lib/Headers/cpuid.h index 0bb9912b465ffef7d1ce9cd8cb2d0a525ada6fc0..bb7692efb78ffe1902d5c7ec2b9f473143bc4385 100644 --- a/clang/lib/Headers/cpuid.h +++ b/clang/lib/Headers/cpuid.h @@ -10,7 +10,7 @@ #ifndef __CPUID_H #define __CPUID_H -#if !(__x86_64__ || __i386__) +#if !defined(__x86_64__) && !defined(__i386__) #error this header is for x86 only #endif @@ -256,7 +256,7 @@ #define bit_AVX10_256 0x00020000 #define bit_AVX10_512 0x00040000 -#if __i386__ +#ifdef __i386__ #define __cpuid(__leaf, __eax, __ebx, __ecx, __edx) \ __asm("cpuid" : "=a"(__eax), "=b" (__ebx), "=c"(__ecx), "=d"(__edx) \ : "0"(__leaf)) @@ -285,7 +285,7 @@ static __inline unsigned int __get_cpuid_max (unsigned int __leaf, unsigned int *__sig) { unsigned int __eax, __ebx, __ecx, __edx; -#if __i386__ +#ifdef __i386__ int __cpuid_supported; __asm(" pushfl\n" diff --git a/clang/lib/Lex/HeaderSearch.cpp b/clang/lib/Lex/HeaderSearch.cpp index 0632882b2961469c2c905b4c8a951e6bb6683937..574723b33866af4577ca052bebfa48c75d548a36 100644 --- a/clang/lib/Lex/HeaderSearch.cpp +++ b/clang/lib/Lex/HeaderSearch.cpp @@ -1574,6 +1574,7 @@ bool HeaderSearch::ShouldEnterIncludeFile(Preprocessor &PP, } } + FileInfo.IsLocallyIncluded = true; IsFirstIncludeOfFile = PP.markIncluded(File); return true; } diff --git a/clang/lib/Parse/ParseExpr.cpp b/clang/lib/Parse/ParseExpr.cpp index 32d96f81c4c8de09b0723a7d94ef72d149a9cbb3..7d6febb04a82c430588cf3b7c64e504ad05c3b3d 100644 --- a/clang/lib/Parse/ParseExpr.cpp +++ b/clang/lib/Parse/ParseExpr.cpp @@ -31,6 +31,7 @@ #include "clang/Sema/ParsedTemplate.h" #include "clang/Sema/Scope.h" #include "clang/Sema/SemaCUDA.h" +#include "clang/Sema/SemaOpenACC.h" #include "clang/Sema/SemaOpenMP.h" #include "clang/Sema/SemaSYCL.h" #include "clang/Sema/TypoCorrection.h" @@ -2070,15 +2071,22 @@ Parser::ParsePostfixExpressionSuffix(ExprResult LHS) { if (!LHS.isInvalid() && !HasError && !Length.isInvalid() && !Stride.isInvalid() && Tok.is(tok::r_square)) { if (ColonLocFirst.isValid() || ColonLocSecond.isValid()) { - // FIXME: OpenACC hasn't implemented Sema/Array section handling at a - // semantic level yet. For now, just reuse the OpenMP implementation - // as it gets the parsing/type management mostly right, and we can - // replace this call to ActOnOpenACCArraySectionExpr in the future. - // Eventually we'll genericize the OPenMPArraySectionExpr type as - // well. - LHS = Actions.OpenMP().ActOnOMPArraySectionExpr( - LHS.get(), Loc, ArgExprs.empty() ? nullptr : ArgExprs[0], - ColonLocFirst, ColonLocSecond, Length.get(), Stride.get(), RLoc); + // Like above, AllowOpenACCArraySections is 'more specific' and only + // enabled when actively parsing a 'var' in a 'var-list' during + // clause/'cache' construct parsing, so it is more specific. So we + // should do it first, so that the correct node gets created. + if (AllowOpenACCArraySections) { + assert(!Stride.isUsable() && !ColonLocSecond.isValid() && + "Stride/second colon not allowed for OpenACC"); + LHS = Actions.OpenACC().ActOnArraySectionExpr( + LHS.get(), Loc, ArgExprs.empty() ? nullptr : ArgExprs[0], + ColonLocFirst, Length.get(), RLoc); + } else { + LHS = Actions.OpenMP().ActOnOMPArraySectionExpr( + LHS.get(), Loc, ArgExprs.empty() ? nullptr : ArgExprs[0], + ColonLocFirst, ColonLocSecond, Length.get(), Stride.get(), + RLoc); + } } else { LHS = Actions.ActOnArraySubscriptExpr(getCurScope(), LHS.get(), Loc, ArgExprs, RLoc); diff --git a/clang/lib/Parse/ParseOpenACC.cpp b/clang/lib/Parse/ParseOpenACC.cpp index 8a18fca8064ee119ae2d429844eb41021b93cc72..29326f5d993a9d56b861a61bfbaa437518b62295 100644 --- a/clang/lib/Parse/ParseOpenACC.cpp +++ b/clang/lib/Parse/ParseOpenACC.cpp @@ -327,7 +327,7 @@ OpenACCReductionOperator ParseReductionOperator(Parser &P) { return OpenACCReductionOperator::Max; if (ReductionKindTok.getIdentifierInfo()->isStr("min")) return OpenACCReductionOperator::Min; - LLVM_FALLTHROUGH; + [[fallthrough]]; default: P.Diag(ReductionKindTok, diag::err_acc_invalid_reduction_operator); return OpenACCReductionOperator::Invalid; @@ -945,7 +945,7 @@ Parser::OpenACCClauseParseResult Parser::ParseOpenACCClauseParams( // the 'update' clause, so we have to handle it here. U se an assert to // make sure we get the right differentiator. assert(DirKind == OpenACCDirectiveKind::Update); - LLVM_FALLTHROUGH; + [[fallthrough]]; case OpenACCClauseKind::Attach: case OpenACCClauseKind::Copy: case OpenACCClauseKind::Delete: diff --git a/clang/lib/Sema/JumpDiagnostics.cpp b/clang/lib/Sema/JumpDiagnostics.cpp index ce6211c23218bbd2024bad7aa5dcb690e005ebeb..8af36d5c24e3d232ad0a067c84ff56b93340c341 100644 --- a/clang/lib/Sema/JumpDiagnostics.cpp +++ b/clang/lib/Sema/JumpDiagnostics.cpp @@ -180,7 +180,8 @@ static ScopePair GetDiagForGotoScopeDecl(Sema &S, const Decl *D) { } const Expr *Init = VD->getInit(); - if (S.Context.getLangOpts().CPlusPlus && VD->hasLocalStorage() && Init) { + if (S.Context.getLangOpts().CPlusPlus && VD->hasLocalStorage() && Init && + !Init->containsErrors()) { // C++11 [stmt.dcl]p3: // A program that jumps from a point where a variable with automatic // storage duration is not in scope to a point where it is in scope diff --git a/clang/lib/Sema/MultiplexExternalSemaSource.cpp b/clang/lib/Sema/MultiplexExternalSemaSource.cpp index 6a5f9f6680e640972990384cfe01661d4a5eb959..79e656eb4b7e27d47869e3ef192fc644f4612cd4 100644 --- a/clang/lib/Sema/MultiplexExternalSemaSource.cpp +++ b/clang/lib/Sema/MultiplexExternalSemaSource.cpp @@ -46,7 +46,7 @@ void MultiplexExternalSemaSource::AddSource(ExternalSemaSource *Source) { // ExternalASTSource. //===----------------------------------------------------------------------===// -Decl *MultiplexExternalSemaSource::GetExternalDecl(Decl::DeclID ID) { +Decl *MultiplexExternalSemaSource::GetExternalDecl(GlobalDeclID ID) { for(size_t i = 0; i < Sources.size(); ++i) if (Decl *Result = Sources[i]->GetExternalDecl(ID)) return Result; diff --git a/clang/lib/Sema/SemaChecking.cpp b/clang/lib/Sema/SemaChecking.cpp index 51757f4cf727d6433144bf664637a3b9900f0da9..e33113ab9c4c1d1e8080f5639a3798279cfc8e33 100644 --- a/clang/lib/Sema/SemaChecking.cpp +++ b/clang/lib/Sema/SemaChecking.cpp @@ -7953,7 +7953,8 @@ void Sema::checkCall(NamedDecl *FDecl, const FunctionProtoType *Proto, // For variadic functions, we may have more args than parameters. // For some K&R functions, we may have less args than parameters. const auto N = std::min(Proto->getNumParams(), Args.size()); - bool AnyScalableArgsOrRet = Proto->getReturnType()->isSizelessVectorType(); + bool IsScalableRet = Proto->getReturnType()->isSizelessVectorType(); + bool IsScalableArg = false; for (unsigned ArgIdx = 0; ArgIdx < N; ++ArgIdx) { // Args[ArgIdx] can be null in malformed code. if (const Expr *Arg = Args[ArgIdx]) { @@ -7968,7 +7969,7 @@ void Sema::checkCall(NamedDecl *FDecl, const FunctionProtoType *Proto, QualType ParamTy = Proto->getParamType(ArgIdx); if (ParamTy->isSizelessVectorType()) - AnyScalableArgsOrRet = true; + IsScalableArg = true; QualType ArgTy = Arg->getType(); CheckArgAlignment(Arg->getExprLoc(), FDecl, std::to_string(ArgIdx + 1), ArgTy, ParamTy); @@ -7993,7 +7994,8 @@ void Sema::checkCall(NamedDecl *FDecl, const FunctionProtoType *Proto, // arguments or return values, then warn the user that the streaming and // non-streaming vector lengths may be different. const auto *CallerFD = dyn_cast(CurContext); - if (CallerFD && (!FD || !FD->getBuiltinID()) && AnyScalableArgsOrRet) { + if (CallerFD && (!FD || !FD->getBuiltinID()) && + (IsScalableArg || IsScalableRet)) { bool IsCalleeStreaming = ExtInfo.AArch64SMEAttributes & FunctionType::SME_PStateSMEnabledMask; bool IsCalleeStreamingCompatible = @@ -8002,8 +8004,14 @@ void Sema::checkCall(NamedDecl *FDecl, const FunctionProtoType *Proto, ArmStreamingType CallerFnType = getArmStreamingFnType(CallerFD); if (!IsCalleeStreamingCompatible && (CallerFnType == ArmStreamingCompatible || - ((CallerFnType == ArmStreaming) ^ IsCalleeStreaming))) - Diag(Loc, diag::warn_sme_streaming_pass_return_vl_to_non_streaming); + ((CallerFnType == ArmStreaming) ^ IsCalleeStreaming))) { + if (IsScalableArg) + Diag(Loc, diag::warn_sme_streaming_pass_return_vl_to_non_streaming) + << /*IsArg=*/true; + if (IsScalableRet) + Diag(Loc, diag::warn_sme_streaming_pass_return_vl_to_non_streaming) + << /*IsArg=*/false; + } } FunctionType::ArmStateValue CalleeArmZAState = @@ -18716,8 +18724,10 @@ void Sema::CheckArrayAccess(const Expr *expr) { expr = cast(expr)->getBase(); break; } - case Stmt::OMPArraySectionExprClass: { - const OMPArraySectionExpr *ASE = cast(expr); + case Stmt::ArraySectionExprClass: { + const ArraySectionExpr *ASE = cast(expr); + // FIXME: We should probably be checking all of the elements to the + // 'length' here as well. if (ASE->getLowerBound()) CheckArrayAccess(ASE->getBase(), ASE->getLowerBound(), /*ASE=*/nullptr, AllowOnePastEnd > 0); diff --git a/clang/lib/Sema/SemaDecl.cpp b/clang/lib/Sema/SemaDecl.cpp index 452e00fa32b10208a3ce638f4f501eecd818af85..e0745fe9a4536794f437579f5037d1169fef24bb 100644 --- a/clang/lib/Sema/SemaDecl.cpp +++ b/clang/lib/Sema/SemaDecl.cpp @@ -12417,12 +12417,16 @@ bool Sema::CheckFunctionDeclaration(Scope *S, FunctionDecl *NewFD, bool UsesZT0 = Attr && Attr->isNewZT0(); if (NewFD->hasAttr()) { - if (NewFD->getReturnType()->isSizelessVectorType() || - llvm::any_of(NewFD->parameters(), [](ParmVarDecl *P) { + if (NewFD->getReturnType()->isSizelessVectorType()) + Diag(NewFD->getLocation(), + diag::warn_sme_locally_streaming_has_vl_args_returns) + << /*IsArg=*/false; + if (llvm::any_of(NewFD->parameters(), [](ParmVarDecl *P) { return P->getOriginalType()->isSizelessVectorType(); })) Diag(NewFD->getLocation(), - diag::warn_sme_locally_streaming_has_vl_args_returns); + diag::warn_sme_locally_streaming_has_vl_args_returns) + << /*IsArg=*/true; } if (const auto *FPT = NewFD->getType()->getAs()) { FunctionProtoType::ExtProtoInfo EPI = FPT->getExtProtoInfo(); @@ -13498,16 +13502,18 @@ void Sema::checkNonTrivialCUnion(QualType QT, SourceLocation Loc, void Sema::AddInitializerToDecl(Decl *RealDecl, Expr *Init, bool DirectInit) { // If there is no declaration, there was an error parsing it. Just ignore // the initializer. - if (!RealDecl || RealDecl->isInvalidDecl()) { + if (!RealDecl) { CorrectDelayedTyposInExpr(Init, dyn_cast_or_null(RealDecl)); return; } - if (CXXMethodDecl *Method = dyn_cast(RealDecl)) { - // Pure-specifiers are handled in ActOnPureSpecifier. - Diag(Method->getLocation(), diag::err_member_function_initialization) - << Method->getDeclName() << Init->getSourceRange(); - Method->setInvalidDecl(); + if (auto *Method = dyn_cast(RealDecl)) { + if (!Method->isInvalidDecl()) { + // Pure-specifiers are handled in ActOnPureSpecifier. + Diag(Method->getLocation(), diag::err_member_function_initialization) + << Method->getDeclName() << Init->getSourceRange(); + Method->setInvalidDecl(); + } return; } @@ -13519,6 +13525,15 @@ void Sema::AddInitializerToDecl(Decl *RealDecl, Expr *Init, bool DirectInit) { return; } + if (VDecl->isInvalidDecl()) { + CorrectDelayedTyposInExpr(Init, VDecl); + ExprResult Recovery = + CreateRecoveryExpr(Init->getBeginLoc(), Init->getEndLoc(), {Init}); + if (Expr *E = Recovery.get()) + VDecl->setInit(E); + return; + } + // WebAssembly tables can't be used to initialise a variable. if (Init && !Init->getType().isNull() && Init->getType()->isWebAssemblyTableType()) { diff --git a/clang/lib/Sema/SemaExceptionSpec.cpp b/clang/lib/Sema/SemaExceptionSpec.cpp index 00384f9dc16aa04bf43ff94243bda82f8aefb4fd..c9dd6bb2413e38b204ed473ee9a9f88e610d5484 100644 --- a/clang/lib/Sema/SemaExceptionSpec.cpp +++ b/clang/lib/Sema/SemaExceptionSpec.cpp @@ -1314,7 +1314,7 @@ CanThrowResult Sema::canThrow(const Stmt *S) { // Some might be dependent for other reasons. case Expr::ArraySubscriptExprClass: case Expr::MatrixSubscriptExprClass: - case Expr::OMPArraySectionExprClass: + case Expr::ArraySectionExprClass: case Expr::OMPArrayShapingExprClass: case Expr::OMPIteratorExprClass: case Expr::BinaryOperatorClass: diff --git a/clang/lib/Sema/SemaExpr.cpp b/clang/lib/Sema/SemaExpr.cpp index 5c861467bc1023dc85dba17e56d5fdafc2fa6fc3..50f92c496a539a7c1ec459d54831cd6ecbe7f014 100644 --- a/clang/lib/Sema/SemaExpr.cpp +++ b/clang/lib/Sema/SemaExpr.cpp @@ -5069,11 +5069,18 @@ ExprResult Sema::ActOnArraySubscriptExpr(Scope *S, Expr *base, SourceLocation rbLoc) { if (base && !base->getType().isNull() && - base->hasPlaceholderType(BuiltinType::OMPArraySection)) - return OpenMP().ActOnOMPArraySectionExpr(base, lbLoc, ArgExprs.front(), - SourceLocation(), SourceLocation(), - /*Length*/ nullptr, - /*Stride=*/nullptr, rbLoc); + base->hasPlaceholderType(BuiltinType::ArraySection)) { + auto *AS = cast(base); + if (AS->isOMPArraySection()) + return OpenMP().ActOnOMPArraySectionExpr( + base, lbLoc, ArgExprs.front(), SourceLocation(), SourceLocation(), + /*Length*/ nullptr, + /*Stride=*/nullptr, rbLoc); + + return OpenACC().ActOnArraySectionExpr(base, lbLoc, ArgExprs.front(), + SourceLocation(), /*Length*/ nullptr, + rbLoc); + } // Since this might be a postfix expression, get rid of ParenListExprs. if (isa(base)) { @@ -6361,7 +6368,7 @@ static bool isPlaceholderToRemoveAsArg(QualType type) { case BuiltinType::BoundMember: case BuiltinType::BuiltinFn: case BuiltinType::IncompleteMatrixIdx: - case BuiltinType::OMPArraySection: + case BuiltinType::ArraySection: case BuiltinType::OMPArrayShaping: case BuiltinType::OMPIterator: return true; @@ -21343,8 +21350,9 @@ ExprResult Sema::CheckPlaceholderExpr(Expr *E) { return ExprError(); // Expressions of unknown type. - case BuiltinType::OMPArraySection: - Diag(E->getBeginLoc(), diag::err_omp_array_section_use); + case BuiltinType::ArraySection: + Diag(E->getBeginLoc(), diag::err_array_section_use) + << cast(E)->isOMPArraySection(); return ExprError(); // Expressions of unknown type. diff --git a/clang/lib/Sema/SemaInit.cpp b/clang/lib/Sema/SemaInit.cpp index 793e16df17891459d79a4cfd208d55f24558eb76..003a157990d307b43b5dc0a252f73c2004a148a7 100644 --- a/clang/lib/Sema/SemaInit.cpp +++ b/clang/lib/Sema/SemaInit.cpp @@ -7753,9 +7753,9 @@ static void visitLocalsRetainedByReferenceBinding(IndirectLocalPath &Path, break; } - case Stmt::OMPArraySectionExprClass: { + case Stmt::ArraySectionExprClass: { visitLocalsRetainedByInitializer(Path, - cast(Init)->getBase(), + cast(Init)->getBase(), Visit, true, EnableLifetimeWarnings); break; } diff --git a/clang/lib/Sema/SemaOpenACC.cpp b/clang/lib/Sema/SemaOpenACC.cpp index ba69e71e30a181f855f3015c870a201675b37768..d5cfe82a5d70980dd93cadc8a3678cb50528d64a 100644 --- a/clang/lib/Sema/SemaOpenACC.cpp +++ b/clang/lib/Sema/SemaOpenACC.cpp @@ -423,6 +423,21 @@ ExprResult SemaOpenACC::ActOnIntExpr(OpenACCDirectiveKind DK, return IntExpr; } +ExprResult SemaOpenACC::ActOnArraySectionExpr(Expr *Base, SourceLocation LBLoc, + Expr *LowerBound, + SourceLocation ColonLoc, + Expr *Length, + SourceLocation RBLoc) { + ASTContext &Context = getASTContext(); + + // TODO OpenACC: We likely have to reproduce a lot of the same logic from the + // OMP version of this, but at the moment we don't have a good way to test it, + // so for now we'll just create the node. + return new (Context) + ArraySectionExpr(Base, LowerBound, Length, Context.ArraySectionTy, + VK_LValue, OK_Ordinary, ColonLoc, RBLoc); +} + bool SemaOpenACC::ActOnStartStmtDirective(OpenACCDirectiveKind K, SourceLocation StartLoc) { return diagnoseConstructAppertainment(*this, K, StartLoc, /*IsStmt=*/true); diff --git a/clang/lib/Sema/SemaOpenMP.cpp b/clang/lib/Sema/SemaOpenMP.cpp index 5ba09926acf2b9e92c9eb3bcfc29b004d1fdebd3..cee8da495c549566de34ccff6973ccb6b7f2c5e4 100644 --- a/clang/lib/Sema/SemaOpenMP.cpp +++ b/clang/lib/Sema/SemaOpenMP.cpp @@ -2230,7 +2230,7 @@ bool SemaOpenMP::isOpenMPCapturedByRef(const ValueDecl *D, unsigned Level, dyn_cast(Last->getAssociatedExpression()); if ((UO && UO->getOpcode() == UO_Deref) || isa(Last->getAssociatedExpression()) || - isa(Last->getAssociatedExpression()) || + isa(Last->getAssociatedExpression()) || isa(EI->getAssociatedExpression()) || isa(Last->getAssociatedExpression())) { IsVariableAssociatedWithSection = true; @@ -3884,7 +3884,7 @@ public: MappableComponent &MC) { return MC.getAssociatedDeclaration() == nullptr && - (isa( + (isa( MC.getAssociatedExpression()) || isa( MC.getAssociatedExpression()) || @@ -4062,7 +4062,7 @@ public: // Do both expressions have the same kind? if (CCI->getAssociatedExpression()->getStmtClass() != SC.getAssociatedExpression()->getStmtClass()) - if (!((isa( + if (!((isa( SC.getAssociatedExpression()) || isa( SC.getAssociatedExpression())) && @@ -5428,9 +5428,9 @@ static std::pair getPrivateItem(Sema &S, Expr *&RefExpr, Base = TempASE->getBase()->IgnoreParenImpCasts(); RefExpr = Base; IsArrayExpr = ArraySubscript; - } else if (auto *OASE = dyn_cast_or_null(RefExpr)) { + } else if (auto *OASE = dyn_cast_or_null(RefExpr)) { Expr *Base = OASE->getBase()->IgnoreParenImpCasts(); - while (auto *TempOASE = dyn_cast(Base)) + while (auto *TempOASE = dyn_cast(Base)) Base = TempOASE->getBase()->IgnoreParenImpCasts(); while (auto *TempASE = dyn_cast(Base)) Base = TempASE->getBase()->IgnoreParenImpCasts(); @@ -6060,10 +6060,10 @@ processImplicitMapsWithDefaultMappers(Sema &S, DSAStackTy *Stack, // Array section - need to check for the mapping of the array section // element. QualType CanonType = E->getType().getCanonicalType(); - if (CanonType->isSpecificBuiltinType(BuiltinType::OMPArraySection)) { - const auto *OASE = cast(E->IgnoreParenImpCasts()); + if (CanonType->isSpecificBuiltinType(BuiltinType::ArraySection)) { + const auto *OASE = cast(E->IgnoreParenImpCasts()); QualType BaseType = - OMPArraySectionExpr::getBaseOriginalType(OASE->getBase()); + ArraySectionExpr::getBaseOriginalType(OASE->getBase()); QualType ElemType; if (const auto *ATy = BaseType->getAsArrayTypeUnsafe()) ElemType = ATy->getElementType(); @@ -19513,7 +19513,7 @@ struct ReductionData { } // namespace static bool checkOMPArraySectionConstantForReduction( - ASTContext &Context, const OMPArraySectionExpr *OASE, bool &SingleElement, + ASTContext &Context, const ArraySectionExpr *OASE, bool &SingleElement, SmallVectorImpl &ArraySizes) { const Expr *Length = OASE->getLength(); if (Length == nullptr) { @@ -19540,7 +19540,7 @@ static bool checkOMPArraySectionConstantForReduction( // We require length = 1 for all array sections except the right-most to // guarantee that the memory region is contiguous and has no holes in it. - while (const auto *TempOASE = dyn_cast(Base)) { + while (const auto *TempOASE = dyn_cast(Base)) { Length = TempOASE->getLength(); if (Length == nullptr) { // For array sections of the form [1:] or [:], we would need to analyze @@ -19745,12 +19745,12 @@ static bool actOnOMPReductionKindClause( Expr *TaskgroupDescriptor = nullptr; QualType Type; auto *ASE = dyn_cast(RefExpr->IgnoreParens()); - auto *OASE = dyn_cast(RefExpr->IgnoreParens()); + auto *OASE = dyn_cast(RefExpr->IgnoreParens()); if (ASE) { Type = ASE->getType().getNonReferenceType(); } else if (OASE) { QualType BaseType = - OMPArraySectionExpr::getBaseOriginalType(OASE->getBase()); + ArraySectionExpr::getBaseOriginalType(OASE->getBase()); if (const auto *ATy = BaseType->getAsArrayTypeUnsafe()) Type = ATy->getElementType(); else @@ -21284,10 +21284,10 @@ OMPClause *SemaOpenMP::ActOnOpenMPDependClause( // List items used in depend clauses cannot be zero-length array // sections. QualType ExprTy = RefExpr->getType().getNonReferenceType(); - const auto *OASE = dyn_cast(SimpleExpr); + const auto *OASE = dyn_cast(SimpleExpr); if (OASE) { QualType BaseType = - OMPArraySectionExpr::getBaseOriginalType(OASE->getBase()); + ArraySectionExpr::getBaseOriginalType(OASE->getBase()); if (BaseType.isNull()) return nullptr; if (const auto *ATy = BaseType->getAsArrayTypeUnsafe()) @@ -21346,7 +21346,7 @@ OMPClause *SemaOpenMP::ActOnOpenMPDependClause( Res = SemaRef.CreateBuiltinUnaryOp(ELoc, UO_AddrOf, RefExpr->IgnoreParenImpCasts()); } - if (!Res.isUsable() && !isa(SimpleExpr) && + if (!Res.isUsable() && !isa(SimpleExpr) && !isa(SimpleExpr)) { Diag(ELoc, diag::err_omp_expected_addressable_lvalue_or_array_item) << (getLangOpts().OpenMP >= 50 ? 1 : 0) @@ -21447,7 +21447,7 @@ static bool checkTypeMappable(SourceLocation SL, SourceRange SR, Sema &SemaRef, static bool checkArrayExpressionDoesNotReferToWholeSize(Sema &SemaRef, const Expr *E, QualType BaseQTy) { - const auto *OASE = dyn_cast(E); + const auto *OASE = dyn_cast(E); // If this is an array subscript, it refers to the whole size if the size of // the dimension is constant and equals 1. Also, an array section assumes the @@ -21505,7 +21505,7 @@ static bool checkArrayExpressionDoesNotReferToWholeSize(Sema &SemaRef, static bool checkArrayExpressionDoesNotReferToUnitySize(Sema &SemaRef, const Expr *E, QualType BaseQTy) { - const auto *OASE = dyn_cast(E); + const auto *OASE = dyn_cast(E); // An array subscript always refer to a single element. Also, an array section // assumes the format of an array subscript if no colon is used. @@ -21720,14 +21720,14 @@ public: return RelevantExpr || Visit(E); } - bool VisitOMPArraySectionExpr(OMPArraySectionExpr *OASE) { + bool VisitArraySectionExpr(ArraySectionExpr *OASE) { // After OMP 5.0 Array section in reduction clause will be implicitly // mapped assert(!(SemaRef.getLangOpts().OpenMP < 50 && NoDiagnose) && "Array sections cannot be implicitly mapped."); Expr *E = OASE->getBase()->IgnoreParenImpCasts(); QualType CurType = - OMPArraySectionExpr::getBaseOriginalType(E).getCanonicalType(); + ArraySectionExpr::getBaseOriginalType(E).getCanonicalType(); // OpenMP 4.5 [2.15.5.1, map Clause, Restrictions, C++, p.1] // If the type of a list item is a reference to a type T then the type @@ -21900,7 +21900,7 @@ static const Expr *checkMapClauseExpressionBase( auto CE = CurComponents.rend(); for (; CI != CE; ++CI) { const auto *OASE = - dyn_cast(CI->getAssociatedExpression()); + dyn_cast(CI->getAssociatedExpression()); if (!OASE) continue; if (OASE && OASE->getLength()) @@ -21970,10 +21970,10 @@ static bool checkMapConflicts( // variable in map clauses of the same construct. if (CurrentRegionOnly && (isa(CI->getAssociatedExpression()) || - isa(CI->getAssociatedExpression()) || + isa(CI->getAssociatedExpression()) || isa(CI->getAssociatedExpression())) && (isa(SI->getAssociatedExpression()) || - isa(SI->getAssociatedExpression()) || + isa(SI->getAssociatedExpression()) || isa(SI->getAssociatedExpression()))) { SemaRef.Diag(CI->getAssociatedExpression()->getExprLoc(), diag::err_omp_multiple_array_items_in_map_clause) @@ -22001,11 +22001,10 @@ static bool checkMapConflicts( if (const auto *ASE = dyn_cast(SI->getAssociatedExpression())) { Type = ASE->getBase()->IgnoreParenImpCasts()->getType(); - } else if (const auto *OASE = dyn_cast( + } else if (const auto *OASE = dyn_cast( SI->getAssociatedExpression())) { const Expr *E = OASE->getBase()->IgnoreParenImpCasts(); - Type = - OMPArraySectionExpr::getBaseOriginalType(E).getCanonicalType(); + Type = ArraySectionExpr::getBaseOriginalType(E).getCanonicalType(); } else if (const auto *OASE = dyn_cast( SI->getAssociatedExpression())) { Type = OASE->getBase()->getType()->getPointeeType(); @@ -22480,13 +22479,13 @@ static void checkMappableExpressionList( (void)I; QualType Type; auto *ASE = dyn_cast(VE->IgnoreParens()); - auto *OASE = dyn_cast(VE->IgnoreParens()); + auto *OASE = dyn_cast(VE->IgnoreParens()); auto *OAShE = dyn_cast(VE->IgnoreParens()); if (ASE) { Type = ASE->getType().getNonReferenceType(); } else if (OASE) { QualType BaseType = - OMPArraySectionExpr::getBaseOriginalType(OASE->getBase()); + ArraySectionExpr::getBaseOriginalType(OASE->getBase()); if (const auto *ATy = BaseType->getAsArrayTypeUnsafe()) Type = ATy->getElementType(); else @@ -23955,7 +23954,7 @@ SemaOpenMP::ActOnOpenMPUseDeviceAddrClause(ArrayRef VarList, MVLI.VarBaseDeclarations.push_back(D); MVLI.VarComponents.emplace_back(); Expr *Component = SimpleRefExpr; - if (VD && (isa(RefExpr->IgnoreParenImpCasts()) || + if (VD && (isa(RefExpr->IgnoreParenImpCasts()) || isa(RefExpr->IgnoreParenImpCasts()))) Component = SemaRef.DefaultFunctionArrayLvalueConversion(SimpleRefExpr).get(); @@ -24105,7 +24104,7 @@ SemaOpenMP::ActOnOpenMPHasDeviceAddrClause(ArrayRef VarList, // against other clauses later on. Expr *Component = SimpleRefExpr; auto *VD = dyn_cast(D); - if (VD && (isa(RefExpr->IgnoreParenImpCasts()) || + if (VD && (isa(RefExpr->IgnoreParenImpCasts()) || isa(RefExpr->IgnoreParenImpCasts()))) Component = SemaRef.DefaultFunctionArrayLvalueConversion(SimpleRefExpr).get(); @@ -24519,7 +24518,7 @@ OMPClause *SemaOpenMP::ActOnOpenMPAffinityClause( Sema::TentativeAnalysisScope Trap(SemaRef); Res = SemaRef.CreateBuiltinUnaryOp(ELoc, UO_AddrOf, SimpleExpr); } - if (!Res.isUsable() && !isa(SimpleExpr) && + if (!Res.isUsable() && !isa(SimpleExpr) && !isa(SimpleExpr)) { Diag(ELoc, diag::err_omp_expected_addressable_lvalue_or_array_item) << 1 << 0 << RefExpr->getSourceRange(); @@ -24632,7 +24631,7 @@ ExprResult SemaOpenMP::ActOnOMPArraySectionExpr( Expr *Stride, SourceLocation RBLoc) { ASTContext &Context = getASTContext(); if (Base->hasPlaceholderType() && - !Base->hasPlaceholderType(BuiltinType::OMPArraySection)) { + !Base->hasPlaceholderType(BuiltinType::ArraySection)) { ExprResult Result = SemaRef.CheckPlaceholderExpr(Base); if (Result.isInvalid()) return ExprError(); @@ -24672,13 +24671,13 @@ ExprResult SemaOpenMP::ActOnOMPArraySectionExpr( (LowerBound->isTypeDependent() || LowerBound->isValueDependent())) || (Length && (Length->isTypeDependent() || Length->isValueDependent())) || (Stride && (Stride->isTypeDependent() || Stride->isValueDependent()))) { - return new (Context) OMPArraySectionExpr( + return new (Context) ArraySectionExpr( Base, LowerBound, Length, Stride, Context.DependentTy, VK_LValue, OK_Ordinary, ColonLocFirst, ColonLocSecond, RBLoc); } // Perform default conversions. - QualType OriginalTy = OMPArraySectionExpr::getBaseOriginalType(Base); + QualType OriginalTy = ArraySectionExpr::getBaseOriginalType(Base); QualType ResultTy; if (OriginalTy->isAnyPointerType()) { ResultTy = OriginalTy->getPointeeType(); @@ -24801,14 +24800,14 @@ ExprResult SemaOpenMP::ActOnOMPArraySectionExpr( } } - if (!Base->hasPlaceholderType(BuiltinType::OMPArraySection)) { + if (!Base->hasPlaceholderType(BuiltinType::ArraySection)) { ExprResult Result = SemaRef.DefaultFunctionArrayLvalueConversion(Base); if (Result.isInvalid()) return ExprError(); Base = Result.get(); } - return new (Context) OMPArraySectionExpr( - Base, LowerBound, Length, Stride, Context.OMPArraySectionTy, VK_LValue, + return new (Context) ArraySectionExpr( + Base, LowerBound, Length, Stride, Context.ArraySectionTy, VK_LValue, OK_Ordinary, ColonLocFirst, ColonLocSecond, RBLoc); } diff --git a/clang/lib/Sema/SemaRISCVVectorLookup.cpp b/clang/lib/Sema/SemaRISCVVectorLookup.cpp index bf89a4ac51afd22e5660fac5e5a0f364733aa154..26e13e87b1d6b65a0abb1fd964dfe097a2a6d422 100644 --- a/clang/lib/Sema/SemaRISCVVectorLookup.cpp +++ b/clang/lib/Sema/SemaRISCVVectorLookup.cpp @@ -216,6 +216,7 @@ void RISCVIntrinsicManagerImpl::ConstructRVVIntrinsics( {"zvksed", RVV_REQ_Zvksed}, {"zvksh", RVV_REQ_Zvksh}, {"zvfbfwma", RVV_REQ_Zvfbfwma}, + {"zvfbfmin", RVV_REQ_Zvfbfmin}, {"experimental", RVV_REQ_Experimental}}; // Construction of RVVIntrinsicRecords need to sync with createRVVIntrinsics diff --git a/clang/lib/Sema/SemaTemplate.cpp b/clang/lib/Sema/SemaTemplate.cpp index 4bda31ba67c02d03e1d9323fdef4d3e763ca871c..bbcb7c33a985793bd8331e5e3ed5a49cd3b789e6 100644 --- a/clang/lib/Sema/SemaTemplate.cpp +++ b/clang/lib/Sema/SemaTemplate.cpp @@ -9460,6 +9460,7 @@ DeclResult Sema::ActOnClassTemplateSpecialization( Diag(TemplateNameLoc, diag::err_partial_spec_fully_specialized) << ClassTemplate->getDeclName(); isPartialSpecialization = false; + Invalid = true; } } @@ -9675,6 +9676,7 @@ DeclResult Sema::ActOnClassTemplateSpecialization( if (SkipBody && SkipBody->ShouldSkip) return SkipBody->Previous; + Specialization->setInvalidDecl(Invalid); return Specialization; } diff --git a/clang/lib/Sema/SemaTemplateDeduction.cpp b/clang/lib/Sema/SemaTemplateDeduction.cpp index 0b6375001f532623a3a86b0fcf57f163e7afc07b..c3815bca038554bfa1cf76775b1550c55fcbd6c0 100644 --- a/clang/lib/Sema/SemaTemplateDeduction.cpp +++ b/clang/lib/Sema/SemaTemplateDeduction.cpp @@ -1914,6 +1914,9 @@ static TemplateDeductionResult DeduceTemplateArgumentsByTypeMatch( if (!S.isCompleteType(Info.getLocation(), A)) return Result; + if (getCanonicalRD(A)->isInvalidDecl()) + return Result; + // Reset the incorrectly deduced argument from above. Deduced = DeducedOrig; diff --git a/clang/lib/Sema/SemaTemplateInstantiateDecl.cpp b/clang/lib/Sema/SemaTemplateInstantiateDecl.cpp index 787a485e0b2f8c36f9526e3d3f2b5728e68329a6..d544cfac55ba36c057e6fa84667470061df929f9 100644 --- a/clang/lib/Sema/SemaTemplateInstantiateDecl.cpp +++ b/clang/lib/Sema/SemaTemplateInstantiateDecl.cpp @@ -5184,6 +5184,7 @@ void Sema::InstantiateFunctionDefinition(SourceLocation PointOfInstantiation, ParmVarDecl *Parm = Function->getParamDecl(0); TypeSourceInfo *NewParmSI = IR.TransformType(Parm->getTypeSourceInfo()); + assert(NewParmSI && "Type transformation failed."); Parm->setType(NewParmSI->getType()); Parm->setTypeSourceInfo(NewParmSI); }; diff --git a/clang/lib/Sema/TreeTransform.h b/clang/lib/Sema/TreeTransform.h index 539a18eb92a7ce324d5788acf6b91d60b20594c1..f47bc219e6fa32b2368c7b0338c96779f17ec98b 100644 --- a/clang/lib/Sema/TreeTransform.h +++ b/clang/lib/Sema/TreeTransform.h @@ -2784,15 +2784,23 @@ public: /// /// By default, performs semantic analysis to build the new expression. /// Subclasses may override this routine to provide different behavior. - ExprResult RebuildOMPArraySectionExpr(Expr *Base, SourceLocation LBracketLoc, - Expr *LowerBound, - SourceLocation ColonLocFirst, - SourceLocation ColonLocSecond, - Expr *Length, Expr *Stride, - SourceLocation RBracketLoc) { - return getSema().OpenMP().ActOnOMPArraySectionExpr( - Base, LBracketLoc, LowerBound, ColonLocFirst, ColonLocSecond, Length, - Stride, RBracketLoc); + ExprResult RebuildArraySectionExpr(bool IsOMPArraySection, Expr *Base, + SourceLocation LBracketLoc, + Expr *LowerBound, + SourceLocation ColonLocFirst, + SourceLocation ColonLocSecond, + Expr *Length, Expr *Stride, + SourceLocation RBracketLoc) { + if (IsOMPArraySection) + return getSema().OpenMP().ActOnOMPArraySectionExpr( + Base, LBracketLoc, LowerBound, ColonLocFirst, ColonLocSecond, Length, + Stride, RBracketLoc); + + assert(Stride == nullptr && !ColonLocSecond.isValid() && + "Stride/second colon not allowed for OpenACC"); + + return getSema().OpenACC().ActOnArraySectionExpr( + Base, LBracketLoc, LowerBound, ColonLocFirst, Length, RBracketLoc); } /// Build a new array shaping expression. @@ -11742,7 +11750,7 @@ TreeTransform::TransformMatrixSubscriptExpr(MatrixSubscriptExpr *E) { template ExprResult -TreeTransform::TransformOMPArraySectionExpr(OMPArraySectionExpr *E) { +TreeTransform::TransformArraySectionExpr(ArraySectionExpr *E) { ExprResult Base = getDerived().TransformExpr(E->getBase()); if (Base.isInvalid()) return ExprError(); @@ -11762,20 +11770,25 @@ TreeTransform::TransformOMPArraySectionExpr(OMPArraySectionExpr *E) { } ExprResult Stride; - if (Expr *Str = E->getStride()) { - Stride = getDerived().TransformExpr(Str); - if (Stride.isInvalid()) - return ExprError(); + if (E->isOMPArraySection()) { + if (Expr *Str = E->getStride()) { + Stride = getDerived().TransformExpr(Str); + if (Stride.isInvalid()) + return ExprError(); + } } if (!getDerived().AlwaysRebuild() && Base.get() == E->getBase() && - LowerBound.get() == E->getLowerBound() && Length.get() == E->getLength()) + LowerBound.get() == E->getLowerBound() && + Length.get() == E->getLength() && + (E->isOpenACCArraySection() || Stride.get() == E->getStride())) return E; - return getDerived().RebuildOMPArraySectionExpr( - Base.get(), E->getBase()->getEndLoc(), LowerBound.get(), - E->getColonLocFirst(), E->getColonLocSecond(), Length.get(), Stride.get(), - E->getRBracketLoc()); + return getDerived().RebuildArraySectionExpr( + E->isOMPArraySection(), Base.get(), E->getBase()->getEndLoc(), + LowerBound.get(), E->getColonLocFirst(), + E->isOMPArraySection() ? E->getColonLocSecond() : SourceLocation{}, + Length.get(), Stride.get(), E->getRBracketLoc()); } template @@ -12943,19 +12956,6 @@ TreeTransform::TransformCXXNewExpr(CXXNewExpr *E) { ArraySize = NewArraySize.get(); } - // Per C++0x [expr.new]p5, the type being constructed may be a - // typedef of an array type. - QualType AllocType = AllocTypeInfo->getType(); - if (ArraySize && E->isTypeDependent()) { - if (const ConstantArrayType *Array = - SemaRef.Context.getAsConstantArrayType(AllocType)) { - ArraySize = IntegerLiteral::Create(SemaRef.Context, Array->getSize(), - SemaRef.Context.getSizeType(), - E->getBeginLoc()); - AllocType = Array->getElementType(); - } - } - // Transform the placement arguments (if any). bool ArgumentChanged = false; SmallVector PlacementArgs; @@ -13017,6 +13017,7 @@ TreeTransform::TransformCXXNewExpr(CXXNewExpr *E) { return E; } + QualType AllocType = AllocTypeInfo->getType(); if (!ArraySize) { // If no array size was specified, but the new expression was // instantiated with an array type (e.g., "new T" where T is @@ -14198,6 +14199,8 @@ TreeTransform::TransformLambdaExpr(LambdaExpr *E) { // FIXME: Sema's lambda-building mechanism expects us to push an expression // evaluation context even if we're not transforming the function body. getSema().PushExpressionEvaluationContext( + E->getCallOperator()->isConsteval() ? + Sema::ExpressionEvaluationContext::ImmediateFunctionContext : Sema::ExpressionEvaluationContext::PotentiallyEvaluated); Sema::CodeSynthesisContext C; diff --git a/clang/lib/Serialization/ASTCommon.cpp b/clang/lib/Serialization/ASTCommon.cpp index f8d54c0c3989064e43b250f4eb7208d197eba168..e017f5bdb48858b6b936145395b3bf858f124a71 100644 --- a/clang/lib/Serialization/ASTCommon.cpp +++ b/clang/lib/Serialization/ASTCommon.cpp @@ -261,8 +261,8 @@ serialization::TypeIdxFromBuiltin(const BuiltinType *BT) { case BuiltinType::IncompleteMatrixIdx: ID = PREDEF_TYPE_INCOMPLETE_MATRIX_IDX; break; - case BuiltinType::OMPArraySection: - ID = PREDEF_TYPE_OMP_ARRAY_SECTION; + case BuiltinType::ArraySection: + ID = PREDEF_TYPE_ARRAY_SECTION; break; case BuiltinType::OMPArrayShaping: ID = PREDEF_TYPE_OMP_ARRAY_SHAPING; diff --git a/clang/lib/Serialization/ASTReader.cpp b/clang/lib/Serialization/ASTReader.cpp index 43b69045bb05436ff9e086f8992a8189eb91fae1..0ef57a3ea804efcaa9e513e273e8a6b4fab2b4af 100644 --- a/clang/lib/Serialization/ASTReader.cpp +++ b/clang/lib/Serialization/ASTReader.cpp @@ -5101,8 +5101,9 @@ void ASTReader::InitializeContext() { // If there's a listener, notify them that we "read" the translation unit. if (DeserializationListener) - DeserializationListener->DeclRead(PREDEF_DECL_TRANSLATION_UNIT_ID, - Context.getTranslationUnitDecl()); + DeserializationListener->DeclRead( + GlobalDeclID(PREDEF_DECL_TRANSLATION_UNIT_ID), + Context.getTranslationUnitDecl()); // FIXME: Find a better way to deal with collisions between these // built-in types. Right now, we just ignore the problem. @@ -6010,9 +6011,9 @@ llvm::Error ASTReader::ReadSubmoduleBlock(ModuleFile &F, case SUBMODULE_INITIALIZERS: { if (!ContextObj) break; - SmallVector Inits; + SmallVector Inits; for (auto &ID : Record) - Inits.push_back(getGlobalDeclID(F, LocalDeclID(ID)).get()); + Inits.push_back(getGlobalDeclID(F, LocalDeclID(ID))); ContextObj->addLazyModuleInitializers(CurrentModule, Inits); break; } @@ -7384,11 +7385,11 @@ QualType ASTReader::GetType(TypeID ID) { case PREDEF_TYPE_INCOMPLETE_MATRIX_IDX: T = Context.IncompleteMatrixIdxTy; break; - case PREDEF_TYPE_OMP_ARRAY_SECTION: - T = Context.OMPArraySectionTy; + case PREDEF_TYPE_ARRAY_SECTION: + T = Context.ArraySectionTy; break; case PREDEF_TYPE_OMP_ARRAY_SHAPING: - T = Context.OMPArraySectionTy; + T = Context.OMPArrayShapingTy; break; case PREDEF_TYPE_OMP_ITERATOR: T = Context.OMPIteratorTy; @@ -7517,9 +7518,7 @@ ASTRecordReader::readASTTemplateArgumentListInfo() { return ASTTemplateArgumentListInfo::Create(getContext(), Result); } -Decl *ASTReader::GetExternalDecl(DeclID ID) { - return GetDecl(GlobalDeclID(ID)); -} +Decl *ASTReader::GetExternalDecl(GlobalDeclID ID) { return GetDecl(ID); } void ASTReader::CompleteRedeclChain(const Decl *D) { if (NumCurrentElementsDeserializing) { @@ -7668,8 +7667,7 @@ GlobalDeclID ASTReader::getGlobalDeclID(ModuleFile &F, return GlobalDeclID(ID + I->second); } -bool ASTReader::isDeclIDFromModule(serialization::GlobalDeclID ID, - ModuleFile &M) const { +bool ASTReader::isDeclIDFromModule(GlobalDeclID ID, ModuleFile &M) const { // Predefined decls aren't from any module. if (ID.get() < NUM_PREDEF_DECL_IDS) return false; @@ -7768,7 +7766,7 @@ static Decl *getPredefinedDecl(ASTContext &Context, PredefinedDeclIDs ID) { Decl *ASTReader::GetExistingDecl(GlobalDeclID ID) { assert(ContextObj && "reading decl with no AST context"); if (ID.get() < NUM_PREDEF_DECL_IDS) { - Decl *D = getPredefinedDecl(*ContextObj, (PredefinedDeclIDs)ID.get()); + Decl *D = getPredefinedDecl(*ContextObj, (PredefinedDeclIDs)ID); if (D) { // Track that we have merged the declaration with ID \p ID into the // pre-existing predefined declaration \p D. @@ -7805,28 +7803,28 @@ Decl *ASTReader::GetDecl(GlobalDeclID ID) { if (!DeclsLoaded[Index]) { ReadDeclRecord(ID); if (DeserializationListener) - DeserializationListener->DeclRead(ID.get(), DeclsLoaded[Index]); + DeserializationListener->DeclRead(ID, DeclsLoaded[Index]); } return DeclsLoaded[Index]; } -DeclID ASTReader::mapGlobalIDToModuleFileGlobalID(ModuleFile &M, - GlobalDeclID GlobalID) { +LocalDeclID ASTReader::mapGlobalIDToModuleFileGlobalID(ModuleFile &M, + GlobalDeclID GlobalID) { DeclID ID = GlobalID.get(); if (ID < NUM_PREDEF_DECL_IDS) - return ID; + return LocalDeclID(ID); GlobalDeclMapType::const_iterator I = GlobalDeclMap.find(GlobalID); assert(I != GlobalDeclMap.end() && "Corrupted global declaration map"); ModuleFile *Owner = I->second; - llvm::DenseMap::iterator Pos - = M.GlobalToLocalDeclIDs.find(Owner); + llvm::DenseMap::iterator Pos = + M.GlobalToLocalDeclIDs.find(Owner); if (Pos == M.GlobalToLocalDeclIDs.end()) - return 0; + return LocalDeclID(); - return ID - Owner->BaseDeclID + Pos->second; + return LocalDeclID(ID - Owner->BaseDeclID + Pos->second); } GlobalDeclID ASTReader::ReadDeclID(ModuleFile &F, const RecordData &Record, @@ -7872,7 +7870,7 @@ void ASTReader::FindExternalLexicalDecls( if (!IsKindWeWant(K)) continue; - auto ID = (serialization::DeclID)+LexicalDecls[I + 1]; + auto ID = (DeclID) + LexicalDecls[I + 1]; // Don't add predefined declarations to the lexical context more // than once. @@ -7954,7 +7952,7 @@ void ASTReader::FindFileRegionDecls(FileID File, SourceLocation EndLoc = BeginLoc.getLocWithOffset(Length); DeclIDComp DIDComp(*this, *DInfo.Mod); - ArrayRef::iterator BeginIt = + ArrayRef::iterator BeginIt = llvm::lower_bound(DInfo.Decls, BeginLoc, DIDComp); if (BeginIt != DInfo.Decls.begin()) --BeginIt; @@ -7967,13 +7965,12 @@ void ASTReader::FindFileRegionDecls(FileID File, ->isTopLevelDeclInObjCContainer()) --BeginIt; - ArrayRef::iterator EndIt = + ArrayRef::iterator EndIt = llvm::upper_bound(DInfo.Decls, EndLoc, DIDComp); if (EndIt != DInfo.Decls.end()) ++EndIt; - for (ArrayRef::iterator - DIt = BeginIt; DIt != EndIt; ++DIt) + for (ArrayRef::iterator DIt = BeginIt; DIt != EndIt; ++DIt) Decls.push_back(GetDecl(getGlobalDeclID(*DInfo.Mod, *DIt))); } @@ -7994,6 +7991,7 @@ ASTReader::FindExternalVisibleDeclsByName(const DeclContext *DC, // Load the list of declarations. SmallVector Decls; llvm::SmallPtrSet Found; + for (GlobalDeclID ID : It->second.Table.find(Name)) { NamedDecl *ND = cast(GetDecl(ID)); if (ND->getDeclName() == Name && Found.insert(ND).second) diff --git a/clang/lib/Serialization/ASTReaderDecl.cpp b/clang/lib/Serialization/ASTReaderDecl.cpp index bb82173dfe0b3ac6a0320d2b8aef8f1848b52307..744f11de88c2f89cfca2e9999e71582082145ad2 100644 --- a/clang/lib/Serialization/ASTReaderDecl.cpp +++ b/clang/lib/Serialization/ASTReaderDecl.cpp @@ -273,17 +273,15 @@ namespace clang { auto *&LazySpecializations = D->getCommonPtr()->LazySpecializations; if (auto &Old = LazySpecializations) { - IDs.insert(IDs.end(), GlobalDeclIDIterator(Old + 1), - GlobalDeclIDIterator(Old + 1 + Old[0])); + IDs.insert(IDs.end(), Old + 1, Old + 1 + Old[0].get()); llvm::sort(IDs); IDs.erase(std::unique(IDs.begin(), IDs.end()), IDs.end()); } - auto *Result = new (C) serialization::DeclID[1 + IDs.size()]; - *Result = IDs.size(); + auto *Result = new (C) GlobalDeclID[1 + IDs.size()]; + *Result = GlobalDeclID(IDs.size()); - std::copy(DeclIDIterator(IDs.begin()), DeclIDIterator(IDs.end()), - Result + 1); + std::copy(IDs.begin(), IDs.end(), Result + 1); LazySpecializations = Result; } @@ -558,7 +556,7 @@ void ASTDeclReader::Visit(Decl *D) { // If this is a tag declaration with a typedef name for linkage, it's safe // to load that typedef now. - if (NamedDeclForTagDecl != GlobalDeclID()) + if (NamedDeclForTagDecl.isValid()) cast(D)->TypedefNameDeclOrQualifier = cast(Reader.GetDecl(NamedDeclForTagDecl)); } else if (auto *ID = dyn_cast(D)) { @@ -603,7 +601,7 @@ void ASTDeclReader::VisitDecl(Decl *D) { GlobalDeclID SemaDCIDForTemplateParmDecl = readDeclID(); GlobalDeclID LexicalDCIDForTemplateParmDecl = HasStandaloneLexicalDC ? readDeclID() : GlobalDeclID(); - if (LexicalDCIDForTemplateParmDecl == GlobalDeclID()) + if (LexicalDCIDForTemplateParmDecl.isInvalid()) LexicalDCIDForTemplateParmDecl = SemaDCIDForTemplateParmDecl; Reader.addPendingDeclContextInfo(D, SemaDCIDForTemplateParmDecl, @@ -1860,7 +1858,7 @@ void ASTDeclReader::VisitNamespaceDecl(NamespaceDecl *D) { mergeRedeclarable(D, Redecl); - if (AnonNamespace != GlobalDeclID()) { + if (AnonNamespace.isValid()) { // Each module has its own anonymous namespace, which is disjoint from // any other module's anonymous namespaces, so don't attach the anonymous // namespace at all. @@ -2792,9 +2790,9 @@ ASTDeclReader::VisitRedeclarable(Redeclarable *D) { uint64_t RedeclOffset = 0; - // 0 indicates that this declaration was the only declaration of its entity, - // and is used for space optimization. - if (FirstDeclID == GlobalDeclID()) { + // invalid FirstDeclID indicates that this declaration was the only + // declaration of its entity, and is used for space optimization. + if (FirstDeclID.isInvalid()) { FirstDeclID = ThisDeclID; IsKeyDecl = true; IsFirstLocalDecl = true; @@ -3829,240 +3827,232 @@ Decl *ASTReader::ReadDeclRecord(GlobalDeclID ID) { Twine("ASTReader::readDeclRecord failed reading decl code: ") + toString(MaybeDeclCode.takeError())); - DeclID RawGlobalID = ID.get(); switch ((DeclCode)MaybeDeclCode.get()) { case DECL_CONTEXT_LEXICAL: case DECL_CONTEXT_VISIBLE: llvm_unreachable("Record cannot be de-serialized with readDeclRecord"); case DECL_TYPEDEF: - D = TypedefDecl::CreateDeserialized(Context, RawGlobalID); + D = TypedefDecl::CreateDeserialized(Context, ID); break; case DECL_TYPEALIAS: - D = TypeAliasDecl::CreateDeserialized(Context, RawGlobalID); + D = TypeAliasDecl::CreateDeserialized(Context, ID); break; case DECL_ENUM: - D = EnumDecl::CreateDeserialized(Context, RawGlobalID); + D = EnumDecl::CreateDeserialized(Context, ID); break; case DECL_RECORD: - D = RecordDecl::CreateDeserialized(Context, RawGlobalID); + D = RecordDecl::CreateDeserialized(Context, ID); break; case DECL_ENUM_CONSTANT: - D = EnumConstantDecl::CreateDeserialized(Context, RawGlobalID); + D = EnumConstantDecl::CreateDeserialized(Context, ID); break; case DECL_FUNCTION: - D = FunctionDecl::CreateDeserialized(Context, RawGlobalID); + D = FunctionDecl::CreateDeserialized(Context, ID); break; case DECL_LINKAGE_SPEC: - D = LinkageSpecDecl::CreateDeserialized(Context, RawGlobalID); + D = LinkageSpecDecl::CreateDeserialized(Context, ID); break; case DECL_EXPORT: - D = ExportDecl::CreateDeserialized(Context, RawGlobalID); + D = ExportDecl::CreateDeserialized(Context, ID); break; case DECL_LABEL: - D = LabelDecl::CreateDeserialized(Context, RawGlobalID); + D = LabelDecl::CreateDeserialized(Context, ID); break; case DECL_NAMESPACE: - D = NamespaceDecl::CreateDeserialized(Context, RawGlobalID); + D = NamespaceDecl::CreateDeserialized(Context, ID); break; case DECL_NAMESPACE_ALIAS: - D = NamespaceAliasDecl::CreateDeserialized(Context, RawGlobalID); + D = NamespaceAliasDecl::CreateDeserialized(Context, ID); break; case DECL_USING: - D = UsingDecl::CreateDeserialized(Context, RawGlobalID); + D = UsingDecl::CreateDeserialized(Context, ID); break; case DECL_USING_PACK: - D = UsingPackDecl::CreateDeserialized(Context, RawGlobalID, - Record.readInt()); + D = UsingPackDecl::CreateDeserialized(Context, ID, Record.readInt()); break; case DECL_USING_SHADOW: - D = UsingShadowDecl::CreateDeserialized(Context, RawGlobalID); + D = UsingShadowDecl::CreateDeserialized(Context, ID); break; case DECL_USING_ENUM: - D = UsingEnumDecl::CreateDeserialized(Context, RawGlobalID); + D = UsingEnumDecl::CreateDeserialized(Context, ID); break; case DECL_CONSTRUCTOR_USING_SHADOW: - D = ConstructorUsingShadowDecl::CreateDeserialized(Context, RawGlobalID); + D = ConstructorUsingShadowDecl::CreateDeserialized(Context, ID); break; case DECL_USING_DIRECTIVE: - D = UsingDirectiveDecl::CreateDeserialized(Context, RawGlobalID); + D = UsingDirectiveDecl::CreateDeserialized(Context, ID); break; case DECL_UNRESOLVED_USING_VALUE: - D = UnresolvedUsingValueDecl::CreateDeserialized(Context, RawGlobalID); + D = UnresolvedUsingValueDecl::CreateDeserialized(Context, ID); break; case DECL_UNRESOLVED_USING_TYPENAME: - D = UnresolvedUsingTypenameDecl::CreateDeserialized(Context, RawGlobalID); + D = UnresolvedUsingTypenameDecl::CreateDeserialized(Context, ID); break; case DECL_UNRESOLVED_USING_IF_EXISTS: - D = UnresolvedUsingIfExistsDecl::CreateDeserialized(Context, RawGlobalID); + D = UnresolvedUsingIfExistsDecl::CreateDeserialized(Context, ID); break; case DECL_CXX_RECORD: - D = CXXRecordDecl::CreateDeserialized(Context, RawGlobalID); + D = CXXRecordDecl::CreateDeserialized(Context, ID); break; case DECL_CXX_DEDUCTION_GUIDE: - D = CXXDeductionGuideDecl::CreateDeserialized(Context, RawGlobalID); + D = CXXDeductionGuideDecl::CreateDeserialized(Context, ID); break; case DECL_CXX_METHOD: - D = CXXMethodDecl::CreateDeserialized(Context, RawGlobalID); + D = CXXMethodDecl::CreateDeserialized(Context, ID); break; case DECL_CXX_CONSTRUCTOR: - D = CXXConstructorDecl::CreateDeserialized(Context, RawGlobalID, - Record.readInt()); + D = CXXConstructorDecl::CreateDeserialized(Context, ID, Record.readInt()); break; case DECL_CXX_DESTRUCTOR: - D = CXXDestructorDecl::CreateDeserialized(Context, RawGlobalID); + D = CXXDestructorDecl::CreateDeserialized(Context, ID); break; case DECL_CXX_CONVERSION: - D = CXXConversionDecl::CreateDeserialized(Context, RawGlobalID); + D = CXXConversionDecl::CreateDeserialized(Context, ID); break; case DECL_ACCESS_SPEC: - D = AccessSpecDecl::CreateDeserialized(Context, RawGlobalID); + D = AccessSpecDecl::CreateDeserialized(Context, ID); break; case DECL_FRIEND: - D = FriendDecl::CreateDeserialized(Context, RawGlobalID, Record.readInt()); + D = FriendDecl::CreateDeserialized(Context, ID, Record.readInt()); break; case DECL_FRIEND_TEMPLATE: - D = FriendTemplateDecl::CreateDeserialized(Context, RawGlobalID); + D = FriendTemplateDecl::CreateDeserialized(Context, ID); break; case DECL_CLASS_TEMPLATE: - D = ClassTemplateDecl::CreateDeserialized(Context, RawGlobalID); + D = ClassTemplateDecl::CreateDeserialized(Context, ID); break; case DECL_CLASS_TEMPLATE_SPECIALIZATION: - D = ClassTemplateSpecializationDecl::CreateDeserialized(Context, - RawGlobalID); + D = ClassTemplateSpecializationDecl::CreateDeserialized(Context, ID); break; case DECL_CLASS_TEMPLATE_PARTIAL_SPECIALIZATION: - D = ClassTemplatePartialSpecializationDecl::CreateDeserialized(Context, - RawGlobalID); + D = ClassTemplatePartialSpecializationDecl::CreateDeserialized(Context, ID); break; case DECL_VAR_TEMPLATE: - D = VarTemplateDecl::CreateDeserialized(Context, RawGlobalID); + D = VarTemplateDecl::CreateDeserialized(Context, ID); break; case DECL_VAR_TEMPLATE_SPECIALIZATION: - D = VarTemplateSpecializationDecl::CreateDeserialized(Context, RawGlobalID); + D = VarTemplateSpecializationDecl::CreateDeserialized(Context, ID); break; case DECL_VAR_TEMPLATE_PARTIAL_SPECIALIZATION: - D = VarTemplatePartialSpecializationDecl::CreateDeserialized(Context, - RawGlobalID); + D = VarTemplatePartialSpecializationDecl::CreateDeserialized(Context, ID); break; case DECL_FUNCTION_TEMPLATE: - D = FunctionTemplateDecl::CreateDeserialized(Context, RawGlobalID); + D = FunctionTemplateDecl::CreateDeserialized(Context, ID); break; case DECL_TEMPLATE_TYPE_PARM: { bool HasTypeConstraint = Record.readInt(); - D = TemplateTypeParmDecl::CreateDeserialized(Context, RawGlobalID, + D = TemplateTypeParmDecl::CreateDeserialized(Context, ID, HasTypeConstraint); break; } case DECL_NON_TYPE_TEMPLATE_PARM: { bool HasTypeConstraint = Record.readInt(); - D = NonTypeTemplateParmDecl::CreateDeserialized(Context, RawGlobalID, + D = NonTypeTemplateParmDecl::CreateDeserialized(Context, ID, HasTypeConstraint); break; } case DECL_EXPANDED_NON_TYPE_TEMPLATE_PARM_PACK: { bool HasTypeConstraint = Record.readInt(); D = NonTypeTemplateParmDecl::CreateDeserialized( - Context, RawGlobalID, Record.readInt(), HasTypeConstraint); + Context, ID, Record.readInt(), HasTypeConstraint); break; } case DECL_TEMPLATE_TEMPLATE_PARM: - D = TemplateTemplateParmDecl::CreateDeserialized(Context, RawGlobalID); + D = TemplateTemplateParmDecl::CreateDeserialized(Context, ID); break; case DECL_EXPANDED_TEMPLATE_TEMPLATE_PARM_PACK: - D = TemplateTemplateParmDecl::CreateDeserialized(Context, RawGlobalID, + D = TemplateTemplateParmDecl::CreateDeserialized(Context, ID, Record.readInt()); break; case DECL_TYPE_ALIAS_TEMPLATE: - D = TypeAliasTemplateDecl::CreateDeserialized(Context, RawGlobalID); + D = TypeAliasTemplateDecl::CreateDeserialized(Context, ID); break; case DECL_CONCEPT: - D = ConceptDecl::CreateDeserialized(Context, RawGlobalID); + D = ConceptDecl::CreateDeserialized(Context, ID); break; case DECL_REQUIRES_EXPR_BODY: - D = RequiresExprBodyDecl::CreateDeserialized(Context, RawGlobalID); + D = RequiresExprBodyDecl::CreateDeserialized(Context, ID); break; case DECL_STATIC_ASSERT: - D = StaticAssertDecl::CreateDeserialized(Context, RawGlobalID); + D = StaticAssertDecl::CreateDeserialized(Context, ID); break; case DECL_OBJC_METHOD: - D = ObjCMethodDecl::CreateDeserialized(Context, RawGlobalID); + D = ObjCMethodDecl::CreateDeserialized(Context, ID); break; case DECL_OBJC_INTERFACE: - D = ObjCInterfaceDecl::CreateDeserialized(Context, RawGlobalID); + D = ObjCInterfaceDecl::CreateDeserialized(Context, ID); break; case DECL_OBJC_IVAR: - D = ObjCIvarDecl::CreateDeserialized(Context, RawGlobalID); + D = ObjCIvarDecl::CreateDeserialized(Context, ID); break; case DECL_OBJC_PROTOCOL: - D = ObjCProtocolDecl::CreateDeserialized(Context, RawGlobalID); + D = ObjCProtocolDecl::CreateDeserialized(Context, ID); break; case DECL_OBJC_AT_DEFS_FIELD: - D = ObjCAtDefsFieldDecl::CreateDeserialized(Context, RawGlobalID); + D = ObjCAtDefsFieldDecl::CreateDeserialized(Context, ID); break; case DECL_OBJC_CATEGORY: - D = ObjCCategoryDecl::CreateDeserialized(Context, RawGlobalID); + D = ObjCCategoryDecl::CreateDeserialized(Context, ID); break; case DECL_OBJC_CATEGORY_IMPL: - D = ObjCCategoryImplDecl::CreateDeserialized(Context, RawGlobalID); + D = ObjCCategoryImplDecl::CreateDeserialized(Context, ID); break; case DECL_OBJC_IMPLEMENTATION: - D = ObjCImplementationDecl::CreateDeserialized(Context, RawGlobalID); + D = ObjCImplementationDecl::CreateDeserialized(Context, ID); break; case DECL_OBJC_COMPATIBLE_ALIAS: - D = ObjCCompatibleAliasDecl::CreateDeserialized(Context, RawGlobalID); + D = ObjCCompatibleAliasDecl::CreateDeserialized(Context, ID); break; case DECL_OBJC_PROPERTY: - D = ObjCPropertyDecl::CreateDeserialized(Context, RawGlobalID); + D = ObjCPropertyDecl::CreateDeserialized(Context, ID); break; case DECL_OBJC_PROPERTY_IMPL: - D = ObjCPropertyImplDecl::CreateDeserialized(Context, RawGlobalID); + D = ObjCPropertyImplDecl::CreateDeserialized(Context, ID); break; case DECL_FIELD: - D = FieldDecl::CreateDeserialized(Context, RawGlobalID); + D = FieldDecl::CreateDeserialized(Context, ID); break; case DECL_INDIRECTFIELD: - D = IndirectFieldDecl::CreateDeserialized(Context, RawGlobalID); + D = IndirectFieldDecl::CreateDeserialized(Context, ID); break; case DECL_VAR: - D = VarDecl::CreateDeserialized(Context, RawGlobalID); + D = VarDecl::CreateDeserialized(Context, ID); break; case DECL_IMPLICIT_PARAM: - D = ImplicitParamDecl::CreateDeserialized(Context, RawGlobalID); + D = ImplicitParamDecl::CreateDeserialized(Context, ID); break; case DECL_PARM_VAR: - D = ParmVarDecl::CreateDeserialized(Context, RawGlobalID); + D = ParmVarDecl::CreateDeserialized(Context, ID); break; case DECL_DECOMPOSITION: - D = DecompositionDecl::CreateDeserialized(Context, RawGlobalID, - Record.readInt()); + D = DecompositionDecl::CreateDeserialized(Context, ID, Record.readInt()); break; case DECL_BINDING: - D = BindingDecl::CreateDeserialized(Context, RawGlobalID); + D = BindingDecl::CreateDeserialized(Context, ID); break; case DECL_FILE_SCOPE_ASM: - D = FileScopeAsmDecl::CreateDeserialized(Context, RawGlobalID); + D = FileScopeAsmDecl::CreateDeserialized(Context, ID); break; case DECL_TOP_LEVEL_STMT_DECL: - D = TopLevelStmtDecl::CreateDeserialized(Context, RawGlobalID); + D = TopLevelStmtDecl::CreateDeserialized(Context, ID); break; case DECL_BLOCK: - D = BlockDecl::CreateDeserialized(Context, RawGlobalID); + D = BlockDecl::CreateDeserialized(Context, ID); break; case DECL_MS_PROPERTY: - D = MSPropertyDecl::CreateDeserialized(Context, RawGlobalID); + D = MSPropertyDecl::CreateDeserialized(Context, ID); break; case DECL_MS_GUID: - D = MSGuidDecl::CreateDeserialized(Context, RawGlobalID); + D = MSGuidDecl::CreateDeserialized(Context, ID); break; case DECL_UNNAMED_GLOBAL_CONSTANT: - D = UnnamedGlobalConstantDecl::CreateDeserialized(Context, RawGlobalID); + D = UnnamedGlobalConstantDecl::CreateDeserialized(Context, ID); break; case DECL_TEMPLATE_PARAM_OBJECT: - D = TemplateParamObjectDecl::CreateDeserialized(Context, RawGlobalID); + D = TemplateParamObjectDecl::CreateDeserialized(Context, ID); break; case DECL_CAPTURED: - D = CapturedDecl::CreateDeserialized(Context, RawGlobalID, - Record.readInt()); + D = CapturedDecl::CreateDeserialized(Context, ID, Record.readInt()); break; case DECL_CXX_BASE_SPECIFIERS: Error("attempt to read a C++ base-specifier record as a declaration"); @@ -4073,66 +4063,62 @@ Decl *ASTReader::ReadDeclRecord(GlobalDeclID ID) { case DECL_IMPORT: // Note: last entry of the ImportDecl record is the number of stored source // locations. - D = ImportDecl::CreateDeserialized(Context, RawGlobalID, Record.back()); + D = ImportDecl::CreateDeserialized(Context, ID, Record.back()); break; case DECL_OMP_THREADPRIVATE: { Record.skipInts(1); unsigned NumChildren = Record.readInt(); Record.skipInts(1); - D = OMPThreadPrivateDecl::CreateDeserialized(Context, RawGlobalID, - NumChildren); + D = OMPThreadPrivateDecl::CreateDeserialized(Context, ID, NumChildren); break; } case DECL_OMP_ALLOCATE: { unsigned NumClauses = Record.readInt(); unsigned NumVars = Record.readInt(); Record.skipInts(1); - D = OMPAllocateDecl::CreateDeserialized(Context, RawGlobalID, NumVars, - NumClauses); + D = OMPAllocateDecl::CreateDeserialized(Context, ID, NumVars, NumClauses); break; } case DECL_OMP_REQUIRES: { unsigned NumClauses = Record.readInt(); Record.skipInts(2); - D = OMPRequiresDecl::CreateDeserialized(Context, RawGlobalID, NumClauses); + D = OMPRequiresDecl::CreateDeserialized(Context, ID, NumClauses); break; } case DECL_OMP_DECLARE_REDUCTION: - D = OMPDeclareReductionDecl::CreateDeserialized(Context, RawGlobalID); + D = OMPDeclareReductionDecl::CreateDeserialized(Context, ID); break; case DECL_OMP_DECLARE_MAPPER: { unsigned NumClauses = Record.readInt(); Record.skipInts(2); - D = OMPDeclareMapperDecl::CreateDeserialized(Context, RawGlobalID, - NumClauses); + D = OMPDeclareMapperDecl::CreateDeserialized(Context, ID, NumClauses); break; } case DECL_OMP_CAPTUREDEXPR: - D = OMPCapturedExprDecl::CreateDeserialized(Context, RawGlobalID); + D = OMPCapturedExprDecl::CreateDeserialized(Context, ID); break; case DECL_PRAGMA_COMMENT: - D = PragmaCommentDecl::CreateDeserialized(Context, RawGlobalID, - Record.readInt()); + D = PragmaCommentDecl::CreateDeserialized(Context, ID, Record.readInt()); break; case DECL_PRAGMA_DETECT_MISMATCH: - D = PragmaDetectMismatchDecl::CreateDeserialized(Context, RawGlobalID, + D = PragmaDetectMismatchDecl::CreateDeserialized(Context, ID, Record.readInt()); break; case DECL_EMPTY: - D = EmptyDecl::CreateDeserialized(Context, RawGlobalID); + D = EmptyDecl::CreateDeserialized(Context, ID); break; case DECL_LIFETIME_EXTENDED_TEMPORARY: - D = LifetimeExtendedTemporaryDecl::CreateDeserialized(Context, RawGlobalID); + D = LifetimeExtendedTemporaryDecl::CreateDeserialized(Context, ID); break; case DECL_OBJC_TYPE_PARAM: - D = ObjCTypeParamDecl::CreateDeserialized(Context, RawGlobalID); + D = ObjCTypeParamDecl::CreateDeserialized(Context, ID); break; case DECL_HLSL_BUFFER: - D = HLSLBufferDecl::CreateDeserialized(Context, RawGlobalID); + D = HLSLBufferDecl::CreateDeserialized(Context, ID); break; case DECL_IMPLICIT_CONCEPT_SPECIALIZATION: - D = ImplicitConceptSpecializationDecl::CreateDeserialized( - Context, RawGlobalID, Record.readInt()); + D = ImplicitConceptSpecializationDecl::CreateDeserialized(Context, ID, + Record.readInt()); break; } @@ -4215,7 +4201,7 @@ void ASTReader::loadDeclUpdateRecords(PendingUpdateRecord &Record) { // The declaration may have been modified by files later in the chain. // If this is the case, read the record containing the updates from each file // and pass it to ASTDeclReader to make the modifications. - serialization::GlobalDeclID ID = Record.ID; + GlobalDeclID ID = Record.ID; Decl *D = Record.D; ProcessingUpdatesRAIIObj ProcessingUpdates(*this); DeclUpdateOffsetsMap::iterator UpdI = DeclUpdateOffsets.find(ID); @@ -4357,7 +4343,7 @@ namespace { llvm::SmallPtrSetImpl &Deserialized; ObjCCategoryDecl *Tail = nullptr; llvm::DenseMap NameCategoryMap; - serialization::GlobalDeclID InterfaceID; + GlobalDeclID InterfaceID; unsigned PreviousGeneration; void add(ObjCCategoryDecl *Cat) { @@ -4399,11 +4385,10 @@ namespace { } public: - ObjCCategoriesVisitor(ASTReader &Reader, - ObjCInterfaceDecl *Interface, - llvm::SmallPtrSetImpl &Deserialized, - serialization::GlobalDeclID InterfaceID, - unsigned PreviousGeneration) + ObjCCategoriesVisitor( + ASTReader &Reader, ObjCInterfaceDecl *Interface, + llvm::SmallPtrSetImpl &Deserialized, + GlobalDeclID InterfaceID, unsigned PreviousGeneration) : Reader(Reader), Interface(Interface), Deserialized(Deserialized), InterfaceID(InterfaceID), PreviousGeneration(PreviousGeneration) { // Populate the name -> category map with the set of known categories. @@ -4425,8 +4410,9 @@ namespace { // Map global ID of the definition down to the local ID used in this // module file. If there is no such mapping, we'll find nothing here // (or in any module it imports). - DeclID LocalID = Reader.mapGlobalIDToModuleFileGlobalID(M, InterfaceID); - if (!LocalID) + LocalDeclID LocalID = + Reader.mapGlobalIDToModuleFileGlobalID(M, InterfaceID); + if (LocalID.isInvalid()) return true; // Perform a binary search to find the local redeclarations for this @@ -4457,8 +4443,7 @@ namespace { } // namespace -void ASTReader::loadObjCCategories(serialization::GlobalDeclID ID, - ObjCInterfaceDecl *D, +void ASTReader::loadObjCCategories(GlobalDeclID ID, ObjCInterfaceDecl *D, unsigned PreviousGeneration) { ObjCCategoriesVisitor Visitor(*this, D, CategoriesDeserialized, ID, PreviousGeneration); diff --git a/clang/lib/Serialization/ASTReaderStmt.cpp b/clang/lib/Serialization/ASTReaderStmt.cpp index baded0fe19831ff62d6b8d5739093fcad8407b20..7d3930022a69c02997ddfd92be91bcc29e7e5ecf 100644 --- a/clang/lib/Serialization/ASTReaderStmt.cpp +++ b/clang/lib/Serialization/ASTReaderStmt.cpp @@ -956,14 +956,22 @@ void ASTStmtReader::VisitMatrixSubscriptExpr(MatrixSubscriptExpr *E) { E->setRBracketLoc(readSourceLocation()); } -void ASTStmtReader::VisitOMPArraySectionExpr(OMPArraySectionExpr *E) { +void ASTStmtReader::VisitArraySectionExpr(ArraySectionExpr *E) { VisitExpr(E); + E->ASType = Record.readEnum(); + E->setBase(Record.readSubExpr()); E->setLowerBound(Record.readSubExpr()); E->setLength(Record.readSubExpr()); - E->setStride(Record.readSubExpr()); + + if (E->isOMPArraySection()) + E->setStride(Record.readSubExpr()); + E->setColonLocFirst(readSourceLocation()); - E->setColonLocSecond(readSourceLocation()); + + if (E->isOMPArraySection()) + E->setColonLocSecond(readSourceLocation()); + E->setRBracketLoc(readSourceLocation()); } @@ -3090,8 +3098,8 @@ Stmt *ASTReader::ReadStmtFromStream(ModuleFile &F) { S = new (Context) MatrixSubscriptExpr(Empty); break; - case EXPR_OMP_ARRAY_SECTION: - S = new (Context) OMPArraySectionExpr(Empty); + case EXPR_ARRAY_SECTION: + S = new (Context) ArraySectionExpr(Empty); break; case EXPR_OMP_ARRAY_SHAPING: diff --git a/clang/lib/Serialization/ASTWriter.cpp b/clang/lib/Serialization/ASTWriter.cpp index 21cf72ab0f912146fc89b1be2b91a2c7f5f4418b..0408eeb6a95b0075d7a1c23b7be299d653bccf52 100644 --- a/clang/lib/Serialization/ASTWriter.cpp +++ b/clang/lib/Serialization/ASTWriter.cpp @@ -171,34 +171,9 @@ GetAffectingModuleMaps(const Preprocessor &PP, Module *RootModule) { .ModulesPruneNonAffectingModuleMaps) return std::nullopt; - SmallVector ModulesToProcess{RootModule}; - const HeaderSearch &HS = PP.getHeaderSearchInfo(); - - SmallVector FilesByUID; - HS.getFileMgr().GetUniqueIDMapping(FilesByUID); - - if (FilesByUID.size() > HS.header_file_size()) - FilesByUID.resize(HS.header_file_size()); - - for (unsigned UID = 0, LastUID = FilesByUID.size(); UID != LastUID; ++UID) { - OptionalFileEntryRef File = FilesByUID[UID]; - if (!File) - continue; - - const HeaderFileInfo *HFI = HS.getExistingLocalFileInfo(*File); - if (!HFI || (HFI->isModuleHeader && !HFI->isCompilingModuleHeader)) - continue; - - for (const auto &KH : HS.findResolvedModulesForHeader(*File)) { - if (!KH.getModule()) - continue; - ModulesToProcess.push_back(KH.getModule()); - } - } - const ModuleMap &MM = HS.getModuleMap(); - SourceManager &SourceMgr = PP.getSourceManager(); + const SourceManager &SourceMgr = PP.getSourceManager(); std::set ModuleMaps; auto CollectIncludingModuleMaps = [&](FileID FID, FileEntryRef F) { @@ -233,12 +208,48 @@ GetAffectingModuleMaps(const Preprocessor &PP, Module *RootModule) { } }; - for (const Module *CurrentModule : ModulesToProcess) { + // Handle all the affecting modules referenced from the root module. + + std::queue Q; + Q.push(RootModule); + while (!Q.empty()) { + const Module *CurrentModule = Q.front(); + Q.pop(); + CollectIncludingMapsFromAncestors(CurrentModule); for (const Module *ImportedModule : CurrentModule->Imports) CollectIncludingMapsFromAncestors(ImportedModule); for (const Module *UndeclaredModule : CurrentModule->UndeclaredUses) CollectIncludingMapsFromAncestors(UndeclaredModule); + + for (auto *M : CurrentModule->submodules()) + Q.push(M); + } + + // Handle textually-included headers that belong to other modules. + + SmallVector FilesByUID; + HS.getFileMgr().GetUniqueIDMapping(FilesByUID); + + if (FilesByUID.size() > HS.header_file_size()) + FilesByUID.resize(HS.header_file_size()); + + for (unsigned UID = 0, LastUID = FilesByUID.size(); UID != LastUID; ++UID) { + OptionalFileEntryRef File = FilesByUID[UID]; + if (!File) + continue; + + const HeaderFileInfo *HFI = HS.getExistingLocalFileInfo(*File); + if (!HFI) + continue; // We have no information on this being a header file. + if (!HFI->isCompilingModuleHeader && HFI->isModuleHeader) + continue; // Modular header, handled in the above module-based loop. + if (!HFI->isCompilingModuleHeader && !HFI->IsLocallyIncluded) + continue; // Non-modular header not included locally is not affecting. + + for (const auto &KH : HS.findResolvedModulesForHeader(*File)) + if (const Module *M = KH.getModule()) + CollectIncludingMapsFromAncestors(M); } return ModuleMaps; @@ -2053,14 +2064,13 @@ void ASTWriter::WriteHeaderSearch(const HeaderSearch &HS) { if (!File) continue; - // Get the file info. Skip emitting this file if we have no information on - // it as a header file (in which case HFI will be null) or if it hasn't - // changed since it was loaded. Also skip it if it's for a modular header - // from a different module; in that case, we rely on the module(s) - // containing the header to provide this information. const HeaderFileInfo *HFI = HS.getExistingLocalFileInfo(*File); - if (!HFI || (HFI->isModuleHeader && !HFI->isCompilingModuleHeader)) - continue; + if (!HFI) + continue; // We have no information on this being a header file. + if (!HFI->isCompilingModuleHeader && HFI->isModuleHeader) + continue; // Header file info is tracked by the owning module file. + if (!HFI->isCompilingModuleHeader && !PP->alreadyIncluded(*File)) + continue; // Non-modular header not included is not needed. // Massage the file path into an appropriate form. StringRef Filename = File->getName(); @@ -3033,7 +3043,7 @@ void ASTWriter::WriteSubmodules(Module *WritingModule) { RecordData Inits; for (Decl *D : Context->getModuleInitializers(Mod)) if (wasDeclEmitted(D)) - Inits.push_back(GetDeclRef(D)); + AddDeclRef(D, Inits); if (!Inits.empty()) Stream.EmitRecord(SUBMODULE_INITIALIZERS, Inits); @@ -3216,7 +3226,7 @@ uint64_t ASTWriter::WriteDeclContextLexicalBlock(ASTContext &Context, continue; KindDeclPairs.push_back(D->getKind()); - KindDeclPairs.push_back(GetDeclRef(D)); + KindDeclPairs.push_back(GetDeclRef(D).get()); } ++NumLexicalDeclContexts; @@ -3251,7 +3261,7 @@ void ASTWriter::WriteTypeDeclOffsets() { unsigned DeclOffsetAbbrev = Stream.EmitAbbrev(std::move(Abbrev)); { RecordData::value_type Record[] = {DECL_OFFSET, DeclOffsets.size(), - FirstDeclID - NUM_PREDEF_DECL_IDS}; + FirstDeclID.get() - NUM_PREDEF_DECL_IDS}; Stream.EmitRecordWithBlob(DeclOffsetAbbrev, Record, bytes(DeclOffsets)); } } @@ -3272,7 +3282,7 @@ void ASTWriter::WriteFileDeclIDsMap() { Info.FirstDeclIndex = FileGroupedDeclIDs.size(); llvm::stable_sort(Info.DeclIDs); for (auto &LocDeclEntry : Info.DeclIDs) - FileGroupedDeclIDs.push_back(LocDeclEntry.second); + FileGroupedDeclIDs.push_back(LocDeclEntry.second.get()); } auto Abbrev = std::make_shared(); @@ -3410,11 +3420,11 @@ public: for (const ObjCMethodList *Method = &Methods.Instance; Method; Method = Method->getNext()) if (ShouldWriteMethodListNode(Method)) - LE.write(Writer.getDeclID(Method->getMethod())); + LE.write((DeclID)Writer.getDeclID(Method->getMethod())); for (const ObjCMethodList *Method = &Methods.Factory; Method; Method = Method->getNext()) if (ShouldWriteMethodListNode(Method)) - LE.write(Writer.getDeclID(Method->getMethod())); + LE.write((DeclID)Writer.getDeclID(Method->getMethod())); assert(Out.tell() - Start == DataLen && "Data length is wrong"); } @@ -3618,7 +3628,6 @@ class ASTIdentifierTableTrait { /// doesn't check whether the name has macros defined; use PublicMacroIterator /// to check that. bool isInterestingIdentifier(const IdentifierInfo *II, uint64_t MacroOffset) { - II->getObjCOrBuiltinID(); bool IsInteresting = II->getNotableIdentifierID() != tok::NotableIdentifierKind::not_notable || @@ -3734,8 +3743,8 @@ public: // Only emit declarations that aren't from a chained PCH, though. SmallVector Decls(IdResolver.decls(II)); for (NamedDecl *D : llvm::reverse(Decls)) - LE.write( - Writer.getDeclID(getDeclForLocalLookup(PP.getLangOpts(), D))); + LE.write((DeclID)Writer.getDeclID( + getDeclForLocalLookup(PP.getLangOpts(), D))); } } }; @@ -3851,7 +3860,7 @@ namespace { // Trait used for the on-disk hash table used in the method pool. class ASTDeclContextNameLookupTrait { ASTWriter &Writer; - llvm::SmallVector DeclIDs; + llvm::SmallVector DeclIDs; public: using key_type = DeclarationNameKey; @@ -3884,8 +3893,10 @@ public: data_type ImportData(const reader::ASTDeclContextNameLookupTrait::data_type &FromReader) { unsigned Start = DeclIDs.size(); - DeclIDs.insert(DeclIDs.end(), DeclIDIterator(FromReader.begin()), - DeclIDIterator(FromReader.end())); + DeclIDs.insert( + DeclIDs.end(), + DeclIDIterator(FromReader.begin()), + DeclIDIterator(FromReader.end())); return std::make_pair(Start, DeclIDs.size()); } @@ -3974,7 +3985,7 @@ public: endian::Writer LE(Out, llvm::endianness::little); uint64_t Start = Out.tell(); (void)Start; for (unsigned I = Lookup.first, N = Lookup.second; I != N; ++I) - LE.write(DeclIDs[I]); + LE.write((DeclID)DeclIDs[I]); assert(Out.tell() - Start == DataLen && "Data length is wrong"); } }; @@ -4308,7 +4319,8 @@ void ASTWriter::WriteDeclContextVisibleUpdate(const DeclContext *DC) { DC = cast(Chain->getKeyDeclaration(cast(DC))); // Write the lookup table - RecordData::value_type Record[] = {UPDATE_VISIBLE, getDeclID(cast(DC))}; + RecordData::value_type Record[] = {UPDATE_VISIBLE, + getDeclID(cast(DC)).get()}; Stream.EmitRecordWithBlob(UpdateVisibleAbbrev, Record, LookupTable); } @@ -4362,7 +4374,7 @@ void ASTWriter::WriteObjCCategories() { Cat = Class->known_categories_begin(), CatEnd = Class->known_categories_end(); Cat != CatEnd; ++Cat, ++Size) { - assert(getDeclID(*Cat) != 0 && "Bogus category"); + assert(getDeclID(*Cat).isValid() && "Bogus category"); AddDeclRef(*Cat, Categories); } @@ -5080,7 +5092,7 @@ void ASTWriter::WriteSpecialDeclRecords(Sema &SemaRef) { if (!D || !wasDeclEmitted(D)) SemaDeclRefs.push_back(0); else - SemaDeclRefs.push_back(getDeclID(D)); + AddDeclRef(D, SemaDeclRefs); }; AddEmittedDeclRefOrZero(SemaRef.getStdNamespace()); @@ -5091,13 +5103,13 @@ void ASTWriter::WriteSpecialDeclRecords(Sema &SemaRef) { Stream.EmitRecord(SEMA_DECL_REFS, SemaDeclRefs); // Write the record containing decls to be checked for deferred diags. - SmallVector DeclsToCheckForDeferredDiags; + RecordData DeclsToCheckForDeferredDiags; for (auto *D : SemaRef.DeclsToCheckForDeferredDiags) if (wasDeclEmitted(D)) - DeclsToCheckForDeferredDiags.push_back(getDeclID(D)); + AddDeclRef(D, DeclsToCheckForDeferredDiags); if (!DeclsToCheckForDeferredDiags.empty()) Stream.EmitRecord(DECLS_TO_CHECK_FOR_DEFERRED_DIAGS, - DeclsToCheckForDeferredDiags); + DeclsToCheckForDeferredDiags); // Write the record containing CUDA-specific declaration references. RecordData CUDASpecialDeclRefs; @@ -5464,7 +5476,7 @@ void ASTWriter::WriteDeclAndTypes(ASTContext &Context) { if (VisibleOffset) VisibleOffset -= DeclTypesBlockStartOffset; - DelayedNamespaceRecord.push_back(getDeclID(NS)); + AddDeclRef(NS, DelayedNamespaceRecord); DelayedNamespaceRecord.push_back(LexicalOffset); DelayedNamespaceRecord.push_back(VisibleOffset); } @@ -5498,7 +5510,7 @@ void ASTWriter::WriteDeclAndTypes(ASTContext &Context) { continue; NewGlobalKindDeclPairs.push_back(D->getKind()); - NewGlobalKindDeclPairs.push_back(GetDeclRef(D)); + NewGlobalKindDeclPairs.push_back(GetDeclRef(D).get()); } auto Abv = std::make_shared(); @@ -5559,7 +5571,7 @@ void ASTWriter::WriteDeclUpdatesBlocks(RecordDataImpl &OffsetsRecord) { case UPD_CXX_ADDED_TEMPLATE_SPECIALIZATION: case UPD_CXX_ADDED_ANONYMOUS_NAMESPACE: assert(Update.getDecl() && "no decl to add?"); - Record.push_back(GetDeclRef(Update.getDecl())); + Record.AddDeclRef(Update.getDecl()); break; case UPD_CXX_ADDED_FUNCTION_DEFINITION: @@ -5700,7 +5712,7 @@ void ASTWriter::WriteDeclUpdatesBlocks(RecordDataImpl &OffsetsRecord) { } } - OffsetsRecord.push_back(GetDeclRef(D)); + AddDeclRef(D, OffsetsRecord); OffsetsRecord.push_back(Record.Emit(DECL_UPDATES)); } } @@ -5965,18 +5977,18 @@ void ASTWriter::AddEmittedDeclRef(const Decl *D, RecordDataImpl &Record) { if (!wasDeclEmitted(D)) return; - Record.push_back(GetDeclRef(D)); + Record.push_back(GetDeclRef(D).get()); } void ASTWriter::AddDeclRef(const Decl *D, RecordDataImpl &Record) { - Record.push_back(GetDeclRef(D)); + Record.push_back(GetDeclRef(D).get()); } -DeclID ASTWriter::GetDeclRef(const Decl *D) { +LocalDeclID ASTWriter::GetDeclRef(const Decl *D) { assert(WritingAST && "Cannot request a declaration ID before AST writing"); if (!D) { - return 0; + return LocalDeclID(); } // If the DeclUpdate from the GMF gets touched, emit it. @@ -5990,14 +6002,14 @@ DeclID ASTWriter::GetDeclRef(const Decl *D) { // If D comes from an AST file, its declaration ID is already known and // fixed. if (D->isFromASTFile()) - return D->getGlobalID(); + return LocalDeclID(D->getGlobalID()); assert(!(reinterpret_cast(D) & 0x01) && "Invalid decl pointer"); - DeclID &ID = DeclIDs[D]; - if (ID == 0) { + LocalDeclID &ID = DeclIDs[D]; + if (ID.isInvalid()) { if (DoneWritingDeclsAndTypes) { assert(0 && "New decl seen after serializing all the decls to emit!"); - return 0; + return LocalDeclID(); } // We haven't seen this declaration before. Give it a new ID and @@ -6009,14 +6021,14 @@ DeclID ASTWriter::GetDeclRef(const Decl *D) { return ID; } -DeclID ASTWriter::getDeclID(const Decl *D) { +LocalDeclID ASTWriter::getDeclID(const Decl *D) { if (!D) - return 0; + return LocalDeclID(); // If D comes from an AST file, its declaration ID is already known and // fixed. if (D->isFromASTFile()) - return D->getGlobalID(); + return LocalDeclID(D->getGlobalID()); assert(DeclIDs.contains(D) && "Declaration not emitted!"); return DeclIDs[D]; @@ -6037,8 +6049,8 @@ bool ASTWriter::wasDeclEmitted(const Decl *D) const { return Emitted; } -void ASTWriter::associateDeclWithFile(const Decl *D, DeclID ID) { - assert(ID); +void ASTWriter::associateDeclWithFile(const Decl *D, LocalDeclID ID) { + assert(ID.isValid()); assert(D); SourceLocation Loc = D->getLocation(); @@ -6070,7 +6082,7 @@ void ASTWriter::associateDeclWithFile(const Decl *D, DeclID ID) { if (!Info) Info = std::make_unique(); - std::pair LocDecl(Offset, ID); + std::pair LocDecl(Offset, ID); LocDeclIDsTy &Decls = Info->DeclIDs; Decls.push_back(LocDecl); } @@ -6340,7 +6352,7 @@ void ASTRecordWriter::AddCXXDefinitionData(const CXXRecordDecl *D) { Writer->Context->getLangOpts().ModulesDebugInfo && !D->isDependentType(); Record->push_back(ModulesDebugInfo); if (ModulesDebugInfo) - Writer->ModularCodegenDecls.push_back(Writer->GetDeclRef(D)); + Writer->AddDeclRef(D, Writer->ModularCodegenDecls); // IsLambda bit is already saved. @@ -6444,7 +6456,7 @@ void ASTWriter::ReaderInitialized(ASTReader *Reader) { // Note, this will get called multiple times, once one the reader starts up // and again each time it's done reading a PCH or module. - FirstDeclID = NUM_PREDEF_DECL_IDS + Chain->getTotalNumDecls(); + FirstDeclID = LocalDeclID(NUM_PREDEF_DECL_IDS + Chain->getTotalNumDecls()); FirstTypeID = NUM_PREDEF_TYPE_IDS + Chain->getTotalNumTypes(); FirstIdentID = NUM_PREDEF_IDENT_IDS + Chain->getTotalNumIdentifiers(); FirstMacroID = NUM_PREDEF_MACRO_IDS + Chain->getTotalNumMacros(); diff --git a/clang/lib/Serialization/ASTWriterDecl.cpp b/clang/lib/Serialization/ASTWriterDecl.cpp index c6db107e0ca42961e2fd646b2e4128d1b4bbcde4..0edc4feda3ef2337b14dafb2bcf441df66c1d12a 100644 --- a/clang/lib/Serialization/ASTWriterDecl.cpp +++ b/clang/lib/Serialization/ASTWriterDecl.cpp @@ -223,9 +223,9 @@ namespace clang { assert(!Common->LazySpecializations); } - ArrayRef LazySpecializations; + ArrayRef LazySpecializations; if (auto *LS = Common->LazySpecializations) - LazySpecializations = llvm::ArrayRef(LS + 1, LS[0]); + LazySpecializations = llvm::ArrayRef(LS + 1, LS[0].get()); // Add a slot to the record for the number of specializations. unsigned I = Record.size(); @@ -243,7 +243,9 @@ namespace clang { assert(D->isCanonicalDecl() && "non-canonical decl in set"); AddFirstDeclFromEachModule(D, /*IncludeLocal*/true); } - Record.append(LazySpecializations.begin(), LazySpecializations.end()); + Record.append( + DeclIDIterator(LazySpecializations.begin()), + DeclIDIterator(LazySpecializations.end())); // Update the size entry we added earlier. Record[I] = Record.size() - I - 1; @@ -1166,7 +1168,7 @@ void ASTDeclWriter::VisitVarDecl(VarDecl *D) { Record.push_back(VarDeclBits); if (ModulesCodegen) - Writer.ModularCodegenDecls.push_back(Writer.GetDeclRef(D)); + Writer.AddDeclRef(D, Writer.ModularCodegenDecls); if (D->hasAttr()) { BlockVarCopyInit Init = Writer.Context->getBlockVarCopyInit(D); @@ -2786,10 +2788,10 @@ void ASTWriter::WriteDecl(ASTContext &Context, Decl *D) { "serializing"); // Determine the ID for this declaration. - serialization::DeclID ID; + LocalDeclID ID; assert(!D->isFromASTFile() && "should not be emitting imported decl"); - serialization::DeclID &IDR = DeclIDs[D]; - if (IDR == 0) + LocalDeclID &IDR = DeclIDs[D]; + if (IDR.isInvalid()) IDR = NextDeclID++; ID = IDR; @@ -2807,7 +2809,7 @@ void ASTWriter::WriteDecl(ASTContext &Context, Decl *D) { // Record the offset for this declaration SourceLocation Loc = D->getLocation(); - unsigned Index = ID - FirstDeclID; + unsigned Index = ID.get() - FirstDeclID.get(); if (DeclOffsets.size() == Index) DeclOffsets.emplace_back(getAdjustedLocation(Loc), Offset, DeclTypesBlockStartOffset); @@ -2827,7 +2829,7 @@ void ASTWriter::WriteDecl(ASTContext &Context, Decl *D) { // Note declarations that should be deserialized eagerly so that we can add // them to a record in the AST file later. if (isRequiredDecl(D, Context, WritingModule)) - EagerlyDeserializedDecls.push_back(ID); + AddDeclRef(D, EagerlyDeserializedDecls); } void ASTRecordWriter::AddFunctionDefinition(const FunctionDecl *FD) { @@ -2863,7 +2865,7 @@ void ASTRecordWriter::AddFunctionDefinition(const FunctionDecl *FD) { } Record->push_back(ModulesCodegen); if (ModulesCodegen) - Writer->ModularCodegenDecls.push_back(Writer->GetDeclRef(FD)); + Writer->AddDeclRef(FD, Writer->ModularCodegenDecls); if (auto *CD = dyn_cast(FD)) { Record->push_back(CD->getNumCtorInitializers()); if (CD->getNumCtorInitializers()) diff --git a/clang/lib/Serialization/ASTWriterStmt.cpp b/clang/lib/Serialization/ASTWriterStmt.cpp index cd5f733baf76f4e5d6cfb3004d2fd375fa2281b6..39aec31b6d87900d95e8afa5aa7e4e993b0799f6 100644 --- a/clang/lib/Serialization/ASTWriterStmt.cpp +++ b/clang/lib/Serialization/ASTWriterStmt.cpp @@ -880,16 +880,21 @@ void ASTStmtWriter::VisitMatrixSubscriptExpr(MatrixSubscriptExpr *E) { Code = serialization::EXPR_ARRAY_SUBSCRIPT; } -void ASTStmtWriter::VisitOMPArraySectionExpr(OMPArraySectionExpr *E) { +void ASTStmtWriter::VisitArraySectionExpr(ArraySectionExpr *E) { VisitExpr(E); + Record.writeEnum(E->ASType); Record.AddStmt(E->getBase()); Record.AddStmt(E->getLowerBound()); Record.AddStmt(E->getLength()); - Record.AddStmt(E->getStride()); + if (E->isOMPArraySection()) + Record.AddStmt(E->getStride()); Record.AddSourceLocation(E->getColonLocFirst()); - Record.AddSourceLocation(E->getColonLocSecond()); + + if (E->isOMPArraySection()) + Record.AddSourceLocation(E->getColonLocSecond()); + Record.AddSourceLocation(E->getRBracketLoc()); - Code = serialization::EXPR_OMP_ARRAY_SECTION; + Code = serialization::EXPR_ARRAY_SECTION; } void ASTStmtWriter::VisitOMPArrayShapingExpr(OMPArrayShapingExpr *E) { diff --git a/clang/lib/StaticAnalyzer/Checkers/DereferenceChecker.cpp b/clang/lib/StaticAnalyzer/Checkers/DereferenceChecker.cpp index a678c3827e7f12b37b49733014c20b9cea36b6c5..1cebfbbee77dae25dd4a6022a2773b387516ad79 100644 --- a/clang/lib/StaticAnalyzer/Checkers/DereferenceChecker.cpp +++ b/clang/lib/StaticAnalyzer/Checkers/DereferenceChecker.cpp @@ -188,9 +188,9 @@ void DereferenceChecker::reportBug(DerefKind K, ProgramStateRef State, os << DerefStr1; break; } - case Stmt::OMPArraySectionExprClass: { + case Stmt::ArraySectionExprClass: { os << "Array access"; - const OMPArraySectionExpr *AE = cast(S); + const ArraySectionExpr *AE = cast(S); AddDerefSource(os, Ranges, AE->getBase()->IgnoreParenCasts(), State.get(), N->getLocationContext()); os << DerefStr1; diff --git a/clang/lib/StaticAnalyzer/Checkers/IdenticalExprChecker.cpp b/clang/lib/StaticAnalyzer/Checkers/IdenticalExprChecker.cpp index 1cf81b54e77d32ddb32aecfe7d216fe30084b934..7ac34ef8164e4c20eee1e1427edba4252b9bc9f5 100644 --- a/clang/lib/StaticAnalyzer/Checkers/IdenticalExprChecker.cpp +++ b/clang/lib/StaticAnalyzer/Checkers/IdenticalExprChecker.cpp @@ -350,7 +350,7 @@ static bool isIdenticalStmt(const ASTContext &Ctx, const Stmt *Stmt1, return false; case Stmt::CallExprClass: case Stmt::ArraySubscriptExprClass: - case Stmt::OMPArraySectionExprClass: + case Stmt::ArraySectionExprClass: case Stmt::OMPArrayShapingExprClass: case Stmt::OMPIteratorExprClass: case Stmt::ImplicitCastExprClass: diff --git a/clang/lib/StaticAnalyzer/Checkers/StreamChecker.cpp b/clang/lib/StaticAnalyzer/Checkers/StreamChecker.cpp index bd495cd0f9710de291d9aa20f76d3fea24757efb..a0aa2316a7b45dac40dc41e01ccdecd5a3b4311d 100644 --- a/clang/lib/StaticAnalyzer/Checkers/StreamChecker.cpp +++ b/clang/lib/StaticAnalyzer/Checkers/StreamChecker.cpp @@ -600,7 +600,7 @@ struct StreamOperationEvaluator { SValBuilder &SVB; const ASTContext &ACtx; - SymbolRef StreamSym; + SymbolRef StreamSym = nullptr; const StreamState *SS = nullptr; const CallExpr *CE = nullptr; StreamErrorState NewES; diff --git a/clang/lib/StaticAnalyzer/Core/ExprEngine.cpp b/clang/lib/StaticAnalyzer/Core/ExprEngine.cpp index 09c69f9612d96b8ed81baca77adce23b741e5c79..0b1edf3e5c96bf531883ea4553c7330d138d74f9 100644 --- a/clang/lib/StaticAnalyzer/Core/ExprEngine.cpp +++ b/clang/lib/StaticAnalyzer/Core/ExprEngine.cpp @@ -1948,7 +1948,7 @@ void ExprEngine::Visit(const Stmt *S, ExplodedNode *Pred, case Stmt::CXXPseudoDestructorExprClass: case Stmt::SubstNonTypeTemplateParmExprClass: case Stmt::CXXNullPtrLiteralExprClass: - case Stmt::OMPArraySectionExprClass: + case Stmt::ArraySectionExprClass: case Stmt::OMPArrayShapingExprClass: case Stmt::OMPIteratorExprClass: case Stmt::SYCLUniqueStableNameExprClass: diff --git a/clang/lib/Tooling/DependencyScanning/DependencyScanningWorker.cpp b/clang/lib/Tooling/DependencyScanning/DependencyScanningWorker.cpp index 32850f5eea92a945b99a164b9bc0b7209d841071..0c047b6c5da2f8007a7e4d17c8d8d06d8da549a0 100644 --- a/clang/lib/Tooling/DependencyScanning/DependencyScanningWorker.cpp +++ b/clang/lib/Tooling/DependencyScanning/DependencyScanningWorker.cpp @@ -439,6 +439,9 @@ public: if (Result) setLastCC1Arguments(std::move(OriginalInvocation)); + // Propagate the statistics to the parent FileManager. + DriverFileMgr->AddStats(ScanInstance.getFileManager()); + return Result; } diff --git a/clang/test/AST/Interp/cxx23.cpp b/clang/test/AST/Interp/cxx23.cpp index f0325eef6d87cfbb7763b64574d76bea1da7f868..13cc9f43febc741706c6cb08740b043846b68db7 100644 --- a/clang/test/AST/Interp/cxx23.cpp +++ b/clang/test/AST/Interp/cxx23.cpp @@ -141,3 +141,19 @@ struct check_ice { }; }; static_assert(check_ice<42>::x == 42); + + +namespace VirtualBases { + namespace One { + struct U { int n; }; + struct V : U { int n; }; + struct A : virtual V { int n; }; + struct Aa { int n; }; + struct B : virtual A, Aa {}; + struct C : virtual A, Aa {}; + struct D : B, C {}; + + /// Calls the constructor of D. + D d; + } +} diff --git a/clang/test/AST/Interp/records.cpp b/clang/test/AST/Interp/records.cpp index 3e52354a4a1067a84d549563f529138c4ff13640..9307b9c090c5dd5dabf1e3955dfc3de309221927 100644 --- a/clang/test/AST/Interp/records.cpp +++ b/clang/test/AST/Interp/records.cpp @@ -1330,3 +1330,82 @@ namespace UnnamedBitFields { static_assert(a.f == 1.0, ""); static_assert(a.c == 'a', ""); } + +/// FIXME: This still doesn't work in the new interpreter because +/// we lack type information for dummy pointers. +namespace VirtualBases { + /// This used to crash. + namespace One { + class A { + protected: + int x; + }; + class B : public virtual A { + public: + int getX() { return x; } // ref-note {{declared here}} + }; + + class DV : virtual public B{}; + + void foo() { + DV b; + int a[b.getX()]; // both-warning {{variable length arrays}} \ + // ref-note {{non-constexpr function 'getX' cannot be used}} + } + } + + namespace Two { + struct U { int n; }; + struct A : virtual U { int n; }; + struct B : A {}; + B a; + static_assert((U*)(A*)(&a) == (U*)(&a), ""); + + struct C : virtual A {}; + struct D : B, C {}; + D d; + constexpr B *p = &d; + constexpr C *q = &d; + static_assert((A*)p == (A*)q, ""); // both-error {{failed}} + } + + namespace Three { + struct U { int n; }; + struct V : U { int n; }; + struct A : virtual V { int n; }; + struct Aa { int n; }; + struct B : virtual A, Aa {}; + + struct C : virtual A, Aa {}; + + struct D : B, C {}; + + D d; + + constexpr B *p = &d; + constexpr C *q = &d; + + static_assert((void*)p != (void*)q, ""); + static_assert((A*)p == (A*)q, ""); + static_assert((Aa*)p != (Aa*)q, ""); + + constexpr V *v = p; + constexpr V *w = q; + constexpr V *x = (A*)p; + static_assert(v == w, ""); + static_assert(v == x, ""); + + static_assert((U*)&d == p, ""); + static_assert((U*)&d == q, ""); + static_assert((U*)&d == v, ""); + static_assert((U*)&d == w, ""); + static_assert((U*)&d == x, ""); + + struct X {}; + struct Y1 : virtual X {}; + struct Y2 : X {}; + struct Z : Y1, Y2 {}; + Z z; + static_assert((X*)(Y1*)&z != (X*)(Y2*)&z, ""); + } +} diff --git a/clang/test/AST/ast-dump-expr-json.cpp b/clang/test/AST/ast-dump-expr-json.cpp index 0fb07b0b434cc3861782e0119dae2d0d2e5dbade..bdd5ea19e418358210f901d3ea3c7ab85bd160f0 100644 --- a/clang/test/AST/ast-dump-expr-json.cpp +++ b/clang/test/AST/ast-dump-expr-json.cpp @@ -2333,7 +2333,7 @@ void TestNonADLCall3() { // CHECK-NEXT: "kind": "FunctionDecl", // CHECK-NEXT: "name": "operator delete", // CHECK-NEXT: "type": { -// CHECK-NEXT: "qualType": "void (void *) noexcept" +// CHECK-NEXT: "qualType": "void (void *, unsigned long) noexcept" // CHECK-NEXT: } // CHECK-NEXT: }, // CHECK-NEXT: "inner": [ diff --git a/clang/test/AST/ast-dump-expr.cpp b/clang/test/AST/ast-dump-expr.cpp index 69e65e22d61d0d0d2198f360388f81db030ff94f..de88f29bc4b0a99add10a6b43e2c616fab40394b 100644 --- a/clang/test/AST/ast-dump-expr.cpp +++ b/clang/test/AST/ast-dump-expr.cpp @@ -164,7 +164,7 @@ void UnaryExpressions(int *p) { // CHECK-NEXT: DeclRefExpr 0x{{[^ ]*}} 'int *' lvalue ParmVar 0x{{[^ ]*}} 'p' 'int *' ::delete p; - // CHECK: CXXDeleteExpr 0x{{[^ ]*}} 'void' global Function 0x{{[^ ]*}} 'operator delete' 'void (void *) noexcept' + // CHECK: CXXDeleteExpr 0x{{[^ ]*}} 'void' global Function 0x{{[^ ]*}} 'operator delete' 'void (void *, unsigned long) noexcept' // CHECK-NEXT: ImplicitCastExpr // CHECK-NEXT: DeclRefExpr 0x{{[^ ]*}} 'int *' lvalue ParmVar 0x{{[^ ]*}} 'p' 'int *' diff --git a/clang/test/AST/ast-dump-recovery.cpp b/clang/test/AST/ast-dump-recovery.cpp index cfb013585ad7443a52d53475e8661810d6ae670b..77527743fe85772c1e3d155c2ca075135926acd0 100644 --- a/clang/test/AST/ast-dump-recovery.cpp +++ b/clang/test/AST/ast-dump-recovery.cpp @@ -413,6 +413,14 @@ void RecoveryExprForInvalidDecls(Unknown InvalidDecl) { // CHECK-NEXT: `-RecoveryExpr {{.*}} '' } +void InitializerOfInvalidDecl() { + int ValidDecl; + Unkown InvalidDecl = ValidDecl; + // CHECK: VarDecl {{.*}} invalid InvalidDecl + // CHECK-NEXT: `-RecoveryExpr {{.*}} '' contains-errors + // CHECK-NEXT: `-DeclRefExpr {{.*}} 'int' lvalue Var {{.*}} 'ValidDecl' +} + void RecoverToAnInvalidDecl() { Unknown* foo; // invalid decl goo; // the typo was correct to the invalid foo. diff --git a/clang/test/AST/ast-dump-stmt-json.cpp b/clang/test/AST/ast-dump-stmt-json.cpp index 667a12a0120244e6a6adb7d20870df586a983233..a473d17da94244f842834dc2951589c717e7f22f 100644 --- a/clang/test/AST/ast-dump-stmt-json.cpp +++ b/clang/test/AST/ast-dump-stmt-json.cpp @@ -994,7 +994,7 @@ void TestDependentGenericSelectionExpr(Ty T) { // CHECK-NEXT: "kind": "FunctionDecl", // CHECK-NEXT: "name": "operator delete", // CHECK-NEXT: "type": { -// CHECK-NEXT: "qualType": "void (void *) noexcept" +// CHECK-NEXT: "qualType": "void (void *, unsigned long) noexcept" // CHECK-NEXT: } // CHECK-NEXT: }, // CHECK-NEXT: "inner": [ @@ -1369,7 +1369,7 @@ void TestDependentGenericSelectionExpr(Ty T) { // CHECK-NEXT: "kind": "FunctionDecl", // CHECK-NEXT: "name": "operator delete", // CHECK-NEXT: "type": { -// CHECK-NEXT: "qualType": "void (void *) noexcept" +// CHECK-NEXT: "qualType": "void (void *, unsigned long) noexcept" // CHECK-NEXT: } // CHECK-NEXT: }, // CHECK-NEXT: "inner": [ @@ -1722,7 +1722,6 @@ void TestDependentGenericSelectionExpr(Ty T) { // CHECK-NEXT: "end": {} // CHECK-NEXT: }, // CHECK-NEXT: "isImplicit": true, -// CHECK-NEXT: "isUsed": true, // CHECK-NEXT: "name": "operator delete", // CHECK-NEXT: "mangledName": "_ZdlPv", // CHECK-NEXT: "type": { @@ -1810,6 +1809,126 @@ void TestDependentGenericSelectionExpr(Ty T) { // CHECK-NEXT: } +// CHECK-NOT: {{^}}Dumping +// CHECK: "kind": "FunctionDecl", +// CHECK-NEXT: "loc": {}, +// CHECK-NEXT: "range": { +// CHECK-NEXT: "begin": {}, +// CHECK-NEXT: "end": {} +// CHECK-NEXT: }, +// CHECK-NEXT: "isImplicit": true, +// CHECK-NEXT: "isUsed": true, +// CHECK-NEXT: "name": "operator delete", +// CHECK-NEXT: "mangledName": "_ZdlPvm", +// CHECK-NEXT: "type": { +// CHECK-NEXT: "qualType": "void (void *, unsigned long) noexcept" +// CHECK-NEXT: }, +// CHECK-NEXT: "inner": [ +// CHECK-NEXT: { +// CHECK-NEXT: "id": "0x{{.*}}", +// CHECK-NEXT: "kind": "ParmVarDecl", +// CHECK-NEXT: "loc": {}, +// CHECK-NEXT: "range": { +// CHECK-NEXT: "begin": {}, +// CHECK-NEXT: "end": {} +// CHECK-NEXT: }, +// CHECK-NEXT: "isImplicit": true, +// CHECK-NEXT: "type": { +// CHECK-NEXT: "qualType": "void *" +// CHECK-NEXT: } +// CHECK-NEXT: }, +// CHECK-NEXT: { +// CHECK-NEXT: "id": "0x{{.*}}", +// CHECK-NEXT: "kind": "ParmVarDecl", +// CHECK-NEXT: "loc": {}, +// CHECK-NEXT: "range": { +// CHECK-NEXT: "begin": {}, +// CHECK-NEXT: "end": {} +// CHECK-NEXT: }, +// CHECK-NEXT: "isImplicit": true, +// CHECK-NEXT: "type": { +// CHECK-NEXT: "qualType": "unsigned long" +// CHECK-NEXT: } +// CHECK-NEXT: }, +// CHECK-NEXT: { +// CHECK-NEXT: "id": "0x{{.*}}", +// CHECK-NEXT: "kind": "VisibilityAttr", +// CHECK-NEXT: "range": { +// CHECK-NEXT: "begin": {}, +// CHECK-NEXT: "end": {} +// CHECK-NEXT: }, +// CHECK-NEXT: "implicit": true, +// CHECK-NEXT: "visibility": "default" +// CHECK-NEXT: } +// CHECK-NEXT: ] +// CHECK-NEXT: } + +// CHECK-NOT: {{^}}Dumping +// CHECK: "kind": "FunctionDecl", +// CHECK-NEXT: "loc": {}, +// CHECK-NEXT: "range": { +// CHECK-NEXT: "begin": {}, +// CHECK-NEXT: "end": {} +// CHECK-NEXT: }, +// CHECK-NEXT: "isImplicit": true, +// CHECK-NEXT: "name": "operator delete", +// CHECK-NEXT: "mangledName": "_ZdlPvmSt11align_val_t", +// CHECK-NEXT: "type": { +// CHECK-NEXT: "qualType": "void (void *, unsigned long, std::align_val_t) noexcept" +// CHECK-NEXT: }, +// CHECK-NEXT: "inner": [ +// CHECK-NEXT: { +// CHECK-NEXT: "id": "0x{{.*}}", +// CHECK-NEXT: "kind": "ParmVarDecl", +// CHECK-NEXT: "loc": {}, +// CHECK-NEXT: "range": { +// CHECK-NEXT: "begin": {}, +// CHECK-NEXT: "end": {} +// CHECK-NEXT: }, +// CHECK-NEXT: "isImplicit": true, +// CHECK-NEXT: "type": { +// CHECK-NEXT: "qualType": "void *" +// CHECK-NEXT: } +// CHECK-NEXT: }, +// CHECK-NEXT: { +// CHECK-NEXT: "id": "0x{{.*}}", +// CHECK-NEXT: "kind": "ParmVarDecl", +// CHECK-NEXT: "loc": {}, +// CHECK-NEXT: "range": { +// CHECK-NEXT: "begin": {}, +// CHECK-NEXT: "end": {} +// CHECK-NEXT: }, +// CHECK-NEXT: "isImplicit": true, +// CHECK-NEXT: "type": { +// CHECK-NEXT: "qualType": "unsigned long" +// CHECK-NEXT: } +// CHECK-NEXT: }, +// CHECK-NEXT: { +// CHECK-NEXT: "id": "0x{{.*}}", +// CHECK-NEXT: "kind": "ParmVarDecl", +// CHECK-NEXT: "loc": {}, +// CHECK-NEXT: "range": { +// CHECK-NEXT: "begin": {}, +// CHECK-NEXT: "end": {} +// CHECK-NEXT: }, +// CHECK-NEXT: "isImplicit": true, +// CHECK-NEXT: "type": { +// CHECK-NEXT: "qualType": "std::align_val_t" +// CHECK-NEXT: } +// CHECK-NEXT: }, +// CHECK-NEXT: { +// CHECK-NEXT: "id": "0x{{.*}}", +// CHECK-NEXT: "kind": "VisibilityAttr", +// CHECK-NEXT: "range": { +// CHECK-NEXT: "begin": {}, +// CHECK-NEXT: "end": {} +// CHECK-NEXT: }, +// CHECK-NEXT: "implicit": true, +// CHECK-NEXT: "visibility": "default" +// CHECK-NEXT: } +// CHECK-NEXT: ] +// CHECK-NEXT: } + // CHECK-NOT: {{^}}Dumping // CHECK: "kind": "FunctionDecl", // CHECK-NEXT: "loc": {}, @@ -1906,6 +2025,125 @@ void TestDependentGenericSelectionExpr(Ty T) { // CHECK-NEXT: } +// CHECK-NOT: {{^}}Dumping +// CHECK: "kind": "FunctionDecl", +// CHECK-NEXT: "loc": {}, +// CHECK-NEXT: "range": { +// CHECK-NEXT: "begin": {}, +// CHECK-NEXT: "end": {} +// CHECK-NEXT: }, +// CHECK-NEXT: "isImplicit": true, +// CHECK-NEXT: "name": "operator delete[]", +// CHECK-NEXT: "mangledName": "_ZdaPvm", +// CHECK-NEXT: "type": { +// CHECK-NEXT: "qualType": "void (void *, unsigned long) noexcept" +// CHECK-NEXT: }, +// CHECK-NEXT: "inner": [ +// CHECK-NEXT: { +// CHECK-NEXT: "id": "0x{{.*}}", +// CHECK-NEXT: "kind": "ParmVarDecl", +// CHECK-NEXT: "loc": {}, +// CHECK-NEXT: "range": { +// CHECK-NEXT: "begin": {}, +// CHECK-NEXT: "end": {} +// CHECK-NEXT: }, +// CHECK-NEXT: "isImplicit": true, +// CHECK-NEXT: "type": { +// CHECK-NEXT: "qualType": "void *" +// CHECK-NEXT: } +// CHECK-NEXT: }, +// CHECK-NEXT: { +// CHECK-NEXT: "id": "0x{{.*}}", +// CHECK-NEXT: "kind": "ParmVarDecl", +// CHECK-NEXT: "loc": {}, +// CHECK-NEXT: "range": { +// CHECK-NEXT: "begin": {}, +// CHECK-NEXT: "end": {} +// CHECK-NEXT: }, +// CHECK-NEXT: "isImplicit": true, +// CHECK-NEXT: "type": { +// CHECK-NEXT: "qualType": "unsigned long" +// CHECK-NEXT: } +// CHECK-NEXT: }, +// CHECK-NEXT: { +// CHECK-NEXT: "id": "0x{{.*}}", +// CHECK-NEXT: "kind": "VisibilityAttr", +// CHECK-NEXT: "range": { +// CHECK-NEXT: "begin": {}, +// CHECK-NEXT: "end": {} +// CHECK-NEXT: }, +// CHECK-NEXT: "implicit": true, +// CHECK-NEXT: "visibility": "default" +// CHECK-NEXT: } +// CHECK-NEXT: ] +// CHECK-NEXT: } + +// CHECK-NOT: {{^}}Dumping +// CHECK: "kind": "FunctionDecl", +// CHECK-NEXT: "loc": {}, +// CHECK-NEXT: "range": { +// CHECK-NEXT: "begin": {}, +// CHECK-NEXT: "end": {} +// CHECK-NEXT: }, +// CHECK-NEXT: "isImplicit": true, +// CHECK-NEXT: "name": "operator delete[]", +// CHECK-NEXT: "mangledName": "_ZdaPvmSt11align_val_t", +// CHECK-NEXT: "type": { +// CHECK-NEXT: "qualType": "void (void *, unsigned long, std::align_val_t) noexcept" +// CHECK-NEXT: }, +// CHECK-NEXT: "inner": [ +// CHECK-NEXT: { +// CHECK-NEXT: "id": "0x{{.*}}", +// CHECK-NEXT: "kind": "ParmVarDecl", +// CHECK-NEXT: "loc": {}, +// CHECK-NEXT: "range": { +// CHECK-NEXT: "begin": {}, +// CHECK-NEXT: "end": {} +// CHECK-NEXT: }, +// CHECK-NEXT: "isImplicit": true, +// CHECK-NEXT: "type": { +// CHECK-NEXT: "qualType": "void *" +// CHECK-NEXT: } +// CHECK-NEXT: }, +// CHECK-NEXT: { +// CHECK-NEXT: "id": "0x{{.*}}", +// CHECK-NEXT: "kind": "ParmVarDecl", +// CHECK-NEXT: "loc": {}, +// CHECK-NEXT: "range": { +// CHECK-NEXT: "begin": {}, +// CHECK-NEXT: "end": {} +// CHECK-NEXT: }, +// CHECK-NEXT: "isImplicit": true, +// CHECK-NEXT: "type": { +// CHECK-NEXT: "qualType": "unsigned long" +// CHECK-NEXT: } +// CHECK-NEXT: }, +// CHECK-NEXT: { +// CHECK-NEXT: "id": "0x{{.*}}", +// CHECK-NEXT: "kind": "ParmVarDecl", +// CHECK-NEXT: "loc": {}, +// CHECK-NEXT: "range": { +// CHECK-NEXT: "begin": {}, +// CHECK-NEXT: "end": {} +// CHECK-NEXT: }, +// CHECK-NEXT: "isImplicit": true, +// CHECK-NEXT: "type": { +// CHECK-NEXT: "qualType": "std::align_val_t" +// CHECK-NEXT: } +// CHECK-NEXT: }, +// CHECK-NEXT: { +// CHECK-NEXT: "id": "0x{{.*}}", +// CHECK-NEXT: "kind": "VisibilityAttr", +// CHECK-NEXT: "range": { +// CHECK-NEXT: "begin": {}, +// CHECK-NEXT: "end": {} +// CHECK-NEXT: }, +// CHECK-NEXT: "implicit": true, +// CHECK-NEXT: "visibility": "default" +// CHECK-NEXT: } +// CHECK-NEXT: ] +// CHECK-NEXT: } + // CHECK-NOT: {{^}}Dumping // CHECK: "kind": "FunctionTemplateDecl", // CHECK-NEXT: "loc": { diff --git a/clang/test/Analysis/cxxnewexpr-callback.cpp b/clang/test/Analysis/cxxnewexpr-callback.cpp index fe7a9fffad93dba2af28ac3a1910fec929f710c0..7df58cfa9ca284389205eb1234b705977db489cf 100644 --- a/clang/test/Analysis/cxxnewexpr-callback.cpp +++ b/clang/test/Analysis/cxxnewexpr-callback.cpp @@ -9,7 +9,7 @@ void free(void *); } // namespace std void *operator new(size_t size) { return std::malloc(size); } -void operator delete(void *ptr) { std::free(ptr); } +void operator delete(void *ptr, size_t size) { std::free(ptr); } struct S { S() {} @@ -49,7 +49,7 @@ void test() { // CHECK-NEXT: PostCall (operator delete) } -void operator delete(void *ptr) { +void operator delete(void *ptr, size_t size) { std::free(ptr); // CHECK-NO-INLINE-NEXT: PreCall (std::free) // CHECK-NO-INLINE-NEXT: PostCall (std::free) diff --git a/clang/test/CXX/basic/basic.stc/basic.stc.dynamic/basic.stc.dynamic.deallocation/p2.cpp b/clang/test/CXX/basic/basic.stc/basic.stc.dynamic/basic.stc.dynamic.deallocation/p2.cpp index 9e3210c6650f7b61a363d662021b98ca3781db14..706549f56c52f4178ec227ed16fb3c11b12a5873 100644 --- a/clang/test/CXX/basic/basic.stc/basic.stc.dynamic/basic.stc.dynamic.deallocation/p2.cpp +++ b/clang/test/CXX/basic/basic.stc/basic.stc.dynamic/basic.stc.dynamic.deallocation/p2.cpp @@ -1,4 +1,4 @@ -// RUN: %clang_cc1 -std=c++1z -fsized-deallocation -fexceptions -verify %s +// RUN: %clang_cc1 -std=c++1z -fexceptions -verify %s using size_t = decltype(sizeof(0)); diff --git a/clang/test/CXX/drs/cwg292.cpp b/clang/test/CXX/drs/cwg292.cpp index b05d3b92d6275fe123a393ec8637e3e73aaf6f52..a7bcbe6f50519d17850825dd852bfc2de88e2225 100644 --- a/clang/test/CXX/drs/cwg292.cpp +++ b/clang/test/CXX/drs/cwg292.cpp @@ -1,10 +1,10 @@ -// RUN: %clang_cc1 -std=c++98 %s -triple x86_64-linux-gnu -emit-llvm -disable-llvm-passes -o - -fexceptions -fcxx-exceptions -pedantic-errors | llvm-cxxfilt -n | FileCheck %s --check-prefixes CHECK -// RUN: %clang_cc1 -std=c++11 %s -triple x86_64-linux-gnu -emit-llvm -disable-llvm-passes -o - -fexceptions -fcxx-exceptions -pedantic-errors | llvm-cxxfilt -n | FileCheck %s --check-prefixes CHECK -// RUN: %clang_cc1 -std=c++14 %s -triple x86_64-linux-gnu -emit-llvm -disable-llvm-passes -o - -fexceptions -fcxx-exceptions -pedantic-errors | llvm-cxxfilt -n | FileCheck %s --check-prefixes CHECK -// RUN: %clang_cc1 -std=c++17 %s -triple x86_64-linux-gnu -emit-llvm -disable-llvm-passes -o - -fexceptions -fcxx-exceptions -pedantic-errors | llvm-cxxfilt -n | FileCheck %s --check-prefixes CHECK -// RUN: %clang_cc1 -std=c++20 %s -triple x86_64-linux-gnu -emit-llvm -disable-llvm-passes -o - -fexceptions -fcxx-exceptions -pedantic-errors | llvm-cxxfilt -n | FileCheck %s --check-prefixes CHECK -// RUN: %clang_cc1 -std=c++23 %s -triple x86_64-linux-gnu -emit-llvm -disable-llvm-passes -o - -fexceptions -fcxx-exceptions -pedantic-errors | llvm-cxxfilt -n | FileCheck %s --check-prefixes CHECK -// RUN: %clang_cc1 -std=c++2c %s -triple x86_64-linux-gnu -emit-llvm -disable-llvm-passes -o - -fexceptions -fcxx-exceptions -pedantic-errors | llvm-cxxfilt -n | FileCheck %s --check-prefixes CHECK +// RUN: %clang_cc1 -std=c++98 %s -triple x86_64-linux-gnu -emit-llvm -disable-llvm-passes -o - -fexceptions -fcxx-exceptions -pedantic-errors | llvm-cxxfilt -n | FileCheck %s --check-prefixes CHECK,CXX98-11 +// RUN: %clang_cc1 -std=c++11 %s -triple x86_64-linux-gnu -emit-llvm -disable-llvm-passes -o - -fexceptions -fcxx-exceptions -pedantic-errors | llvm-cxxfilt -n | FileCheck %s --check-prefixes CHECK,CXX98-11 +// RUN: %clang_cc1 -std=c++14 %s -triple x86_64-linux-gnu -emit-llvm -disable-llvm-passes -o - -fexceptions -fcxx-exceptions -pedantic-errors | llvm-cxxfilt -n | FileCheck %s --check-prefixes CHECK,SINCE-CXX14 +// RUN: %clang_cc1 -std=c++17 %s -triple x86_64-linux-gnu -emit-llvm -disable-llvm-passes -o - -fexceptions -fcxx-exceptions -pedantic-errors | llvm-cxxfilt -n | FileCheck %s --check-prefixes CHECK,SINCE-CXX14 +// RUN: %clang_cc1 -std=c++20 %s -triple x86_64-linux-gnu -emit-llvm -disable-llvm-passes -o - -fexceptions -fcxx-exceptions -pedantic-errors | llvm-cxxfilt -n | FileCheck %s --check-prefixes CHECK,SINCE-CXX14 +// RUN: %clang_cc1 -std=c++23 %s -triple x86_64-linux-gnu -emit-llvm -disable-llvm-passes -o - -fexceptions -fcxx-exceptions -pedantic-errors | llvm-cxxfilt -n | FileCheck %s --check-prefixes CHECK,SINCE-CXX14 +// RUN: %clang_cc1 -std=c++2c %s -triple x86_64-linux-gnu -emit-llvm -disable-llvm-passes -o - -fexceptions -fcxx-exceptions -pedantic-errors | llvm-cxxfilt -n | FileCheck %s --check-prefixes CHECK,SINCE-CXX14 namespace cwg292 { // cwg292: 2.9 @@ -23,7 +23,8 @@ void f() { // CHECK: invoke {{.*}} i32 @cwg292::g()() // CHECK-NEXT: to {{.*}} unwind label %lpad // CHECK-LABEL: lpad: -// CHECK: call void @operator delete(void*)(ptr {{.*}} %[[CALL]]) +// CXX98-11: call void @operator delete(void*)(ptr {{.*}} %[[CALL]]) +// SINCE-CXX14: call void @operator delete(void*, unsigned long)(ptr {{.*}} %[[CALL]], i64 noundef 1) // CHECK-LABEL: eh.resume: // CHECK-LABEL: } diff --git a/clang/test/CXX/expr/expr.unary/expr.new/p14.cpp b/clang/test/CXX/expr/expr.unary/expr.new/p14.cpp index 6537cdcfeafa049fc4693c1016f9694ed36b61cd..d0b24c8fe47b7cb7eb7d8242a9726b418a665ae8 100644 --- a/clang/test/CXX/expr/expr.unary/expr.new/p14.cpp +++ b/clang/test/CXX/expr/expr.unary/expr.new/p14.cpp @@ -1,4 +1,4 @@ -// RUN: %clang_cc1 -std=c++1z -fsized-deallocation -fexceptions %s -verify +// RUN: %clang_cc1 -std=c++1z -fexceptions %s -verify using size_t = decltype(sizeof(0)); namespace std { enum class align_val_t : size_t {}; } diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vcreate.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vcreate.c new file mode 100644 index 0000000000000000000000000000000000000000..8c8e1cdfb658847c0656b83ab61b91f98fe9b39b --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vcreate.c @@ -0,0 +1,477 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local @test_vcreate_v_bf16m1_bf16m2( +// CHECK-RV64-SAME: [[V0:%.*]], [[V1:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.insert.nxv8bf16.nxv4bf16( poison, [[V0]], i64 0) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = call @llvm.vector.insert.nxv8bf16.nxv4bf16( [[TMP0]], [[V1]], i64 4) +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16m2_t test_vcreate_v_bf16m1_bf16m2(vbfloat16m1_t v0, vbfloat16m1_t v1) { + return __riscv_vcreate_v_bf16m1_bf16m2(v0, v1); +} + +// CHECK-RV64-LABEL: define dso_local @test_vcreate_v_bf16m1_bf16m4( +// CHECK-RV64-SAME: [[V0:%.*]], [[V1:%.*]], [[V2:%.*]], [[V3:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.insert.nxv16bf16.nxv4bf16( poison, [[V0]], i64 0) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = call @llvm.vector.insert.nxv16bf16.nxv4bf16( [[TMP0]], [[V1]], i64 4) +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call @llvm.vector.insert.nxv16bf16.nxv4bf16( [[TMP1]], [[V2]], i64 8) +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call @llvm.vector.insert.nxv16bf16.nxv4bf16( [[TMP2]], [[V3]], i64 12) +// CHECK-RV64-NEXT: ret [[TMP3]] +// +vbfloat16m4_t test_vcreate_v_bf16m1_bf16m4(vbfloat16m1_t v0, vbfloat16m1_t v1, + vbfloat16m1_t v2, vbfloat16m1_t v3) { + return __riscv_vcreate_v_bf16m1_bf16m4(v0, v1, v2, v3); +} + +// CHECK-RV64-LABEL: define dso_local @test_vcreate_v_bf16m1_bf16m8( +// CHECK-RV64-SAME: [[V0:%.*]], [[V1:%.*]], [[V2:%.*]], [[V3:%.*]], [[V4:%.*]], [[V5:%.*]], [[V6:%.*]], [[V7:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.insert.nxv32bf16.nxv4bf16( poison, [[V0]], i64 0) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = call @llvm.vector.insert.nxv32bf16.nxv4bf16( [[TMP0]], [[V1]], i64 4) +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call @llvm.vector.insert.nxv32bf16.nxv4bf16( [[TMP1]], [[V2]], i64 8) +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call @llvm.vector.insert.nxv32bf16.nxv4bf16( [[TMP2]], [[V3]], i64 12) +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call @llvm.vector.insert.nxv32bf16.nxv4bf16( [[TMP3]], [[V4]], i64 16) +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call @llvm.vector.insert.nxv32bf16.nxv4bf16( [[TMP4]], [[V5]], i64 20) +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call @llvm.vector.insert.nxv32bf16.nxv4bf16( [[TMP5]], [[V6]], i64 24) +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call @llvm.vector.insert.nxv32bf16.nxv4bf16( [[TMP6]], [[V7]], i64 28) +// CHECK-RV64-NEXT: ret [[TMP7]] +// +vbfloat16m8_t test_vcreate_v_bf16m1_bf16m8(vbfloat16m1_t v0, vbfloat16m1_t v1, + vbfloat16m1_t v2, vbfloat16m1_t v3, + vbfloat16m1_t v4, vbfloat16m1_t v5, + vbfloat16m1_t v6, vbfloat16m1_t v7) { + return __riscv_vcreate_v_bf16m1_bf16m8(v0, v1, v2, v3, v4, v5, v6, v7); +} + +// CHECK-RV64-LABEL: define dso_local @test_vcreate_v_bf16m2_bf16m4( +// CHECK-RV64-SAME: [[V0:%.*]], [[V1:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.insert.nxv16bf16.nxv8bf16( poison, [[V0]], i64 0) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = call @llvm.vector.insert.nxv16bf16.nxv8bf16( [[TMP0]], [[V1]], i64 8) +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16m4_t test_vcreate_v_bf16m2_bf16m4(vbfloat16m2_t v0, vbfloat16m2_t v1) { + return __riscv_vcreate_v_bf16m2_bf16m4(v0, v1); +} + +// CHECK-RV64-LABEL: define dso_local @test_vcreate_v_bf16m2_bf16m8( +// CHECK-RV64-SAME: [[V0:%.*]], [[V1:%.*]], [[V2:%.*]], [[V3:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.insert.nxv32bf16.nxv8bf16( poison, [[V0]], i64 0) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = call @llvm.vector.insert.nxv32bf16.nxv8bf16( [[TMP0]], [[V1]], i64 8) +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call @llvm.vector.insert.nxv32bf16.nxv8bf16( [[TMP1]], [[V2]], i64 16) +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call @llvm.vector.insert.nxv32bf16.nxv8bf16( [[TMP2]], [[V3]], i64 24) +// CHECK-RV64-NEXT: ret [[TMP3]] +// +vbfloat16m8_t test_vcreate_v_bf16m2_bf16m8(vbfloat16m2_t v0, vbfloat16m2_t v1, + vbfloat16m2_t v2, vbfloat16m2_t v3) { + return __riscv_vcreate_v_bf16m2_bf16m8(v0, v1, v2, v3); +} + +// CHECK-RV64-LABEL: define dso_local @test_vcreate_v_bf16m4_bf16m8( +// CHECK-RV64-SAME: [[V0:%.*]], [[V1:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.insert.nxv32bf16.nxv16bf16( poison, [[V0]], i64 0) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = call @llvm.vector.insert.nxv32bf16.nxv16bf16( [[TMP0]], [[V1]], i64 16) +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16m8_t test_vcreate_v_bf16m4_bf16m8(vbfloat16m4_t v0, vbfloat16m4_t v1) { + return __riscv_vcreate_v_bf16m4_bf16m8(v0, v1); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vcreate_v_bf16mf4x2( +// CHECK-RV64-SAME: [[V0:%.*]], [[V1:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , } poison, [[V0]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = insertvalue { , } [[TMP0]], [[V1]], 1 +// CHECK-RV64-NEXT: ret { , } [[TMP1]] +// +vbfloat16mf4x2_t test_vcreate_v_bf16mf4x2(vbfloat16mf4_t v0, + vbfloat16mf4_t v1) { + return __riscv_vcreate_v_bf16mf4x2(v0, v1); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vcreate_v_bf16mf4x3( +// CHECK-RV64-SAME: [[V0:%.*]], [[V1:%.*]], [[V2:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , } poison, [[V0]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = insertvalue { , , } [[TMP0]], [[V1]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , } [[TMP1]], [[V2]], 2 +// CHECK-RV64-NEXT: ret { , , } [[TMP2]] +// +vbfloat16mf4x3_t test_vcreate_v_bf16mf4x3(vbfloat16mf4_t v0, vbfloat16mf4_t v1, + vbfloat16mf4_t v2) { + return __riscv_vcreate_v_bf16mf4x3(v0, v1, v2); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vcreate_v_bf16mf4x4( +// CHECK-RV64-SAME: [[V0:%.*]], [[V1:%.*]], [[V2:%.*]], [[V3:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , , } poison, [[V0]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = insertvalue { , , , } [[TMP0]], [[V1]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , } [[TMP1]], [[V2]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = insertvalue { , , , } [[TMP2]], [[V3]], 3 +// CHECK-RV64-NEXT: ret { , , , } [[TMP3]] +// +vbfloat16mf4x4_t test_vcreate_v_bf16mf4x4(vbfloat16mf4_t v0, vbfloat16mf4_t v1, + vbfloat16mf4_t v2, + vbfloat16mf4_t v3) { + return __riscv_vcreate_v_bf16mf4x4(v0, v1, v2, v3); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vcreate_v_bf16mf4x5( +// CHECK-RV64-SAME: [[V0:%.*]], [[V1:%.*]], [[V2:%.*]], [[V3:%.*]], [[V4:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , , , } poison, [[V0]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = insertvalue { , , , , } [[TMP0]], [[V1]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , , } [[TMP1]], [[V2]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = insertvalue { , , , , } [[TMP2]], [[V3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , , } [[TMP3]], [[V4]], 4 +// CHECK-RV64-NEXT: ret { , , , , } [[TMP4]] +// +vbfloat16mf4x5_t test_vcreate_v_bf16mf4x5(vbfloat16mf4_t v0, vbfloat16mf4_t v1, + vbfloat16mf4_t v2, vbfloat16mf4_t v3, + vbfloat16mf4_t v4) { + return __riscv_vcreate_v_bf16mf4x5(v0, v1, v2, v3, v4); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vcreate_v_bf16mf4x6( +// CHECK-RV64-SAME: [[V0:%.*]], [[V1:%.*]], [[V2:%.*]], [[V3:%.*]], [[V4:%.*]], [[V5:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , , , , } poison, [[V0]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = insertvalue { , , , , , } [[TMP0]], [[V1]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , , , } [[TMP1]], [[V2]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = insertvalue { , , , , , } [[TMP2]], [[V3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , , , } [[TMP3]], [[V4]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = insertvalue { , , , , , } [[TMP4]], [[V5]], 5 +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP5]] +// +vbfloat16mf4x6_t test_vcreate_v_bf16mf4x6(vbfloat16mf4_t v0, vbfloat16mf4_t v1, + vbfloat16mf4_t v2, vbfloat16mf4_t v3, + vbfloat16mf4_t v4, + vbfloat16mf4_t v5) { + return __riscv_vcreate_v_bf16mf4x6(v0, v1, v2, v3, v4, v5); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vcreate_v_bf16mf4x7( +// CHECK-RV64-SAME: [[V0:%.*]], [[V1:%.*]], [[V2:%.*]], [[V3:%.*]], [[V4:%.*]], [[V5:%.*]], [[V6:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , , , , , } poison, [[V0]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = insertvalue { , , , , , , } [[TMP0]], [[V1]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , , , , } [[TMP1]], [[V2]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = insertvalue { , , , , , , } [[TMP2]], [[V3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , , , , } [[TMP3]], [[V4]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = insertvalue { , , , , , , } [[TMP4]], [[V5]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , , , , } [[TMP5]], [[V6]], 6 +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP6]] +// +vbfloat16mf4x7_t test_vcreate_v_bf16mf4x7(vbfloat16mf4_t v0, vbfloat16mf4_t v1, + vbfloat16mf4_t v2, vbfloat16mf4_t v3, + vbfloat16mf4_t v4, vbfloat16mf4_t v5, + vbfloat16mf4_t v6) { + return __riscv_vcreate_v_bf16mf4x7(v0, v1, v2, v3, v4, v5, v6); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vcreate_v_bf16mf4x8( +// CHECK-RV64-SAME: [[V0:%.*]], [[V1:%.*]], [[V2:%.*]], [[V3:%.*]], [[V4:%.*]], [[V5:%.*]], [[V6:%.*]], [[V7:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , , , , , , } poison, [[V0]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = insertvalue { , , , , , , , } [[TMP0]], [[V1]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , , , , , } [[TMP1]], [[V2]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = insertvalue { , , , , , , , } [[TMP2]], [[V3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , , , , , } [[TMP3]], [[V4]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = insertvalue { , , , , , , , } [[TMP4]], [[V5]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , , , , , } [[TMP5]], [[V6]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , , , , , , } [[TMP6]], [[V7]], 7 +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP7]] +// +vbfloat16mf4x8_t test_vcreate_v_bf16mf4x8(vbfloat16mf4_t v0, vbfloat16mf4_t v1, + vbfloat16mf4_t v2, vbfloat16mf4_t v3, + vbfloat16mf4_t v4, vbfloat16mf4_t v5, + vbfloat16mf4_t v6, + vbfloat16mf4_t v7) { + return __riscv_vcreate_v_bf16mf4x8(v0, v1, v2, v3, v4, v5, v6, v7); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vcreate_v_bf16mf2x2( +// CHECK-RV64-SAME: [[V0:%.*]], [[V1:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , } poison, [[V0]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = insertvalue { , } [[TMP0]], [[V1]], 1 +// CHECK-RV64-NEXT: ret { , } [[TMP1]] +// +vbfloat16mf2x2_t test_vcreate_v_bf16mf2x2(vbfloat16mf2_t v0, + vbfloat16mf2_t v1) { + return __riscv_vcreate_v_bf16mf2x2(v0, v1); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vcreate_v_bf16mf2x3( +// CHECK-RV64-SAME: [[V0:%.*]], [[V1:%.*]], [[V2:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , } poison, [[V0]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = insertvalue { , , } [[TMP0]], [[V1]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , } [[TMP1]], [[V2]], 2 +// CHECK-RV64-NEXT: ret { , , } [[TMP2]] +// +vbfloat16mf2x3_t test_vcreate_v_bf16mf2x3(vbfloat16mf2_t v0, vbfloat16mf2_t v1, + vbfloat16mf2_t v2) { + return __riscv_vcreate_v_bf16mf2x3(v0, v1, v2); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vcreate_v_bf16mf2x4( +// CHECK-RV64-SAME: [[V0:%.*]], [[V1:%.*]], [[V2:%.*]], [[V3:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , , } poison, [[V0]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = insertvalue { , , , } [[TMP0]], [[V1]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , } [[TMP1]], [[V2]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = insertvalue { , , , } [[TMP2]], [[V3]], 3 +// CHECK-RV64-NEXT: ret { , , , } [[TMP3]] +// +vbfloat16mf2x4_t test_vcreate_v_bf16mf2x4(vbfloat16mf2_t v0, vbfloat16mf2_t v1, + vbfloat16mf2_t v2, + vbfloat16mf2_t v3) { + return __riscv_vcreate_v_bf16mf2x4(v0, v1, v2, v3); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vcreate_v_bf16mf2x5( +// CHECK-RV64-SAME: [[V0:%.*]], [[V1:%.*]], [[V2:%.*]], [[V3:%.*]], [[V4:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , , , } poison, [[V0]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = insertvalue { , , , , } [[TMP0]], [[V1]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , , } [[TMP1]], [[V2]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = insertvalue { , , , , } [[TMP2]], [[V3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , , } [[TMP3]], [[V4]], 4 +// CHECK-RV64-NEXT: ret { , , , , } [[TMP4]] +// +vbfloat16mf2x5_t test_vcreate_v_bf16mf2x5(vbfloat16mf2_t v0, vbfloat16mf2_t v1, + vbfloat16mf2_t v2, vbfloat16mf2_t v3, + vbfloat16mf2_t v4) { + return __riscv_vcreate_v_bf16mf2x5(v0, v1, v2, v3, v4); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vcreate_v_bf16mf2x6( +// CHECK-RV64-SAME: [[V0:%.*]], [[V1:%.*]], [[V2:%.*]], [[V3:%.*]], [[V4:%.*]], [[V5:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , , , , } poison, [[V0]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = insertvalue { , , , , , } [[TMP0]], [[V1]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , , , } [[TMP1]], [[V2]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = insertvalue { , , , , , } [[TMP2]], [[V3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , , , } [[TMP3]], [[V4]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = insertvalue { , , , , , } [[TMP4]], [[V5]], 5 +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP5]] +// +vbfloat16mf2x6_t test_vcreate_v_bf16mf2x6(vbfloat16mf2_t v0, vbfloat16mf2_t v1, + vbfloat16mf2_t v2, vbfloat16mf2_t v3, + vbfloat16mf2_t v4, + vbfloat16mf2_t v5) { + return __riscv_vcreate_v_bf16mf2x6(v0, v1, v2, v3, v4, v5); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vcreate_v_bf16mf2x7( +// CHECK-RV64-SAME: [[V0:%.*]], [[V1:%.*]], [[V2:%.*]], [[V3:%.*]], [[V4:%.*]], [[V5:%.*]], [[V6:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , , , , , } poison, [[V0]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = insertvalue { , , , , , , } [[TMP0]], [[V1]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , , , , } [[TMP1]], [[V2]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = insertvalue { , , , , , , } [[TMP2]], [[V3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , , , , } [[TMP3]], [[V4]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = insertvalue { , , , , , , } [[TMP4]], [[V5]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , , , , } [[TMP5]], [[V6]], 6 +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP6]] +// +vbfloat16mf2x7_t test_vcreate_v_bf16mf2x7(vbfloat16mf2_t v0, vbfloat16mf2_t v1, + vbfloat16mf2_t v2, vbfloat16mf2_t v3, + vbfloat16mf2_t v4, vbfloat16mf2_t v5, + vbfloat16mf2_t v6) { + return __riscv_vcreate_v_bf16mf2x7(v0, v1, v2, v3, v4, v5, v6); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vcreate_v_bf16mf2x8( +// CHECK-RV64-SAME: [[V0:%.*]], [[V1:%.*]], [[V2:%.*]], [[V3:%.*]], [[V4:%.*]], [[V5:%.*]], [[V6:%.*]], [[V7:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , , , , , , } poison, [[V0]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = insertvalue { , , , , , , , } [[TMP0]], [[V1]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , , , , , } [[TMP1]], [[V2]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = insertvalue { , , , , , , , } [[TMP2]], [[V3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , , , , , } [[TMP3]], [[V4]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = insertvalue { , , , , , , , } [[TMP4]], [[V5]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , , , , , } [[TMP5]], [[V6]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , , , , , , } [[TMP6]], [[V7]], 7 +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP7]] +// +vbfloat16mf2x8_t test_vcreate_v_bf16mf2x8(vbfloat16mf2_t v0, vbfloat16mf2_t v1, + vbfloat16mf2_t v2, vbfloat16mf2_t v3, + vbfloat16mf2_t v4, vbfloat16mf2_t v5, + vbfloat16mf2_t v6, + vbfloat16mf2_t v7) { + return __riscv_vcreate_v_bf16mf2x8(v0, v1, v2, v3, v4, v5, v6, v7); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vcreate_v_bf16m1x2( +// CHECK-RV64-SAME: [[V0:%.*]], [[V1:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , } poison, [[V0]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = insertvalue { , } [[TMP0]], [[V1]], 1 +// CHECK-RV64-NEXT: ret { , } [[TMP1]] +// +vbfloat16m1x2_t test_vcreate_v_bf16m1x2(vbfloat16m1_t v0, vbfloat16m1_t v1) { + return __riscv_vcreate_v_bf16m1x2(v0, v1); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vcreate_v_bf16m1x3( +// CHECK-RV64-SAME: [[V0:%.*]], [[V1:%.*]], [[V2:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , } poison, [[V0]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = insertvalue { , , } [[TMP0]], [[V1]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , } [[TMP1]], [[V2]], 2 +// CHECK-RV64-NEXT: ret { , , } [[TMP2]] +// +vbfloat16m1x3_t test_vcreate_v_bf16m1x3(vbfloat16m1_t v0, vbfloat16m1_t v1, + vbfloat16m1_t v2) { + return __riscv_vcreate_v_bf16m1x3(v0, v1, v2); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vcreate_v_bf16m1x4( +// CHECK-RV64-SAME: [[V0:%.*]], [[V1:%.*]], [[V2:%.*]], [[V3:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , , } poison, [[V0]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = insertvalue { , , , } [[TMP0]], [[V1]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , } [[TMP1]], [[V2]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = insertvalue { , , , } [[TMP2]], [[V3]], 3 +// CHECK-RV64-NEXT: ret { , , , } [[TMP3]] +// +vbfloat16m1x4_t test_vcreate_v_bf16m1x4(vbfloat16m1_t v0, vbfloat16m1_t v1, + vbfloat16m1_t v2, vbfloat16m1_t v3) { + return __riscv_vcreate_v_bf16m1x4(v0, v1, v2, v3); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vcreate_v_bf16m1x5( +// CHECK-RV64-SAME: [[V0:%.*]], [[V1:%.*]], [[V2:%.*]], [[V3:%.*]], [[V4:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , , , } poison, [[V0]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = insertvalue { , , , , } [[TMP0]], [[V1]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , , } [[TMP1]], [[V2]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = insertvalue { , , , , } [[TMP2]], [[V3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , , } [[TMP3]], [[V4]], 4 +// CHECK-RV64-NEXT: ret { , , , , } [[TMP4]] +// +vbfloat16m1x5_t test_vcreate_v_bf16m1x5(vbfloat16m1_t v0, vbfloat16m1_t v1, + vbfloat16m1_t v2, vbfloat16m1_t v3, + vbfloat16m1_t v4) { + return __riscv_vcreate_v_bf16m1x5(v0, v1, v2, v3, v4); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vcreate_v_bf16m1x6( +// CHECK-RV64-SAME: [[V0:%.*]], [[V1:%.*]], [[V2:%.*]], [[V3:%.*]], [[V4:%.*]], [[V5:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , , , , } poison, [[V0]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = insertvalue { , , , , , } [[TMP0]], [[V1]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , , , } [[TMP1]], [[V2]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = insertvalue { , , , , , } [[TMP2]], [[V3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , , , } [[TMP3]], [[V4]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = insertvalue { , , , , , } [[TMP4]], [[V5]], 5 +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP5]] +// +vbfloat16m1x6_t test_vcreate_v_bf16m1x6(vbfloat16m1_t v0, vbfloat16m1_t v1, + vbfloat16m1_t v2, vbfloat16m1_t v3, + vbfloat16m1_t v4, vbfloat16m1_t v5) { + return __riscv_vcreate_v_bf16m1x6(v0, v1, v2, v3, v4, v5); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vcreate_v_bf16m1x7( +// CHECK-RV64-SAME: [[V0:%.*]], [[V1:%.*]], [[V2:%.*]], [[V3:%.*]], [[V4:%.*]], [[V5:%.*]], [[V6:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , , , , , } poison, [[V0]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = insertvalue { , , , , , , } [[TMP0]], [[V1]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , , , , } [[TMP1]], [[V2]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = insertvalue { , , , , , , } [[TMP2]], [[V3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , , , , } [[TMP3]], [[V4]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = insertvalue { , , , , , , } [[TMP4]], [[V5]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , , , , } [[TMP5]], [[V6]], 6 +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP6]] +// +vbfloat16m1x7_t test_vcreate_v_bf16m1x7(vbfloat16m1_t v0, vbfloat16m1_t v1, + vbfloat16m1_t v2, vbfloat16m1_t v3, + vbfloat16m1_t v4, vbfloat16m1_t v5, + vbfloat16m1_t v6) { + return __riscv_vcreate_v_bf16m1x7(v0, v1, v2, v3, v4, v5, v6); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vcreate_v_bf16m1x8( +// CHECK-RV64-SAME: [[V0:%.*]], [[V1:%.*]], [[V2:%.*]], [[V3:%.*]], [[V4:%.*]], [[V5:%.*]], [[V6:%.*]], [[V7:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , , , , , , } poison, [[V0]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = insertvalue { , , , , , , , } [[TMP0]], [[V1]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , , , , , } [[TMP1]], [[V2]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = insertvalue { , , , , , , , } [[TMP2]], [[V3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , , , , , } [[TMP3]], [[V4]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = insertvalue { , , , , , , , } [[TMP4]], [[V5]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , , , , , } [[TMP5]], [[V6]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , , , , , , } [[TMP6]], [[V7]], 7 +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP7]] +// +vbfloat16m1x8_t test_vcreate_v_bf16m1x8(vbfloat16m1_t v0, vbfloat16m1_t v1, + vbfloat16m1_t v2, vbfloat16m1_t v3, + vbfloat16m1_t v4, vbfloat16m1_t v5, + vbfloat16m1_t v6, vbfloat16m1_t v7) { + return __riscv_vcreate_v_bf16m1x8(v0, v1, v2, v3, v4, v5, v6, v7); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vcreate_v_bf16m2x2( +// CHECK-RV64-SAME: [[V0:%.*]], [[V1:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , } poison, [[V0]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = insertvalue { , } [[TMP0]], [[V1]], 1 +// CHECK-RV64-NEXT: ret { , } [[TMP1]] +// +vbfloat16m2x2_t test_vcreate_v_bf16m2x2(vbfloat16m2_t v0, vbfloat16m2_t v1) { + return __riscv_vcreate_v_bf16m2x2(v0, v1); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vcreate_v_bf16m2x3( +// CHECK-RV64-SAME: [[V0:%.*]], [[V1:%.*]], [[V2:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , } poison, [[V0]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = insertvalue { , , } [[TMP0]], [[V1]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , } [[TMP1]], [[V2]], 2 +// CHECK-RV64-NEXT: ret { , , } [[TMP2]] +// +vbfloat16m2x3_t test_vcreate_v_bf16m2x3(vbfloat16m2_t v0, vbfloat16m2_t v1, + vbfloat16m2_t v2) { + return __riscv_vcreate_v_bf16m2x3(v0, v1, v2); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vcreate_v_bf16m2x4( +// CHECK-RV64-SAME: [[V0:%.*]], [[V1:%.*]], [[V2:%.*]], [[V3:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , , } poison, [[V0]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = insertvalue { , , , } [[TMP0]], [[V1]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , } [[TMP1]], [[V2]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = insertvalue { , , , } [[TMP2]], [[V3]], 3 +// CHECK-RV64-NEXT: ret { , , , } [[TMP3]] +// +vbfloat16m2x4_t test_vcreate_v_bf16m2x4(vbfloat16m2_t v0, vbfloat16m2_t v1, + vbfloat16m2_t v2, vbfloat16m2_t v3) { + return __riscv_vcreate_v_bf16m2x4(v0, v1, v2, v3); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vcreate_v_bf16m4x2( +// CHECK-RV64-SAME: [[V0:%.*]], [[V1:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , } poison, [[V0]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = insertvalue { , } [[TMP0]], [[V1]], 1 +// CHECK-RV64-NEXT: ret { , } [[TMP1]] +// +vbfloat16m4x2_t test_vcreate_v_bf16m4x2(vbfloat16m4_t v0, vbfloat16m4_t v1) { + return __riscv_vcreate_v_bf16m4x2(v0, v1); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vget.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vget.c new file mode 100644 index 0000000000000000000000000000000000000000..11a385dbe5c9a2a5ebc82e94ee6329704b7204f5 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vget.c @@ -0,0 +1,333 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16m2_bf16m1( +// CHECK-RV64-SAME: [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.extract.nxv4bf16.nxv8bf16( [[SRC]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vget_v_bf16m2_bf16m1(vbfloat16m2_t src, size_t index) { + return __riscv_vget_v_bf16m2_bf16m1(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16m4_bf16m1( +// CHECK-RV64-SAME: [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.extract.nxv4bf16.nxv16bf16( [[SRC]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vget_v_bf16m4_bf16m1(vbfloat16m4_t src, size_t index) { + return __riscv_vget_v_bf16m4_bf16m1(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16m8_bf16m1( +// CHECK-RV64-SAME: [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.extract.nxv4bf16.nxv32bf16( [[SRC]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vget_v_bf16m8_bf16m1(vbfloat16m8_t src, size_t index) { + return __riscv_vget_v_bf16m8_bf16m1(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16m4_bf16m2( +// CHECK-RV64-SAME: [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.extract.nxv8bf16.nxv16bf16( [[SRC]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vget_v_bf16m4_bf16m2(vbfloat16m4_t src, size_t index) { + return __riscv_vget_v_bf16m4_bf16m2(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16m8_bf16m2( +// CHECK-RV64-SAME: [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.extract.nxv8bf16.nxv32bf16( [[SRC]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vget_v_bf16m8_bf16m2(vbfloat16m8_t src, size_t index) { + return __riscv_vget_v_bf16m8_bf16m2(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16m8_bf16m4( +// CHECK-RV64-SAME: [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.extract.nxv16bf16.nxv32bf16( [[SRC]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vget_v_bf16m8_bf16m4(vbfloat16m8_t src, size_t index) { + return __riscv_vget_v_bf16m8_bf16m4(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16mf4x2_bf16mf4( +// CHECK-RV64-SAME: { , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vget_v_bf16mf4x2_bf16mf4(vbfloat16mf4x2_t src, + size_t index) { + return __riscv_vget_v_bf16mf4x2_bf16mf4(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16mf4x3_bf16mf4( +// CHECK-RV64-SAME: { , , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vget_v_bf16mf4x3_bf16mf4(vbfloat16mf4x3_t src, + size_t index) { + return __riscv_vget_v_bf16mf4x3_bf16mf4(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16mf4x4_bf16mf4( +// CHECK-RV64-SAME: { , , , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vget_v_bf16mf4x4_bf16mf4(vbfloat16mf4x4_t src, + size_t index) { + return __riscv_vget_v_bf16mf4x4_bf16mf4(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16mf4x5_bf16mf4( +// CHECK-RV64-SAME: { , , , , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vget_v_bf16mf4x5_bf16mf4(vbfloat16mf4x5_t src, + size_t index) { + return __riscv_vget_v_bf16mf4x5_bf16mf4(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16mf4x6_bf16mf4( +// CHECK-RV64-SAME: { , , , , , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vget_v_bf16mf4x6_bf16mf4(vbfloat16mf4x6_t src, + size_t index) { + return __riscv_vget_v_bf16mf4x6_bf16mf4(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16mf4x7_bf16mf4( +// CHECK-RV64-SAME: { , , , , , , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vget_v_bf16mf4x7_bf16mf4(vbfloat16mf4x7_t src, + size_t index) { + return __riscv_vget_v_bf16mf4x7_bf16mf4(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16mf4x8_bf16mf4( +// CHECK-RV64-SAME: { , , , , , , , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vget_v_bf16mf4x8_bf16mf4(vbfloat16mf4x8_t src, + size_t index) { + return __riscv_vget_v_bf16mf4x8_bf16mf4(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16mf2x2_bf16mf2( +// CHECK-RV64-SAME: { , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vget_v_bf16mf2x2_bf16mf2(vbfloat16mf2x2_t src, + size_t index) { + return __riscv_vget_v_bf16mf2x2_bf16mf2(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16mf2x3_bf16mf2( +// CHECK-RV64-SAME: { , , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vget_v_bf16mf2x3_bf16mf2(vbfloat16mf2x3_t src, + size_t index) { + return __riscv_vget_v_bf16mf2x3_bf16mf2(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16mf2x4_bf16mf2( +// CHECK-RV64-SAME: { , , , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vget_v_bf16mf2x4_bf16mf2(vbfloat16mf2x4_t src, + size_t index) { + return __riscv_vget_v_bf16mf2x4_bf16mf2(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16mf2x5_bf16mf2( +// CHECK-RV64-SAME: { , , , , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vget_v_bf16mf2x5_bf16mf2(vbfloat16mf2x5_t src, + size_t index) { + return __riscv_vget_v_bf16mf2x5_bf16mf2(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16mf2x6_bf16mf2( +// CHECK-RV64-SAME: { , , , , , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vget_v_bf16mf2x6_bf16mf2(vbfloat16mf2x6_t src, + size_t index) { + return __riscv_vget_v_bf16mf2x6_bf16mf2(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16mf2x7_bf16mf2( +// CHECK-RV64-SAME: { , , , , , , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vget_v_bf16mf2x7_bf16mf2(vbfloat16mf2x7_t src, + size_t index) { + return __riscv_vget_v_bf16mf2x7_bf16mf2(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16mf2x8_bf16mf2( +// CHECK-RV64-SAME: { , , , , , , , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vget_v_bf16mf2x8_bf16mf2(vbfloat16mf2x8_t src, + size_t index) { + return __riscv_vget_v_bf16mf2x8_bf16mf2(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16m1x2_bf16m1( +// CHECK-RV64-SAME: { , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vget_v_bf16m1x2_bf16m1(vbfloat16m1x2_t src, size_t index) { + return __riscv_vget_v_bf16m1x2_bf16m1(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16m1x3_bf16m1( +// CHECK-RV64-SAME: { , , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vget_v_bf16m1x3_bf16m1(vbfloat16m1x3_t src, size_t index) { + return __riscv_vget_v_bf16m1x3_bf16m1(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16m1x4_bf16m1( +// CHECK-RV64-SAME: { , , , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vget_v_bf16m1x4_bf16m1(vbfloat16m1x4_t src, size_t index) { + return __riscv_vget_v_bf16m1x4_bf16m1(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16m1x5_bf16m1( +// CHECK-RV64-SAME: { , , , , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vget_v_bf16m1x5_bf16m1(vbfloat16m1x5_t src, size_t index) { + return __riscv_vget_v_bf16m1x5_bf16m1(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16m1x6_bf16m1( +// CHECK-RV64-SAME: { , , , , , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vget_v_bf16m1x6_bf16m1(vbfloat16m1x6_t src, size_t index) { + return __riscv_vget_v_bf16m1x6_bf16m1(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16m1x7_bf16m1( +// CHECK-RV64-SAME: { , , , , , , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vget_v_bf16m1x7_bf16m1(vbfloat16m1x7_t src, size_t index) { + return __riscv_vget_v_bf16m1x7_bf16m1(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16m1x8_bf16m1( +// CHECK-RV64-SAME: { , , , , , , , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vget_v_bf16m1x8_bf16m1(vbfloat16m1x8_t src, size_t index) { + return __riscv_vget_v_bf16m1x8_bf16m1(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16m2x2_bf16m2( +// CHECK-RV64-SAME: { , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vget_v_bf16m2x2_bf16m2(vbfloat16m2x2_t src, size_t index) { + return __riscv_vget_v_bf16m2x2_bf16m2(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16m2x3_bf16m2( +// CHECK-RV64-SAME: { , , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vget_v_bf16m2x3_bf16m2(vbfloat16m2x3_t src, size_t index) { + return __riscv_vget_v_bf16m2x3_bf16m2(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16m2x4_bf16m2( +// CHECK-RV64-SAME: { , , , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vget_v_bf16m2x4_bf16m2(vbfloat16m2x4_t src, size_t index) { + return __riscv_vget_v_bf16m2x4_bf16m2(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16m4x2_bf16m4( +// CHECK-RV64-SAME: { , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vget_v_bf16m4x2_bf16m4(vbfloat16m4x2_t src, size_t index) { + return __riscv_vget_v_bf16m4x2_bf16m4(src, 0); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vle16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vle16.c new file mode 100644 index 0000000000000000000000000000000000000000..6f54ddf3f87c07ec3f647cbce3cd31c4ba975791 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vle16.c @@ -0,0 +1,132 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16mf4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.nxv1bf16.i64( poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vle16_v_bf16mf4(const __bf16 *rs1, size_t vl) { + return __riscv_vle16_v_bf16mf4(rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16mf2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.nxv2bf16.i64( poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vle16_v_bf16mf2(const __bf16 *rs1, size_t vl) { + return __riscv_vle16_v_bf16mf2(rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16m1( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.nxv4bf16.i64( poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vle16_v_bf16m1(const __bf16 *rs1, size_t vl) { + return __riscv_vle16_v_bf16m1(rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16m2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.nxv8bf16.i64( poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vle16_v_bf16m2(const __bf16 *rs1, size_t vl) { + return __riscv_vle16_v_bf16m2(rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16m4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.nxv16bf16.i64( poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vle16_v_bf16m4(const __bf16 *rs1, size_t vl) { + return __riscv_vle16_v_bf16m4(rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16m8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.nxv32bf16.i64( poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vle16_v_bf16m8(const __bf16 *rs1, size_t vl) { + return __riscv_vle16_v_bf16m8(rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16mf4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.mask.nxv1bf16.i64( poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vle16_v_bf16mf4_m(vbool64_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vle16_v_bf16mf4_m(vm, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16mf2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.mask.nxv2bf16.i64( poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vle16_v_bf16mf2_m(vbool32_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vle16_v_bf16mf2_m(vm, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16m1_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.mask.nxv4bf16.i64( poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vle16_v_bf16m1_m(vbool16_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vle16_v_bf16m1_m(vm, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16m2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.mask.nxv8bf16.i64( poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vle16_v_bf16m2_m(vbool8_t vm, const __bf16 *rs1, size_t vl) { + return __riscv_vle16_v_bf16m2_m(vm, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16m4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.mask.nxv16bf16.i64( poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vle16_v_bf16m4_m(vbool4_t vm, const __bf16 *rs1, size_t vl) { + return __riscv_vle16_v_bf16m4_m(vm, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16m8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.mask.nxv32bf16.i64( poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vle16_v_bf16m8_m(vbool2_t vm, const __bf16 *rs1, size_t vl) { + return __riscv_vle16_v_bf16m8_m(vm, rs1, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vle16ff.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vle16ff.c new file mode 100644 index 0000000000000000000000000000000000000000..f73cfe73bae05c6a2345a23ff5838fda33827564 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vle16ff.c @@ -0,0 +1,177 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16mf4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.nxv1bf16.i64( poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16mf4_t test_vle16ff_v_bf16mf4(const __bf16 *rs1, size_t *new_vl, + size_t vl) { + return __riscv_vle16ff_v_bf16mf4(rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16mf2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.nxv2bf16.i64( poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16mf2_t test_vle16ff_v_bf16mf2(const __bf16 *rs1, size_t *new_vl, + size_t vl) { + return __riscv_vle16ff_v_bf16mf2(rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16m1( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.nxv4bf16.i64( poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16m1_t test_vle16ff_v_bf16m1(const __bf16 *rs1, size_t *new_vl, + size_t vl) { + return __riscv_vle16ff_v_bf16m1(rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16m2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.nxv8bf16.i64( poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16m2_t test_vle16ff_v_bf16m2(const __bf16 *rs1, size_t *new_vl, + size_t vl) { + return __riscv_vle16ff_v_bf16m2(rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16m4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.nxv16bf16.i64( poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16m4_t test_vle16ff_v_bf16m4(const __bf16 *rs1, size_t *new_vl, + size_t vl) { + return __riscv_vle16ff_v_bf16m4(rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16m8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.nxv32bf16.i64( poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16m8_t test_vle16ff_v_bf16m8(const __bf16 *rs1, size_t *new_vl, + size_t vl) { + return __riscv_vle16ff_v_bf16m8(rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16mf4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.mask.nxv1bf16.i64( poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16mf4_t test_vle16ff_v_bf16mf4_m(vbool64_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vle16ff_v_bf16mf4_m(vm, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16mf2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.mask.nxv2bf16.i64( poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16mf2_t test_vle16ff_v_bf16mf2_m(vbool32_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vle16ff_v_bf16mf2_m(vm, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16m1_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.mask.nxv4bf16.i64( poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16m1_t test_vle16ff_v_bf16m1_m(vbool16_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vle16ff_v_bf16m1_m(vm, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16m2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.mask.nxv8bf16.i64( poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16m2_t test_vle16ff_v_bf16m2_m(vbool8_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vle16ff_v_bf16m2_m(vm, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16m4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.mask.nxv16bf16.i64( poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16m4_t test_vle16ff_v_bf16m4_m(vbool4_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vle16ff_v_bf16m4_m(vm, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16m8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.mask.nxv32bf16.i64( poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16m8_t test_vle16ff_v_bf16m8_m(vbool2_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vle16ff_v_bf16m8_m(vm, rs1, new_vl, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlmul_ext_v.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlmul_ext_v.c new file mode 100644 index 0000000000000000000000000000000000000000..3ab73c512316116d471fa21242e3e8e35669fc6f --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlmul_ext_v.c @@ -0,0 +1,159 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_ext_v_bf16mf4_bf16mf2( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.insert.nxv2bf16.nxv1bf16( poison, [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vlmul_ext_v_bf16mf4_bf16mf2(vbfloat16mf4_t value) { + return __riscv_vlmul_ext_v_bf16mf4_bf16mf2(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_ext_v_bf16mf4_bf16m1( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.insert.nxv4bf16.nxv1bf16( poison, [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vlmul_ext_v_bf16mf4_bf16m1(vbfloat16mf4_t value) { + return __riscv_vlmul_ext_v_bf16mf4_bf16m1(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_ext_v_bf16mf4_bf16m2( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.insert.nxv8bf16.nxv1bf16( poison, [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vlmul_ext_v_bf16mf4_bf16m2(vbfloat16mf4_t value) { + return __riscv_vlmul_ext_v_bf16mf4_bf16m2(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_ext_v_bf16mf4_bf16m4( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.insert.nxv16bf16.nxv1bf16( poison, [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vlmul_ext_v_bf16mf4_bf16m4(vbfloat16mf4_t value) { + return __riscv_vlmul_ext_v_bf16mf4_bf16m4(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_ext_v_bf16mf4_bf16m8( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.insert.nxv32bf16.nxv1bf16( poison, [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vlmul_ext_v_bf16mf4_bf16m8(vbfloat16mf4_t value) { + return __riscv_vlmul_ext_v_bf16mf4_bf16m8(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_ext_v_bf16mf2_bf16m1( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.insert.nxv4bf16.nxv2bf16( poison, [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vlmul_ext_v_bf16mf2_bf16m1(vbfloat16mf2_t value) { + return __riscv_vlmul_ext_v_bf16mf2_bf16m1(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_ext_v_bf16mf2_bf16m2( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.insert.nxv8bf16.nxv2bf16( poison, [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vlmul_ext_v_bf16mf2_bf16m2(vbfloat16mf2_t value) { + return __riscv_vlmul_ext_v_bf16mf2_bf16m2(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_ext_v_bf16mf2_bf16m4( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.insert.nxv16bf16.nxv2bf16( poison, [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vlmul_ext_v_bf16mf2_bf16m4(vbfloat16mf2_t value) { + return __riscv_vlmul_ext_v_bf16mf2_bf16m4(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_ext_v_bf16mf2_bf16m8( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.insert.nxv32bf16.nxv2bf16( poison, [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vlmul_ext_v_bf16mf2_bf16m8(vbfloat16mf2_t value) { + return __riscv_vlmul_ext_v_bf16mf2_bf16m8(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_ext_v_bf16m1_bf16m2( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.insert.nxv8bf16.nxv4bf16( poison, [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vlmul_ext_v_bf16m1_bf16m2(vbfloat16m1_t value) { + return __riscv_vlmul_ext_v_bf16m1_bf16m2(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_ext_v_bf16m1_bf16m4( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.insert.nxv16bf16.nxv4bf16( poison, [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vlmul_ext_v_bf16m1_bf16m4(vbfloat16m1_t value) { + return __riscv_vlmul_ext_v_bf16m1_bf16m4(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_ext_v_bf16m1_bf16m8( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.insert.nxv32bf16.nxv4bf16( poison, [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vlmul_ext_v_bf16m1_bf16m8(vbfloat16m1_t value) { + return __riscv_vlmul_ext_v_bf16m1_bf16m8(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_ext_v_bf16m2_bf16m4( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.insert.nxv16bf16.nxv8bf16( poison, [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vlmul_ext_v_bf16m2_bf16m4(vbfloat16m2_t value) { + return __riscv_vlmul_ext_v_bf16m2_bf16m4(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_ext_v_bf16m2_bf16m8( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.insert.nxv32bf16.nxv8bf16( poison, [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vlmul_ext_v_bf16m2_bf16m8(vbfloat16m2_t value) { + return __riscv_vlmul_ext_v_bf16m2_bf16m8(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_ext_v_bf16m4_bf16m8( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.insert.nxv32bf16.nxv16bf16( poison, [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vlmul_ext_v_bf16m4_bf16m8(vbfloat16m4_t value) { + return __riscv_vlmul_ext_v_bf16m4_bf16m8(value); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlmul_trunc_v.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlmul_trunc_v.c new file mode 100644 index 0000000000000000000000000000000000000000..478b1e556113e678409cbb07185dca44d9a805ba --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlmul_trunc_v.c @@ -0,0 +1,159 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_trunc_v_bf16mf2_bf16mf4( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.extract.nxv1bf16.nxv2bf16( [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vlmul_trunc_v_bf16mf2_bf16mf4(vbfloat16mf2_t value) { + return __riscv_vlmul_trunc_v_bf16mf2_bf16mf4(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_trunc_v_bf16m1_bf16mf4( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.extract.nxv1bf16.nxv4bf16( [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vlmul_trunc_v_bf16m1_bf16mf4(vbfloat16m1_t value) { + return __riscv_vlmul_trunc_v_bf16m1_bf16mf4(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_trunc_v_bf16m1_bf16mf2( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.extract.nxv2bf16.nxv4bf16( [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vlmul_trunc_v_bf16m1_bf16mf2(vbfloat16m1_t value) { + return __riscv_vlmul_trunc_v_bf16m1_bf16mf2(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_trunc_v_bf16m2_bf16mf4( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.extract.nxv1bf16.nxv8bf16( [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vlmul_trunc_v_bf16m2_bf16mf4(vbfloat16m2_t value) { + return __riscv_vlmul_trunc_v_bf16m2_bf16mf4(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_trunc_v_bf16m2_bf16mf2( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.extract.nxv2bf16.nxv8bf16( [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vlmul_trunc_v_bf16m2_bf16mf2(vbfloat16m2_t value) { + return __riscv_vlmul_trunc_v_bf16m2_bf16mf2(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_trunc_v_bf16m2_bf16m1( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.extract.nxv4bf16.nxv8bf16( [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vlmul_trunc_v_bf16m2_bf16m1(vbfloat16m2_t value) { + return __riscv_vlmul_trunc_v_bf16m2_bf16m1(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_trunc_v_bf16m4_bf16mf4( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.extract.nxv1bf16.nxv16bf16( [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vlmul_trunc_v_bf16m4_bf16mf4(vbfloat16m4_t value) { + return __riscv_vlmul_trunc_v_bf16m4_bf16mf4(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_trunc_v_bf16m4_bf16mf2( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.extract.nxv2bf16.nxv16bf16( [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vlmul_trunc_v_bf16m4_bf16mf2(vbfloat16m4_t value) { + return __riscv_vlmul_trunc_v_bf16m4_bf16mf2(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_trunc_v_bf16m4_bf16m1( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.extract.nxv4bf16.nxv16bf16( [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vlmul_trunc_v_bf16m4_bf16m1(vbfloat16m4_t value) { + return __riscv_vlmul_trunc_v_bf16m4_bf16m1(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_trunc_v_bf16m4_bf16m2( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.extract.nxv8bf16.nxv16bf16( [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vlmul_trunc_v_bf16m4_bf16m2(vbfloat16m4_t value) { + return __riscv_vlmul_trunc_v_bf16m4_bf16m2(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_trunc_v_bf16m8_bf16mf4( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.extract.nxv1bf16.nxv32bf16( [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vlmul_trunc_v_bf16m8_bf16mf4(vbfloat16m8_t value) { + return __riscv_vlmul_trunc_v_bf16m8_bf16mf4(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_trunc_v_bf16m8_bf16mf2( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.extract.nxv2bf16.nxv32bf16( [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vlmul_trunc_v_bf16m8_bf16mf2(vbfloat16m8_t value) { + return __riscv_vlmul_trunc_v_bf16m8_bf16mf2(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_trunc_v_bf16m8_bf16m1( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.extract.nxv4bf16.nxv32bf16( [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vlmul_trunc_v_bf16m8_bf16m1(vbfloat16m8_t value) { + return __riscv_vlmul_trunc_v_bf16m8_bf16m1(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_trunc_v_bf16m8_bf16m2( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.extract.nxv8bf16.nxv32bf16( [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vlmul_trunc_v_bf16m8_bf16m2(vbfloat16m8_t value) { + return __riscv_vlmul_trunc_v_bf16m8_bf16m2(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_trunc_v_bf16m8_bf16m4( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.extract.nxv16bf16.nxv32bf16( [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vlmul_trunc_v_bf16m8_bf16m4(vbfloat16m8_t value) { + return __riscv_vlmul_trunc_v_bf16m8_bf16m4(value); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vloxei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vloxei16.c new file mode 100644 index 0000000000000000000000000000000000000000..147c820da9a600da86cd6eb4a569975f80d8db0f --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vloxei16.c @@ -0,0 +1,141 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16mf4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.nxv1bf16.nxv1i16.i64( poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vloxei16_v_bf16mf4(const __bf16 *rs1, vuint16mf4_t rs2, + size_t vl) { + return __riscv_vloxei16_v_bf16mf4(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16mf2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.nxv2bf16.nxv2i16.i64( poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vloxei16_v_bf16mf2(const __bf16 *rs1, vuint16mf2_t rs2, + size_t vl) { + return __riscv_vloxei16_v_bf16mf2(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16m1( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.nxv4bf16.nxv4i16.i64( poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vloxei16_v_bf16m1(const __bf16 *rs1, vuint16m1_t rs2, + size_t vl) { + return __riscv_vloxei16_v_bf16m1(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16m2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.nxv8bf16.nxv8i16.i64( poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vloxei16_v_bf16m2(const __bf16 *rs1, vuint16m2_t rs2, + size_t vl) { + return __riscv_vloxei16_v_bf16m2(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16m4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.nxv16bf16.nxv16i16.i64( poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vloxei16_v_bf16m4(const __bf16 *rs1, vuint16m4_t rs2, + size_t vl) { + return __riscv_vloxei16_v_bf16m4(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16m8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.nxv32bf16.nxv32i16.i64( poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vloxei16_v_bf16m8(const __bf16 *rs1, vuint16m8_t rs2, + size_t vl) { + return __riscv_vloxei16_v_bf16m8(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16mf4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.mask.nxv1bf16.nxv1i16.i64( poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vloxei16_v_bf16mf4_m(vbool64_t vm, const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxei16_v_bf16mf4_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16mf2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.mask.nxv2bf16.nxv2i16.i64( poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vloxei16_v_bf16mf2_m(vbool32_t vm, const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxei16_v_bf16mf2_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16m1_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.mask.nxv4bf16.nxv4i16.i64( poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vloxei16_v_bf16m1_m(vbool16_t vm, const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vloxei16_v_bf16m1_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16m2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.mask.nxv8bf16.nxv8i16.i64( poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vloxei16_v_bf16m2_m(vbool8_t vm, const __bf16 *rs1, + vuint16m2_t rs2, size_t vl) { + return __riscv_vloxei16_v_bf16m2_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16m4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.mask.nxv16bf16.nxv16i16.i64( poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vloxei16_v_bf16m4_m(vbool4_t vm, const __bf16 *rs1, + vuint16m4_t rs2, size_t vl) { + return __riscv_vloxei16_v_bf16m4_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16m8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.mask.nxv32bf16.nxv32i16.i64( poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vloxei16_v_bf16m8_m(vbool2_t vm, const __bf16 *rs1, + vuint16m8_t rs2, size_t vl) { + return __riscv_vloxei16_v_bf16m8_m(vm, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vloxseg2ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vloxseg2ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..c35a6eb68171a3b11a650aea175225fff1d22973 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vloxseg2ei16.c @@ -0,0 +1,121 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16mf4x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vloxseg2.nxv1bf16.nxv1i16.i64( poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16mf4x2_t test_vloxseg2ei16_v_bf16mf4x2(const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg2ei16_v_bf16mf4x2(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16mf2x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vloxseg2.nxv2bf16.nxv2i16.i64( poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16mf2x2_t test_vloxseg2ei16_v_bf16mf2x2(const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg2ei16_v_bf16mf2x2(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16m1x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vloxseg2.nxv4bf16.nxv4i16.i64( poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16m1x2_t test_vloxseg2ei16_v_bf16m1x2(const __bf16 *rs1, vuint16m1_t rs2, + size_t vl) { + return __riscv_vloxseg2ei16_v_bf16m1x2(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16m2x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vloxseg2.nxv8bf16.nxv8i16.i64( poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16m2x2_t test_vloxseg2ei16_v_bf16m2x2(const __bf16 *rs1, vuint16m2_t rs2, + size_t vl) { + return __riscv_vloxseg2ei16_v_bf16m2x2(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16m4x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vloxseg2.nxv16bf16.nxv16i16.i64( poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16m4x2_t test_vloxseg2ei16_v_bf16m4x2(const __bf16 *rs1, vuint16m4_t rs2, + size_t vl) { + return __riscv_vloxseg2ei16_v_bf16m4x2(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16mf4x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vloxseg2.mask.nxv1bf16.nxv1i16.i64( poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16mf4x2_t test_vloxseg2ei16_v_bf16mf4x2_m(vbool64_t vm, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg2ei16_v_bf16mf4x2_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16mf2x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vloxseg2.mask.nxv2bf16.nxv2i16.i64( poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16mf2x2_t test_vloxseg2ei16_v_bf16mf2x2_m(vbool32_t vm, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg2ei16_v_bf16mf2x2_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16m1x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vloxseg2.mask.nxv4bf16.nxv4i16.i64( poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16m1x2_t test_vloxseg2ei16_v_bf16m1x2_m(vbool16_t vm, const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg2ei16_v_bf16m1x2_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16m2x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vloxseg2.mask.nxv8bf16.nxv8i16.i64( poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16m2x2_t test_vloxseg2ei16_v_bf16m2x2_m(vbool8_t vm, const __bf16 *rs1, + vuint16m2_t rs2, size_t vl) { + return __riscv_vloxseg2ei16_v_bf16m2x2_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16m4x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vloxseg2.mask.nxv16bf16.nxv16i16.i64( poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16m4x2_t test_vloxseg2ei16_v_bf16m4x2_m(vbool4_t vm, const __bf16 *rs1, + vuint16m4_t rs2, size_t vl) { + return __riscv_vloxseg2ei16_v_bf16m4x2_m(vm, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vloxseg3ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vloxseg3ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..00c14b562bc5108fdfd17d1d57bcc74842c6df03 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vloxseg3ei16.c @@ -0,0 +1,99 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vloxseg3ei16_v_bf16mf4x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vloxseg3.nxv1bf16.nxv1i16.i64( poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16mf4x3_t test_vloxseg3ei16_v_bf16mf4x3(const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg3ei16_v_bf16mf4x3(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vloxseg3ei16_v_bf16mf2x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vloxseg3.nxv2bf16.nxv2i16.i64( poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16mf2x3_t test_vloxseg3ei16_v_bf16mf2x3(const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg3ei16_v_bf16mf2x3(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vloxseg3ei16_v_bf16m1x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vloxseg3.nxv4bf16.nxv4i16.i64( poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16m1x3_t test_vloxseg3ei16_v_bf16m1x3(const __bf16 *rs1, vuint16m1_t rs2, + size_t vl) { + return __riscv_vloxseg3ei16_v_bf16m1x3(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vloxseg3ei16_v_bf16m2x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vloxseg3.nxv8bf16.nxv8i16.i64( poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16m2x3_t test_vloxseg3ei16_v_bf16m2x3(const __bf16 *rs1, vuint16m2_t rs2, + size_t vl) { + return __riscv_vloxseg3ei16_v_bf16m2x3(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vloxseg3ei16_v_bf16mf4x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vloxseg3.mask.nxv1bf16.nxv1i16.i64( poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16mf4x3_t test_vloxseg3ei16_v_bf16mf4x3_m(vbool64_t vm, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg3ei16_v_bf16mf4x3_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vloxseg3ei16_v_bf16mf2x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vloxseg3.mask.nxv2bf16.nxv2i16.i64( poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16mf2x3_t test_vloxseg3ei16_v_bf16mf2x3_m(vbool32_t vm, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg3ei16_v_bf16mf2x3_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vloxseg3ei16_v_bf16m1x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vloxseg3.mask.nxv4bf16.nxv4i16.i64( poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16m1x3_t test_vloxseg3ei16_v_bf16m1x3_m(vbool16_t vm, const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg3ei16_v_bf16m1x3_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vloxseg3ei16_v_bf16m2x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vloxseg3.mask.nxv8bf16.nxv8i16.i64( poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16m2x3_t test_vloxseg3ei16_v_bf16m2x3_m(vbool8_t vm, const __bf16 *rs1, + vuint16m2_t rs2, size_t vl) { + return __riscv_vloxseg3ei16_v_bf16m2x3_m(vm, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vloxseg4ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vloxseg4ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..9289638807d6188054e17c5f2cb2d2358f583914 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vloxseg4ei16.c @@ -0,0 +1,99 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vloxseg4ei16_v_bf16mf4x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vloxseg4.nxv1bf16.nxv1i16.i64( poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16mf4x4_t test_vloxseg4ei16_v_bf16mf4x4(const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg4ei16_v_bf16mf4x4(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vloxseg4ei16_v_bf16mf2x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vloxseg4.nxv2bf16.nxv2i16.i64( poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16mf2x4_t test_vloxseg4ei16_v_bf16mf2x4(const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg4ei16_v_bf16mf2x4(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vloxseg4ei16_v_bf16m1x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vloxseg4.nxv4bf16.nxv4i16.i64( poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16m1x4_t test_vloxseg4ei16_v_bf16m1x4(const __bf16 *rs1, vuint16m1_t rs2, + size_t vl) { + return __riscv_vloxseg4ei16_v_bf16m1x4(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vloxseg4ei16_v_bf16m2x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vloxseg4.nxv8bf16.nxv8i16.i64( poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16m2x4_t test_vloxseg4ei16_v_bf16m2x4(const __bf16 *rs1, vuint16m2_t rs2, + size_t vl) { + return __riscv_vloxseg4ei16_v_bf16m2x4(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vloxseg4ei16_v_bf16mf4x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vloxseg4.mask.nxv1bf16.nxv1i16.i64( poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16mf4x4_t test_vloxseg4ei16_v_bf16mf4x4_m(vbool64_t vm, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg4ei16_v_bf16mf4x4_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vloxseg4ei16_v_bf16mf2x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vloxseg4.mask.nxv2bf16.nxv2i16.i64( poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16mf2x4_t test_vloxseg4ei16_v_bf16mf2x4_m(vbool32_t vm, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg4ei16_v_bf16mf2x4_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vloxseg4ei16_v_bf16m1x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vloxseg4.mask.nxv4bf16.nxv4i16.i64( poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16m1x4_t test_vloxseg4ei16_v_bf16m1x4_m(vbool16_t vm, const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg4ei16_v_bf16m1x4_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vloxseg4ei16_v_bf16m2x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vloxseg4.mask.nxv8bf16.nxv8i16.i64( poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16m2x4_t test_vloxseg4ei16_v_bf16m2x4_m(vbool8_t vm, const __bf16 *rs1, + vuint16m2_t rs2, size_t vl) { + return __riscv_vloxseg4ei16_v_bf16m2x4_m(vm, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vloxseg5ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vloxseg5ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..04c210d7a7966ede2616dc1ce21ec76e5843a59d --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vloxseg5ei16.c @@ -0,0 +1,77 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vloxseg5ei16_v_bf16mf4x5( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , } @llvm.riscv.vloxseg5.nxv1bf16.nxv1i16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP0]] +// +vbfloat16mf4x5_t test_vloxseg5ei16_v_bf16mf4x5(const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg5ei16_v_bf16mf4x5(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vloxseg5ei16_v_bf16mf2x5( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , } @llvm.riscv.vloxseg5.nxv2bf16.nxv2i16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP0]] +// +vbfloat16mf2x5_t test_vloxseg5ei16_v_bf16mf2x5(const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg5ei16_v_bf16mf2x5(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vloxseg5ei16_v_bf16m1x5( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , } @llvm.riscv.vloxseg5.nxv4bf16.nxv4i16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP0]] +// +vbfloat16m1x5_t test_vloxseg5ei16_v_bf16m1x5(const __bf16 *rs1, vuint16m1_t rs2, + size_t vl) { + return __riscv_vloxseg5ei16_v_bf16m1x5(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vloxseg5ei16_v_bf16mf4x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , } @llvm.riscv.vloxseg5.mask.nxv1bf16.nxv1i16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP0]] +// +vbfloat16mf4x5_t test_vloxseg5ei16_v_bf16mf4x5_m(vbool64_t vm, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg5ei16_v_bf16mf4x5_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vloxseg5ei16_v_bf16mf2x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , } @llvm.riscv.vloxseg5.mask.nxv2bf16.nxv2i16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP0]] +// +vbfloat16mf2x5_t test_vloxseg5ei16_v_bf16mf2x5_m(vbool32_t vm, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg5ei16_v_bf16mf2x5_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vloxseg5ei16_v_bf16m1x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , } @llvm.riscv.vloxseg5.mask.nxv4bf16.nxv4i16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP0]] +// +vbfloat16m1x5_t test_vloxseg5ei16_v_bf16m1x5_m(vbool16_t vm, const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg5ei16_v_bf16m1x5_m(vm, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vloxseg6ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vloxseg6ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..7ef2249630d9425d78cef64ef1ad351b966b3880 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vloxseg6ei16.c @@ -0,0 +1,77 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vloxseg6ei16_v_bf16mf4x6( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , } @llvm.riscv.vloxseg6.nxv1bf16.nxv1i16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP0]] +// +vbfloat16mf4x6_t test_vloxseg6ei16_v_bf16mf4x6(const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg6ei16_v_bf16mf4x6(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vloxseg6ei16_v_bf16mf2x6( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , } @llvm.riscv.vloxseg6.nxv2bf16.nxv2i16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP0]] +// +vbfloat16mf2x6_t test_vloxseg6ei16_v_bf16mf2x6(const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg6ei16_v_bf16mf2x6(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vloxseg6ei16_v_bf16m1x6( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , } @llvm.riscv.vloxseg6.nxv4bf16.nxv4i16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP0]] +// +vbfloat16m1x6_t test_vloxseg6ei16_v_bf16m1x6(const __bf16 *rs1, vuint16m1_t rs2, + size_t vl) { + return __riscv_vloxseg6ei16_v_bf16m1x6(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vloxseg6ei16_v_bf16mf4x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , } @llvm.riscv.vloxseg6.mask.nxv1bf16.nxv1i16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP0]] +// +vbfloat16mf4x6_t test_vloxseg6ei16_v_bf16mf4x6_m(vbool64_t vm, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg6ei16_v_bf16mf4x6_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vloxseg6ei16_v_bf16mf2x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , } @llvm.riscv.vloxseg6.mask.nxv2bf16.nxv2i16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP0]] +// +vbfloat16mf2x6_t test_vloxseg6ei16_v_bf16mf2x6_m(vbool32_t vm, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg6ei16_v_bf16mf2x6_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vloxseg6ei16_v_bf16m1x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , } @llvm.riscv.vloxseg6.mask.nxv4bf16.nxv4i16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP0]] +// +vbfloat16m1x6_t test_vloxseg6ei16_v_bf16m1x6_m(vbool16_t vm, const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg6ei16_v_bf16m1x6_m(vm, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vloxseg7ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vloxseg7ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..b1d5ee604018d4b0e6b230a5e9cb66ce3c01f78f --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vloxseg7ei16.c @@ -0,0 +1,77 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vloxseg7ei16_v_bf16mf4x7( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , } @llvm.riscv.vloxseg7.nxv1bf16.nxv1i16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP0]] +// +vbfloat16mf4x7_t test_vloxseg7ei16_v_bf16mf4x7(const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg7ei16_v_bf16mf4x7(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vloxseg7ei16_v_bf16mf2x7( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , } @llvm.riscv.vloxseg7.nxv2bf16.nxv2i16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP0]] +// +vbfloat16mf2x7_t test_vloxseg7ei16_v_bf16mf2x7(const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg7ei16_v_bf16mf2x7(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vloxseg7ei16_v_bf16m1x7( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , } @llvm.riscv.vloxseg7.nxv4bf16.nxv4i16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP0]] +// +vbfloat16m1x7_t test_vloxseg7ei16_v_bf16m1x7(const __bf16 *rs1, vuint16m1_t rs2, + size_t vl) { + return __riscv_vloxseg7ei16_v_bf16m1x7(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vloxseg7ei16_v_bf16mf4x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , } @llvm.riscv.vloxseg7.mask.nxv1bf16.nxv1i16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP0]] +// +vbfloat16mf4x7_t test_vloxseg7ei16_v_bf16mf4x7_m(vbool64_t vm, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg7ei16_v_bf16mf4x7_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vloxseg7ei16_v_bf16mf2x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , } @llvm.riscv.vloxseg7.mask.nxv2bf16.nxv2i16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP0]] +// +vbfloat16mf2x7_t test_vloxseg7ei16_v_bf16mf2x7_m(vbool32_t vm, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg7ei16_v_bf16mf2x7_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vloxseg7ei16_v_bf16m1x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , } @llvm.riscv.vloxseg7.mask.nxv4bf16.nxv4i16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP0]] +// +vbfloat16m1x7_t test_vloxseg7ei16_v_bf16m1x7_m(vbool16_t vm, const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg7ei16_v_bf16m1x7_m(vm, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vloxseg8ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vloxseg8ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..1e1c762e0d0b8a1ef690ba2d4965882cefb60161 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vloxseg8ei16.c @@ -0,0 +1,77 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vloxseg8ei16_v_bf16mf4x8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , } @llvm.riscv.vloxseg8.nxv1bf16.nxv1i16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP0]] +// +vbfloat16mf4x8_t test_vloxseg8ei16_v_bf16mf4x8(const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg8ei16_v_bf16mf4x8(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vloxseg8ei16_v_bf16mf2x8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , } @llvm.riscv.vloxseg8.nxv2bf16.nxv2i16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP0]] +// +vbfloat16mf2x8_t test_vloxseg8ei16_v_bf16mf2x8(const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg8ei16_v_bf16mf2x8(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vloxseg8ei16_v_bf16m1x8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , } @llvm.riscv.vloxseg8.nxv4bf16.nxv4i16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP0]] +// +vbfloat16m1x8_t test_vloxseg8ei16_v_bf16m1x8(const __bf16 *rs1, vuint16m1_t rs2, + size_t vl) { + return __riscv_vloxseg8ei16_v_bf16m1x8(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vloxseg8ei16_v_bf16mf4x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , } @llvm.riscv.vloxseg8.mask.nxv1bf16.nxv1i16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP0]] +// +vbfloat16mf4x8_t test_vloxseg8ei16_v_bf16mf4x8_m(vbool64_t vm, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg8ei16_v_bf16mf4x8_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vloxseg8ei16_v_bf16mf2x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , } @llvm.riscv.vloxseg8.mask.nxv2bf16.nxv2i16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP0]] +// +vbfloat16mf2x8_t test_vloxseg8ei16_v_bf16mf2x8_m(vbool32_t vm, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg8ei16_v_bf16mf2x8_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vloxseg8ei16_v_bf16m1x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , } @llvm.riscv.vloxseg8.mask.nxv4bf16.nxv4i16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP0]] +// +vbfloat16m1x8_t test_vloxseg8ei16_v_bf16m1x8_m(vbool16_t vm, const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg8ei16_v_bf16m1x8_m(vm, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlse16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlse16.c new file mode 100644 index 0000000000000000000000000000000000000000..c5c98f3abc52d1f82c8a883f87faaf3f845a3154 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlse16.c @@ -0,0 +1,141 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16mf4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.nxv1bf16.i64( poison, ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vlse16_v_bf16mf4(const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlse16_v_bf16mf4(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16mf2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.nxv2bf16.i64( poison, ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vlse16_v_bf16mf2(const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlse16_v_bf16mf2(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16m1( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.nxv4bf16.i64( poison, ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vlse16_v_bf16m1(const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlse16_v_bf16m1(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16m2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.nxv8bf16.i64( poison, ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vlse16_v_bf16m2(const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlse16_v_bf16m2(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16m4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.nxv16bf16.i64( poison, ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vlse16_v_bf16m4(const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlse16_v_bf16m4(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16m8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.nxv32bf16.i64( poison, ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vlse16_v_bf16m8(const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlse16_v_bf16m8(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16mf4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.mask.nxv1bf16.i64( poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vlse16_v_bf16mf4_m(vbool64_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlse16_v_bf16mf4_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16mf2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.mask.nxv2bf16.i64( poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vlse16_v_bf16mf2_m(vbool32_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlse16_v_bf16mf2_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16m1_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.mask.nxv4bf16.i64( poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vlse16_v_bf16m1_m(vbool16_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlse16_v_bf16m1_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16m2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.mask.nxv8bf16.i64( poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vlse16_v_bf16m2_m(vbool8_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlse16_v_bf16m2_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16m4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.mask.nxv16bf16.i64( poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vlse16_v_bf16m4_m(vbool4_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlse16_v_bf16m4_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16m8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.mask.nxv32bf16.i64( poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vlse16_v_bf16m8_m(vbool2_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlse16_v_bf16m8_m(vm, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlseg2e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlseg2e16.c new file mode 100644 index 0000000000000000000000000000000000000000..6ea8a1b4a4292e747e7517e078d3a0bf96a7ee84 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlseg2e16.c @@ -0,0 +1,114 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16mf4x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vlseg2.nxv1bf16.i64( poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16mf4x2_t test_vlseg2e16_v_bf16mf4x2(const __bf16 *rs1, size_t vl) { + return __riscv_vlseg2e16_v_bf16mf4x2(rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16mf2x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vlseg2.nxv2bf16.i64( poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16mf2x2_t test_vlseg2e16_v_bf16mf2x2(const __bf16 *rs1, size_t vl) { + return __riscv_vlseg2e16_v_bf16mf2x2(rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16m1x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vlseg2.nxv4bf16.i64( poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16m1x2_t test_vlseg2e16_v_bf16m1x2(const __bf16 *rs1, size_t vl) { + return __riscv_vlseg2e16_v_bf16m1x2(rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16m2x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vlseg2.nxv8bf16.i64( poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16m2x2_t test_vlseg2e16_v_bf16m2x2(const __bf16 *rs1, size_t vl) { + return __riscv_vlseg2e16_v_bf16m2x2(rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16m4x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vlseg2.nxv16bf16.i64( poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16m4x2_t test_vlseg2e16_v_bf16m4x2(const __bf16 *rs1, size_t vl) { + return __riscv_vlseg2e16_v_bf16m4x2(rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16mf4x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vlseg2.mask.nxv1bf16.i64( poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16mf4x2_t test_vlseg2e16_v_bf16mf4x2_m(vbool64_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg2e16_v_bf16mf4x2_m(vm, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16mf2x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vlseg2.mask.nxv2bf16.i64( poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16mf2x2_t test_vlseg2e16_v_bf16mf2x2_m(vbool32_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg2e16_v_bf16mf2x2_m(vm, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16m1x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vlseg2.mask.nxv4bf16.i64( poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16m1x2_t test_vlseg2e16_v_bf16m1x2_m(vbool16_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg2e16_v_bf16m1x2_m(vm, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16m2x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vlseg2.mask.nxv8bf16.i64( poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16m2x2_t test_vlseg2e16_v_bf16m2x2_m(vbool8_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg2e16_v_bf16m2x2_m(vm, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16m4x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vlseg2.mask.nxv16bf16.i64( poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16m4x2_t test_vlseg2e16_v_bf16m4x2_m(vbool4_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg2e16_v_bf16m4x2_m(vm, rs1, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlseg2e16ff.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlseg2e16ff.c new file mode 100644 index 0000000000000000000000000000000000000000..cecf6f1153946ad3257f30d7dbb4e32f2461b657 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlseg2e16ff.c @@ -0,0 +1,179 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16mf4x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.nxv1bf16.i64( poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP5]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP4]] +// +vbfloat16mf4x2_t test_vlseg2e16ff_v_bf16mf4x2(const __bf16 *rs1, size_t *new_vl, + size_t vl) { + return __riscv_vlseg2e16ff_v_bf16mf4x2(rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16mf2x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.nxv2bf16.i64( poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP5]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP4]] +// +vbfloat16mf2x2_t test_vlseg2e16ff_v_bf16mf2x2(const __bf16 *rs1, size_t *new_vl, + size_t vl) { + return __riscv_vlseg2e16ff_v_bf16mf2x2(rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16m1x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.nxv4bf16.i64( poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP5]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP4]] +// +vbfloat16m1x2_t test_vlseg2e16ff_v_bf16m1x2(const __bf16 *rs1, size_t *new_vl, + size_t vl) { + return __riscv_vlseg2e16ff_v_bf16m1x2(rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16m2x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.nxv8bf16.i64( poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP5]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP4]] +// +vbfloat16m2x2_t test_vlseg2e16ff_v_bf16m2x2(const __bf16 *rs1, size_t *new_vl, + size_t vl) { + return __riscv_vlseg2e16ff_v_bf16m2x2(rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16m4x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.nxv16bf16.i64( poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP5]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP4]] +// +vbfloat16m4x2_t test_vlseg2e16ff_v_bf16m4x2(const __bf16 *rs1, size_t *new_vl, + size_t vl) { + return __riscv_vlseg2e16ff_v_bf16m4x2(rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16mf4x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.mask.nxv1bf16.i64( poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP5]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP4]] +// +vbfloat16mf4x2_t test_vlseg2e16ff_v_bf16mf4x2_m(vbool64_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff_v_bf16mf4x2_m(vm, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16mf2x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.mask.nxv2bf16.i64( poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP5]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP4]] +// +vbfloat16mf2x2_t test_vlseg2e16ff_v_bf16mf2x2_m(vbool32_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff_v_bf16mf2x2_m(vm, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16m1x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.mask.nxv4bf16.i64( poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP5]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP4]] +// +vbfloat16m1x2_t test_vlseg2e16ff_v_bf16m1x2_m(vbool16_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff_v_bf16m1x2_m(vm, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16m2x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.mask.nxv8bf16.i64( poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP5]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP4]] +// +vbfloat16m2x2_t test_vlseg2e16ff_v_bf16m2x2_m(vbool8_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff_v_bf16m2x2_m(vm, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16m4x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.mask.nxv16bf16.i64( poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP5]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP4]] +// +vbfloat16m4x2_t test_vlseg2e16ff_v_bf16m4x2_m(vbool4_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff_v_bf16m4x2_m(vm, rs1, new_vl, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlseg3e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlseg3e16.c new file mode 100644 index 0000000000000000000000000000000000000000..2c8d679d8d63ecc6b201d361308ea4b6c1ea3078 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlseg3e16.c @@ -0,0 +1,93 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16_v_bf16mf4x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vlseg3.nxv1bf16.i64( poison, poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16mf4x3_t test_vlseg3e16_v_bf16mf4x3(const __bf16 *rs1, size_t vl) { + return __riscv_vlseg3e16_v_bf16mf4x3(rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16_v_bf16mf2x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vlseg3.nxv2bf16.i64( poison, poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16mf2x3_t test_vlseg3e16_v_bf16mf2x3(const __bf16 *rs1, size_t vl) { + return __riscv_vlseg3e16_v_bf16mf2x3(rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16_v_bf16m1x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vlseg3.nxv4bf16.i64( poison, poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16m1x3_t test_vlseg3e16_v_bf16m1x3(const __bf16 *rs1, size_t vl) { + return __riscv_vlseg3e16_v_bf16m1x3(rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16_v_bf16m2x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vlseg3.nxv8bf16.i64( poison, poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16m2x3_t test_vlseg3e16_v_bf16m2x3(const __bf16 *rs1, size_t vl) { + return __riscv_vlseg3e16_v_bf16m2x3(rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16_v_bf16mf4x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vlseg3.mask.nxv1bf16.i64( poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16mf4x3_t test_vlseg3e16_v_bf16mf4x3_m(vbool64_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg3e16_v_bf16mf4x3_m(vm, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16_v_bf16mf2x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vlseg3.mask.nxv2bf16.i64( poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16mf2x3_t test_vlseg3e16_v_bf16mf2x3_m(vbool32_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg3e16_v_bf16mf2x3_m(vm, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16_v_bf16m1x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vlseg3.mask.nxv4bf16.i64( poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16m1x3_t test_vlseg3e16_v_bf16m1x3_m(vbool16_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg3e16_v_bf16m1x3_m(vm, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16_v_bf16m2x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vlseg3.mask.nxv8bf16.i64( poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16m2x3_t test_vlseg3e16_v_bf16m2x3_m(vbool8_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg3e16_v_bf16m2x3_m(vm, rs1, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlseg3e16ff.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlseg3e16ff.c new file mode 100644 index 0000000000000000000000000000000000000000..e7660a74c93d304037cf036065742a7ac18fdb7c --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlseg3e16ff.c @@ -0,0 +1,161 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16ff_v_bf16mf4x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , i64 } @llvm.riscv.vlseg3ff.nxv1bf16.i64( poison, poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , } [[TMP6]] +// +vbfloat16mf4x3_t test_vlseg3e16ff_v_bf16mf4x3(const __bf16 *rs1, size_t *new_vl, + size_t vl) { + return __riscv_vlseg3e16ff_v_bf16mf4x3(rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16ff_v_bf16mf2x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , i64 } @llvm.riscv.vlseg3ff.nxv2bf16.i64( poison, poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , } [[TMP6]] +// +vbfloat16mf2x3_t test_vlseg3e16ff_v_bf16mf2x3(const __bf16 *rs1, size_t *new_vl, + size_t vl) { + return __riscv_vlseg3e16ff_v_bf16mf2x3(rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16ff_v_bf16m1x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , i64 } @llvm.riscv.vlseg3ff.nxv4bf16.i64( poison, poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , } [[TMP6]] +// +vbfloat16m1x3_t test_vlseg3e16ff_v_bf16m1x3(const __bf16 *rs1, size_t *new_vl, + size_t vl) { + return __riscv_vlseg3e16ff_v_bf16m1x3(rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16ff_v_bf16m2x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , i64 } @llvm.riscv.vlseg3ff.nxv8bf16.i64( poison, poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , } [[TMP6]] +// +vbfloat16m2x3_t test_vlseg3e16ff_v_bf16m2x3(const __bf16 *rs1, size_t *new_vl, + size_t vl) { + return __riscv_vlseg3e16ff_v_bf16m2x3(rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16ff_v_bf16mf4x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , i64 } @llvm.riscv.vlseg3ff.mask.nxv1bf16.i64( poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , } [[TMP6]] +// +vbfloat16mf4x3_t test_vlseg3e16ff_v_bf16mf4x3_m(vbool64_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg3e16ff_v_bf16mf4x3_m(vm, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16ff_v_bf16mf2x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , i64 } @llvm.riscv.vlseg3ff.mask.nxv2bf16.i64( poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , } [[TMP6]] +// +vbfloat16mf2x3_t test_vlseg3e16ff_v_bf16mf2x3_m(vbool32_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg3e16ff_v_bf16mf2x3_m(vm, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16ff_v_bf16m1x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , i64 } @llvm.riscv.vlseg3ff.mask.nxv4bf16.i64( poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , } [[TMP6]] +// +vbfloat16m1x3_t test_vlseg3e16ff_v_bf16m1x3_m(vbool16_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg3e16ff_v_bf16m1x3_m(vm, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16ff_v_bf16m2x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , i64 } @llvm.riscv.vlseg3ff.mask.nxv8bf16.i64( poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , } [[TMP6]] +// +vbfloat16m2x3_t test_vlseg3e16ff_v_bf16m2x3_m(vbool8_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg3e16ff_v_bf16m2x3_m(vm, rs1, new_vl, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlseg4e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlseg4e16.c new file mode 100644 index 0000000000000000000000000000000000000000..c7480e10028a95336698ae1f09bea024bae8f278 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlseg4e16.c @@ -0,0 +1,93 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16_v_bf16mf4x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vlseg4.nxv1bf16.i64( poison, poison, poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16mf4x4_t test_vlseg4e16_v_bf16mf4x4(const __bf16 *rs1, size_t vl) { + return __riscv_vlseg4e16_v_bf16mf4x4(rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16_v_bf16mf2x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vlseg4.nxv2bf16.i64( poison, poison, poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16mf2x4_t test_vlseg4e16_v_bf16mf2x4(const __bf16 *rs1, size_t vl) { + return __riscv_vlseg4e16_v_bf16mf2x4(rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16_v_bf16m1x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vlseg4.nxv4bf16.i64( poison, poison, poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16m1x4_t test_vlseg4e16_v_bf16m1x4(const __bf16 *rs1, size_t vl) { + return __riscv_vlseg4e16_v_bf16m1x4(rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16_v_bf16m2x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vlseg4.nxv8bf16.i64( poison, poison, poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16m2x4_t test_vlseg4e16_v_bf16m2x4(const __bf16 *rs1, size_t vl) { + return __riscv_vlseg4e16_v_bf16m2x4(rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16_v_bf16mf4x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vlseg4.mask.nxv1bf16.i64( poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16mf4x4_t test_vlseg4e16_v_bf16mf4x4_m(vbool64_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg4e16_v_bf16mf4x4_m(vm, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16_v_bf16mf2x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vlseg4.mask.nxv2bf16.i64( poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16mf2x4_t test_vlseg4e16_v_bf16mf2x4_m(vbool32_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg4e16_v_bf16mf2x4_m(vm, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16_v_bf16m1x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vlseg4.mask.nxv4bf16.i64( poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16m1x4_t test_vlseg4e16_v_bf16m1x4_m(vbool16_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg4e16_v_bf16m1x4_m(vm, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16_v_bf16m2x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vlseg4.mask.nxv8bf16.i64( poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16m2x4_t test_vlseg4e16_v_bf16m2x4_m(vbool8_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg4e16_v_bf16m2x4_m(vm, rs1, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlseg4e16ff.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlseg4e16ff.c new file mode 100644 index 0000000000000000000000000000000000000000..de1e40c98729cee1c7e3c710edd995a46c85de1e --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlseg4e16ff.c @@ -0,0 +1,177 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16ff_v_bf16mf4x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , i64 } @llvm.riscv.vlseg4ff.nxv1bf16.i64( poison, poison, poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , } [[TMP6]], [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 4 +// CHECK-RV64-NEXT: store i64 [[TMP9]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , } [[TMP8]] +// +vbfloat16mf4x4_t test_vlseg4e16ff_v_bf16mf4x4(const __bf16 *rs1, size_t *new_vl, + size_t vl) { + return __riscv_vlseg4e16ff_v_bf16mf4x4(rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16ff_v_bf16mf2x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , i64 } @llvm.riscv.vlseg4ff.nxv2bf16.i64( poison, poison, poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , } [[TMP6]], [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 4 +// CHECK-RV64-NEXT: store i64 [[TMP9]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , } [[TMP8]] +// +vbfloat16mf2x4_t test_vlseg4e16ff_v_bf16mf2x4(const __bf16 *rs1, size_t *new_vl, + size_t vl) { + return __riscv_vlseg4e16ff_v_bf16mf2x4(rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16ff_v_bf16m1x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , i64 } @llvm.riscv.vlseg4ff.nxv4bf16.i64( poison, poison, poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , } [[TMP6]], [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 4 +// CHECK-RV64-NEXT: store i64 [[TMP9]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , } [[TMP8]] +// +vbfloat16m1x4_t test_vlseg4e16ff_v_bf16m1x4(const __bf16 *rs1, size_t *new_vl, + size_t vl) { + return __riscv_vlseg4e16ff_v_bf16m1x4(rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16ff_v_bf16m2x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , i64 } @llvm.riscv.vlseg4ff.nxv8bf16.i64( poison, poison, poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , } [[TMP6]], [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 4 +// CHECK-RV64-NEXT: store i64 [[TMP9]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , } [[TMP8]] +// +vbfloat16m2x4_t test_vlseg4e16ff_v_bf16m2x4(const __bf16 *rs1, size_t *new_vl, + size_t vl) { + return __riscv_vlseg4e16ff_v_bf16m2x4(rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16ff_v_bf16mf4x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , i64 } @llvm.riscv.vlseg4ff.mask.nxv1bf16.i64( poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , } [[TMP6]], [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 4 +// CHECK-RV64-NEXT: store i64 [[TMP9]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , } [[TMP8]] +// +vbfloat16mf4x4_t test_vlseg4e16ff_v_bf16mf4x4_m(vbool64_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg4e16ff_v_bf16mf4x4_m(vm, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16ff_v_bf16mf2x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , i64 } @llvm.riscv.vlseg4ff.mask.nxv2bf16.i64( poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , } [[TMP6]], [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 4 +// CHECK-RV64-NEXT: store i64 [[TMP9]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , } [[TMP8]] +// +vbfloat16mf2x4_t test_vlseg4e16ff_v_bf16mf2x4_m(vbool32_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg4e16ff_v_bf16mf2x4_m(vm, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16ff_v_bf16m1x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , i64 } @llvm.riscv.vlseg4ff.mask.nxv4bf16.i64( poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , } [[TMP6]], [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 4 +// CHECK-RV64-NEXT: store i64 [[TMP9]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , } [[TMP8]] +// +vbfloat16m1x4_t test_vlseg4e16ff_v_bf16m1x4_m(vbool16_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg4e16ff_v_bf16m1x4_m(vm, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16ff_v_bf16m2x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , i64 } @llvm.riscv.vlseg4ff.mask.nxv8bf16.i64( poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , } [[TMP6]], [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 4 +// CHECK-RV64-NEXT: store i64 [[TMP9]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , } [[TMP8]] +// +vbfloat16m2x4_t test_vlseg4e16ff_v_bf16m2x4_m(vbool8_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg4e16ff_v_bf16m2x4_m(vm, rs1, new_vl, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlseg5e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlseg5e16.c new file mode 100644 index 0000000000000000000000000000000000000000..08d4af94ee542bc53952490d06d427038ae71196 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlseg5e16.c @@ -0,0 +1,72 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16_v_bf16mf4x5( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , } @llvm.riscv.vlseg5.nxv1bf16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP0]] +// +vbfloat16mf4x5_t test_vlseg5e16_v_bf16mf4x5(const __bf16 *rs1, size_t vl) { + return __riscv_vlseg5e16_v_bf16mf4x5(rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16_v_bf16mf2x5( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , } @llvm.riscv.vlseg5.nxv2bf16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP0]] +// +vbfloat16mf2x5_t test_vlseg5e16_v_bf16mf2x5(const __bf16 *rs1, size_t vl) { + return __riscv_vlseg5e16_v_bf16mf2x5(rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16_v_bf16m1x5( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , } @llvm.riscv.vlseg5.nxv4bf16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP0]] +// +vbfloat16m1x5_t test_vlseg5e16_v_bf16m1x5(const __bf16 *rs1, size_t vl) { + return __riscv_vlseg5e16_v_bf16m1x5(rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16_v_bf16mf4x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , } @llvm.riscv.vlseg5.mask.nxv1bf16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP0]] +// +vbfloat16mf4x5_t test_vlseg5e16_v_bf16mf4x5_m(vbool64_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg5e16_v_bf16mf4x5_m(vm, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16_v_bf16mf2x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , } @llvm.riscv.vlseg5.mask.nxv2bf16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP0]] +// +vbfloat16mf2x5_t test_vlseg5e16_v_bf16mf2x5_m(vbool32_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg5e16_v_bf16mf2x5_m(vm, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16_v_bf16m1x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , } @llvm.riscv.vlseg5.mask.nxv4bf16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP0]] +// +vbfloat16m1x5_t test_vlseg5e16_v_bf16m1x5_m(vbool16_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg5e16_v_bf16m1x5_m(vm, rs1, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlseg5e16ff.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlseg5e16ff.c new file mode 100644 index 0000000000000000000000000000000000000000..b19b51a28edacb6c3bf435804fb96d95c03f5e46 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlseg5e16ff.c @@ -0,0 +1,147 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16ff_v_bf16mf4x5( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , i64 } @llvm.riscv.vlseg5ff.nxv1bf16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , } [[TMP6]], [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 4 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , } [[TMP8]], [[TMP9]], 4 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 5 +// CHECK-RV64-NEXT: store i64 [[TMP11]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , } [[TMP10]] +// +vbfloat16mf4x5_t test_vlseg5e16ff_v_bf16mf4x5(const __bf16 *rs1, size_t *new_vl, + size_t vl) { + return __riscv_vlseg5e16ff_v_bf16mf4x5(rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16ff_v_bf16mf2x5( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , i64 } @llvm.riscv.vlseg5ff.nxv2bf16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , } [[TMP6]], [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 4 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , } [[TMP8]], [[TMP9]], 4 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 5 +// CHECK-RV64-NEXT: store i64 [[TMP11]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , } [[TMP10]] +// +vbfloat16mf2x5_t test_vlseg5e16ff_v_bf16mf2x5(const __bf16 *rs1, size_t *new_vl, + size_t vl) { + return __riscv_vlseg5e16ff_v_bf16mf2x5(rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16ff_v_bf16m1x5( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , i64 } @llvm.riscv.vlseg5ff.nxv4bf16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , } [[TMP6]], [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 4 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , } [[TMP8]], [[TMP9]], 4 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 5 +// CHECK-RV64-NEXT: store i64 [[TMP11]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , } [[TMP10]] +// +vbfloat16m1x5_t test_vlseg5e16ff_v_bf16m1x5(const __bf16 *rs1, size_t *new_vl, + size_t vl) { + return __riscv_vlseg5e16ff_v_bf16m1x5(rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16ff_v_bf16mf4x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , i64 } @llvm.riscv.vlseg5ff.mask.nxv1bf16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , } [[TMP6]], [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 4 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , } [[TMP8]], [[TMP9]], 4 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 5 +// CHECK-RV64-NEXT: store i64 [[TMP11]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , } [[TMP10]] +// +vbfloat16mf4x5_t test_vlseg5e16ff_v_bf16mf4x5_m(vbool64_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg5e16ff_v_bf16mf4x5_m(vm, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16ff_v_bf16mf2x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , i64 } @llvm.riscv.vlseg5ff.mask.nxv2bf16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , } [[TMP6]], [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 4 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , } [[TMP8]], [[TMP9]], 4 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 5 +// CHECK-RV64-NEXT: store i64 [[TMP11]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , } [[TMP10]] +// +vbfloat16mf2x5_t test_vlseg5e16ff_v_bf16mf2x5_m(vbool32_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg5e16ff_v_bf16mf2x5_m(vm, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16ff_v_bf16m1x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , i64 } @llvm.riscv.vlseg5ff.mask.nxv4bf16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , } [[TMP6]], [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 4 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , } [[TMP8]], [[TMP9]], 4 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 5 +// CHECK-RV64-NEXT: store i64 [[TMP11]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , } [[TMP10]] +// +vbfloat16m1x5_t test_vlseg5e16ff_v_bf16m1x5_m(vbool16_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg5e16ff_v_bf16m1x5_m(vm, rs1, new_vl, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlseg6e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlseg6e16.c new file mode 100644 index 0000000000000000000000000000000000000000..018c18098122cc4cf2192ac867618793617aff89 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlseg6e16.c @@ -0,0 +1,72 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16_v_bf16mf4x6( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , } @llvm.riscv.vlseg6.nxv1bf16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP0]] +// +vbfloat16mf4x6_t test_vlseg6e16_v_bf16mf4x6(const __bf16 *rs1, size_t vl) { + return __riscv_vlseg6e16_v_bf16mf4x6(rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16_v_bf16mf2x6( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , } @llvm.riscv.vlseg6.nxv2bf16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP0]] +// +vbfloat16mf2x6_t test_vlseg6e16_v_bf16mf2x6(const __bf16 *rs1, size_t vl) { + return __riscv_vlseg6e16_v_bf16mf2x6(rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16_v_bf16m1x6( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , } @llvm.riscv.vlseg6.nxv4bf16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP0]] +// +vbfloat16m1x6_t test_vlseg6e16_v_bf16m1x6(const __bf16 *rs1, size_t vl) { + return __riscv_vlseg6e16_v_bf16m1x6(rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16_v_bf16mf4x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , } @llvm.riscv.vlseg6.mask.nxv1bf16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP0]] +// +vbfloat16mf4x6_t test_vlseg6e16_v_bf16mf4x6_m(vbool64_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg6e16_v_bf16mf4x6_m(vm, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16_v_bf16mf2x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , } @llvm.riscv.vlseg6.mask.nxv2bf16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP0]] +// +vbfloat16mf2x6_t test_vlseg6e16_v_bf16mf2x6_m(vbool32_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg6e16_v_bf16mf2x6_m(vm, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16_v_bf16m1x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , } @llvm.riscv.vlseg6.mask.nxv4bf16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP0]] +// +vbfloat16m1x6_t test_vlseg6e16_v_bf16m1x6_m(vbool16_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg6e16_v_bf16m1x6_m(vm, rs1, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlseg6e16ff.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlseg6e16ff.c new file mode 100644 index 0000000000000000000000000000000000000000..2104f8e083f2d133781a9dcc1be048c7b2a19a0c --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlseg6e16ff.c @@ -0,0 +1,159 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16ff_v_bf16mf4x6( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , i64 } @llvm.riscv.vlseg6ff.nxv1bf16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , } [[TMP6]], [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 4 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , } [[TMP8]], [[TMP9]], 4 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 5 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , } [[TMP10]], [[TMP11]], 5 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 6 +// CHECK-RV64-NEXT: store i64 [[TMP13]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP12]] +// +vbfloat16mf4x6_t test_vlseg6e16ff_v_bf16mf4x6(const __bf16 *rs1, size_t *new_vl, + size_t vl) { + return __riscv_vlseg6e16ff_v_bf16mf4x6(rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16ff_v_bf16mf2x6( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , i64 } @llvm.riscv.vlseg6ff.nxv2bf16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , } [[TMP6]], [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 4 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , } [[TMP8]], [[TMP9]], 4 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 5 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , } [[TMP10]], [[TMP11]], 5 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 6 +// CHECK-RV64-NEXT: store i64 [[TMP13]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP12]] +// +vbfloat16mf2x6_t test_vlseg6e16ff_v_bf16mf2x6(const __bf16 *rs1, size_t *new_vl, + size_t vl) { + return __riscv_vlseg6e16ff_v_bf16mf2x6(rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16ff_v_bf16m1x6( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , i64 } @llvm.riscv.vlseg6ff.nxv4bf16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , } [[TMP6]], [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 4 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , } [[TMP8]], [[TMP9]], 4 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 5 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , } [[TMP10]], [[TMP11]], 5 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 6 +// CHECK-RV64-NEXT: store i64 [[TMP13]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP12]] +// +vbfloat16m1x6_t test_vlseg6e16ff_v_bf16m1x6(const __bf16 *rs1, size_t *new_vl, + size_t vl) { + return __riscv_vlseg6e16ff_v_bf16m1x6(rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16ff_v_bf16mf4x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , i64 } @llvm.riscv.vlseg6ff.mask.nxv1bf16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , } [[TMP6]], [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 4 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , } [[TMP8]], [[TMP9]], 4 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 5 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , } [[TMP10]], [[TMP11]], 5 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 6 +// CHECK-RV64-NEXT: store i64 [[TMP13]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP12]] +// +vbfloat16mf4x6_t test_vlseg6e16ff_v_bf16mf4x6_m(vbool64_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg6e16ff_v_bf16mf4x6_m(vm, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16ff_v_bf16mf2x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , i64 } @llvm.riscv.vlseg6ff.mask.nxv2bf16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , } [[TMP6]], [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 4 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , } [[TMP8]], [[TMP9]], 4 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 5 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , } [[TMP10]], [[TMP11]], 5 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 6 +// CHECK-RV64-NEXT: store i64 [[TMP13]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP12]] +// +vbfloat16mf2x6_t test_vlseg6e16ff_v_bf16mf2x6_m(vbool32_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg6e16ff_v_bf16mf2x6_m(vm, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16ff_v_bf16m1x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , i64 } @llvm.riscv.vlseg6ff.mask.nxv4bf16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , } [[TMP6]], [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 4 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , } [[TMP8]], [[TMP9]], 4 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 5 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , } [[TMP10]], [[TMP11]], 5 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 6 +// CHECK-RV64-NEXT: store i64 [[TMP13]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP12]] +// +vbfloat16m1x6_t test_vlseg6e16ff_v_bf16m1x6_m(vbool16_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg6e16ff_v_bf16m1x6_m(vm, rs1, new_vl, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlseg7e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlseg7e16.c new file mode 100644 index 0000000000000000000000000000000000000000..b15ef25d0c1fcae79de7d0984d442b02ad620c9e --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlseg7e16.c @@ -0,0 +1,72 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16_v_bf16mf4x7( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , } @llvm.riscv.vlseg7.nxv1bf16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP0]] +// +vbfloat16mf4x7_t test_vlseg7e16_v_bf16mf4x7(const __bf16 *rs1, size_t vl) { + return __riscv_vlseg7e16_v_bf16mf4x7(rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16_v_bf16mf2x7( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , } @llvm.riscv.vlseg7.nxv2bf16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP0]] +// +vbfloat16mf2x7_t test_vlseg7e16_v_bf16mf2x7(const __bf16 *rs1, size_t vl) { + return __riscv_vlseg7e16_v_bf16mf2x7(rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16_v_bf16m1x7( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , } @llvm.riscv.vlseg7.nxv4bf16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP0]] +// +vbfloat16m1x7_t test_vlseg7e16_v_bf16m1x7(const __bf16 *rs1, size_t vl) { + return __riscv_vlseg7e16_v_bf16m1x7(rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16_v_bf16mf4x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , } @llvm.riscv.vlseg7.mask.nxv1bf16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP0]] +// +vbfloat16mf4x7_t test_vlseg7e16_v_bf16mf4x7_m(vbool64_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg7e16_v_bf16mf4x7_m(vm, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16_v_bf16mf2x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , } @llvm.riscv.vlseg7.mask.nxv2bf16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP0]] +// +vbfloat16mf2x7_t test_vlseg7e16_v_bf16mf2x7_m(vbool32_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg7e16_v_bf16mf2x7_m(vm, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16_v_bf16m1x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , } @llvm.riscv.vlseg7.mask.nxv4bf16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP0]] +// +vbfloat16m1x7_t test_vlseg7e16_v_bf16m1x7_m(vbool16_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg7e16_v_bf16m1x7_m(vm, rs1, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlseg7e16ff.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlseg7e16ff.c new file mode 100644 index 0000000000000000000000000000000000000000..42361b6375cbf1d1a5ae93487f66bf5506bbec90 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlseg7e16ff.c @@ -0,0 +1,171 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16ff_v_bf16mf4x7( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , i64 } @llvm.riscv.vlseg7ff.nxv1bf16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , , , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , , , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , , , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , , } [[TMP6]], [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 4 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , , } [[TMP8]], [[TMP9]], 4 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 5 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , , } [[TMP10]], [[TMP11]], 5 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 6 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , , } [[TMP12]], [[TMP13]], 6 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 7 +// CHECK-RV64-NEXT: store i64 [[TMP15]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP14]] +// +vbfloat16mf4x7_t test_vlseg7e16ff_v_bf16mf4x7(const __bf16 *rs1, size_t *new_vl, + size_t vl) { + return __riscv_vlseg7e16ff_v_bf16mf4x7(rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16ff_v_bf16mf2x7( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , i64 } @llvm.riscv.vlseg7ff.nxv2bf16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , , , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , , , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , , , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , , } [[TMP6]], [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 4 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , , } [[TMP8]], [[TMP9]], 4 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 5 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , , } [[TMP10]], [[TMP11]], 5 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 6 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , , } [[TMP12]], [[TMP13]], 6 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 7 +// CHECK-RV64-NEXT: store i64 [[TMP15]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP14]] +// +vbfloat16mf2x7_t test_vlseg7e16ff_v_bf16mf2x7(const __bf16 *rs1, size_t *new_vl, + size_t vl) { + return __riscv_vlseg7e16ff_v_bf16mf2x7(rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16ff_v_bf16m1x7( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , i64 } @llvm.riscv.vlseg7ff.nxv4bf16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , , , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , , , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , , , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , , } [[TMP6]], [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 4 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , , } [[TMP8]], [[TMP9]], 4 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 5 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , , } [[TMP10]], [[TMP11]], 5 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 6 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , , } [[TMP12]], [[TMP13]], 6 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 7 +// CHECK-RV64-NEXT: store i64 [[TMP15]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP14]] +// +vbfloat16m1x7_t test_vlseg7e16ff_v_bf16m1x7(const __bf16 *rs1, size_t *new_vl, + size_t vl) { + return __riscv_vlseg7e16ff_v_bf16m1x7(rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16ff_v_bf16mf4x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , i64 } @llvm.riscv.vlseg7ff.mask.nxv1bf16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , , , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , , , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , , , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , , } [[TMP6]], [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 4 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , , } [[TMP8]], [[TMP9]], 4 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 5 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , , } [[TMP10]], [[TMP11]], 5 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 6 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , , } [[TMP12]], [[TMP13]], 6 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 7 +// CHECK-RV64-NEXT: store i64 [[TMP15]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP14]] +// +vbfloat16mf4x7_t test_vlseg7e16ff_v_bf16mf4x7_m(vbool64_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg7e16ff_v_bf16mf4x7_m(vm, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16ff_v_bf16mf2x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , i64 } @llvm.riscv.vlseg7ff.mask.nxv2bf16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , , , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , , , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , , , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , , } [[TMP6]], [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 4 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , , } [[TMP8]], [[TMP9]], 4 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 5 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , , } [[TMP10]], [[TMP11]], 5 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 6 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , , } [[TMP12]], [[TMP13]], 6 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 7 +// CHECK-RV64-NEXT: store i64 [[TMP15]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP14]] +// +vbfloat16mf2x7_t test_vlseg7e16ff_v_bf16mf2x7_m(vbool32_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg7e16ff_v_bf16mf2x7_m(vm, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16ff_v_bf16m1x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , i64 } @llvm.riscv.vlseg7ff.mask.nxv4bf16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , , , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , , , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , , , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , , } [[TMP6]], [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 4 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , , } [[TMP8]], [[TMP9]], 4 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 5 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , , } [[TMP10]], [[TMP11]], 5 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 6 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , , } [[TMP12]], [[TMP13]], 6 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 7 +// CHECK-RV64-NEXT: store i64 [[TMP15]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP14]] +// +vbfloat16m1x7_t test_vlseg7e16ff_v_bf16m1x7_m(vbool16_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg7e16ff_v_bf16m1x7_m(vm, rs1, new_vl, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlseg8e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlseg8e16.c new file mode 100644 index 0000000000000000000000000000000000000000..7f113a21e9bf92e3f46dd28a692197edbcc47969 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlseg8e16.c @@ -0,0 +1,72 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16_v_bf16mf4x8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , } @llvm.riscv.vlseg8.nxv1bf16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP0]] +// +vbfloat16mf4x8_t test_vlseg8e16_v_bf16mf4x8(const __bf16 *rs1, size_t vl) { + return __riscv_vlseg8e16_v_bf16mf4x8(rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16_v_bf16mf2x8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , } @llvm.riscv.vlseg8.nxv2bf16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP0]] +// +vbfloat16mf2x8_t test_vlseg8e16_v_bf16mf2x8(const __bf16 *rs1, size_t vl) { + return __riscv_vlseg8e16_v_bf16mf2x8(rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16_v_bf16m1x8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , } @llvm.riscv.vlseg8.nxv4bf16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP0]] +// +vbfloat16m1x8_t test_vlseg8e16_v_bf16m1x8(const __bf16 *rs1, size_t vl) { + return __riscv_vlseg8e16_v_bf16m1x8(rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16_v_bf16mf4x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , } @llvm.riscv.vlseg8.mask.nxv1bf16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP0]] +// +vbfloat16mf4x8_t test_vlseg8e16_v_bf16mf4x8_m(vbool64_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg8e16_v_bf16mf4x8_m(vm, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16_v_bf16mf2x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , } @llvm.riscv.vlseg8.mask.nxv2bf16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP0]] +// +vbfloat16mf2x8_t test_vlseg8e16_v_bf16mf2x8_m(vbool32_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg8e16_v_bf16mf2x8_m(vm, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16_v_bf16m1x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , } @llvm.riscv.vlseg8.mask.nxv4bf16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP0]] +// +vbfloat16m1x8_t test_vlseg8e16_v_bf16m1x8_m(vbool16_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg8e16_v_bf16m1x8_m(vm, rs1, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlseg8e16ff.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlseg8e16ff.c new file mode 100644 index 0000000000000000000000000000000000000000..c9cf4ba0243cec3a3c7b1cb4156b5f3dfdd0d98f --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlseg8e16ff.c @@ -0,0 +1,183 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16ff_v_bf16mf4x8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , , i64 } @llvm.riscv.vlseg8ff.nxv1bf16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , , , , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , , , , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , , , , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , , , } [[TMP6]], [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 4 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , , , } [[TMP8]], [[TMP9]], 4 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 5 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , , , } [[TMP10]], [[TMP11]], 5 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 6 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , , , } [[TMP12]], [[TMP13]], 6 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 7 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , , , } [[TMP14]], [[TMP15]], 7 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 8 +// CHECK-RV64-NEXT: store i64 [[TMP17]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP16]] +// +vbfloat16mf4x8_t test_vlseg8e16ff_v_bf16mf4x8(const __bf16 *rs1, size_t *new_vl, + size_t vl) { + return __riscv_vlseg8e16ff_v_bf16mf4x8(rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16ff_v_bf16mf2x8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , , i64 } @llvm.riscv.vlseg8ff.nxv2bf16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , , , , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , , , , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , , , , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , , , } [[TMP6]], [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 4 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , , , } [[TMP8]], [[TMP9]], 4 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 5 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , , , } [[TMP10]], [[TMP11]], 5 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 6 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , , , } [[TMP12]], [[TMP13]], 6 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 7 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , , , } [[TMP14]], [[TMP15]], 7 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 8 +// CHECK-RV64-NEXT: store i64 [[TMP17]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP16]] +// +vbfloat16mf2x8_t test_vlseg8e16ff_v_bf16mf2x8(const __bf16 *rs1, size_t *new_vl, + size_t vl) { + return __riscv_vlseg8e16ff_v_bf16mf2x8(rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16ff_v_bf16m1x8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , , i64 } @llvm.riscv.vlseg8ff.nxv4bf16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , , , , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , , , , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , , , , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , , , } [[TMP6]], [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 4 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , , , } [[TMP8]], [[TMP9]], 4 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 5 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , , , } [[TMP10]], [[TMP11]], 5 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 6 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , , , } [[TMP12]], [[TMP13]], 6 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 7 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , , , } [[TMP14]], [[TMP15]], 7 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 8 +// CHECK-RV64-NEXT: store i64 [[TMP17]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP16]] +// +vbfloat16m1x8_t test_vlseg8e16ff_v_bf16m1x8(const __bf16 *rs1, size_t *new_vl, + size_t vl) { + return __riscv_vlseg8e16ff_v_bf16m1x8(rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16ff_v_bf16mf4x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , , i64 } @llvm.riscv.vlseg8ff.mask.nxv1bf16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , , , , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , , , , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , , , , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , , , } [[TMP6]], [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 4 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , , , } [[TMP8]], [[TMP9]], 4 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 5 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , , , } [[TMP10]], [[TMP11]], 5 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 6 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , , , } [[TMP12]], [[TMP13]], 6 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 7 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , , , } [[TMP14]], [[TMP15]], 7 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 8 +// CHECK-RV64-NEXT: store i64 [[TMP17]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP16]] +// +vbfloat16mf4x8_t test_vlseg8e16ff_v_bf16mf4x8_m(vbool64_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg8e16ff_v_bf16mf4x8_m(vm, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16ff_v_bf16mf2x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , , i64 } @llvm.riscv.vlseg8ff.mask.nxv2bf16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , , , , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , , , , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , , , , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , , , } [[TMP6]], [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 4 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , , , } [[TMP8]], [[TMP9]], 4 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 5 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , , , } [[TMP10]], [[TMP11]], 5 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 6 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , , , } [[TMP12]], [[TMP13]], 6 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 7 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , , , } [[TMP14]], [[TMP15]], 7 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 8 +// CHECK-RV64-NEXT: store i64 [[TMP17]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP16]] +// +vbfloat16mf2x8_t test_vlseg8e16ff_v_bf16mf2x8_m(vbool32_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg8e16ff_v_bf16mf2x8_m(vm, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16ff_v_bf16m1x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , , i64 } @llvm.riscv.vlseg8ff.mask.nxv4bf16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , , , , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , , , , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , , , , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , , , } [[TMP6]], [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 4 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , , , } [[TMP8]], [[TMP9]], 4 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 5 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , , , } [[TMP10]], [[TMP11]], 5 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 6 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , , , } [[TMP12]], [[TMP13]], 6 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 7 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , , , } [[TMP14]], [[TMP15]], 7 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 8 +// CHECK-RV64-NEXT: store i64 [[TMP17]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP16]] +// +vbfloat16m1x8_t test_vlseg8e16ff_v_bf16m1x8_m(vbool16_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg8e16ff_v_bf16m1x8_m(vm, rs1, new_vl, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlsseg2e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlsseg2e16.c new file mode 100644 index 0000000000000000000000000000000000000000..92b5c2948fa31646b81e0c02817b3653eb546e03 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlsseg2e16.c @@ -0,0 +1,119 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16mf4x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vlsseg2.nxv1bf16.i64( poison, poison, ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16mf4x2_t test_vlsseg2e16_v_bf16mf4x2(const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg2e16_v_bf16mf4x2(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16mf2x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vlsseg2.nxv2bf16.i64( poison, poison, ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16mf2x2_t test_vlsseg2e16_v_bf16mf2x2(const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg2e16_v_bf16mf2x2(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16m1x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vlsseg2.nxv4bf16.i64( poison, poison, ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16m1x2_t test_vlsseg2e16_v_bf16m1x2(const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg2e16_v_bf16m1x2(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16m2x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vlsseg2.nxv8bf16.i64( poison, poison, ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16m2x2_t test_vlsseg2e16_v_bf16m2x2(const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg2e16_v_bf16m2x2(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16m4x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vlsseg2.nxv16bf16.i64( poison, poison, ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16m4x2_t test_vlsseg2e16_v_bf16m4x2(const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg2e16_v_bf16m4x2(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16mf4x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vlsseg2.mask.nxv1bf16.i64( poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16mf4x2_t test_vlsseg2e16_v_bf16mf4x2_m(vbool64_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg2e16_v_bf16mf4x2_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16mf2x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vlsseg2.mask.nxv2bf16.i64( poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16mf2x2_t test_vlsseg2e16_v_bf16mf2x2_m(vbool32_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg2e16_v_bf16mf2x2_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16m1x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vlsseg2.mask.nxv4bf16.i64( poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16m1x2_t test_vlsseg2e16_v_bf16m1x2_m(vbool16_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg2e16_v_bf16m1x2_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16m2x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vlsseg2.mask.nxv8bf16.i64( poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16m2x2_t test_vlsseg2e16_v_bf16m2x2_m(vbool8_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg2e16_v_bf16m2x2_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16m4x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vlsseg2.mask.nxv16bf16.i64( poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16m4x2_t test_vlsseg2e16_v_bf16m4x2_m(vbool4_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg2e16_v_bf16m4x2_m(vm, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlsseg3e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlsseg3e16.c new file mode 100644 index 0000000000000000000000000000000000000000..d834ead8365ca4dd1d5189c4655921448a4fa8c3 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlsseg3e16.c @@ -0,0 +1,97 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlsseg3e16_v_bf16mf4x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vlsseg3.nxv1bf16.i64( poison, poison, poison, ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16mf4x3_t test_vlsseg3e16_v_bf16mf4x3(const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg3e16_v_bf16mf4x3(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlsseg3e16_v_bf16mf2x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vlsseg3.nxv2bf16.i64( poison, poison, poison, ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16mf2x3_t test_vlsseg3e16_v_bf16mf2x3(const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg3e16_v_bf16mf2x3(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlsseg3e16_v_bf16m1x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vlsseg3.nxv4bf16.i64( poison, poison, poison, ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16m1x3_t test_vlsseg3e16_v_bf16m1x3(const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg3e16_v_bf16m1x3(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlsseg3e16_v_bf16m2x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vlsseg3.nxv8bf16.i64( poison, poison, poison, ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16m2x3_t test_vlsseg3e16_v_bf16m2x3(const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg3e16_v_bf16m2x3(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlsseg3e16_v_bf16mf4x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vlsseg3.mask.nxv1bf16.i64( poison, poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16mf4x3_t test_vlsseg3e16_v_bf16mf4x3_m(vbool64_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg3e16_v_bf16mf4x3_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlsseg3e16_v_bf16mf2x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vlsseg3.mask.nxv2bf16.i64( poison, poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16mf2x3_t test_vlsseg3e16_v_bf16mf2x3_m(vbool32_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg3e16_v_bf16mf2x3_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlsseg3e16_v_bf16m1x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vlsseg3.mask.nxv4bf16.i64( poison, poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16m1x3_t test_vlsseg3e16_v_bf16m1x3_m(vbool16_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg3e16_v_bf16m1x3_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlsseg3e16_v_bf16m2x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vlsseg3.mask.nxv8bf16.i64( poison, poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16m2x3_t test_vlsseg3e16_v_bf16m2x3_m(vbool8_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg3e16_v_bf16m2x3_m(vm, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlsseg4e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlsseg4e16.c new file mode 100644 index 0000000000000000000000000000000000000000..d59822b0fb35f6cdb8a44012147398708c74a5c7 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlsseg4e16.c @@ -0,0 +1,97 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlsseg4e16_v_bf16mf4x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vlsseg4.nxv1bf16.i64( poison, poison, poison, poison, ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16mf4x4_t test_vlsseg4e16_v_bf16mf4x4(const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg4e16_v_bf16mf4x4(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlsseg4e16_v_bf16mf2x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vlsseg4.nxv2bf16.i64( poison, poison, poison, poison, ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16mf2x4_t test_vlsseg4e16_v_bf16mf2x4(const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg4e16_v_bf16mf2x4(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlsseg4e16_v_bf16m1x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vlsseg4.nxv4bf16.i64( poison, poison, poison, poison, ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16m1x4_t test_vlsseg4e16_v_bf16m1x4(const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg4e16_v_bf16m1x4(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlsseg4e16_v_bf16m2x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vlsseg4.nxv8bf16.i64( poison, poison, poison, poison, ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16m2x4_t test_vlsseg4e16_v_bf16m2x4(const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg4e16_v_bf16m2x4(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlsseg4e16_v_bf16mf4x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vlsseg4.mask.nxv1bf16.i64( poison, poison, poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16mf4x4_t test_vlsseg4e16_v_bf16mf4x4_m(vbool64_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg4e16_v_bf16mf4x4_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlsseg4e16_v_bf16mf2x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vlsseg4.mask.nxv2bf16.i64( poison, poison, poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16mf2x4_t test_vlsseg4e16_v_bf16mf2x4_m(vbool32_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg4e16_v_bf16mf2x4_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlsseg4e16_v_bf16m1x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vlsseg4.mask.nxv4bf16.i64( poison, poison, poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16m1x4_t test_vlsseg4e16_v_bf16m1x4_m(vbool16_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg4e16_v_bf16m1x4_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlsseg4e16_v_bf16m2x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vlsseg4.mask.nxv8bf16.i64( poison, poison, poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16m2x4_t test_vlsseg4e16_v_bf16m2x4_m(vbool8_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg4e16_v_bf16m2x4_m(vm, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlsseg5e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlsseg5e16.c new file mode 100644 index 0000000000000000000000000000000000000000..a8c653585b3be3e5b0c691e3f1ad54b92222a7f6 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlsseg5e16.c @@ -0,0 +1,75 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlsseg5e16_v_bf16mf4x5( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , } @llvm.riscv.vlsseg5.nxv1bf16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP0]] +// +vbfloat16mf4x5_t test_vlsseg5e16_v_bf16mf4x5(const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg5e16_v_bf16mf4x5(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlsseg5e16_v_bf16mf2x5( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , } @llvm.riscv.vlsseg5.nxv2bf16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP0]] +// +vbfloat16mf2x5_t test_vlsseg5e16_v_bf16mf2x5(const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg5e16_v_bf16mf2x5(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlsseg5e16_v_bf16m1x5( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , } @llvm.riscv.vlsseg5.nxv4bf16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP0]] +// +vbfloat16m1x5_t test_vlsseg5e16_v_bf16m1x5(const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg5e16_v_bf16m1x5(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlsseg5e16_v_bf16mf4x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , } @llvm.riscv.vlsseg5.mask.nxv1bf16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP0]] +// +vbfloat16mf4x5_t test_vlsseg5e16_v_bf16mf4x5_m(vbool64_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg5e16_v_bf16mf4x5_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlsseg5e16_v_bf16mf2x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , } @llvm.riscv.vlsseg5.mask.nxv2bf16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP0]] +// +vbfloat16mf2x5_t test_vlsseg5e16_v_bf16mf2x5_m(vbool32_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg5e16_v_bf16mf2x5_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlsseg5e16_v_bf16m1x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , } @llvm.riscv.vlsseg5.mask.nxv4bf16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP0]] +// +vbfloat16m1x5_t test_vlsseg5e16_v_bf16m1x5_m(vbool16_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg5e16_v_bf16m1x5_m(vm, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlsseg6e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlsseg6e16.c new file mode 100644 index 0000000000000000000000000000000000000000..1271f7b4eb7678a8f0cdf2200e37dbcf2e430e63 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlsseg6e16.c @@ -0,0 +1,75 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlsseg6e16_v_bf16mf4x6( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , } @llvm.riscv.vlsseg6.nxv1bf16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP0]] +// +vbfloat16mf4x6_t test_vlsseg6e16_v_bf16mf4x6(const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg6e16_v_bf16mf4x6(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlsseg6e16_v_bf16mf2x6( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , } @llvm.riscv.vlsseg6.nxv2bf16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP0]] +// +vbfloat16mf2x6_t test_vlsseg6e16_v_bf16mf2x6(const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg6e16_v_bf16mf2x6(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlsseg6e16_v_bf16m1x6( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , } @llvm.riscv.vlsseg6.nxv4bf16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP0]] +// +vbfloat16m1x6_t test_vlsseg6e16_v_bf16m1x6(const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg6e16_v_bf16m1x6(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlsseg6e16_v_bf16mf4x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , } @llvm.riscv.vlsseg6.mask.nxv1bf16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP0]] +// +vbfloat16mf4x6_t test_vlsseg6e16_v_bf16mf4x6_m(vbool64_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg6e16_v_bf16mf4x6_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlsseg6e16_v_bf16mf2x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , } @llvm.riscv.vlsseg6.mask.nxv2bf16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP0]] +// +vbfloat16mf2x6_t test_vlsseg6e16_v_bf16mf2x6_m(vbool32_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg6e16_v_bf16mf2x6_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlsseg6e16_v_bf16m1x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , } @llvm.riscv.vlsseg6.mask.nxv4bf16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP0]] +// +vbfloat16m1x6_t test_vlsseg6e16_v_bf16m1x6_m(vbool16_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg6e16_v_bf16m1x6_m(vm, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlsseg7e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlsseg7e16.c new file mode 100644 index 0000000000000000000000000000000000000000..f86541cc27f9f95ba9de6014c9d02b7639b6ae65 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlsseg7e16.c @@ -0,0 +1,75 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlsseg7e16_v_bf16mf4x7( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , } @llvm.riscv.vlsseg7.nxv1bf16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP0]] +// +vbfloat16mf4x7_t test_vlsseg7e16_v_bf16mf4x7(const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg7e16_v_bf16mf4x7(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlsseg7e16_v_bf16mf2x7( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , } @llvm.riscv.vlsseg7.nxv2bf16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP0]] +// +vbfloat16mf2x7_t test_vlsseg7e16_v_bf16mf2x7(const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg7e16_v_bf16mf2x7(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlsseg7e16_v_bf16m1x7( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , } @llvm.riscv.vlsseg7.nxv4bf16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP0]] +// +vbfloat16m1x7_t test_vlsseg7e16_v_bf16m1x7(const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg7e16_v_bf16m1x7(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlsseg7e16_v_bf16mf4x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , } @llvm.riscv.vlsseg7.mask.nxv1bf16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP0]] +// +vbfloat16mf4x7_t test_vlsseg7e16_v_bf16mf4x7_m(vbool64_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg7e16_v_bf16mf4x7_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlsseg7e16_v_bf16mf2x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , } @llvm.riscv.vlsseg7.mask.nxv2bf16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP0]] +// +vbfloat16mf2x7_t test_vlsseg7e16_v_bf16mf2x7_m(vbool32_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg7e16_v_bf16mf2x7_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlsseg7e16_v_bf16m1x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , } @llvm.riscv.vlsseg7.mask.nxv4bf16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP0]] +// +vbfloat16m1x7_t test_vlsseg7e16_v_bf16m1x7_m(vbool16_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg7e16_v_bf16m1x7_m(vm, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlsseg8e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlsseg8e16.c new file mode 100644 index 0000000000000000000000000000000000000000..071ff57a56f97b978ec875e157af8188385e362b --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vlsseg8e16.c @@ -0,0 +1,75 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlsseg8e16_v_bf16mf4x8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , } @llvm.riscv.vlsseg8.nxv1bf16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP0]] +// +vbfloat16mf4x8_t test_vlsseg8e16_v_bf16mf4x8(const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg8e16_v_bf16mf4x8(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlsseg8e16_v_bf16mf2x8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , } @llvm.riscv.vlsseg8.nxv2bf16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP0]] +// +vbfloat16mf2x8_t test_vlsseg8e16_v_bf16mf2x8(const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg8e16_v_bf16mf2x8(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlsseg8e16_v_bf16m1x8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , } @llvm.riscv.vlsseg8.nxv4bf16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP0]] +// +vbfloat16m1x8_t test_vlsseg8e16_v_bf16m1x8(const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg8e16_v_bf16m1x8(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlsseg8e16_v_bf16mf4x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , } @llvm.riscv.vlsseg8.mask.nxv1bf16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP0]] +// +vbfloat16mf4x8_t test_vlsseg8e16_v_bf16mf4x8_m(vbool64_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg8e16_v_bf16mf4x8_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlsseg8e16_v_bf16mf2x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , } @llvm.riscv.vlsseg8.mask.nxv2bf16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP0]] +// +vbfloat16mf2x8_t test_vlsseg8e16_v_bf16mf2x8_m(vbool32_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg8e16_v_bf16mf2x8_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlsseg8e16_v_bf16m1x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , } @llvm.riscv.vlsseg8.mask.nxv4bf16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP0]] +// +vbfloat16m1x8_t test_vlsseg8e16_v_bf16m1x8_m(vbool16_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg8e16_v_bf16m1x8_m(vm, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vluxei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vluxei16.c new file mode 100644 index 0000000000000000000000000000000000000000..cb51dc0abbb851cbe246c9e94d2aec1978e45f5d --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vluxei16.c @@ -0,0 +1,141 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16mf4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.nxv1bf16.nxv1i16.i64( poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vluxei16_v_bf16mf4(const __bf16 *rs1, vuint16mf4_t rs2, + size_t vl) { + return __riscv_vluxei16_v_bf16mf4(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16mf2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.nxv2bf16.nxv2i16.i64( poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vluxei16_v_bf16mf2(const __bf16 *rs1, vuint16mf2_t rs2, + size_t vl) { + return __riscv_vluxei16_v_bf16mf2(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16m1( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.nxv4bf16.nxv4i16.i64( poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vluxei16_v_bf16m1(const __bf16 *rs1, vuint16m1_t rs2, + size_t vl) { + return __riscv_vluxei16_v_bf16m1(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16m2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.nxv8bf16.nxv8i16.i64( poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vluxei16_v_bf16m2(const __bf16 *rs1, vuint16m2_t rs2, + size_t vl) { + return __riscv_vluxei16_v_bf16m2(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16m4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.nxv16bf16.nxv16i16.i64( poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vluxei16_v_bf16m4(const __bf16 *rs1, vuint16m4_t rs2, + size_t vl) { + return __riscv_vluxei16_v_bf16m4(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16m8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.nxv32bf16.nxv32i16.i64( poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vluxei16_v_bf16m8(const __bf16 *rs1, vuint16m8_t rs2, + size_t vl) { + return __riscv_vluxei16_v_bf16m8(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16mf4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.mask.nxv1bf16.nxv1i16.i64( poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vluxei16_v_bf16mf4_m(vbool64_t vm, const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxei16_v_bf16mf4_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16mf2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.mask.nxv2bf16.nxv2i16.i64( poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vluxei16_v_bf16mf2_m(vbool32_t vm, const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxei16_v_bf16mf2_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16m1_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.mask.nxv4bf16.nxv4i16.i64( poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vluxei16_v_bf16m1_m(vbool16_t vm, const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vluxei16_v_bf16m1_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16m2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.mask.nxv8bf16.nxv8i16.i64( poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vluxei16_v_bf16m2_m(vbool8_t vm, const __bf16 *rs1, + vuint16m2_t rs2, size_t vl) { + return __riscv_vluxei16_v_bf16m2_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16m4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.mask.nxv16bf16.nxv16i16.i64( poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vluxei16_v_bf16m4_m(vbool4_t vm, const __bf16 *rs1, + vuint16m4_t rs2, size_t vl) { + return __riscv_vluxei16_v_bf16m4_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16m8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.mask.nxv32bf16.nxv32i16.i64( poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vluxei16_v_bf16m8_m(vbool2_t vm, const __bf16 *rs1, + vuint16m8_t rs2, size_t vl) { + return __riscv_vluxei16_v_bf16m8_m(vm, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vluxseg2ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vluxseg2ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..983c9936448523dd536ab450f48812e4c6f05fd3 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vluxseg2ei16.c @@ -0,0 +1,121 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16mf4x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vluxseg2.nxv1bf16.nxv1i16.i64( poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16mf4x2_t test_vluxseg2ei16_v_bf16mf4x2(const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg2ei16_v_bf16mf4x2(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16mf2x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vluxseg2.nxv2bf16.nxv2i16.i64( poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16mf2x2_t test_vluxseg2ei16_v_bf16mf2x2(const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg2ei16_v_bf16mf2x2(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16m1x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vluxseg2.nxv4bf16.nxv4i16.i64( poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16m1x2_t test_vluxseg2ei16_v_bf16m1x2(const __bf16 *rs1, vuint16m1_t rs2, + size_t vl) { + return __riscv_vluxseg2ei16_v_bf16m1x2(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16m2x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vluxseg2.nxv8bf16.nxv8i16.i64( poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16m2x2_t test_vluxseg2ei16_v_bf16m2x2(const __bf16 *rs1, vuint16m2_t rs2, + size_t vl) { + return __riscv_vluxseg2ei16_v_bf16m2x2(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16m4x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vluxseg2.nxv16bf16.nxv16i16.i64( poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16m4x2_t test_vluxseg2ei16_v_bf16m4x2(const __bf16 *rs1, vuint16m4_t rs2, + size_t vl) { + return __riscv_vluxseg2ei16_v_bf16m4x2(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16mf4x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vluxseg2.mask.nxv1bf16.nxv1i16.i64( poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16mf4x2_t test_vluxseg2ei16_v_bf16mf4x2_m(vbool64_t vm, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg2ei16_v_bf16mf4x2_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16mf2x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vluxseg2.mask.nxv2bf16.nxv2i16.i64( poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16mf2x2_t test_vluxseg2ei16_v_bf16mf2x2_m(vbool32_t vm, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg2ei16_v_bf16mf2x2_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16m1x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vluxseg2.mask.nxv4bf16.nxv4i16.i64( poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16m1x2_t test_vluxseg2ei16_v_bf16m1x2_m(vbool16_t vm, const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg2ei16_v_bf16m1x2_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16m2x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vluxseg2.mask.nxv8bf16.nxv8i16.i64( poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16m2x2_t test_vluxseg2ei16_v_bf16m2x2_m(vbool8_t vm, const __bf16 *rs1, + vuint16m2_t rs2, size_t vl) { + return __riscv_vluxseg2ei16_v_bf16m2x2_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16m4x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vluxseg2.mask.nxv16bf16.nxv16i16.i64( poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16m4x2_t test_vluxseg2ei16_v_bf16m4x2_m(vbool4_t vm, const __bf16 *rs1, + vuint16m4_t rs2, size_t vl) { + return __riscv_vluxseg2ei16_v_bf16m4x2_m(vm, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vluxseg3ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vluxseg3ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..8d89952bea2b0b6e5e0531718471204242f17cc7 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vluxseg3ei16.c @@ -0,0 +1,99 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vluxseg3ei16_v_bf16mf4x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vluxseg3.nxv1bf16.nxv1i16.i64( poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16mf4x3_t test_vluxseg3ei16_v_bf16mf4x3(const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg3ei16_v_bf16mf4x3(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vluxseg3ei16_v_bf16mf2x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vluxseg3.nxv2bf16.nxv2i16.i64( poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16mf2x3_t test_vluxseg3ei16_v_bf16mf2x3(const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg3ei16_v_bf16mf2x3(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vluxseg3ei16_v_bf16m1x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vluxseg3.nxv4bf16.nxv4i16.i64( poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16m1x3_t test_vluxseg3ei16_v_bf16m1x3(const __bf16 *rs1, vuint16m1_t rs2, + size_t vl) { + return __riscv_vluxseg3ei16_v_bf16m1x3(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vluxseg3ei16_v_bf16m2x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vluxseg3.nxv8bf16.nxv8i16.i64( poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16m2x3_t test_vluxseg3ei16_v_bf16m2x3(const __bf16 *rs1, vuint16m2_t rs2, + size_t vl) { + return __riscv_vluxseg3ei16_v_bf16m2x3(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vluxseg3ei16_v_bf16mf4x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vluxseg3.mask.nxv1bf16.nxv1i16.i64( poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16mf4x3_t test_vluxseg3ei16_v_bf16mf4x3_m(vbool64_t vm, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg3ei16_v_bf16mf4x3_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vluxseg3ei16_v_bf16mf2x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vluxseg3.mask.nxv2bf16.nxv2i16.i64( poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16mf2x3_t test_vluxseg3ei16_v_bf16mf2x3_m(vbool32_t vm, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg3ei16_v_bf16mf2x3_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vluxseg3ei16_v_bf16m1x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vluxseg3.mask.nxv4bf16.nxv4i16.i64( poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16m1x3_t test_vluxseg3ei16_v_bf16m1x3_m(vbool16_t vm, const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg3ei16_v_bf16m1x3_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vluxseg3ei16_v_bf16m2x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vluxseg3.mask.nxv8bf16.nxv8i16.i64( poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16m2x3_t test_vluxseg3ei16_v_bf16m2x3_m(vbool8_t vm, const __bf16 *rs1, + vuint16m2_t rs2, size_t vl) { + return __riscv_vluxseg3ei16_v_bf16m2x3_m(vm, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vluxseg4ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vluxseg4ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..2751b1245f1670308f5d197b841eb98d71ade12b --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vluxseg4ei16.c @@ -0,0 +1,99 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vluxseg4ei16_v_bf16mf4x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vluxseg4.nxv1bf16.nxv1i16.i64( poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16mf4x4_t test_vluxseg4ei16_v_bf16mf4x4(const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg4ei16_v_bf16mf4x4(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vluxseg4ei16_v_bf16mf2x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vluxseg4.nxv2bf16.nxv2i16.i64( poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16mf2x4_t test_vluxseg4ei16_v_bf16mf2x4(const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg4ei16_v_bf16mf2x4(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vluxseg4ei16_v_bf16m1x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vluxseg4.nxv4bf16.nxv4i16.i64( poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16m1x4_t test_vluxseg4ei16_v_bf16m1x4(const __bf16 *rs1, vuint16m1_t rs2, + size_t vl) { + return __riscv_vluxseg4ei16_v_bf16m1x4(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vluxseg4ei16_v_bf16m2x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vluxseg4.nxv8bf16.nxv8i16.i64( poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16m2x4_t test_vluxseg4ei16_v_bf16m2x4(const __bf16 *rs1, vuint16m2_t rs2, + size_t vl) { + return __riscv_vluxseg4ei16_v_bf16m2x4(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vluxseg4ei16_v_bf16mf4x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vluxseg4.mask.nxv1bf16.nxv1i16.i64( poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16mf4x4_t test_vluxseg4ei16_v_bf16mf4x4_m(vbool64_t vm, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg4ei16_v_bf16mf4x4_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vluxseg4ei16_v_bf16mf2x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vluxseg4.mask.nxv2bf16.nxv2i16.i64( poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16mf2x4_t test_vluxseg4ei16_v_bf16mf2x4_m(vbool32_t vm, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg4ei16_v_bf16mf2x4_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vluxseg4ei16_v_bf16m1x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vluxseg4.mask.nxv4bf16.nxv4i16.i64( poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16m1x4_t test_vluxseg4ei16_v_bf16m1x4_m(vbool16_t vm, const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg4ei16_v_bf16m1x4_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vluxseg4ei16_v_bf16m2x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vluxseg4.mask.nxv8bf16.nxv8i16.i64( poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16m2x4_t test_vluxseg4ei16_v_bf16m2x4_m(vbool8_t vm, const __bf16 *rs1, + vuint16m2_t rs2, size_t vl) { + return __riscv_vluxseg4ei16_v_bf16m2x4_m(vm, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vluxseg5ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vluxseg5ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..9cd84e561dfaa53d99c3db4dce4e9f7d837e467d --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vluxseg5ei16.c @@ -0,0 +1,77 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vluxseg5ei16_v_bf16mf4x5( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , } @llvm.riscv.vluxseg5.nxv1bf16.nxv1i16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP0]] +// +vbfloat16mf4x5_t test_vluxseg5ei16_v_bf16mf4x5(const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg5ei16_v_bf16mf4x5(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vluxseg5ei16_v_bf16mf2x5( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , } @llvm.riscv.vluxseg5.nxv2bf16.nxv2i16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP0]] +// +vbfloat16mf2x5_t test_vluxseg5ei16_v_bf16mf2x5(const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg5ei16_v_bf16mf2x5(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vluxseg5ei16_v_bf16m1x5( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , } @llvm.riscv.vluxseg5.nxv4bf16.nxv4i16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP0]] +// +vbfloat16m1x5_t test_vluxseg5ei16_v_bf16m1x5(const __bf16 *rs1, vuint16m1_t rs2, + size_t vl) { + return __riscv_vluxseg5ei16_v_bf16m1x5(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vluxseg5ei16_v_bf16mf4x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , } @llvm.riscv.vluxseg5.mask.nxv1bf16.nxv1i16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP0]] +// +vbfloat16mf4x5_t test_vluxseg5ei16_v_bf16mf4x5_m(vbool64_t vm, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg5ei16_v_bf16mf4x5_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vluxseg5ei16_v_bf16mf2x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , } @llvm.riscv.vluxseg5.mask.nxv2bf16.nxv2i16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP0]] +// +vbfloat16mf2x5_t test_vluxseg5ei16_v_bf16mf2x5_m(vbool32_t vm, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg5ei16_v_bf16mf2x5_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vluxseg5ei16_v_bf16m1x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , } @llvm.riscv.vluxseg5.mask.nxv4bf16.nxv4i16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP0]] +// +vbfloat16m1x5_t test_vluxseg5ei16_v_bf16m1x5_m(vbool16_t vm, const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg5ei16_v_bf16m1x5_m(vm, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vluxseg6ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vluxseg6ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..95ce415c871cf124c889ae60f139f8f94aeee021 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vluxseg6ei16.c @@ -0,0 +1,77 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vluxseg6ei16_v_bf16mf4x6( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , } @llvm.riscv.vluxseg6.nxv1bf16.nxv1i16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP0]] +// +vbfloat16mf4x6_t test_vluxseg6ei16_v_bf16mf4x6(const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg6ei16_v_bf16mf4x6(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vluxseg6ei16_v_bf16mf2x6( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , } @llvm.riscv.vluxseg6.nxv2bf16.nxv2i16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP0]] +// +vbfloat16mf2x6_t test_vluxseg6ei16_v_bf16mf2x6(const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg6ei16_v_bf16mf2x6(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vluxseg6ei16_v_bf16m1x6( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , } @llvm.riscv.vluxseg6.nxv4bf16.nxv4i16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP0]] +// +vbfloat16m1x6_t test_vluxseg6ei16_v_bf16m1x6(const __bf16 *rs1, vuint16m1_t rs2, + size_t vl) { + return __riscv_vluxseg6ei16_v_bf16m1x6(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vluxseg6ei16_v_bf16mf4x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , } @llvm.riscv.vluxseg6.mask.nxv1bf16.nxv1i16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP0]] +// +vbfloat16mf4x6_t test_vluxseg6ei16_v_bf16mf4x6_m(vbool64_t vm, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg6ei16_v_bf16mf4x6_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vluxseg6ei16_v_bf16mf2x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , } @llvm.riscv.vluxseg6.mask.nxv2bf16.nxv2i16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP0]] +// +vbfloat16mf2x6_t test_vluxseg6ei16_v_bf16mf2x6_m(vbool32_t vm, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg6ei16_v_bf16mf2x6_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vluxseg6ei16_v_bf16m1x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , } @llvm.riscv.vluxseg6.mask.nxv4bf16.nxv4i16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP0]] +// +vbfloat16m1x6_t test_vluxseg6ei16_v_bf16m1x6_m(vbool16_t vm, const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg6ei16_v_bf16m1x6_m(vm, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vluxseg7ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vluxseg7ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..c1b84c434e4e75ab279d482310595d6a49440ec1 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vluxseg7ei16.c @@ -0,0 +1,77 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vluxseg7ei16_v_bf16mf4x7( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , } @llvm.riscv.vluxseg7.nxv1bf16.nxv1i16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP0]] +// +vbfloat16mf4x7_t test_vluxseg7ei16_v_bf16mf4x7(const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg7ei16_v_bf16mf4x7(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vluxseg7ei16_v_bf16mf2x7( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , } @llvm.riscv.vluxseg7.nxv2bf16.nxv2i16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP0]] +// +vbfloat16mf2x7_t test_vluxseg7ei16_v_bf16mf2x7(const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg7ei16_v_bf16mf2x7(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vluxseg7ei16_v_bf16m1x7( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , } @llvm.riscv.vluxseg7.nxv4bf16.nxv4i16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP0]] +// +vbfloat16m1x7_t test_vluxseg7ei16_v_bf16m1x7(const __bf16 *rs1, vuint16m1_t rs2, + size_t vl) { + return __riscv_vluxseg7ei16_v_bf16m1x7(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vluxseg7ei16_v_bf16mf4x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , } @llvm.riscv.vluxseg7.mask.nxv1bf16.nxv1i16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP0]] +// +vbfloat16mf4x7_t test_vluxseg7ei16_v_bf16mf4x7_m(vbool64_t vm, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg7ei16_v_bf16mf4x7_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vluxseg7ei16_v_bf16mf2x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , } @llvm.riscv.vluxseg7.mask.nxv2bf16.nxv2i16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP0]] +// +vbfloat16mf2x7_t test_vluxseg7ei16_v_bf16mf2x7_m(vbool32_t vm, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg7ei16_v_bf16mf2x7_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vluxseg7ei16_v_bf16m1x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , } @llvm.riscv.vluxseg7.mask.nxv4bf16.nxv4i16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP0]] +// +vbfloat16m1x7_t test_vluxseg7ei16_v_bf16m1x7_m(vbool16_t vm, const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg7ei16_v_bf16m1x7_m(vm, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vluxseg8ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vluxseg8ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..32e5ab40e40a2e20953dca3f2715dc9aa8105a52 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vluxseg8ei16.c @@ -0,0 +1,77 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vluxseg8ei16_v_bf16mf4x8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , } @llvm.riscv.vluxseg8.nxv1bf16.nxv1i16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP0]] +// +vbfloat16mf4x8_t test_vluxseg8ei16_v_bf16mf4x8(const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg8ei16_v_bf16mf4x8(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vluxseg8ei16_v_bf16mf2x8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , } @llvm.riscv.vluxseg8.nxv2bf16.nxv2i16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP0]] +// +vbfloat16mf2x8_t test_vluxseg8ei16_v_bf16mf2x8(const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg8ei16_v_bf16mf2x8(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vluxseg8ei16_v_bf16m1x8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , } @llvm.riscv.vluxseg8.nxv4bf16.nxv4i16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP0]] +// +vbfloat16m1x8_t test_vluxseg8ei16_v_bf16m1x8(const __bf16 *rs1, vuint16m1_t rs2, + size_t vl) { + return __riscv_vluxseg8ei16_v_bf16m1x8(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vluxseg8ei16_v_bf16mf4x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , } @llvm.riscv.vluxseg8.mask.nxv1bf16.nxv1i16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP0]] +// +vbfloat16mf4x8_t test_vluxseg8ei16_v_bf16mf4x8_m(vbool64_t vm, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg8ei16_v_bf16mf4x8_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vluxseg8ei16_v_bf16mf2x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , } @llvm.riscv.vluxseg8.mask.nxv2bf16.nxv2i16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP0]] +// +vbfloat16mf2x8_t test_vluxseg8ei16_v_bf16mf2x8_m(vbool32_t vm, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg8ei16_v_bf16mf2x8_m(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vluxseg8ei16_v_bf16m1x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , } @llvm.riscv.vluxseg8.mask.nxv4bf16.nxv4i16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP0]] +// +vbfloat16m1x8_t test_vluxseg8ei16_v_bf16m1x8_m(vbool16_t vm, const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg8ei16_v_bf16m1x8_m(vm, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vreinterpret.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vreinterpret.c new file mode 100644 index 0000000000000000000000000000000000000000..30120be47154bce70da2cbc953451225badd4f8b --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vreinterpret.c @@ -0,0 +1,249 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local @test_vreinterpret_v_i16mf4_bf16mf4( +// CHECK-RV64-SAME: [[SRC:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = bitcast [[SRC]] to +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vreinterpret_v_i16mf4_bf16mf4(vint16mf4_t src) { + return __riscv_vreinterpret_v_i16mf4_bf16mf4(src); +} + +// CHECK-RV64-LABEL: define dso_local @test_vreinterpret_v_i16mf2_bf16mf2( +// CHECK-RV64-SAME: [[SRC:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = bitcast [[SRC]] to +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vreinterpret_v_i16mf2_bf16mf2(vint16mf2_t src) { + return __riscv_vreinterpret_v_i16mf2_bf16mf2(src); +} + +// CHECK-RV64-LABEL: define dso_local @test_vreinterpret_v_i16m1_bf16m1( +// CHECK-RV64-SAME: [[SRC:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = bitcast [[SRC]] to +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vreinterpret_v_i16m1_bf16m1(vint16m1_t src) { + return __riscv_vreinterpret_v_i16m1_bf16m1(src); +} + +// CHECK-RV64-LABEL: define dso_local @test_vreinterpret_v_i16m2_bf16m2( +// CHECK-RV64-SAME: [[SRC:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = bitcast [[SRC]] to +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vreinterpret_v_i16m2_bf16m2(vint16m2_t src) { + return __riscv_vreinterpret_v_i16m2_bf16m2(src); +} + +// CHECK-RV64-LABEL: define dso_local @test_vreinterpret_v_i16m4_bf16m4( +// CHECK-RV64-SAME: [[SRC:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = bitcast [[SRC]] to +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vreinterpret_v_i16m4_bf16m4(vint16m4_t src) { + return __riscv_vreinterpret_v_i16m4_bf16m4(src); +} + +// CHECK-RV64-LABEL: define dso_local @test_vreinterpret_v_i16m8_bf16m8( +// CHECK-RV64-SAME: [[SRC:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = bitcast [[SRC]] to +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vreinterpret_v_i16m8_bf16m8(vint16m8_t src) { + return __riscv_vreinterpret_v_i16m8_bf16m8(src); +} + +// CHECK-RV64-LABEL: define dso_local @test_vreinterpret_v_u16mf4_bf16mf4( +// CHECK-RV64-SAME: [[SRC:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = bitcast [[SRC]] to +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vreinterpret_v_u16mf4_bf16mf4(vuint16mf4_t src) { + return __riscv_vreinterpret_v_u16mf4_bf16mf4(src); +} + +// CHECK-RV64-LABEL: define dso_local @test_vreinterpret_v_u16mf2_bf16mf2( +// CHECK-RV64-SAME: [[SRC:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = bitcast [[SRC]] to +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vreinterpret_v_u16mf2_bf16mf2(vuint16mf2_t src) { + return __riscv_vreinterpret_v_u16mf2_bf16mf2(src); +} + +// CHECK-RV64-LABEL: define dso_local @test_vreinterpret_v_u16m1_bf16m1( +// CHECK-RV64-SAME: [[SRC:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = bitcast [[SRC]] to +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vreinterpret_v_u16m1_bf16m1(vuint16m1_t src) { + return __riscv_vreinterpret_v_u16m1_bf16m1(src); +} + +// CHECK-RV64-LABEL: define dso_local @test_vreinterpret_v_u16m2_bf16m2( +// CHECK-RV64-SAME: [[SRC:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = bitcast [[SRC]] to +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vreinterpret_v_u16m2_bf16m2(vuint16m2_t src) { + return __riscv_vreinterpret_v_u16m2_bf16m2(src); +} + +// CHECK-RV64-LABEL: define dso_local @test_vreinterpret_v_u16m4_bf16m4( +// CHECK-RV64-SAME: [[SRC:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = bitcast [[SRC]] to +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vreinterpret_v_u16m4_bf16m4(vuint16m4_t src) { + return __riscv_vreinterpret_v_u16m4_bf16m4(src); +} + +// CHECK-RV64-LABEL: define dso_local @test_vreinterpret_v_u16m8_bf16m8( +// CHECK-RV64-SAME: [[SRC:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = bitcast [[SRC]] to +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vreinterpret_v_u16m8_bf16m8(vuint16m8_t src) { + return __riscv_vreinterpret_v_u16m8_bf16m8(src); +} + +// CHECK-RV64-LABEL: define dso_local @test_vreinterpret_v_bf16mf4_i16mf4( +// CHECK-RV64-SAME: [[SRC:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = bitcast [[SRC]] to +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vint16mf4_t test_vreinterpret_v_bf16mf4_i16mf4(vbfloat16mf4_t src) { + return __riscv_vreinterpret_v_bf16mf4_i16mf4(src); +} + +// CHECK-RV64-LABEL: define dso_local @test_vreinterpret_v_bf16mf2_i16mf2( +// CHECK-RV64-SAME: [[SRC:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = bitcast [[SRC]] to +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vint16mf2_t test_vreinterpret_v_bf16mf2_i16mf2(vbfloat16mf2_t src) { + return __riscv_vreinterpret_v_bf16mf2_i16mf2(src); +} + +// CHECK-RV64-LABEL: define dso_local @test_vreinterpret_v_bf16m1_i16m1( +// CHECK-RV64-SAME: [[SRC:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = bitcast [[SRC]] to +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vint16m1_t test_vreinterpret_v_bf16m1_i16m1(vbfloat16m1_t src) { + return __riscv_vreinterpret_v_bf16m1_i16m1(src); +} + +// CHECK-RV64-LABEL: define dso_local @test_vreinterpret_v_bf16m2_i16m2( +// CHECK-RV64-SAME: [[SRC:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = bitcast [[SRC]] to +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vint16m2_t test_vreinterpret_v_bf16m2_i16m2(vbfloat16m2_t src) { + return __riscv_vreinterpret_v_bf16m2_i16m2(src); +} + +// CHECK-RV64-LABEL: define dso_local @test_vreinterpret_v_bf16m4_i16m4( +// CHECK-RV64-SAME: [[SRC:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = bitcast [[SRC]] to +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vint16m4_t test_vreinterpret_v_bf16m4_i16m4(vbfloat16m4_t src) { + return __riscv_vreinterpret_v_bf16m4_i16m4(src); +} + +// CHECK-RV64-LABEL: define dso_local @test_vreinterpret_v_bf16m8_i16m8( +// CHECK-RV64-SAME: [[SRC:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = bitcast [[SRC]] to +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vint16m8_t test_vreinterpret_v_bf16m8_i16m8(vbfloat16m8_t src) { + return __riscv_vreinterpret_v_bf16m8_i16m8(src); +} + +// CHECK-RV64-LABEL: define dso_local @test_vreinterpret_v_bf16mf4_u16mf4( +// CHECK-RV64-SAME: [[SRC:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = bitcast [[SRC]] to +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vuint16mf4_t test_vreinterpret_v_bf16mf4_u16mf4(vbfloat16mf4_t src) { + return __riscv_vreinterpret_v_bf16mf4_u16mf4(src); +} + +// CHECK-RV64-LABEL: define dso_local @test_vreinterpret_v_bf16mf2_u16mf2( +// CHECK-RV64-SAME: [[SRC:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = bitcast [[SRC]] to +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vuint16mf2_t test_vreinterpret_v_bf16mf2_u16mf2(vbfloat16mf2_t src) { + return __riscv_vreinterpret_v_bf16mf2_u16mf2(src); +} + +// CHECK-RV64-LABEL: define dso_local @test_vreinterpret_v_bf16m1_u16m1( +// CHECK-RV64-SAME: [[SRC:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = bitcast [[SRC]] to +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vuint16m1_t test_vreinterpret_v_bf16m1_u16m1(vbfloat16m1_t src) { + return __riscv_vreinterpret_v_bf16m1_u16m1(src); +} + +// CHECK-RV64-LABEL: define dso_local @test_vreinterpret_v_bf16m2_u16m2( +// CHECK-RV64-SAME: [[SRC:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = bitcast [[SRC]] to +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vuint16m2_t test_vreinterpret_v_bf16m2_u16m2(vbfloat16m2_t src) { + return __riscv_vreinterpret_v_bf16m2_u16m2(src); +} + +// CHECK-RV64-LABEL: define dso_local @test_vreinterpret_v_bf16m4_u16m4( +// CHECK-RV64-SAME: [[SRC:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = bitcast [[SRC]] to +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vuint16m4_t test_vreinterpret_v_bf16m4_u16m4(vbfloat16m4_t src) { + return __riscv_vreinterpret_v_bf16m4_u16m4(src); +} + +// CHECK-RV64-LABEL: define dso_local @test_vreinterpret_v_bf16m8_u16m8( +// CHECK-RV64-SAME: [[SRC:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = bitcast [[SRC]] to +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vuint16m8_t test_vreinterpret_v_bf16m8_u16m8(vbfloat16m8_t src) { + return __riscv_vreinterpret_v_bf16m8_u16m8(src); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vse16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vse16.c new file mode 100644 index 0000000000000000000000000000000000000000..4bfc5b7350cbc6a13b2adffdbfef002da8b310d7 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vse16.c @@ -0,0 +1,135 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vse16_v_bf16mf4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vse.nxv1bf16.i64( [[VS3]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vse16_v_bf16mf4(__bf16 *rs1, vbfloat16mf4_t vs3, size_t vl) { + return __riscv_vse16_v_bf16mf4(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vse16_v_bf16mf2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vse.nxv2bf16.i64( [[VS3]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vse16_v_bf16mf2(__bf16 *rs1, vbfloat16mf2_t vs3, size_t vl) { + return __riscv_vse16_v_bf16mf2(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vse16_v_bf16m1( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vse.nxv4bf16.i64( [[VS3]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vse16_v_bf16m1(__bf16 *rs1, vbfloat16m1_t vs3, size_t vl) { + return __riscv_vse16_v_bf16m1(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vse16_v_bf16m2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vse.nxv8bf16.i64( [[VS3]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vse16_v_bf16m2(__bf16 *rs1, vbfloat16m2_t vs3, size_t vl) { + return __riscv_vse16_v_bf16m2(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vse16_v_bf16m4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vse.nxv16bf16.i64( [[VS3]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vse16_v_bf16m4(__bf16 *rs1, vbfloat16m4_t vs3, size_t vl) { + return __riscv_vse16_v_bf16m4(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vse16_v_bf16m8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vse.nxv32bf16.i64( [[VS3]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vse16_v_bf16m8(__bf16 *rs1, vbfloat16m8_t vs3, size_t vl) { + return __riscv_vse16_v_bf16m8(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vse16_v_bf16mf4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vse.mask.nxv1bf16.i64( [[VS3]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vse16_v_bf16mf4_m(vbool64_t vm, __bf16 *rs1, vbfloat16mf4_t vs3, + size_t vl) { + return __riscv_vse16_v_bf16mf4_m(vm, rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vse16_v_bf16mf2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vse.mask.nxv2bf16.i64( [[VS3]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vse16_v_bf16mf2_m(vbool32_t vm, __bf16 *rs1, vbfloat16mf2_t vs3, + size_t vl) { + return __riscv_vse16_v_bf16mf2_m(vm, rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vse16_v_bf16m1_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vse.mask.nxv4bf16.i64( [[VS3]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vse16_v_bf16m1_m(vbool16_t vm, __bf16 *rs1, vbfloat16m1_t vs3, + size_t vl) { + return __riscv_vse16_v_bf16m1_m(vm, rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vse16_v_bf16m2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vse.mask.nxv8bf16.i64( [[VS3]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vse16_v_bf16m2_m(vbool8_t vm, __bf16 *rs1, vbfloat16m2_t vs3, + size_t vl) { + return __riscv_vse16_v_bf16m2_m(vm, rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vse16_v_bf16m4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vse.mask.nxv16bf16.i64( [[VS3]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vse16_v_bf16m4_m(vbool4_t vm, __bf16 *rs1, vbfloat16m4_t vs3, + size_t vl) { + return __riscv_vse16_v_bf16m4_m(vm, rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vse16_v_bf16m8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vse.mask.nxv32bf16.i64( [[VS3]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vse16_v_bf16m8_m(vbool2_t vm, __bf16 *rs1, vbfloat16m8_t vs3, + size_t vl) { + return __riscv_vse16_v_bf16m8_m(vm, rs1, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vset.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vset.c new file mode 100644 index 0000000000000000000000000000000000000000..779c24bd6469b007a1e2cef14ed364bafb6989e5 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vset.c @@ -0,0 +1,364 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local @test_vset_v_bf16m1_bf16m2( +// CHECK-RV64-SAME: [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.insert.nxv8bf16.nxv4bf16( [[DEST]], [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vset_v_bf16m1_bf16m2(vbfloat16m2_t dest, size_t index, + vbfloat16m1_t value) { + return __riscv_vset_v_bf16m1_bf16m2(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vset_v_bf16m1_bf16m4( +// CHECK-RV64-SAME: [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.insert.nxv16bf16.nxv4bf16( [[DEST]], [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vset_v_bf16m1_bf16m4(vbfloat16m4_t dest, size_t index, + vbfloat16m1_t value) { + return __riscv_vset_v_bf16m1_bf16m4(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vset_v_bf16m2_bf16m4( +// CHECK-RV64-SAME: [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.insert.nxv16bf16.nxv8bf16( [[DEST]], [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vset_v_bf16m2_bf16m4(vbfloat16m4_t dest, size_t index, + vbfloat16m2_t value) { + return __riscv_vset_v_bf16m2_bf16m4(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vset_v_bf16m1_bf16m8( +// CHECK-RV64-SAME: [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.insert.nxv32bf16.nxv4bf16( [[DEST]], [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vset_v_bf16m1_bf16m8(vbfloat16m8_t dest, size_t index, + vbfloat16m1_t value) { + return __riscv_vset_v_bf16m1_bf16m8(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vset_v_bf16m2_bf16m8( +// CHECK-RV64-SAME: [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.insert.nxv32bf16.nxv8bf16( [[DEST]], [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vset_v_bf16m2_bf16m8(vbfloat16m8_t dest, size_t index, + vbfloat16m2_t value) { + return __riscv_vset_v_bf16m2_bf16m8(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vset_v_bf16m4_bf16m8( +// CHECK-RV64-SAME: [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.insert.nxv32bf16.nxv16bf16( [[DEST]], [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vset_v_bf16m4_bf16m8(vbfloat16m8_t dest, size_t index, + vbfloat16m4_t value) { + return __riscv_vset_v_bf16m4_bf16m8(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vset_v_bf16mf4_bf16mf4x2( +// CHECK-RV64-SAME: { , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16mf4x2_t test_vset_v_bf16mf4_bf16mf4x2(vbfloat16mf4x2_t dest, + size_t index, + vbfloat16mf4_t value) { + return __riscv_vset_v_bf16mf4_bf16mf4x2(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vset_v_bf16mf4_bf16mf4x3( +// CHECK-RV64-SAME: { , , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16mf4x3_t test_vset_v_bf16mf4_bf16mf4x3(vbfloat16mf4x3_t dest, + size_t index, + vbfloat16mf4_t value) { + return __riscv_vset_v_bf16mf4_bf16mf4x3(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vset_v_bf16mf4_bf16mf4x4( +// CHECK-RV64-SAME: { , , , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16mf4x4_t test_vset_v_bf16mf4_bf16mf4x4(vbfloat16mf4x4_t dest, + size_t index, + vbfloat16mf4_t value) { + return __riscv_vset_v_bf16mf4_bf16mf4x4(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vset_v_bf16mf4_bf16mf4x5( +// CHECK-RV64-SAME: { , , , , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , , , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , , , , } [[TMP0]] +// +vbfloat16mf4x5_t test_vset_v_bf16mf4_bf16mf4x5(vbfloat16mf4x5_t dest, + size_t index, + vbfloat16mf4_t value) { + return __riscv_vset_v_bf16mf4_bf16mf4x5(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vset_v_bf16mf4_bf16mf4x6( +// CHECK-RV64-SAME: { , , , , , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , , , , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP0]] +// +vbfloat16mf4x6_t test_vset_v_bf16mf4_bf16mf4x6(vbfloat16mf4x6_t dest, + size_t index, + vbfloat16mf4_t value) { + return __riscv_vset_v_bf16mf4_bf16mf4x6(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vset_v_bf16mf4_bf16mf4x7( +// CHECK-RV64-SAME: { , , , , , , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , , , , , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP0]] +// +vbfloat16mf4x7_t test_vset_v_bf16mf4_bf16mf4x7(vbfloat16mf4x7_t dest, + size_t index, + vbfloat16mf4_t value) { + return __riscv_vset_v_bf16mf4_bf16mf4x7(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vset_v_bf16mf4_bf16mf4x8( +// CHECK-RV64-SAME: { , , , , , , , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , , , , , , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP0]] +// +vbfloat16mf4x8_t test_vset_v_bf16mf4_bf16mf4x8(vbfloat16mf4x8_t dest, + size_t index, + vbfloat16mf4_t value) { + return __riscv_vset_v_bf16mf4_bf16mf4x8(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vset_v_bf16mf2_bf16mf2x2( +// CHECK-RV64-SAME: { , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16mf2x2_t test_vset_v_bf16mf2_bf16mf2x2(vbfloat16mf2x2_t dest, + size_t index, + vbfloat16mf2_t value) { + return __riscv_vset_v_bf16mf2_bf16mf2x2(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vset_v_bf16mf2_bf16mf2x3( +// CHECK-RV64-SAME: { , , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16mf2x3_t test_vset_v_bf16mf2_bf16mf2x3(vbfloat16mf2x3_t dest, + size_t index, + vbfloat16mf2_t value) { + return __riscv_vset_v_bf16mf2_bf16mf2x3(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vset_v_bf16mf2_bf16mf2x4( +// CHECK-RV64-SAME: { , , , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16mf2x4_t test_vset_v_bf16mf2_bf16mf2x4(vbfloat16mf2x4_t dest, + size_t index, + vbfloat16mf2_t value) { + return __riscv_vset_v_bf16mf2_bf16mf2x4(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vset_v_bf16mf2_bf16mf2x5( +// CHECK-RV64-SAME: { , , , , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , , , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , , , , } [[TMP0]] +// +vbfloat16mf2x5_t test_vset_v_bf16mf2_bf16mf2x5(vbfloat16mf2x5_t dest, + size_t index, + vbfloat16mf2_t value) { + return __riscv_vset_v_bf16mf2_bf16mf2x5(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vset_v_bf16mf2_bf16mf2x6( +// CHECK-RV64-SAME: { , , , , , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , , , , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP0]] +// +vbfloat16mf2x6_t test_vset_v_bf16mf2_bf16mf2x6(vbfloat16mf2x6_t dest, + size_t index, + vbfloat16mf2_t value) { + return __riscv_vset_v_bf16mf2_bf16mf2x6(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vset_v_bf16mf2_bf16mf2x7( +// CHECK-RV64-SAME: { , , , , , , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , , , , , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP0]] +// +vbfloat16mf2x7_t test_vset_v_bf16mf2_bf16mf2x7(vbfloat16mf2x7_t dest, + size_t index, + vbfloat16mf2_t value) { + return __riscv_vset_v_bf16mf2_bf16mf2x7(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vset_v_bf16mf2_bf16mf2x8( +// CHECK-RV64-SAME: { , , , , , , , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , , , , , , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP0]] +// +vbfloat16mf2x8_t test_vset_v_bf16mf2_bf16mf2x8(vbfloat16mf2x8_t dest, + size_t index, + vbfloat16mf2_t value) { + return __riscv_vset_v_bf16mf2_bf16mf2x8(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vset_v_bf16m1_bf16m1x2( +// CHECK-RV64-SAME: { , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16m1x2_t test_vset_v_bf16m1_bf16m1x2(vbfloat16m1x2_t dest, size_t index, + vbfloat16m1_t value) { + return __riscv_vset_v_bf16m1_bf16m1x2(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vset_v_bf16m1_bf16m1x3( +// CHECK-RV64-SAME: { , , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16m1x3_t test_vset_v_bf16m1_bf16m1x3(vbfloat16m1x3_t dest, size_t index, + vbfloat16m1_t value) { + return __riscv_vset_v_bf16m1_bf16m1x3(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vset_v_bf16m1_bf16m1x4( +// CHECK-RV64-SAME: { , , , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16m1x4_t test_vset_v_bf16m1_bf16m1x4(vbfloat16m1x4_t dest, size_t index, + vbfloat16m1_t value) { + return __riscv_vset_v_bf16m1_bf16m1x4(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vset_v_bf16m1_bf16m1x5( +// CHECK-RV64-SAME: { , , , , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , , , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , , , , } [[TMP0]] +// +vbfloat16m1x5_t test_vset_v_bf16m1_bf16m1x5(vbfloat16m1x5_t dest, size_t index, + vbfloat16m1_t value) { + return __riscv_vset_v_bf16m1_bf16m1x5(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vset_v_bf16m1_bf16m1x6( +// CHECK-RV64-SAME: { , , , , , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , , , , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP0]] +// +vbfloat16m1x6_t test_vset_v_bf16m1_bf16m1x6(vbfloat16m1x6_t dest, size_t index, + vbfloat16m1_t value) { + return __riscv_vset_v_bf16m1_bf16m1x6(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vset_v_bf16m1_bf16m1x7( +// CHECK-RV64-SAME: { , , , , , , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , , , , , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP0]] +// +vbfloat16m1x7_t test_vset_v_bf16m1_bf16m1x7(vbfloat16m1x7_t dest, size_t index, + vbfloat16m1_t value) { + return __riscv_vset_v_bf16m1_bf16m1x7(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vset_v_bf16m1_bf16m1x8( +// CHECK-RV64-SAME: { , , , , , , , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , , , , , , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP0]] +// +vbfloat16m1x8_t test_vset_v_bf16m1_bf16m1x8(vbfloat16m1x8_t dest, size_t index, + vbfloat16m1_t value) { + return __riscv_vset_v_bf16m1_bf16m1x8(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vset_v_bf16m2_bf16m2x2( +// CHECK-RV64-SAME: { , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16m2x2_t test_vset_v_bf16m2_bf16m2x2(vbfloat16m2x2_t dest, size_t index, + vbfloat16m2_t value) { + return __riscv_vset_v_bf16m2_bf16m2x2(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vset_v_bf16m2_bf16m2x3( +// CHECK-RV64-SAME: { , , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16m2x3_t test_vset_v_bf16m2_bf16m2x3(vbfloat16m2x3_t dest, size_t index, + vbfloat16m2_t value) { + return __riscv_vset_v_bf16m2_bf16m2x3(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vset_v_bf16m2_bf16m2x4( +// CHECK-RV64-SAME: { , , , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16m2x4_t test_vset_v_bf16m2_bf16m2x4(vbfloat16m2x4_t dest, size_t index, + vbfloat16m2_t value) { + return __riscv_vset_v_bf16m2_bf16m2x4(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vset_v_bf16m4_bf16m4x2( +// CHECK-RV64-SAME: { , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16m4x2_t test_vset_v_bf16m4_bf16m4x2(vbfloat16m4x2_t dest, size_t index, + vbfloat16m4_t value) { + return __riscv_vset_v_bf16m4_bf16m4x2(dest, 0, value); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsoxei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsoxei16.c new file mode 100644 index 0000000000000000000000000000000000000000..dc3c25f4cbe8f28bbde5c4dc87b80a20157182da --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsoxei16.c @@ -0,0 +1,141 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxei16_v_bf16mf4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxei.nxv1bf16.nxv1i16.i64( [[VS3]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxei16_v_bf16mf4(__bf16 *rs1, vuint16mf4_t rs2, vbfloat16mf4_t vs3, + size_t vl) { + return __riscv_vsoxei16_v_bf16mf4(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxei16_v_bf16mf2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxei.nxv2bf16.nxv2i16.i64( [[VS3]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxei16_v_bf16mf2(__bf16 *rs1, vuint16mf2_t rs2, vbfloat16mf2_t vs3, + size_t vl) { + return __riscv_vsoxei16_v_bf16mf2(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxei16_v_bf16m1( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxei.nxv4bf16.nxv4i16.i64( [[VS3]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxei16_v_bf16m1(__bf16 *rs1, vuint16m1_t rs2, vbfloat16m1_t vs3, + size_t vl) { + return __riscv_vsoxei16_v_bf16m1(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxei16_v_bf16m2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxei.nxv8bf16.nxv8i16.i64( [[VS3]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxei16_v_bf16m2(__bf16 *rs1, vuint16m2_t rs2, vbfloat16m2_t vs3, + size_t vl) { + return __riscv_vsoxei16_v_bf16m2(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxei16_v_bf16m4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxei.nxv16bf16.nxv16i16.i64( [[VS3]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxei16_v_bf16m4(__bf16 *rs1, vuint16m4_t rs2, vbfloat16m4_t vs3, + size_t vl) { + return __riscv_vsoxei16_v_bf16m4(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxei16_v_bf16m8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxei.nxv32bf16.nxv32i16.i64( [[VS3]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxei16_v_bf16m8(__bf16 *rs1, vuint16m8_t rs2, vbfloat16m8_t vs3, + size_t vl) { + return __riscv_vsoxei16_v_bf16m8(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxei16_v_bf16mf4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxei.mask.nxv1bf16.nxv1i16.i64( [[VS3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxei16_v_bf16mf4_m(vbool64_t vm, __bf16 *rs1, vuint16mf4_t rs2, + vbfloat16mf4_t vs3, size_t vl) { + return __riscv_vsoxei16_v_bf16mf4_m(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxei16_v_bf16mf2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxei.mask.nxv2bf16.nxv2i16.i64( [[VS3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxei16_v_bf16mf2_m(vbool32_t vm, __bf16 *rs1, vuint16mf2_t rs2, + vbfloat16mf2_t vs3, size_t vl) { + return __riscv_vsoxei16_v_bf16mf2_m(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxei16_v_bf16m1_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxei.mask.nxv4bf16.nxv4i16.i64( [[VS3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxei16_v_bf16m1_m(vbool16_t vm, __bf16 *rs1, vuint16m1_t rs2, + vbfloat16m1_t vs3, size_t vl) { + return __riscv_vsoxei16_v_bf16m1_m(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxei16_v_bf16m2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxei.mask.nxv8bf16.nxv8i16.i64( [[VS3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxei16_v_bf16m2_m(vbool8_t vm, __bf16 *rs1, vuint16m2_t rs2, + vbfloat16m2_t vs3, size_t vl) { + return __riscv_vsoxei16_v_bf16m2_m(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxei16_v_bf16m4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxei.mask.nxv16bf16.nxv16i16.i64( [[VS3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxei16_v_bf16m4_m(vbool4_t vm, __bf16 *rs1, vuint16m4_t rs2, + vbfloat16m4_t vs3, size_t vl) { + return __riscv_vsoxei16_v_bf16m4_m(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxei16_v_bf16m8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxei.mask.nxv32bf16.nxv32i16.i64( [[VS3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxei16_v_bf16m8_m(vbool2_t vm, __bf16 *rs1, vuint16m8_t rs2, + vbfloat16m8_t vs3, size_t vl) { + return __riscv_vsoxei16_v_bf16m8_m(vm, rs1, rs2, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsoxseg2ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsoxseg2ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..a98ca6ae63a6bd15bf1b59a65c32168f90b23784 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsoxseg2ei16.c @@ -0,0 +1,141 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg2ei16_v_bf16mf4x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg2.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg2ei16_v_bf16mf4x2(__bf16 *rs1, vuint16mf4_t vs2, + vbfloat16mf4x2_t vs3, size_t vl) { + return __riscv_vsoxseg2ei16_v_bf16mf4x2(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg2ei16_v_bf16mf2x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg2.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg2ei16_v_bf16mf2x2(__bf16 *rs1, vuint16mf2_t vs2, + vbfloat16mf2x2_t vs3, size_t vl) { + return __riscv_vsoxseg2ei16_v_bf16mf2x2(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg2ei16_v_bf16m1x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg2.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg2ei16_v_bf16m1x2(__bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x2_t vs3, size_t vl) { + return __riscv_vsoxseg2ei16_v_bf16m1x2(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg2ei16_v_bf16m2x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg2.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg2ei16_v_bf16m2x2(__bf16 *rs1, vuint16m2_t vs2, + vbfloat16m2x2_t vs3, size_t vl) { + return __riscv_vsoxseg2ei16_v_bf16m2x2(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg2ei16_v_bf16m4x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg2.nxv16bf16.nxv16i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg2ei16_v_bf16m4x2(__bf16 *rs1, vuint16m4_t vs2, + vbfloat16m4x2_t vs3, size_t vl) { + return __riscv_vsoxseg2ei16_v_bf16m4x2(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg2ei16_v_bf16mf4x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg2.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg2ei16_v_bf16mf4x2_m(vbool64_t vm, __bf16 *rs1, + vuint16mf4_t vs2, vbfloat16mf4x2_t vs3, + size_t vl) { + return __riscv_vsoxseg2ei16_v_bf16mf4x2_m(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg2ei16_v_bf16mf2x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg2.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg2ei16_v_bf16mf2x2_m(vbool32_t vm, __bf16 *rs1, + vuint16mf2_t vs2, vbfloat16mf2x2_t vs3, + size_t vl) { + return __riscv_vsoxseg2ei16_v_bf16mf2x2_m(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg2ei16_v_bf16m1x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg2.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg2ei16_v_bf16m1x2_m(vbool16_t vm, __bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x2_t vs3, size_t vl) { + return __riscv_vsoxseg2ei16_v_bf16m1x2_m(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg2ei16_v_bf16m2x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg2.mask.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg2ei16_v_bf16m2x2_m(vbool8_t vm, __bf16 *rs1, vuint16m2_t vs2, + vbfloat16m2x2_t vs3, size_t vl) { + return __riscv_vsoxseg2ei16_v_bf16m2x2_m(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg2ei16_v_bf16m4x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg2.mask.nxv16bf16.nxv16i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg2ei16_v_bf16m4x2_m(vbool4_t vm, __bf16 *rs1, vuint16m4_t vs2, + vbfloat16m4x2_t vs3, size_t vl) { + return __riscv_vsoxseg2ei16_v_bf16m4x2_m(vm, rs1, vs2, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsoxseg3ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsoxseg3ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..0f08957b30a7e5291934b540cef59831a951a8a8 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsoxseg3ei16.c @@ -0,0 +1,123 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg3ei16_v_bf16mf4x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg3.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg3ei16_v_bf16mf4x3(__bf16 *rs1, vuint16mf4_t vs2, + vbfloat16mf4x3_t vs3, size_t vl) { + return __riscv_vsoxseg3ei16_v_bf16mf4x3(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg3ei16_v_bf16mf2x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg3.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg3ei16_v_bf16mf2x3(__bf16 *rs1, vuint16mf2_t vs2, + vbfloat16mf2x3_t vs3, size_t vl) { + return __riscv_vsoxseg3ei16_v_bf16mf2x3(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg3ei16_v_bf16m1x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg3.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg3ei16_v_bf16m1x3(__bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x3_t vs3, size_t vl) { + return __riscv_vsoxseg3ei16_v_bf16m1x3(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg3ei16_v_bf16m2x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg3.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg3ei16_v_bf16m2x3(__bf16 *rs1, vuint16m2_t vs2, + vbfloat16m2x3_t vs3, size_t vl) { + return __riscv_vsoxseg3ei16_v_bf16m2x3(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg3ei16_v_bf16mf4x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg3.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg3ei16_v_bf16mf4x3_m(vbool64_t vm, __bf16 *rs1, + vuint16mf4_t vs2, vbfloat16mf4x3_t vs3, + size_t vl) { + return __riscv_vsoxseg3ei16_v_bf16mf4x3_m(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg3ei16_v_bf16mf2x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg3.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg3ei16_v_bf16mf2x3_m(vbool32_t vm, __bf16 *rs1, + vuint16mf2_t vs2, vbfloat16mf2x3_t vs3, + size_t vl) { + return __riscv_vsoxseg3ei16_v_bf16mf2x3_m(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg3ei16_v_bf16m1x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg3.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg3ei16_v_bf16m1x3_m(vbool16_t vm, __bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x3_t vs3, size_t vl) { + return __riscv_vsoxseg3ei16_v_bf16m1x3_m(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg3ei16_v_bf16m2x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg3.mask.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg3ei16_v_bf16m2x3_m(vbool8_t vm, __bf16 *rs1, vuint16m2_t vs2, + vbfloat16m2x3_t vs3, size_t vl) { + return __riscv_vsoxseg3ei16_v_bf16m2x3_m(vm, rs1, vs2, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsoxseg4ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsoxseg4ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..0b29625998b0879a9b2603deded2b8f51d068b79 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsoxseg4ei16.c @@ -0,0 +1,131 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg4ei16_v_bf16mf4x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg4.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg4ei16_v_bf16mf4x4(__bf16 *rs1, vuint16mf4_t vs2, + vbfloat16mf4x4_t vs3, size_t vl) { + return __riscv_vsoxseg4ei16_v_bf16mf4x4(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg4ei16_v_bf16mf2x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg4.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg4ei16_v_bf16mf2x4(__bf16 *rs1, vuint16mf2_t vs2, + vbfloat16mf2x4_t vs3, size_t vl) { + return __riscv_vsoxseg4ei16_v_bf16mf2x4(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg4ei16_v_bf16m1x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg4.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg4ei16_v_bf16m1x4(__bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x4_t vs3, size_t vl) { + return __riscv_vsoxseg4ei16_v_bf16m1x4(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg4ei16_v_bf16m2x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg4.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg4ei16_v_bf16m2x4(__bf16 *rs1, vuint16m2_t vs2, + vbfloat16m2x4_t vs3, size_t vl) { + return __riscv_vsoxseg4ei16_v_bf16m2x4(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg4ei16_v_bf16mf4x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg4.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg4ei16_v_bf16mf4x4_m(vbool64_t vm, __bf16 *rs1, + vuint16mf4_t vs2, vbfloat16mf4x4_t vs3, + size_t vl) { + return __riscv_vsoxseg4ei16_v_bf16mf4x4_m(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg4ei16_v_bf16mf2x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg4.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg4ei16_v_bf16mf2x4_m(vbool32_t vm, __bf16 *rs1, + vuint16mf2_t vs2, vbfloat16mf2x4_t vs3, + size_t vl) { + return __riscv_vsoxseg4ei16_v_bf16mf2x4_m(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg4ei16_v_bf16m1x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg4.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg4ei16_v_bf16m1x4_m(vbool16_t vm, __bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x4_t vs3, size_t vl) { + return __riscv_vsoxseg4ei16_v_bf16m1x4_m(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg4ei16_v_bf16m2x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg4.mask.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg4ei16_v_bf16m2x4_m(vbool8_t vm, __bf16 *rs1, vuint16m2_t vs2, + vbfloat16m2x4_t vs3, size_t vl) { + return __riscv_vsoxseg4ei16_v_bf16m2x4_m(vm, rs1, vs2, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsoxseg5ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsoxseg5ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..0fc4d57918a4998951a221ffc1044d0d28d7f7b5 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsoxseg5ei16.c @@ -0,0 +1,107 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg5ei16_v_bf16mf4x5( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg5.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg5ei16_v_bf16mf4x5(__bf16 *rs1, vuint16mf4_t vs2, + vbfloat16mf4x5_t vs3, size_t vl) { + return __riscv_vsoxseg5ei16_v_bf16mf4x5(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg5ei16_v_bf16mf2x5( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg5.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg5ei16_v_bf16mf2x5(__bf16 *rs1, vuint16mf2_t vs2, + vbfloat16mf2x5_t vs3, size_t vl) { + return __riscv_vsoxseg5ei16_v_bf16mf2x5(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg5ei16_v_bf16m1x5( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg5.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg5ei16_v_bf16m1x5(__bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x5_t vs3, size_t vl) { + return __riscv_vsoxseg5ei16_v_bf16m1x5(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg5ei16_v_bf16mf4x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg5.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg5ei16_v_bf16mf4x5_m(vbool64_t vm, __bf16 *rs1, + vuint16mf4_t vs2, vbfloat16mf4x5_t vs3, + size_t vl) { + return __riscv_vsoxseg5ei16_v_bf16mf4x5_m(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg5ei16_v_bf16mf2x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg5.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg5ei16_v_bf16mf2x5_m(vbool32_t vm, __bf16 *rs1, + vuint16mf2_t vs2, vbfloat16mf2x5_t vs3, + size_t vl) { + return __riscv_vsoxseg5ei16_v_bf16mf2x5_m(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg5ei16_v_bf16m1x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg5.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg5ei16_v_bf16m1x5_m(vbool16_t vm, __bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x5_t vs3, size_t vl) { + return __riscv_vsoxseg5ei16_v_bf16m1x5_m(vm, rs1, vs2, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsoxseg6ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsoxseg6ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..e0c628c7eeec7614b8776670916a2631a464a704 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsoxseg6ei16.c @@ -0,0 +1,113 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg6ei16_v_bf16mf4x6( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg6.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg6ei16_v_bf16mf4x6(__bf16 *rs1, vuint16mf4_t vs2, + vbfloat16mf4x6_t vs3, size_t vl) { + return __riscv_vsoxseg6ei16_v_bf16mf4x6(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg6ei16_v_bf16mf2x6( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg6.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg6ei16_v_bf16mf2x6(__bf16 *rs1, vuint16mf2_t vs2, + vbfloat16mf2x6_t vs3, size_t vl) { + return __riscv_vsoxseg6ei16_v_bf16mf2x6(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg6ei16_v_bf16m1x6( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg6.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg6ei16_v_bf16m1x6(__bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x6_t vs3, size_t vl) { + return __riscv_vsoxseg6ei16_v_bf16m1x6(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg6ei16_v_bf16mf4x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg6.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg6ei16_v_bf16mf4x6_m(vbool64_t vm, __bf16 *rs1, + vuint16mf4_t vs2, vbfloat16mf4x6_t vs3, + size_t vl) { + return __riscv_vsoxseg6ei16_v_bf16mf4x6_m(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg6ei16_v_bf16mf2x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg6.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg6ei16_v_bf16mf2x6_m(vbool32_t vm, __bf16 *rs1, + vuint16mf2_t vs2, vbfloat16mf2x6_t vs3, + size_t vl) { + return __riscv_vsoxseg6ei16_v_bf16mf2x6_m(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg6ei16_v_bf16m1x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg6.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg6ei16_v_bf16m1x6_m(vbool16_t vm, __bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x6_t vs3, size_t vl) { + return __riscv_vsoxseg6ei16_v_bf16m1x6_m(vm, rs1, vs2, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsoxseg7ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsoxseg7ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..4ae28ba5cedd94c86306b94f5c94526eb2252632 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsoxseg7ei16.c @@ -0,0 +1,119 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg7ei16_v_bf16mf4x7( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg7.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg7ei16_v_bf16mf4x7(__bf16 *rs1, vuint16mf4_t vs2, + vbfloat16mf4x7_t vs3, size_t vl) { + return __riscv_vsoxseg7ei16_v_bf16mf4x7(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg7ei16_v_bf16mf2x7( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg7.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg7ei16_v_bf16mf2x7(__bf16 *rs1, vuint16mf2_t vs2, + vbfloat16mf2x7_t vs3, size_t vl) { + return __riscv_vsoxseg7ei16_v_bf16mf2x7(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg7ei16_v_bf16m1x7( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg7.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg7ei16_v_bf16m1x7(__bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x7_t vs3, size_t vl) { + return __riscv_vsoxseg7ei16_v_bf16m1x7(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg7ei16_v_bf16mf4x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg7.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg7ei16_v_bf16mf4x7_m(vbool64_t vm, __bf16 *rs1, + vuint16mf4_t vs2, vbfloat16mf4x7_t vs3, + size_t vl) { + return __riscv_vsoxseg7ei16_v_bf16mf4x7_m(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg7ei16_v_bf16mf2x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg7.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg7ei16_v_bf16mf2x7_m(vbool32_t vm, __bf16 *rs1, + vuint16mf2_t vs2, vbfloat16mf2x7_t vs3, + size_t vl) { + return __riscv_vsoxseg7ei16_v_bf16mf2x7_m(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg7ei16_v_bf16m1x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg7.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg7ei16_v_bf16m1x7_m(vbool16_t vm, __bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x7_t vs3, size_t vl) { + return __riscv_vsoxseg7ei16_v_bf16m1x7_m(vm, rs1, vs2, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsoxseg8ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsoxseg8ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..942a3239934adb9b4902da485295e65f1faf0e0e --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsoxseg8ei16.c @@ -0,0 +1,125 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg8ei16_v_bf16mf4x8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VS3]], 7 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg8.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg8ei16_v_bf16mf4x8(__bf16 *rs1, vuint16mf4_t vs2, + vbfloat16mf4x8_t vs3, size_t vl) { + return __riscv_vsoxseg8ei16_v_bf16mf4x8(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg8ei16_v_bf16mf2x8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VS3]], 7 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg8.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg8ei16_v_bf16mf2x8(__bf16 *rs1, vuint16mf2_t vs2, + vbfloat16mf2x8_t vs3, size_t vl) { + return __riscv_vsoxseg8ei16_v_bf16mf2x8(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg8ei16_v_bf16m1x8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VS3]], 7 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg8.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg8ei16_v_bf16m1x8(__bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x8_t vs3, size_t vl) { + return __riscv_vsoxseg8ei16_v_bf16m1x8(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg8ei16_v_bf16mf4x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VS3]], 7 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg8.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg8ei16_v_bf16mf4x8_m(vbool64_t vm, __bf16 *rs1, + vuint16mf4_t vs2, vbfloat16mf4x8_t vs3, + size_t vl) { + return __riscv_vsoxseg8ei16_v_bf16mf4x8_m(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg8ei16_v_bf16mf2x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VS3]], 7 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg8.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg8ei16_v_bf16mf2x8_m(vbool32_t vm, __bf16 *rs1, + vuint16mf2_t vs2, vbfloat16mf2x8_t vs3, + size_t vl) { + return __riscv_vsoxseg8ei16_v_bf16mf2x8_m(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg8ei16_v_bf16m1x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VS3]], 7 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg8.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg8ei16_v_bf16m1x8_m(vbool16_t vm, __bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x8_t vs3, size_t vl) { + return __riscv_vsoxseg8ei16_v_bf16m1x8_m(vm, rs1, vs2, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsse16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsse16.c new file mode 100644 index 0000000000000000000000000000000000000000..13eb05bb3b0c80c51ae7f3763be1a6c30e04346f --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsse16.c @@ -0,0 +1,141 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vsse16_v_bf16mf4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsse.nxv1bf16.i64( [[VS3]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsse16_v_bf16mf4(__bf16 *rs1, ptrdiff_t rs2, vbfloat16mf4_t vs3, + size_t vl) { + return __riscv_vsse16_v_bf16mf4(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsse16_v_bf16mf2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsse.nxv2bf16.i64( [[VS3]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsse16_v_bf16mf2(__bf16 *rs1, ptrdiff_t rs2, vbfloat16mf2_t vs3, + size_t vl) { + return __riscv_vsse16_v_bf16mf2(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsse16_v_bf16m1( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsse.nxv4bf16.i64( [[VS3]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsse16_v_bf16m1(__bf16 *rs1, ptrdiff_t rs2, vbfloat16m1_t vs3, + size_t vl) { + return __riscv_vsse16_v_bf16m1(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsse16_v_bf16m2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsse.nxv8bf16.i64( [[VS3]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsse16_v_bf16m2(__bf16 *rs1, ptrdiff_t rs2, vbfloat16m2_t vs3, + size_t vl) { + return __riscv_vsse16_v_bf16m2(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsse16_v_bf16m4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsse.nxv16bf16.i64( [[VS3]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsse16_v_bf16m4(__bf16 *rs1, ptrdiff_t rs2, vbfloat16m4_t vs3, + size_t vl) { + return __riscv_vsse16_v_bf16m4(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsse16_v_bf16m8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsse.nxv32bf16.i64( [[VS3]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsse16_v_bf16m8(__bf16 *rs1, ptrdiff_t rs2, vbfloat16m8_t vs3, + size_t vl) { + return __riscv_vsse16_v_bf16m8(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsse16_v_bf16mf4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsse.mask.nxv1bf16.i64( [[VS3]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsse16_v_bf16mf4_m(vbool64_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf4_t vs3, size_t vl) { + return __riscv_vsse16_v_bf16mf4_m(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsse16_v_bf16mf2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsse.mask.nxv2bf16.i64( [[VS3]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsse16_v_bf16mf2_m(vbool32_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf2_t vs3, size_t vl) { + return __riscv_vsse16_v_bf16mf2_m(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsse16_v_bf16m1_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsse.mask.nxv4bf16.i64( [[VS3]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsse16_v_bf16m1_m(vbool16_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16m1_t vs3, size_t vl) { + return __riscv_vsse16_v_bf16m1_m(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsse16_v_bf16m2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsse.mask.nxv8bf16.i64( [[VS3]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsse16_v_bf16m2_m(vbool8_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16m2_t vs3, size_t vl) { + return __riscv_vsse16_v_bf16m2_m(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsse16_v_bf16m4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsse.mask.nxv16bf16.i64( [[VS3]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsse16_v_bf16m4_m(vbool4_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16m4_t vs3, size_t vl) { + return __riscv_vsse16_v_bf16m4_m(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsse16_v_bf16m8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsse.mask.nxv32bf16.i64( [[VS3]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsse16_v_bf16m8_m(vbool2_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16m8_t vs3, size_t vl) { + return __riscv_vsse16_v_bf16m8_m(vm, rs1, rs2, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsseg2e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsseg2e16.c new file mode 100644 index 0000000000000000000000000000000000000000..a6384b15423902ef6d014c89d8b405f8f1ce88c0 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsseg2e16.c @@ -0,0 +1,134 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg2e16_v_bf16mf4x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg2.nxv1bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg2e16_v_bf16mf4x2(__bf16 *rs1, vbfloat16mf4x2_t vs3, size_t vl) { + return __riscv_vsseg2e16_v_bf16mf4x2(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg2e16_v_bf16mf2x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg2.nxv2bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg2e16_v_bf16mf2x2(__bf16 *rs1, vbfloat16mf2x2_t vs3, size_t vl) { + return __riscv_vsseg2e16_v_bf16mf2x2(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg2e16_v_bf16m1x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg2.nxv4bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg2e16_v_bf16m1x2(__bf16 *rs1, vbfloat16m1x2_t vs3, size_t vl) { + return __riscv_vsseg2e16_v_bf16m1x2(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg2e16_v_bf16m2x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg2.nxv8bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg2e16_v_bf16m2x2(__bf16 *rs1, vbfloat16m2x2_t vs3, size_t vl) { + return __riscv_vsseg2e16_v_bf16m2x2(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg2e16_v_bf16m4x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg2.nxv16bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg2e16_v_bf16m4x2(__bf16 *rs1, vbfloat16m4x2_t vs3, size_t vl) { + return __riscv_vsseg2e16_v_bf16m4x2(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg2e16_v_bf16mf4x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg2.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg2e16_v_bf16mf4x2_m(vbool64_t vm, __bf16 *rs1, + vbfloat16mf4x2_t vs3, size_t vl) { + return __riscv_vsseg2e16_v_bf16mf4x2_m(vm, rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg2e16_v_bf16mf2x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg2.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg2e16_v_bf16mf2x2_m(vbool32_t vm, __bf16 *rs1, + vbfloat16mf2x2_t vs3, size_t vl) { + return __riscv_vsseg2e16_v_bf16mf2x2_m(vm, rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg2e16_v_bf16m1x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg2.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg2e16_v_bf16m1x2_m(vbool16_t vm, __bf16 *rs1, vbfloat16m1x2_t vs3, + size_t vl) { + return __riscv_vsseg2e16_v_bf16m1x2_m(vm, rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg2e16_v_bf16m2x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg2.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg2e16_v_bf16m2x2_m(vbool8_t vm, __bf16 *rs1, vbfloat16m2x2_t vs3, + size_t vl) { + return __riscv_vsseg2e16_v_bf16m2x2_m(vm, rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg2e16_v_bf16m4x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg2.mask.nxv16bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg2e16_v_bf16m4x2_m(vbool4_t vm, __bf16 *rs1, vbfloat16m4x2_t vs3, + size_t vl) { + return __riscv_vsseg2e16_v_bf16m4x2_m(vm, rs1, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsseg3e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsseg3e16.c new file mode 100644 index 0000000000000000000000000000000000000000..b04177c8db4dc113082353821c748aaaeb95de05 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsseg3e16.c @@ -0,0 +1,117 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg3e16_v_bf16mf4x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg3.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg3e16_v_bf16mf4x3(__bf16 *rs1, vbfloat16mf4x3_t vs3, size_t vl) { + return __riscv_vsseg3e16_v_bf16mf4x3(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg3e16_v_bf16mf2x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg3.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg3e16_v_bf16mf2x3(__bf16 *rs1, vbfloat16mf2x3_t vs3, size_t vl) { + return __riscv_vsseg3e16_v_bf16mf2x3(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg3e16_v_bf16m1x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg3.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg3e16_v_bf16m1x3(__bf16 *rs1, vbfloat16m1x3_t vs3, size_t vl) { + return __riscv_vsseg3e16_v_bf16m1x3(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg3e16_v_bf16m2x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg3.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg3e16_v_bf16m2x3(__bf16 *rs1, vbfloat16m2x3_t vs3, size_t vl) { + return __riscv_vsseg3e16_v_bf16m2x3(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg3e16_v_bf16mf4x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg3.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg3e16_v_bf16mf4x3_m(vbool64_t vm, __bf16 *rs1, + vbfloat16mf4x3_t vs3, size_t vl) { + return __riscv_vsseg3e16_v_bf16mf4x3_m(vm, rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg3e16_v_bf16mf2x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg3.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg3e16_v_bf16mf2x3_m(vbool32_t vm, __bf16 *rs1, + vbfloat16mf2x3_t vs3, size_t vl) { + return __riscv_vsseg3e16_v_bf16mf2x3_m(vm, rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg3e16_v_bf16m1x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg3.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg3e16_v_bf16m1x3_m(vbool16_t vm, __bf16 *rs1, vbfloat16m1x3_t vs3, + size_t vl) { + return __riscv_vsseg3e16_v_bf16m1x3_m(vm, rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg3e16_v_bf16m2x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg3.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg3e16_v_bf16m2x3_m(vbool8_t vm, __bf16 *rs1, vbfloat16m2x3_t vs3, + size_t vl) { + return __riscv_vsseg3e16_v_bf16m2x3_m(vm, rs1, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsseg4e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsseg4e16.c new file mode 100644 index 0000000000000000000000000000000000000000..3745c3af566efd9c97bd43b0eea0eab1d0f3f5fe --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsseg4e16.c @@ -0,0 +1,125 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg4e16_v_bf16mf4x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg4.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg4e16_v_bf16mf4x4(__bf16 *rs1, vbfloat16mf4x4_t vs3, size_t vl) { + return __riscv_vsseg4e16_v_bf16mf4x4(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg4e16_v_bf16mf2x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg4.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg4e16_v_bf16mf2x4(__bf16 *rs1, vbfloat16mf2x4_t vs3, size_t vl) { + return __riscv_vsseg4e16_v_bf16mf2x4(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg4e16_v_bf16m1x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg4.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg4e16_v_bf16m1x4(__bf16 *rs1, vbfloat16m1x4_t vs3, size_t vl) { + return __riscv_vsseg4e16_v_bf16m1x4(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg4e16_v_bf16m2x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg4.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg4e16_v_bf16m2x4(__bf16 *rs1, vbfloat16m2x4_t vs3, size_t vl) { + return __riscv_vsseg4e16_v_bf16m2x4(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg4e16_v_bf16mf4x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg4.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg4e16_v_bf16mf4x4_m(vbool64_t vm, __bf16 *rs1, + vbfloat16mf4x4_t vs3, size_t vl) { + return __riscv_vsseg4e16_v_bf16mf4x4_m(vm, rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg4e16_v_bf16mf2x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg4.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg4e16_v_bf16mf2x4_m(vbool32_t vm, __bf16 *rs1, + vbfloat16mf2x4_t vs3, size_t vl) { + return __riscv_vsseg4e16_v_bf16mf2x4_m(vm, rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg4e16_v_bf16m1x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg4.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg4e16_v_bf16m1x4_m(vbool16_t vm, __bf16 *rs1, vbfloat16m1x4_t vs3, + size_t vl) { + return __riscv_vsseg4e16_v_bf16m1x4_m(vm, rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg4e16_v_bf16m2x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg4.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg4e16_v_bf16m2x4_m(vbool8_t vm, __bf16 *rs1, vbfloat16m2x4_t vs3, + size_t vl) { + return __riscv_vsseg4e16_v_bf16m2x4_m(vm, rs1, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsseg5e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsseg5e16.c new file mode 100644 index 0000000000000000000000000000000000000000..8aa59fbb521ca088ed7be10730c36a8bec9f05d8 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsseg5e16.c @@ -0,0 +1,102 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg5e16_v_bf16mf4x5( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg5.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg5e16_v_bf16mf4x5(__bf16 *rs1, vbfloat16mf4x5_t vs3, size_t vl) { + return __riscv_vsseg5e16_v_bf16mf4x5(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg5e16_v_bf16mf2x5( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg5.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg5e16_v_bf16mf2x5(__bf16 *rs1, vbfloat16mf2x5_t vs3, size_t vl) { + return __riscv_vsseg5e16_v_bf16mf2x5(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg5e16_v_bf16m1x5( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg5.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg5e16_v_bf16m1x5(__bf16 *rs1, vbfloat16m1x5_t vs3, size_t vl) { + return __riscv_vsseg5e16_v_bf16m1x5(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg5e16_v_bf16mf4x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg5.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg5e16_v_bf16mf4x5_m(vbool64_t vm, __bf16 *rs1, + vbfloat16mf4x5_t vs3, size_t vl) { + return __riscv_vsseg5e16_v_bf16mf4x5_m(vm, rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg5e16_v_bf16mf2x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg5.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg5e16_v_bf16mf2x5_m(vbool32_t vm, __bf16 *rs1, + vbfloat16mf2x5_t vs3, size_t vl) { + return __riscv_vsseg5e16_v_bf16mf2x5_m(vm, rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg5e16_v_bf16m1x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg5.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg5e16_v_bf16m1x5_m(vbool16_t vm, __bf16 *rs1, vbfloat16m1x5_t vs3, + size_t vl) { + return __riscv_vsseg5e16_v_bf16m1x5_m(vm, rs1, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsseg6e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsseg6e16.c new file mode 100644 index 0000000000000000000000000000000000000000..a2b3fd5e1102897be2ba5069e56a81a6e4be990e --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsseg6e16.c @@ -0,0 +1,108 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg6e16_v_bf16mf4x6( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg6.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg6e16_v_bf16mf4x6(__bf16 *rs1, vbfloat16mf4x6_t vs3, size_t vl) { + return __riscv_vsseg6e16_v_bf16mf4x6(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg6e16_v_bf16mf2x6( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg6.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg6e16_v_bf16mf2x6(__bf16 *rs1, vbfloat16mf2x6_t vs3, size_t vl) { + return __riscv_vsseg6e16_v_bf16mf2x6(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg6e16_v_bf16m1x6( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg6.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg6e16_v_bf16m1x6(__bf16 *rs1, vbfloat16m1x6_t vs3, size_t vl) { + return __riscv_vsseg6e16_v_bf16m1x6(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg6e16_v_bf16mf4x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg6.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg6e16_v_bf16mf4x6_m(vbool64_t vm, __bf16 *rs1, + vbfloat16mf4x6_t vs3, size_t vl) { + return __riscv_vsseg6e16_v_bf16mf4x6_m(vm, rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg6e16_v_bf16mf2x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg6.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg6e16_v_bf16mf2x6_m(vbool32_t vm, __bf16 *rs1, + vbfloat16mf2x6_t vs3, size_t vl) { + return __riscv_vsseg6e16_v_bf16mf2x6_m(vm, rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg6e16_v_bf16m1x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg6.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg6e16_v_bf16m1x6_m(vbool16_t vm, __bf16 *rs1, vbfloat16m1x6_t vs3, + size_t vl) { + return __riscv_vsseg6e16_v_bf16m1x6_m(vm, rs1, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsseg7e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsseg7e16.c new file mode 100644 index 0000000000000000000000000000000000000000..3664769177658f1e8d1af043b8117b0fefb3f922 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsseg7e16.c @@ -0,0 +1,114 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg7e16_v_bf16mf4x7( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg7.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg7e16_v_bf16mf4x7(__bf16 *rs1, vbfloat16mf4x7_t vs3, size_t vl) { + return __riscv_vsseg7e16_v_bf16mf4x7(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg7e16_v_bf16mf2x7( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg7.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg7e16_v_bf16mf2x7(__bf16 *rs1, vbfloat16mf2x7_t vs3, size_t vl) { + return __riscv_vsseg7e16_v_bf16mf2x7(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg7e16_v_bf16m1x7( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg7.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg7e16_v_bf16m1x7(__bf16 *rs1, vbfloat16m1x7_t vs3, size_t vl) { + return __riscv_vsseg7e16_v_bf16m1x7(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg7e16_v_bf16mf4x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg7.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg7e16_v_bf16mf4x7_m(vbool64_t vm, __bf16 *rs1, + vbfloat16mf4x7_t vs3, size_t vl) { + return __riscv_vsseg7e16_v_bf16mf4x7_m(vm, rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg7e16_v_bf16mf2x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg7.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg7e16_v_bf16mf2x7_m(vbool32_t vm, __bf16 *rs1, + vbfloat16mf2x7_t vs3, size_t vl) { + return __riscv_vsseg7e16_v_bf16mf2x7_m(vm, rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg7e16_v_bf16m1x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg7.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg7e16_v_bf16m1x7_m(vbool16_t vm, __bf16 *rs1, vbfloat16m1x7_t vs3, + size_t vl) { + return __riscv_vsseg7e16_v_bf16m1x7_m(vm, rs1, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsseg8e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsseg8e16.c new file mode 100644 index 0000000000000000000000000000000000000000..2c6717726e7230b6cefb0165715b8189caaef4e9 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsseg8e16.c @@ -0,0 +1,120 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg8e16_v_bf16mf4x8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VS3]], 7 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg8.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg8e16_v_bf16mf4x8(__bf16 *rs1, vbfloat16mf4x8_t vs3, size_t vl) { + return __riscv_vsseg8e16_v_bf16mf4x8(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg8e16_v_bf16mf2x8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VS3]], 7 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg8.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg8e16_v_bf16mf2x8(__bf16 *rs1, vbfloat16mf2x8_t vs3, size_t vl) { + return __riscv_vsseg8e16_v_bf16mf2x8(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg8e16_v_bf16m1x8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VS3]], 7 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg8.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg8e16_v_bf16m1x8(__bf16 *rs1, vbfloat16m1x8_t vs3, size_t vl) { + return __riscv_vsseg8e16_v_bf16m1x8(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg8e16_v_bf16mf4x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VS3]], 7 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg8.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg8e16_v_bf16mf4x8_m(vbool64_t vm, __bf16 *rs1, + vbfloat16mf4x8_t vs3, size_t vl) { + return __riscv_vsseg8e16_v_bf16mf4x8_m(vm, rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg8e16_v_bf16mf2x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VS3]], 7 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg8.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg8e16_v_bf16mf2x8_m(vbool32_t vm, __bf16 *rs1, + vbfloat16mf2x8_t vs3, size_t vl) { + return __riscv_vsseg8e16_v_bf16mf2x8_m(vm, rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg8e16_v_bf16m1x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VS3]], 7 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg8.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg8e16_v_bf16m1x8_m(vbool16_t vm, __bf16 *rs1, vbfloat16m1x8_t vs3, + size_t vl) { + return __riscv_vsseg8e16_v_bf16m1x8_m(vm, rs1, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vssseg2e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vssseg2e16.c new file mode 100644 index 0000000000000000000000000000000000000000..a6aacb536854c51d5c649dd396d428fdef14e458 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vssseg2e16.c @@ -0,0 +1,139 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg2e16_v_bf16mf4x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg2.nxv1bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg2e16_v_bf16mf4x2(__bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf4x2_t vs3, size_t vl) { + return __riscv_vssseg2e16_v_bf16mf4x2(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg2e16_v_bf16mf2x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg2.nxv2bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg2e16_v_bf16mf2x2(__bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf2x2_t vs3, size_t vl) { + return __riscv_vssseg2e16_v_bf16mf2x2(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg2e16_v_bf16m1x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg2.nxv4bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg2e16_v_bf16m1x2(__bf16 *rs1, ptrdiff_t rs2, vbfloat16m1x2_t vs3, + size_t vl) { + return __riscv_vssseg2e16_v_bf16m1x2(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg2e16_v_bf16m2x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg2.nxv8bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg2e16_v_bf16m2x2(__bf16 *rs1, ptrdiff_t rs2, vbfloat16m2x2_t vs3, + size_t vl) { + return __riscv_vssseg2e16_v_bf16m2x2(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg2e16_v_bf16m4x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg2.nxv16bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg2e16_v_bf16m4x2(__bf16 *rs1, ptrdiff_t rs2, vbfloat16m4x2_t vs3, + size_t vl) { + return __riscv_vssseg2e16_v_bf16m4x2(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg2e16_v_bf16mf4x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg2.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg2e16_v_bf16mf4x2_m(vbool64_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf4x2_t vs3, size_t vl) { + return __riscv_vssseg2e16_v_bf16mf4x2_m(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg2e16_v_bf16mf2x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg2.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg2e16_v_bf16mf2x2_m(vbool32_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf2x2_t vs3, size_t vl) { + return __riscv_vssseg2e16_v_bf16mf2x2_m(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg2e16_v_bf16m1x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg2.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg2e16_v_bf16m1x2_m(vbool16_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16m1x2_t vs3, size_t vl) { + return __riscv_vssseg2e16_v_bf16m1x2_m(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg2e16_v_bf16m2x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg2.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg2e16_v_bf16m2x2_m(vbool8_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16m2x2_t vs3, size_t vl) { + return __riscv_vssseg2e16_v_bf16m2x2_m(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg2e16_v_bf16m4x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg2.mask.nxv16bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg2e16_v_bf16m4x2_m(vbool4_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16m4x2_t vs3, size_t vl) { + return __riscv_vssseg2e16_v_bf16m4x2_m(vm, rs1, rs2, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vssseg3e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vssseg3e16.c new file mode 100644 index 0000000000000000000000000000000000000000..4ce7ef9bbf044a3913dd657409e23b7ca1fcbadf --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vssseg3e16.c @@ -0,0 +1,121 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg3e16_v_bf16mf4x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg3.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg3e16_v_bf16mf4x3(__bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf4x3_t vs3, size_t vl) { + return __riscv_vssseg3e16_v_bf16mf4x3(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg3e16_v_bf16mf2x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg3.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg3e16_v_bf16mf2x3(__bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf2x3_t vs3, size_t vl) { + return __riscv_vssseg3e16_v_bf16mf2x3(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg3e16_v_bf16m1x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg3.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg3e16_v_bf16m1x3(__bf16 *rs1, ptrdiff_t rs2, vbfloat16m1x3_t vs3, + size_t vl) { + return __riscv_vssseg3e16_v_bf16m1x3(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg3e16_v_bf16m2x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg3.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg3e16_v_bf16m2x3(__bf16 *rs1, ptrdiff_t rs2, vbfloat16m2x3_t vs3, + size_t vl) { + return __riscv_vssseg3e16_v_bf16m2x3(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg3e16_v_bf16mf4x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg3.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg3e16_v_bf16mf4x3_m(vbool64_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf4x3_t vs3, size_t vl) { + return __riscv_vssseg3e16_v_bf16mf4x3_m(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg3e16_v_bf16mf2x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg3.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg3e16_v_bf16mf2x3_m(vbool32_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf2x3_t vs3, size_t vl) { + return __riscv_vssseg3e16_v_bf16mf2x3_m(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg3e16_v_bf16m1x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg3.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg3e16_v_bf16m1x3_m(vbool16_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16m1x3_t vs3, size_t vl) { + return __riscv_vssseg3e16_v_bf16m1x3_m(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg3e16_v_bf16m2x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg3.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg3e16_v_bf16m2x3_m(vbool8_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16m2x3_t vs3, size_t vl) { + return __riscv_vssseg3e16_v_bf16m2x3_m(vm, rs1, rs2, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vssseg4e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vssseg4e16.c new file mode 100644 index 0000000000000000000000000000000000000000..f8d980f8946fc5a42580f96e0d7094a3fdc41396 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vssseg4e16.c @@ -0,0 +1,129 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg4e16_v_bf16mf4x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg4.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg4e16_v_bf16mf4x4(__bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf4x4_t vs3, size_t vl) { + return __riscv_vssseg4e16_v_bf16mf4x4(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg4e16_v_bf16mf2x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg4.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg4e16_v_bf16mf2x4(__bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf2x4_t vs3, size_t vl) { + return __riscv_vssseg4e16_v_bf16mf2x4(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg4e16_v_bf16m1x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg4.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg4e16_v_bf16m1x4(__bf16 *rs1, ptrdiff_t rs2, vbfloat16m1x4_t vs3, + size_t vl) { + return __riscv_vssseg4e16_v_bf16m1x4(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg4e16_v_bf16m2x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg4.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg4e16_v_bf16m2x4(__bf16 *rs1, ptrdiff_t rs2, vbfloat16m2x4_t vs3, + size_t vl) { + return __riscv_vssseg4e16_v_bf16m2x4(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg4e16_v_bf16mf4x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg4.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg4e16_v_bf16mf4x4_m(vbool64_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf4x4_t vs3, size_t vl) { + return __riscv_vssseg4e16_v_bf16mf4x4_m(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg4e16_v_bf16mf2x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg4.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg4e16_v_bf16mf2x4_m(vbool32_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf2x4_t vs3, size_t vl) { + return __riscv_vssseg4e16_v_bf16mf2x4_m(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg4e16_v_bf16m1x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg4.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg4e16_v_bf16m1x4_m(vbool16_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16m1x4_t vs3, size_t vl) { + return __riscv_vssseg4e16_v_bf16m1x4_m(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg4e16_v_bf16m2x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg4.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg4e16_v_bf16m2x4_m(vbool8_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16m2x4_t vs3, size_t vl) { + return __riscv_vssseg4e16_v_bf16m2x4_m(vm, rs1, rs2, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vssseg5e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vssseg5e16.c new file mode 100644 index 0000000000000000000000000000000000000000..115cdf480d9714e5f07a7e783b27e3060f285914 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vssseg5e16.c @@ -0,0 +1,105 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg5e16_v_bf16mf4x5( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg5.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg5e16_v_bf16mf4x5(__bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf4x5_t vs3, size_t vl) { + return __riscv_vssseg5e16_v_bf16mf4x5(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg5e16_v_bf16mf2x5( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg5.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg5e16_v_bf16mf2x5(__bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf2x5_t vs3, size_t vl) { + return __riscv_vssseg5e16_v_bf16mf2x5(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg5e16_v_bf16m1x5( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg5.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg5e16_v_bf16m1x5(__bf16 *rs1, ptrdiff_t rs2, vbfloat16m1x5_t vs3, + size_t vl) { + return __riscv_vssseg5e16_v_bf16m1x5(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg5e16_v_bf16mf4x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg5.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg5e16_v_bf16mf4x5_m(vbool64_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf4x5_t vs3, size_t vl) { + return __riscv_vssseg5e16_v_bf16mf4x5_m(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg5e16_v_bf16mf2x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg5.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg5e16_v_bf16mf2x5_m(vbool32_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf2x5_t vs3, size_t vl) { + return __riscv_vssseg5e16_v_bf16mf2x5_m(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg5e16_v_bf16m1x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg5.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg5e16_v_bf16m1x5_m(vbool16_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16m1x5_t vs3, size_t vl) { + return __riscv_vssseg5e16_v_bf16m1x5_m(vm, rs1, rs2, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vssseg6e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vssseg6e16.c new file mode 100644 index 0000000000000000000000000000000000000000..c74f19905a4d29f45aac6a962632cfb3987c041f --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vssseg6e16.c @@ -0,0 +1,111 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg6e16_v_bf16mf4x6( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg6.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg6e16_v_bf16mf4x6(__bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf4x6_t vs3, size_t vl) { + return __riscv_vssseg6e16_v_bf16mf4x6(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg6e16_v_bf16mf2x6( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg6.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg6e16_v_bf16mf2x6(__bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf2x6_t vs3, size_t vl) { + return __riscv_vssseg6e16_v_bf16mf2x6(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg6e16_v_bf16m1x6( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg6.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg6e16_v_bf16m1x6(__bf16 *rs1, ptrdiff_t rs2, vbfloat16m1x6_t vs3, + size_t vl) { + return __riscv_vssseg6e16_v_bf16m1x6(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg6e16_v_bf16mf4x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg6.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg6e16_v_bf16mf4x6_m(vbool64_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf4x6_t vs3, size_t vl) { + return __riscv_vssseg6e16_v_bf16mf4x6_m(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg6e16_v_bf16mf2x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg6.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg6e16_v_bf16mf2x6_m(vbool32_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf2x6_t vs3, size_t vl) { + return __riscv_vssseg6e16_v_bf16mf2x6_m(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg6e16_v_bf16m1x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg6.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg6e16_v_bf16m1x6_m(vbool16_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16m1x6_t vs3, size_t vl) { + return __riscv_vssseg6e16_v_bf16m1x6_m(vm, rs1, rs2, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vssseg7e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vssseg7e16.c new file mode 100644 index 0000000000000000000000000000000000000000..d1ff80f684a4a9d3838af8d6466d34191549bd90 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vssseg7e16.c @@ -0,0 +1,117 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg7e16_v_bf16mf4x7( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg7.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg7e16_v_bf16mf4x7(__bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf4x7_t vs3, size_t vl) { + return __riscv_vssseg7e16_v_bf16mf4x7(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg7e16_v_bf16mf2x7( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg7.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg7e16_v_bf16mf2x7(__bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf2x7_t vs3, size_t vl) { + return __riscv_vssseg7e16_v_bf16mf2x7(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg7e16_v_bf16m1x7( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg7.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg7e16_v_bf16m1x7(__bf16 *rs1, ptrdiff_t rs2, vbfloat16m1x7_t vs3, + size_t vl) { + return __riscv_vssseg7e16_v_bf16m1x7(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg7e16_v_bf16mf4x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg7.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg7e16_v_bf16mf4x7_m(vbool64_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf4x7_t vs3, size_t vl) { + return __riscv_vssseg7e16_v_bf16mf4x7_m(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg7e16_v_bf16mf2x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg7.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg7e16_v_bf16mf2x7_m(vbool32_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf2x7_t vs3, size_t vl) { + return __riscv_vssseg7e16_v_bf16mf2x7_m(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg7e16_v_bf16m1x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg7.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg7e16_v_bf16m1x7_m(vbool16_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16m1x7_t vs3, size_t vl) { + return __riscv_vssseg7e16_v_bf16m1x7_m(vm, rs1, rs2, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vssseg8e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vssseg8e16.c new file mode 100644 index 0000000000000000000000000000000000000000..e80ff10dab50e5fa1e2d29a4b238d7d66aebd312 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vssseg8e16.c @@ -0,0 +1,123 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg8e16_v_bf16mf4x8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VS3]], 7 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg8.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg8e16_v_bf16mf4x8(__bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf4x8_t vs3, size_t vl) { + return __riscv_vssseg8e16_v_bf16mf4x8(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg8e16_v_bf16mf2x8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VS3]], 7 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg8.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg8e16_v_bf16mf2x8(__bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf2x8_t vs3, size_t vl) { + return __riscv_vssseg8e16_v_bf16mf2x8(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg8e16_v_bf16m1x8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VS3]], 7 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg8.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg8e16_v_bf16m1x8(__bf16 *rs1, ptrdiff_t rs2, vbfloat16m1x8_t vs3, + size_t vl) { + return __riscv_vssseg8e16_v_bf16m1x8(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg8e16_v_bf16mf4x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VS3]], 7 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg8.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg8e16_v_bf16mf4x8_m(vbool64_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf4x8_t vs3, size_t vl) { + return __riscv_vssseg8e16_v_bf16mf4x8_m(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg8e16_v_bf16mf2x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VS3]], 7 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg8.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg8e16_v_bf16mf2x8_m(vbool32_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf2x8_t vs3, size_t vl) { + return __riscv_vssseg8e16_v_bf16mf2x8_m(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg8e16_v_bf16m1x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VS3]], 7 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg8.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg8e16_v_bf16m1x8_m(vbool16_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16m1x8_t vs3, size_t vl) { + return __riscv_vssseg8e16_v_bf16m1x8_m(vm, rs1, rs2, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsuxei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsuxei16.c new file mode 100644 index 0000000000000000000000000000000000000000..5bbff43146203562d869a90978b7e597b1bf0b71 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsuxei16.c @@ -0,0 +1,141 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxei16_v_bf16mf4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxei.nxv1bf16.nxv1i16.i64( [[VS3]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxei16_v_bf16mf4(__bf16 *rs1, vuint16mf4_t rs2, vbfloat16mf4_t vs3, + size_t vl) { + return __riscv_vsuxei16_v_bf16mf4(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxei16_v_bf16mf2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxei.nxv2bf16.nxv2i16.i64( [[VS3]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxei16_v_bf16mf2(__bf16 *rs1, vuint16mf2_t rs2, vbfloat16mf2_t vs3, + size_t vl) { + return __riscv_vsuxei16_v_bf16mf2(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxei16_v_bf16m1( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxei.nxv4bf16.nxv4i16.i64( [[VS3]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxei16_v_bf16m1(__bf16 *rs1, vuint16m1_t rs2, vbfloat16m1_t vs3, + size_t vl) { + return __riscv_vsuxei16_v_bf16m1(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxei16_v_bf16m2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxei.nxv8bf16.nxv8i16.i64( [[VS3]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxei16_v_bf16m2(__bf16 *rs1, vuint16m2_t rs2, vbfloat16m2_t vs3, + size_t vl) { + return __riscv_vsuxei16_v_bf16m2(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxei16_v_bf16m4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxei.nxv16bf16.nxv16i16.i64( [[VS3]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxei16_v_bf16m4(__bf16 *rs1, vuint16m4_t rs2, vbfloat16m4_t vs3, + size_t vl) { + return __riscv_vsuxei16_v_bf16m4(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxei16_v_bf16m8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxei.nxv32bf16.nxv32i16.i64( [[VS3]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxei16_v_bf16m8(__bf16 *rs1, vuint16m8_t rs2, vbfloat16m8_t vs3, + size_t vl) { + return __riscv_vsuxei16_v_bf16m8(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxei16_v_bf16mf4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxei.mask.nxv1bf16.nxv1i16.i64( [[VS3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxei16_v_bf16mf4_m(vbool64_t vm, __bf16 *rs1, vuint16mf4_t rs2, + vbfloat16mf4_t vs3, size_t vl) { + return __riscv_vsuxei16_v_bf16mf4_m(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxei16_v_bf16mf2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxei.mask.nxv2bf16.nxv2i16.i64( [[VS3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxei16_v_bf16mf2_m(vbool32_t vm, __bf16 *rs1, vuint16mf2_t rs2, + vbfloat16mf2_t vs3, size_t vl) { + return __riscv_vsuxei16_v_bf16mf2_m(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxei16_v_bf16m1_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxei.mask.nxv4bf16.nxv4i16.i64( [[VS3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxei16_v_bf16m1_m(vbool16_t vm, __bf16 *rs1, vuint16m1_t rs2, + vbfloat16m1_t vs3, size_t vl) { + return __riscv_vsuxei16_v_bf16m1_m(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxei16_v_bf16m2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxei.mask.nxv8bf16.nxv8i16.i64( [[VS3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxei16_v_bf16m2_m(vbool8_t vm, __bf16 *rs1, vuint16m2_t rs2, + vbfloat16m2_t vs3, size_t vl) { + return __riscv_vsuxei16_v_bf16m2_m(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxei16_v_bf16m4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxei.mask.nxv16bf16.nxv16i16.i64( [[VS3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxei16_v_bf16m4_m(vbool4_t vm, __bf16 *rs1, vuint16m4_t rs2, + vbfloat16m4_t vs3, size_t vl) { + return __riscv_vsuxei16_v_bf16m4_m(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxei16_v_bf16m8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxei.mask.nxv32bf16.nxv32i16.i64( [[VS3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxei16_v_bf16m8_m(vbool2_t vm, __bf16 *rs1, vuint16m8_t rs2, + vbfloat16m8_t vs3, size_t vl) { + return __riscv_vsuxei16_v_bf16m8_m(vm, rs1, rs2, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsuxseg2ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsuxseg2ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..27db36fa9531e9f447ad0ed3b009e2e6a52b2b8d --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsuxseg2ei16.c @@ -0,0 +1,141 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg2ei16_v_bf16mf4x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg2.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg2ei16_v_bf16mf4x2(__bf16 *rs1, vuint16mf4_t vs2, + vbfloat16mf4x2_t vs3, size_t vl) { + return __riscv_vsuxseg2ei16_v_bf16mf4x2(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg2ei16_v_bf16mf2x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg2.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg2ei16_v_bf16mf2x2(__bf16 *rs1, vuint16mf2_t vs2, + vbfloat16mf2x2_t vs3, size_t vl) { + return __riscv_vsuxseg2ei16_v_bf16mf2x2(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg2ei16_v_bf16m1x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg2.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg2ei16_v_bf16m1x2(__bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x2_t vs3, size_t vl) { + return __riscv_vsuxseg2ei16_v_bf16m1x2(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg2ei16_v_bf16m2x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg2.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg2ei16_v_bf16m2x2(__bf16 *rs1, vuint16m2_t vs2, + vbfloat16m2x2_t vs3, size_t vl) { + return __riscv_vsuxseg2ei16_v_bf16m2x2(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg2ei16_v_bf16m4x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg2.nxv16bf16.nxv16i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg2ei16_v_bf16m4x2(__bf16 *rs1, vuint16m4_t vs2, + vbfloat16m4x2_t vs3, size_t vl) { + return __riscv_vsuxseg2ei16_v_bf16m4x2(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg2ei16_v_bf16mf4x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg2.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg2ei16_v_bf16mf4x2_m(vbool64_t vm, __bf16 *rs1, + vuint16mf4_t vs2, vbfloat16mf4x2_t vs3, + size_t vl) { + return __riscv_vsuxseg2ei16_v_bf16mf4x2_m(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg2ei16_v_bf16mf2x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg2.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg2ei16_v_bf16mf2x2_m(vbool32_t vm, __bf16 *rs1, + vuint16mf2_t vs2, vbfloat16mf2x2_t vs3, + size_t vl) { + return __riscv_vsuxseg2ei16_v_bf16mf2x2_m(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg2ei16_v_bf16m1x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg2.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg2ei16_v_bf16m1x2_m(vbool16_t vm, __bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x2_t vs3, size_t vl) { + return __riscv_vsuxseg2ei16_v_bf16m1x2_m(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg2ei16_v_bf16m2x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg2.mask.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg2ei16_v_bf16m2x2_m(vbool8_t vm, __bf16 *rs1, vuint16m2_t vs2, + vbfloat16m2x2_t vs3, size_t vl) { + return __riscv_vsuxseg2ei16_v_bf16m2x2_m(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg2ei16_v_bf16m4x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg2.mask.nxv16bf16.nxv16i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg2ei16_v_bf16m4x2_m(vbool4_t vm, __bf16 *rs1, vuint16m4_t vs2, + vbfloat16m4x2_t vs3, size_t vl) { + return __riscv_vsuxseg2ei16_v_bf16m4x2_m(vm, rs1, vs2, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsuxseg3ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsuxseg3ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..9c482373689563a731cb725e845532cf8b2e0c15 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsuxseg3ei16.c @@ -0,0 +1,123 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg3ei16_v_bf16mf4x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg3.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg3ei16_v_bf16mf4x3(__bf16 *rs1, vuint16mf4_t vs2, + vbfloat16mf4x3_t vs3, size_t vl) { + return __riscv_vsuxseg3ei16_v_bf16mf4x3(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg3ei16_v_bf16mf2x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg3.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg3ei16_v_bf16mf2x3(__bf16 *rs1, vuint16mf2_t vs2, + vbfloat16mf2x3_t vs3, size_t vl) { + return __riscv_vsuxseg3ei16_v_bf16mf2x3(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg3ei16_v_bf16m1x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg3.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg3ei16_v_bf16m1x3(__bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x3_t vs3, size_t vl) { + return __riscv_vsuxseg3ei16_v_bf16m1x3(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg3ei16_v_bf16m2x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg3.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg3ei16_v_bf16m2x3(__bf16 *rs1, vuint16m2_t vs2, + vbfloat16m2x3_t vs3, size_t vl) { + return __riscv_vsuxseg3ei16_v_bf16m2x3(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg3ei16_v_bf16mf4x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg3.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg3ei16_v_bf16mf4x3_m(vbool64_t vm, __bf16 *rs1, + vuint16mf4_t vs2, vbfloat16mf4x3_t vs3, + size_t vl) { + return __riscv_vsuxseg3ei16_v_bf16mf4x3_m(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg3ei16_v_bf16mf2x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg3.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg3ei16_v_bf16mf2x3_m(vbool32_t vm, __bf16 *rs1, + vuint16mf2_t vs2, vbfloat16mf2x3_t vs3, + size_t vl) { + return __riscv_vsuxseg3ei16_v_bf16mf2x3_m(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg3ei16_v_bf16m1x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg3.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg3ei16_v_bf16m1x3_m(vbool16_t vm, __bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x3_t vs3, size_t vl) { + return __riscv_vsuxseg3ei16_v_bf16m1x3_m(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg3ei16_v_bf16m2x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg3.mask.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg3ei16_v_bf16m2x3_m(vbool8_t vm, __bf16 *rs1, vuint16m2_t vs2, + vbfloat16m2x3_t vs3, size_t vl) { + return __riscv_vsuxseg3ei16_v_bf16m2x3_m(vm, rs1, vs2, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsuxseg4ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsuxseg4ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..63b13ec6a32ffce9af1c744a9b0fab2f51c09931 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsuxseg4ei16.c @@ -0,0 +1,131 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg4ei16_v_bf16mf4x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg4.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg4ei16_v_bf16mf4x4(__bf16 *rs1, vuint16mf4_t vs2, + vbfloat16mf4x4_t vs3, size_t vl) { + return __riscv_vsuxseg4ei16_v_bf16mf4x4(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg4ei16_v_bf16mf2x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg4.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg4ei16_v_bf16mf2x4(__bf16 *rs1, vuint16mf2_t vs2, + vbfloat16mf2x4_t vs3, size_t vl) { + return __riscv_vsuxseg4ei16_v_bf16mf2x4(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg4ei16_v_bf16m1x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg4.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg4ei16_v_bf16m1x4(__bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x4_t vs3, size_t vl) { + return __riscv_vsuxseg4ei16_v_bf16m1x4(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg4ei16_v_bf16m2x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg4.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg4ei16_v_bf16m2x4(__bf16 *rs1, vuint16m2_t vs2, + vbfloat16m2x4_t vs3, size_t vl) { + return __riscv_vsuxseg4ei16_v_bf16m2x4(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg4ei16_v_bf16mf4x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg4.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg4ei16_v_bf16mf4x4_m(vbool64_t vm, __bf16 *rs1, + vuint16mf4_t vs2, vbfloat16mf4x4_t vs3, + size_t vl) { + return __riscv_vsuxseg4ei16_v_bf16mf4x4_m(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg4ei16_v_bf16mf2x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg4.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg4ei16_v_bf16mf2x4_m(vbool32_t vm, __bf16 *rs1, + vuint16mf2_t vs2, vbfloat16mf2x4_t vs3, + size_t vl) { + return __riscv_vsuxseg4ei16_v_bf16mf2x4_m(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg4ei16_v_bf16m1x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg4.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg4ei16_v_bf16m1x4_m(vbool16_t vm, __bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x4_t vs3, size_t vl) { + return __riscv_vsuxseg4ei16_v_bf16m1x4_m(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg4ei16_v_bf16m2x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg4.mask.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg4ei16_v_bf16m2x4_m(vbool8_t vm, __bf16 *rs1, vuint16m2_t vs2, + vbfloat16m2x4_t vs3, size_t vl) { + return __riscv_vsuxseg4ei16_v_bf16m2x4_m(vm, rs1, vs2, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsuxseg5ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsuxseg5ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..4d93f05b0a101827b4cb9ff508b47e529e4ffdfa --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsuxseg5ei16.c @@ -0,0 +1,107 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg5ei16_v_bf16mf4x5( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg5.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg5ei16_v_bf16mf4x5(__bf16 *rs1, vuint16mf4_t vs2, + vbfloat16mf4x5_t vs3, size_t vl) { + return __riscv_vsuxseg5ei16_v_bf16mf4x5(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg5ei16_v_bf16mf2x5( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg5.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg5ei16_v_bf16mf2x5(__bf16 *rs1, vuint16mf2_t vs2, + vbfloat16mf2x5_t vs3, size_t vl) { + return __riscv_vsuxseg5ei16_v_bf16mf2x5(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg5ei16_v_bf16m1x5( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg5.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg5ei16_v_bf16m1x5(__bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x5_t vs3, size_t vl) { + return __riscv_vsuxseg5ei16_v_bf16m1x5(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg5ei16_v_bf16mf4x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg5.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg5ei16_v_bf16mf4x5_m(vbool64_t vm, __bf16 *rs1, + vuint16mf4_t vs2, vbfloat16mf4x5_t vs3, + size_t vl) { + return __riscv_vsuxseg5ei16_v_bf16mf4x5_m(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg5ei16_v_bf16mf2x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg5.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg5ei16_v_bf16mf2x5_m(vbool32_t vm, __bf16 *rs1, + vuint16mf2_t vs2, vbfloat16mf2x5_t vs3, + size_t vl) { + return __riscv_vsuxseg5ei16_v_bf16mf2x5_m(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg5ei16_v_bf16m1x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg5.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg5ei16_v_bf16m1x5_m(vbool16_t vm, __bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x5_t vs3, size_t vl) { + return __riscv_vsuxseg5ei16_v_bf16m1x5_m(vm, rs1, vs2, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsuxseg6ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsuxseg6ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..0b6ef26c3751f08c779c26157b6e8fff74da32c3 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsuxseg6ei16.c @@ -0,0 +1,113 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg6ei16_v_bf16mf4x6( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg6.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg6ei16_v_bf16mf4x6(__bf16 *rs1, vuint16mf4_t vs2, + vbfloat16mf4x6_t vs3, size_t vl) { + return __riscv_vsuxseg6ei16_v_bf16mf4x6(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg6ei16_v_bf16mf2x6( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg6.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg6ei16_v_bf16mf2x6(__bf16 *rs1, vuint16mf2_t vs2, + vbfloat16mf2x6_t vs3, size_t vl) { + return __riscv_vsuxseg6ei16_v_bf16mf2x6(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg6ei16_v_bf16m1x6( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg6.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg6ei16_v_bf16m1x6(__bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x6_t vs3, size_t vl) { + return __riscv_vsuxseg6ei16_v_bf16m1x6(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg6ei16_v_bf16mf4x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg6.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg6ei16_v_bf16mf4x6_m(vbool64_t vm, __bf16 *rs1, + vuint16mf4_t vs2, vbfloat16mf4x6_t vs3, + size_t vl) { + return __riscv_vsuxseg6ei16_v_bf16mf4x6_m(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg6ei16_v_bf16mf2x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg6.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg6ei16_v_bf16mf2x6_m(vbool32_t vm, __bf16 *rs1, + vuint16mf2_t vs2, vbfloat16mf2x6_t vs3, + size_t vl) { + return __riscv_vsuxseg6ei16_v_bf16mf2x6_m(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg6ei16_v_bf16m1x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg6.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg6ei16_v_bf16m1x6_m(vbool16_t vm, __bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x6_t vs3, size_t vl) { + return __riscv_vsuxseg6ei16_v_bf16m1x6_m(vm, rs1, vs2, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsuxseg7ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsuxseg7ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..10debde6ef60837de98c830b354bb6f4642e94c5 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsuxseg7ei16.c @@ -0,0 +1,119 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg7ei16_v_bf16mf4x7( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg7.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg7ei16_v_bf16mf4x7(__bf16 *rs1, vuint16mf4_t vs2, + vbfloat16mf4x7_t vs3, size_t vl) { + return __riscv_vsuxseg7ei16_v_bf16mf4x7(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg7ei16_v_bf16mf2x7( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg7.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg7ei16_v_bf16mf2x7(__bf16 *rs1, vuint16mf2_t vs2, + vbfloat16mf2x7_t vs3, size_t vl) { + return __riscv_vsuxseg7ei16_v_bf16mf2x7(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg7ei16_v_bf16m1x7( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg7.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg7ei16_v_bf16m1x7(__bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x7_t vs3, size_t vl) { + return __riscv_vsuxseg7ei16_v_bf16m1x7(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg7ei16_v_bf16mf4x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg7.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg7ei16_v_bf16mf4x7_m(vbool64_t vm, __bf16 *rs1, + vuint16mf4_t vs2, vbfloat16mf4x7_t vs3, + size_t vl) { + return __riscv_vsuxseg7ei16_v_bf16mf4x7_m(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg7ei16_v_bf16mf2x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg7.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg7ei16_v_bf16mf2x7_m(vbool32_t vm, __bf16 *rs1, + vuint16mf2_t vs2, vbfloat16mf2x7_t vs3, + size_t vl) { + return __riscv_vsuxseg7ei16_v_bf16mf2x7_m(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg7ei16_v_bf16m1x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg7.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg7ei16_v_bf16m1x7_m(vbool16_t vm, __bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x7_t vs3, size_t vl) { + return __riscv_vsuxseg7ei16_v_bf16m1x7_m(vm, rs1, vs2, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsuxseg8ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsuxseg8ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..175c7c478173b6fb0e278a3a5a1d8ce4f81cbe0e --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vsuxseg8ei16.c @@ -0,0 +1,125 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg8ei16_v_bf16mf4x8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VS3]], 7 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg8.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg8ei16_v_bf16mf4x8(__bf16 *rs1, vuint16mf4_t vs2, + vbfloat16mf4x8_t vs3, size_t vl) { + return __riscv_vsuxseg8ei16_v_bf16mf4x8(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg8ei16_v_bf16mf2x8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VS3]], 7 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg8.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg8ei16_v_bf16mf2x8(__bf16 *rs1, vuint16mf2_t vs2, + vbfloat16mf2x8_t vs3, size_t vl) { + return __riscv_vsuxseg8ei16_v_bf16mf2x8(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg8ei16_v_bf16m1x8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VS3]], 7 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg8.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg8ei16_v_bf16m1x8(__bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x8_t vs3, size_t vl) { + return __riscv_vsuxseg8ei16_v_bf16m1x8(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg8ei16_v_bf16mf4x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VS3]], 7 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg8.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg8ei16_v_bf16mf4x8_m(vbool64_t vm, __bf16 *rs1, + vuint16mf4_t vs2, vbfloat16mf4x8_t vs3, + size_t vl) { + return __riscv_vsuxseg8ei16_v_bf16mf4x8_m(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg8ei16_v_bf16mf2x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VS3]], 7 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg8.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg8ei16_v_bf16mf2x8_m(vbool32_t vm, __bf16 *rs1, + vuint16mf2_t vs2, vbfloat16mf2x8_t vs3, + size_t vl) { + return __riscv_vsuxseg8ei16_v_bf16mf2x8_m(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg8ei16_v_bf16m1x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VS3]], 7 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg8.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg8ei16_v_bf16m1x8_m(vbool16_t vm, __bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x8_t vs3, size_t vl) { + return __riscv_vsuxseg8ei16_v_bf16m1x8_m(vm, rs1, vs2, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vundefined.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vundefined.c new file mode 100644 index 0000000000000000000000000000000000000000..5a2c8731b9551cd5c557e24a37e29a883fab2f30 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/bfloat16/vundefined.c @@ -0,0 +1,280 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local @test_vundefined_bf16mf4( +// CHECK-RV64-SAME: ) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: ret poison +// +vbfloat16mf4_t test_vundefined_bf16mf4() { + return __riscv_vundefined_bf16mf4(); +} + +// CHECK-RV64-LABEL: define dso_local @test_vundefined_bf16mf2( +// CHECK-RV64-SAME: ) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: ret poison +// +vbfloat16mf2_t test_vundefined_bf16mf2() { + return __riscv_vundefined_bf16mf2(); +} + +// CHECK-RV64-LABEL: define dso_local @test_vundefined_bf16m1( +// CHECK-RV64-SAME: ) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: ret poison +// +vbfloat16m1_t test_vundefined_bf16m1() { return __riscv_vundefined_bf16m1(); } + +// CHECK-RV64-LABEL: define dso_local @test_vundefined_bf16m2( +// CHECK-RV64-SAME: ) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: ret poison +// +vbfloat16m2_t test_vundefined_bf16m2() { return __riscv_vundefined_bf16m2(); } + +// CHECK-RV64-LABEL: define dso_local @test_vundefined_bf16m4( +// CHECK-RV64-SAME: ) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: ret poison +// +vbfloat16m4_t test_vundefined_bf16m4() { return __riscv_vundefined_bf16m4(); } + +// CHECK-RV64-LABEL: define dso_local @test_vundefined_bf16m8( +// CHECK-RV64-SAME: ) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: ret poison +// +vbfloat16m8_t test_vundefined_bf16m8() { return __riscv_vundefined_bf16m8(); } + +// CHECK-RV64-LABEL: define dso_local { , } @test_vundefined_bf16mf4x2( +// CHECK-RV64-SAME: ) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: ret { , } poison +// +vbfloat16mf4x2_t test_vundefined_bf16mf4x2() { + return __riscv_vundefined_bf16mf4x2(); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vundefined_bf16mf4x3( +// CHECK-RV64-SAME: ) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: ret { , , } poison +// +vbfloat16mf4x3_t test_vundefined_bf16mf4x3() { + return __riscv_vundefined_bf16mf4x3(); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vundefined_bf16mf4x4( +// CHECK-RV64-SAME: ) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: ret { , , , } poison +// +vbfloat16mf4x4_t test_vundefined_bf16mf4x4() { + return __riscv_vundefined_bf16mf4x4(); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vundefined_bf16mf4x5( +// CHECK-RV64-SAME: ) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: ret { , , , , } poison +// +vbfloat16mf4x5_t test_vundefined_bf16mf4x5() { + return __riscv_vundefined_bf16mf4x5(); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vundefined_bf16mf4x6( +// CHECK-RV64-SAME: ) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: ret { , , , , , } poison +// +vbfloat16mf4x6_t test_vundefined_bf16mf4x6() { + return __riscv_vundefined_bf16mf4x6(); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vundefined_bf16mf4x7( +// CHECK-RV64-SAME: ) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: ret { , , , , , , } poison +// +vbfloat16mf4x7_t test_vundefined_bf16mf4x7() { + return __riscv_vundefined_bf16mf4x7(); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vundefined_bf16mf4x8( +// CHECK-RV64-SAME: ) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: ret { , , , , , , , } poison +// +vbfloat16mf4x8_t test_vundefined_bf16mf4x8() { + return __riscv_vundefined_bf16mf4x8(); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vundefined_bf16mf2x2( +// CHECK-RV64-SAME: ) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: ret { , } poison +// +vbfloat16mf2x2_t test_vundefined_bf16mf2x2() { + return __riscv_vundefined_bf16mf2x2(); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vundefined_bf16mf2x3( +// CHECK-RV64-SAME: ) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: ret { , , } poison +// +vbfloat16mf2x3_t test_vundefined_bf16mf2x3() { + return __riscv_vundefined_bf16mf2x3(); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vundefined_bf16mf2x4( +// CHECK-RV64-SAME: ) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: ret { , , , } poison +// +vbfloat16mf2x4_t test_vundefined_bf16mf2x4() { + return __riscv_vundefined_bf16mf2x4(); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vundefined_bf16mf2x5( +// CHECK-RV64-SAME: ) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: ret { , , , , } poison +// +vbfloat16mf2x5_t test_vundefined_bf16mf2x5() { + return __riscv_vundefined_bf16mf2x5(); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vundefined_bf16mf2x6( +// CHECK-RV64-SAME: ) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: ret { , , , , , } poison +// +vbfloat16mf2x6_t test_vundefined_bf16mf2x6() { + return __riscv_vundefined_bf16mf2x6(); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vundefined_bf16mf2x7( +// CHECK-RV64-SAME: ) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: ret { , , , , , , } poison +// +vbfloat16mf2x7_t test_vundefined_bf16mf2x7() { + return __riscv_vundefined_bf16mf2x7(); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vundefined_bf16mf2x8( +// CHECK-RV64-SAME: ) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: ret { , , , , , , , } poison +// +vbfloat16mf2x8_t test_vundefined_bf16mf2x8() { + return __riscv_vundefined_bf16mf2x8(); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vundefined_bf16m1x2( +// CHECK-RV64-SAME: ) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: ret { , } poison +// +vbfloat16m1x2_t test_vundefined_bf16m1x2() { + return __riscv_vundefined_bf16m1x2(); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vundefined_bf16m1x3( +// CHECK-RV64-SAME: ) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: ret { , , } poison +// +vbfloat16m1x3_t test_vundefined_bf16m1x3() { + return __riscv_vundefined_bf16m1x3(); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vundefined_bf16m1x4( +// CHECK-RV64-SAME: ) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: ret { , , , } poison +// +vbfloat16m1x4_t test_vundefined_bf16m1x4() { + return __riscv_vundefined_bf16m1x4(); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vundefined_bf16m1x5( +// CHECK-RV64-SAME: ) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: ret { , , , , } poison +// +vbfloat16m1x5_t test_vundefined_bf16m1x5() { + return __riscv_vundefined_bf16m1x5(); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vundefined_bf16m1x6( +// CHECK-RV64-SAME: ) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: ret { , , , , , } poison +// +vbfloat16m1x6_t test_vundefined_bf16m1x6() { + return __riscv_vundefined_bf16m1x6(); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vundefined_bf16m1x7( +// CHECK-RV64-SAME: ) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: ret { , , , , , , } poison +// +vbfloat16m1x7_t test_vundefined_bf16m1x7() { + return __riscv_vundefined_bf16m1x7(); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vundefined_bf16m1x8( +// CHECK-RV64-SAME: ) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: ret { , , , , , , , } poison +// +vbfloat16m1x8_t test_vundefined_bf16m1x8() { + return __riscv_vundefined_bf16m1x8(); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vundefined_bf16m2x2( +// CHECK-RV64-SAME: ) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: ret { , } poison +// +vbfloat16m2x2_t test_vundefined_bf16m2x2() { + return __riscv_vundefined_bf16m2x2(); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vundefined_bf16m2x3( +// CHECK-RV64-SAME: ) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: ret { , , } poison +// +vbfloat16m2x3_t test_vundefined_bf16m2x3() { + return __riscv_vundefined_bf16m2x3(); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vundefined_bf16m2x4( +// CHECK-RV64-SAME: ) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: ret { , , , } poison +// +vbfloat16m2x4_t test_vundefined_bf16m2x4() { + return __riscv_vundefined_bf16m2x4(); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vundefined_bf16m4x2( +// CHECK-RV64-SAME: ) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: ret { , } poison +// +vbfloat16m4x2_t test_vundefined_bf16m4x2() { + return __riscv_vundefined_bf16m4x2(); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/vaesdf.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/vaesdf.c index 76a9ddc0d5294651536ec95e1d18cee597f8cec6..3e37ac4b7749976b9bd3d82156a1779e2f31693e 100644 --- a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/vaesdf.c +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/vaesdf.c @@ -206,13 +206,3 @@ vuint32m8_t test_vaesdf_vv_u32m8(vuint32m8_t vd, vuint32m8_t vs2, size_t vl) { return __riscv_vaesdf_vv_u32m8(vd, vs2, vl); } -// CHECK-RV64-LABEL: define dso_local @test_vaesdf_vs_u32m8_u32m8 -// CHECK-RV64-SAME: ( [[VD:%.*]], [[VS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { -// CHECK-RV64-NEXT: entry: -// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vaesdf.vs.nxv16i32.nxv16i32.i64( [[VD]], [[VS2]], i64 [[VL]], i64 3) -// CHECK-RV64-NEXT: ret [[TMP0]] -// -vuint32m8_t test_vaesdf_vs_u32m8_u32m8(vuint32m8_t vd, vuint32m8_t vs2, size_t vl) { - return __riscv_vaesdf_vs_u32m8_u32m8(vd, vs2, vl); -} - diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/vaesdm.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/vaesdm.c index 468c3f18378d3c3dbd4eecb1e49a39ee31aba953..c29c1e983fce6748c0942a2bf03bc5d5cc8f95d3 100644 --- a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/vaesdm.c +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/vaesdm.c @@ -206,13 +206,3 @@ vuint32m8_t test_vaesdm_vv_u32m8(vuint32m8_t vd, vuint32m8_t vs2, size_t vl) { return __riscv_vaesdm_vv_u32m8(vd, vs2, vl); } -// CHECK-RV64-LABEL: define dso_local @test_vaesdm_vs_u32m8_u32m8 -// CHECK-RV64-SAME: ( [[VD:%.*]], [[VS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { -// CHECK-RV64-NEXT: entry: -// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vaesdm.vs.nxv16i32.nxv16i32.i64( [[VD]], [[VS2]], i64 [[VL]], i64 3) -// CHECK-RV64-NEXT: ret [[TMP0]] -// -vuint32m8_t test_vaesdm_vs_u32m8_u32m8(vuint32m8_t vd, vuint32m8_t vs2, size_t vl) { - return __riscv_vaesdm_vs_u32m8_u32m8(vd, vs2, vl); -} - diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/vaesef.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/vaesef.c index bc6a17e4b6f0fba07b5bd53e0100540a59a963b8..7ed9f5c36e98d1acd96c8a890e395388db91c372 100644 --- a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/vaesef.c +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/vaesef.c @@ -206,13 +206,3 @@ vuint32m8_t test_vaesef_vv_u32m8(vuint32m8_t vd, vuint32m8_t vs2, size_t vl) { return __riscv_vaesef_vv_u32m8(vd, vs2, vl); } -// CHECK-RV64-LABEL: define dso_local @test_vaesef_vs_u32m8_u32m8 -// CHECK-RV64-SAME: ( [[VD:%.*]], [[VS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { -// CHECK-RV64-NEXT: entry: -// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vaesef.vs.nxv16i32.nxv16i32.i64( [[VD]], [[VS2]], i64 [[VL]], i64 3) -// CHECK-RV64-NEXT: ret [[TMP0]] -// -vuint32m8_t test_vaesef_vs_u32m8_u32m8(vuint32m8_t vd, vuint32m8_t vs2, size_t vl) { - return __riscv_vaesef_vs_u32m8_u32m8(vd, vs2, vl); -} - diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/vaesem.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/vaesem.c index e0e1662b76f9cb29cde526be865904ab5dc4a7e5..34eec0037491fdbef8af75cf41d59e67685f3d61 100644 --- a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/vaesem.c +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/vaesem.c @@ -206,13 +206,3 @@ vuint32m8_t test_vaesem_vv_u32m8(vuint32m8_t vd, vuint32m8_t vs2, size_t vl) { return __riscv_vaesem_vv_u32m8(vd, vs2, vl); } -// CHECK-RV64-LABEL: define dso_local @test_vaesem_vs_u32m8_u32m8 -// CHECK-RV64-SAME: ( [[VD:%.*]], [[VS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { -// CHECK-RV64-NEXT: entry: -// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vaesem.vs.nxv16i32.nxv16i32.i64( [[VD]], [[VS2]], i64 [[VL]], i64 3) -// CHECK-RV64-NEXT: ret [[TMP0]] -// -vuint32m8_t test_vaesem_vs_u32m8_u32m8(vuint32m8_t vd, vuint32m8_t vs2, size_t vl) { - return __riscv_vaesem_vs_u32m8_u32m8(vd, vs2, vl); -} - diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/vaesz.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/vaesz.c index 0700b60fa639953e9fbeae9553e93341b76d38a4..bfe0b0602717fa9efc12c27aaf7d255154ecad76 100644 --- a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/vaesz.c +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/vaesz.c @@ -156,13 +156,3 @@ vuint32m8_t test_vaesz_vs_u32m4_u32m8(vuint32m8_t vd, vuint32m4_t vs2, size_t vl return __riscv_vaesz_vs_u32m4_u32m8(vd, vs2, vl); } -// CHECK-RV64-LABEL: define dso_local @test_vaesz_vs_u32m8_u32m8 -// CHECK-RV64-SAME: ( [[VD:%.*]], [[VS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { -// CHECK-RV64-NEXT: entry: -// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vaesz.vs.nxv16i32.nxv16i32.i64( [[VD]], [[VS2]], i64 [[VL]], i64 3) -// CHECK-RV64-NEXT: ret [[TMP0]] -// -vuint32m8_t test_vaesz_vs_u32m8_u32m8(vuint32m8_t vd, vuint32m8_t vs2, size_t vl) { - return __riscv_vaesz_vs_u32m8_u32m8(vd, vs2, vl); -} - diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/vsm4r.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/vsm4r.c index f9d855a72d2885c75066ede8c9e8a8761d7d1f68..fe9090225596d45b309cb79fb49ba15602ba4541 100644 --- a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/vsm4r.c +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/non-overloaded/vsm4r.c @@ -206,13 +206,3 @@ vuint32m8_t test_vsm4r_vv_u32m8(vuint32m8_t vd, vuint32m8_t vs2, size_t vl) { return __riscv_vsm4r_vv_u32m8(vd, vs2, vl); } -// CHECK-RV64-LABEL: define dso_local @test_vsm4r_vs_u32m8_u32m8 -// CHECK-RV64-SAME: ( [[VD:%.*]], [[VS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { -// CHECK-RV64-NEXT: entry: -// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vsm4r.vs.nxv16i32.nxv16i32.i64( [[VD]], [[VS2]], i64 [[VL]], i64 3) -// CHECK-RV64-NEXT: ret [[TMP0]] -// -vuint32m8_t test_vsm4r_vs_u32m8_u32m8(vuint32m8_t vd, vuint32m8_t vs2, size_t vl) { - return __riscv_vsm4r_vs_u32m8_u32m8(vd, vs2, vl); -} - diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vget.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vget.c new file mode 100644 index 0000000000000000000000000000000000000000..7f8ddf75156b76e8179907ab383d6fd419efb762 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vget.c @@ -0,0 +1,333 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16m2_bf16m1( +// CHECK-RV64-SAME: [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.extract.nxv4bf16.nxv8bf16( [[SRC]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vget_v_bf16m2_bf16m1(vbfloat16m2_t src, size_t index) { + return __riscv_vget_bf16m1(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16m4_bf16m1( +// CHECK-RV64-SAME: [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.extract.nxv4bf16.nxv16bf16( [[SRC]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vget_v_bf16m4_bf16m1(vbfloat16m4_t src, size_t index) { + return __riscv_vget_bf16m1(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16m8_bf16m1( +// CHECK-RV64-SAME: [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.extract.nxv4bf16.nxv32bf16( [[SRC]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vget_v_bf16m8_bf16m1(vbfloat16m8_t src, size_t index) { + return __riscv_vget_bf16m1(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16m4_bf16m2( +// CHECK-RV64-SAME: [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.extract.nxv8bf16.nxv16bf16( [[SRC]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vget_v_bf16m4_bf16m2(vbfloat16m4_t src, size_t index) { + return __riscv_vget_bf16m2(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16m8_bf16m2( +// CHECK-RV64-SAME: [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.extract.nxv8bf16.nxv32bf16( [[SRC]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vget_v_bf16m8_bf16m2(vbfloat16m8_t src, size_t index) { + return __riscv_vget_bf16m2(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16m8_bf16m4( +// CHECK-RV64-SAME: [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.extract.nxv16bf16.nxv32bf16( [[SRC]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vget_v_bf16m8_bf16m4(vbfloat16m8_t src, size_t index) { + return __riscv_vget_bf16m4(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16mf4x2_bf16mf4( +// CHECK-RV64-SAME: { , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vget_v_bf16mf4x2_bf16mf4(vbfloat16mf4x2_t src, + size_t index) { + return __riscv_vget_bf16mf4(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16mf4x3_bf16mf4( +// CHECK-RV64-SAME: { , , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vget_v_bf16mf4x3_bf16mf4(vbfloat16mf4x3_t src, + size_t index) { + return __riscv_vget_bf16mf4(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16mf4x4_bf16mf4( +// CHECK-RV64-SAME: { , , , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vget_v_bf16mf4x4_bf16mf4(vbfloat16mf4x4_t src, + size_t index) { + return __riscv_vget_bf16mf4(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16mf4x5_bf16mf4( +// CHECK-RV64-SAME: { , , , , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vget_v_bf16mf4x5_bf16mf4(vbfloat16mf4x5_t src, + size_t index) { + return __riscv_vget_bf16mf4(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16mf4x6_bf16mf4( +// CHECK-RV64-SAME: { , , , , , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vget_v_bf16mf4x6_bf16mf4(vbfloat16mf4x6_t src, + size_t index) { + return __riscv_vget_bf16mf4(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16mf4x7_bf16mf4( +// CHECK-RV64-SAME: { , , , , , , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vget_v_bf16mf4x7_bf16mf4(vbfloat16mf4x7_t src, + size_t index) { + return __riscv_vget_bf16mf4(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16mf4x8_bf16mf4( +// CHECK-RV64-SAME: { , , , , , , , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vget_v_bf16mf4x8_bf16mf4(vbfloat16mf4x8_t src, + size_t index) { + return __riscv_vget_bf16mf4(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16mf2x2_bf16mf2( +// CHECK-RV64-SAME: { , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vget_v_bf16mf2x2_bf16mf2(vbfloat16mf2x2_t src, + size_t index) { + return __riscv_vget_bf16mf2(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16mf2x3_bf16mf2( +// CHECK-RV64-SAME: { , , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vget_v_bf16mf2x3_bf16mf2(vbfloat16mf2x3_t src, + size_t index) { + return __riscv_vget_bf16mf2(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16mf2x4_bf16mf2( +// CHECK-RV64-SAME: { , , , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vget_v_bf16mf2x4_bf16mf2(vbfloat16mf2x4_t src, + size_t index) { + return __riscv_vget_bf16mf2(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16mf2x5_bf16mf2( +// CHECK-RV64-SAME: { , , , , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vget_v_bf16mf2x5_bf16mf2(vbfloat16mf2x5_t src, + size_t index) { + return __riscv_vget_bf16mf2(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16mf2x6_bf16mf2( +// CHECK-RV64-SAME: { , , , , , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vget_v_bf16mf2x6_bf16mf2(vbfloat16mf2x6_t src, + size_t index) { + return __riscv_vget_bf16mf2(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16mf2x7_bf16mf2( +// CHECK-RV64-SAME: { , , , , , , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vget_v_bf16mf2x7_bf16mf2(vbfloat16mf2x7_t src, + size_t index) { + return __riscv_vget_bf16mf2(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16mf2x8_bf16mf2( +// CHECK-RV64-SAME: { , , , , , , , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vget_v_bf16mf2x8_bf16mf2(vbfloat16mf2x8_t src, + size_t index) { + return __riscv_vget_bf16mf2(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16m1x2_bf16m1( +// CHECK-RV64-SAME: { , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vget_v_bf16m1x2_bf16m1(vbfloat16m1x2_t src, size_t index) { + return __riscv_vget_bf16m1(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16m1x3_bf16m1( +// CHECK-RV64-SAME: { , , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vget_v_bf16m1x3_bf16m1(vbfloat16m1x3_t src, size_t index) { + return __riscv_vget_bf16m1(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16m1x4_bf16m1( +// CHECK-RV64-SAME: { , , , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vget_v_bf16m1x4_bf16m1(vbfloat16m1x4_t src, size_t index) { + return __riscv_vget_bf16m1(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16m1x5_bf16m1( +// CHECK-RV64-SAME: { , , , , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vget_v_bf16m1x5_bf16m1(vbfloat16m1x5_t src, size_t index) { + return __riscv_vget_bf16m1(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16m1x6_bf16m1( +// CHECK-RV64-SAME: { , , , , , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vget_v_bf16m1x6_bf16m1(vbfloat16m1x6_t src, size_t index) { + return __riscv_vget_bf16m1(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16m1x7_bf16m1( +// CHECK-RV64-SAME: { , , , , , , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vget_v_bf16m1x7_bf16m1(vbfloat16m1x7_t src, size_t index) { + return __riscv_vget_bf16m1(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16m1x8_bf16m1( +// CHECK-RV64-SAME: { , , , , , , , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vget_v_bf16m1x8_bf16m1(vbfloat16m1x8_t src, size_t index) { + return __riscv_vget_bf16m1(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16m2x2_bf16m2( +// CHECK-RV64-SAME: { , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vget_v_bf16m2x2_bf16m2(vbfloat16m2x2_t src, size_t index) { + return __riscv_vget_bf16m2(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16m2x3_bf16m2( +// CHECK-RV64-SAME: { , , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vget_v_bf16m2x3_bf16m2(vbfloat16m2x3_t src, size_t index) { + return __riscv_vget_bf16m2(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16m2x4_bf16m2( +// CHECK-RV64-SAME: { , , , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vget_v_bf16m2x4_bf16m2(vbfloat16m2x4_t src, size_t index) { + return __riscv_vget_bf16m2(src, 0); +} + +// CHECK-RV64-LABEL: define dso_local @test_vget_v_bf16m4x2_bf16m4( +// CHECK-RV64-SAME: { , } [[SRC:%.*]], i64 noundef [[INDEX:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[SRC]], 0 +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vget_v_bf16m4x2_bf16m4(vbfloat16m4x2_t src, size_t index) { + return __riscv_vget_bf16m4(src, 0); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vle16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vle16.c new file mode 100644 index 0000000000000000000000000000000000000000..765e9d8346388f1f1fcc1a6a919594bff17b1053 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vle16.c @@ -0,0 +1,72 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16mf4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.mask.nxv1bf16.i64( poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vle16_v_bf16mf4_m(vbool64_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vle16(vm, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16mf2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.mask.nxv2bf16.i64( poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vle16_v_bf16mf2_m(vbool32_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vle16(vm, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16m1_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.mask.nxv4bf16.i64( poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vle16_v_bf16m1_m(vbool16_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vle16(vm, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16m2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.mask.nxv8bf16.i64( poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vle16_v_bf16m2_m(vbool8_t vm, const __bf16 *rs1, size_t vl) { + return __riscv_vle16(vm, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16m4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.mask.nxv16bf16.i64( poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vle16_v_bf16m4_m(vbool4_t vm, const __bf16 *rs1, size_t vl) { + return __riscv_vle16(vm, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16m8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.mask.nxv32bf16.i64( poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vle16_v_bf16m8_m(vbool2_t vm, const __bf16 *rs1, size_t vl) { + return __riscv_vle16(vm, rs1, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vle16ff.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vle16ff.c new file mode 100644 index 0000000000000000000000000000000000000000..9ef6a091b9d5e3d35e05591c5798b34858a4fa08 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vle16ff.c @@ -0,0 +1,93 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16mf4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.mask.nxv1bf16.i64( poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16mf4_t test_vle16ff_v_bf16mf4_m(vbool64_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vle16ff(vm, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16mf2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.mask.nxv2bf16.i64( poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16mf2_t test_vle16ff_v_bf16mf2_m(vbool32_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vle16ff(vm, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16m1_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.mask.nxv4bf16.i64( poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16m1_t test_vle16ff_v_bf16m1_m(vbool16_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vle16ff(vm, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16m2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.mask.nxv8bf16.i64( poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16m2_t test_vle16ff_v_bf16m2_m(vbool8_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vle16ff(vm, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16m4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.mask.nxv16bf16.i64( poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16m4_t test_vle16ff_v_bf16m4_m(vbool4_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vle16ff(vm, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16m8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.mask.nxv32bf16.i64( poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16m8_t test_vle16ff_v_bf16m8_m(vbool2_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vle16ff(vm, rs1, new_vl, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlmul_ext_v.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlmul_ext_v.c new file mode 100644 index 0000000000000000000000000000000000000000..6a4ef411cfa5a7262b13d95757d78a4d981d090e --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlmul_ext_v.c @@ -0,0 +1,159 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_ext_v_bf16mf4_bf16mf2( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.insert.nxv2bf16.nxv1bf16( poison, [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vlmul_ext_v_bf16mf4_bf16mf2(vbfloat16mf4_t value) { + return __riscv_vlmul_ext_bf16mf2(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_ext_v_bf16mf4_bf16m1( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.insert.nxv4bf16.nxv1bf16( poison, [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vlmul_ext_v_bf16mf4_bf16m1(vbfloat16mf4_t value) { + return __riscv_vlmul_ext_bf16m1(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_ext_v_bf16mf4_bf16m2( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.insert.nxv8bf16.nxv1bf16( poison, [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vlmul_ext_v_bf16mf4_bf16m2(vbfloat16mf4_t value) { + return __riscv_vlmul_ext_bf16m2(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_ext_v_bf16mf4_bf16m4( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.insert.nxv16bf16.nxv1bf16( poison, [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vlmul_ext_v_bf16mf4_bf16m4(vbfloat16mf4_t value) { + return __riscv_vlmul_ext_bf16m4(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_ext_v_bf16mf4_bf16m8( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.insert.nxv32bf16.nxv1bf16( poison, [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vlmul_ext_v_bf16mf4_bf16m8(vbfloat16mf4_t value) { + return __riscv_vlmul_ext_bf16m8(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_ext_v_bf16mf2_bf16m1( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.insert.nxv4bf16.nxv2bf16( poison, [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vlmul_ext_v_bf16mf2_bf16m1(vbfloat16mf2_t value) { + return __riscv_vlmul_ext_bf16m1(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_ext_v_bf16mf2_bf16m2( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.insert.nxv8bf16.nxv2bf16( poison, [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vlmul_ext_v_bf16mf2_bf16m2(vbfloat16mf2_t value) { + return __riscv_vlmul_ext_bf16m2(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_ext_v_bf16mf2_bf16m4( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.insert.nxv16bf16.nxv2bf16( poison, [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vlmul_ext_v_bf16mf2_bf16m4(vbfloat16mf2_t value) { + return __riscv_vlmul_ext_bf16m4(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_ext_v_bf16mf2_bf16m8( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.insert.nxv32bf16.nxv2bf16( poison, [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vlmul_ext_v_bf16mf2_bf16m8(vbfloat16mf2_t value) { + return __riscv_vlmul_ext_bf16m8(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_ext_v_bf16m1_bf16m2( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.insert.nxv8bf16.nxv4bf16( poison, [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vlmul_ext_v_bf16m1_bf16m2(vbfloat16m1_t value) { + return __riscv_vlmul_ext_bf16m2(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_ext_v_bf16m1_bf16m4( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.insert.nxv16bf16.nxv4bf16( poison, [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vlmul_ext_v_bf16m1_bf16m4(vbfloat16m1_t value) { + return __riscv_vlmul_ext_bf16m4(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_ext_v_bf16m1_bf16m8( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.insert.nxv32bf16.nxv4bf16( poison, [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vlmul_ext_v_bf16m1_bf16m8(vbfloat16m1_t value) { + return __riscv_vlmul_ext_bf16m8(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_ext_v_bf16m2_bf16m4( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.insert.nxv16bf16.nxv8bf16( poison, [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vlmul_ext_v_bf16m2_bf16m4(vbfloat16m2_t value) { + return __riscv_vlmul_ext_bf16m4(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_ext_v_bf16m2_bf16m8( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.insert.nxv32bf16.nxv8bf16( poison, [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vlmul_ext_v_bf16m2_bf16m8(vbfloat16m2_t value) { + return __riscv_vlmul_ext_bf16m8(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_ext_v_bf16m4_bf16m8( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.insert.nxv32bf16.nxv16bf16( poison, [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vlmul_ext_v_bf16m4_bf16m8(vbfloat16m4_t value) { + return __riscv_vlmul_ext_bf16m8(value); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlmul_trunc_v.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlmul_trunc_v.c new file mode 100644 index 0000000000000000000000000000000000000000..04ca0ac94259aaae885d952430df53dbbeb2c1be --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlmul_trunc_v.c @@ -0,0 +1,159 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_trunc_v_bf16mf2_bf16mf4( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.extract.nxv1bf16.nxv2bf16( [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vlmul_trunc_v_bf16mf2_bf16mf4(vbfloat16mf2_t value) { + return __riscv_vlmul_trunc_bf16mf4(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_trunc_v_bf16m1_bf16mf4( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.extract.nxv1bf16.nxv4bf16( [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vlmul_trunc_v_bf16m1_bf16mf4(vbfloat16m1_t value) { + return __riscv_vlmul_trunc_bf16mf4(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_trunc_v_bf16m1_bf16mf2( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.extract.nxv2bf16.nxv4bf16( [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vlmul_trunc_v_bf16m1_bf16mf2(vbfloat16m1_t value) { + return __riscv_vlmul_trunc_bf16mf2(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_trunc_v_bf16m2_bf16mf4( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.extract.nxv1bf16.nxv8bf16( [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vlmul_trunc_v_bf16m2_bf16mf4(vbfloat16m2_t value) { + return __riscv_vlmul_trunc_bf16mf4(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_trunc_v_bf16m2_bf16mf2( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.extract.nxv2bf16.nxv8bf16( [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vlmul_trunc_v_bf16m2_bf16mf2(vbfloat16m2_t value) { + return __riscv_vlmul_trunc_bf16mf2(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_trunc_v_bf16m2_bf16m1( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.extract.nxv4bf16.nxv8bf16( [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vlmul_trunc_v_bf16m2_bf16m1(vbfloat16m2_t value) { + return __riscv_vlmul_trunc_bf16m1(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_trunc_v_bf16m4_bf16mf4( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.extract.nxv1bf16.nxv16bf16( [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vlmul_trunc_v_bf16m4_bf16mf4(vbfloat16m4_t value) { + return __riscv_vlmul_trunc_bf16mf4(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_trunc_v_bf16m4_bf16mf2( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.extract.nxv2bf16.nxv16bf16( [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vlmul_trunc_v_bf16m4_bf16mf2(vbfloat16m4_t value) { + return __riscv_vlmul_trunc_bf16mf2(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_trunc_v_bf16m4_bf16m1( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.extract.nxv4bf16.nxv16bf16( [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vlmul_trunc_v_bf16m4_bf16m1(vbfloat16m4_t value) { + return __riscv_vlmul_trunc_bf16m1(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_trunc_v_bf16m4_bf16m2( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.extract.nxv8bf16.nxv16bf16( [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vlmul_trunc_v_bf16m4_bf16m2(vbfloat16m4_t value) { + return __riscv_vlmul_trunc_bf16m2(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_trunc_v_bf16m8_bf16mf4( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.extract.nxv1bf16.nxv32bf16( [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vlmul_trunc_v_bf16m8_bf16mf4(vbfloat16m8_t value) { + return __riscv_vlmul_trunc_bf16mf4(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_trunc_v_bf16m8_bf16mf2( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.extract.nxv2bf16.nxv32bf16( [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vlmul_trunc_v_bf16m8_bf16mf2(vbfloat16m8_t value) { + return __riscv_vlmul_trunc_bf16mf2(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_trunc_v_bf16m8_bf16m1( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.extract.nxv4bf16.nxv32bf16( [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vlmul_trunc_v_bf16m8_bf16m1(vbfloat16m8_t value) { + return __riscv_vlmul_trunc_bf16m1(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_trunc_v_bf16m8_bf16m2( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.extract.nxv8bf16.nxv32bf16( [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vlmul_trunc_v_bf16m8_bf16m2(vbfloat16m8_t value) { + return __riscv_vlmul_trunc_bf16m2(value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlmul_trunc_v_bf16m8_bf16m4( +// CHECK-RV64-SAME: [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.extract.nxv16bf16.nxv32bf16( [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vlmul_trunc_v_bf16m8_bf16m4(vbfloat16m8_t value) { + return __riscv_vlmul_trunc_bf16m4(value); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vloxei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vloxei16.c new file mode 100644 index 0000000000000000000000000000000000000000..f57636a7c74c905ab673e9122fed7a31ff3d4d04 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vloxei16.c @@ -0,0 +1,141 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16mf4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.nxv1bf16.nxv1i16.i64( poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vloxei16_v_bf16mf4(const __bf16 *rs1, vuint16mf4_t rs2, + size_t vl) { + return __riscv_vloxei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16mf2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.nxv2bf16.nxv2i16.i64( poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vloxei16_v_bf16mf2(const __bf16 *rs1, vuint16mf2_t rs2, + size_t vl) { + return __riscv_vloxei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16m1( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.nxv4bf16.nxv4i16.i64( poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vloxei16_v_bf16m1(const __bf16 *rs1, vuint16m1_t rs2, + size_t vl) { + return __riscv_vloxei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16m2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.nxv8bf16.nxv8i16.i64( poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vloxei16_v_bf16m2(const __bf16 *rs1, vuint16m2_t rs2, + size_t vl) { + return __riscv_vloxei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16m4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.nxv16bf16.nxv16i16.i64( poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vloxei16_v_bf16m4(const __bf16 *rs1, vuint16m4_t rs2, + size_t vl) { + return __riscv_vloxei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16m8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.nxv32bf16.nxv32i16.i64( poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vloxei16_v_bf16m8(const __bf16 *rs1, vuint16m8_t rs2, + size_t vl) { + return __riscv_vloxei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16mf4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.mask.nxv1bf16.nxv1i16.i64( poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vloxei16_v_bf16mf4_m(vbool64_t vm, const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxei16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16mf2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.mask.nxv2bf16.nxv2i16.i64( poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vloxei16_v_bf16mf2_m(vbool32_t vm, const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxei16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16m1_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.mask.nxv4bf16.nxv4i16.i64( poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vloxei16_v_bf16m1_m(vbool16_t vm, const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vloxei16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16m2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.mask.nxv8bf16.nxv8i16.i64( poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vloxei16_v_bf16m2_m(vbool8_t vm, const __bf16 *rs1, + vuint16m2_t rs2, size_t vl) { + return __riscv_vloxei16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16m4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.mask.nxv16bf16.nxv16i16.i64( poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vloxei16_v_bf16m4_m(vbool4_t vm, const __bf16 *rs1, + vuint16m4_t rs2, size_t vl) { + return __riscv_vloxei16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16m8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.mask.nxv32bf16.nxv32i16.i64( poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vloxei16_v_bf16m8_m(vbool2_t vm, const __bf16 *rs1, + vuint16m8_t rs2, size_t vl) { + return __riscv_vloxei16(vm, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vloxseg2ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vloxseg2ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..e43a37959da5a4ab70425871ea4a06bd970f9e27 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vloxseg2ei16.c @@ -0,0 +1,121 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16mf4x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vloxseg2.nxv1bf16.nxv1i16.i64( poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16mf4x2_t test_vloxseg2ei16_v_bf16mf4x2(const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg2ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16mf2x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vloxseg2.nxv2bf16.nxv2i16.i64( poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16mf2x2_t test_vloxseg2ei16_v_bf16mf2x2(const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg2ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16m1x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vloxseg2.nxv4bf16.nxv4i16.i64( poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16m1x2_t test_vloxseg2ei16_v_bf16m1x2(const __bf16 *rs1, vuint16m1_t rs2, + size_t vl) { + return __riscv_vloxseg2ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16m2x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vloxseg2.nxv8bf16.nxv8i16.i64( poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16m2x2_t test_vloxseg2ei16_v_bf16m2x2(const __bf16 *rs1, vuint16m2_t rs2, + size_t vl) { + return __riscv_vloxseg2ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16m4x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vloxseg2.nxv16bf16.nxv16i16.i64( poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16m4x2_t test_vloxseg2ei16_v_bf16m4x2(const __bf16 *rs1, vuint16m4_t rs2, + size_t vl) { + return __riscv_vloxseg2ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16mf4x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vloxseg2.mask.nxv1bf16.nxv1i16.i64( poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16mf4x2_t test_vloxseg2ei16_v_bf16mf4x2_m(vbool64_t vm, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg2ei16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16mf2x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vloxseg2.mask.nxv2bf16.nxv2i16.i64( poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16mf2x2_t test_vloxseg2ei16_v_bf16mf2x2_m(vbool32_t vm, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg2ei16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16m1x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vloxseg2.mask.nxv4bf16.nxv4i16.i64( poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16m1x2_t test_vloxseg2ei16_v_bf16m1x2_m(vbool16_t vm, const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg2ei16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16m2x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vloxseg2.mask.nxv8bf16.nxv8i16.i64( poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16m2x2_t test_vloxseg2ei16_v_bf16m2x2_m(vbool8_t vm, const __bf16 *rs1, + vuint16m2_t rs2, size_t vl) { + return __riscv_vloxseg2ei16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16m4x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vloxseg2.mask.nxv16bf16.nxv16i16.i64( poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16m4x2_t test_vloxseg2ei16_v_bf16m4x2_m(vbool4_t vm, const __bf16 *rs1, + vuint16m4_t rs2, size_t vl) { + return __riscv_vloxseg2ei16(vm, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vloxseg3ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vloxseg3ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..52950e897a2fddca3117d838b5fc63cf5a908226 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vloxseg3ei16.c @@ -0,0 +1,99 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vloxseg3ei16_v_bf16mf4x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vloxseg3.nxv1bf16.nxv1i16.i64( poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16mf4x3_t test_vloxseg3ei16_v_bf16mf4x3(const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg3ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vloxseg3ei16_v_bf16mf2x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vloxseg3.nxv2bf16.nxv2i16.i64( poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16mf2x3_t test_vloxseg3ei16_v_bf16mf2x3(const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg3ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vloxseg3ei16_v_bf16m1x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vloxseg3.nxv4bf16.nxv4i16.i64( poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16m1x3_t test_vloxseg3ei16_v_bf16m1x3(const __bf16 *rs1, vuint16m1_t rs2, + size_t vl) { + return __riscv_vloxseg3ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vloxseg3ei16_v_bf16m2x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vloxseg3.nxv8bf16.nxv8i16.i64( poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16m2x3_t test_vloxseg3ei16_v_bf16m2x3(const __bf16 *rs1, vuint16m2_t rs2, + size_t vl) { + return __riscv_vloxseg3ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vloxseg3ei16_v_bf16mf4x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vloxseg3.mask.nxv1bf16.nxv1i16.i64( poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16mf4x3_t test_vloxseg3ei16_v_bf16mf4x3_m(vbool64_t vm, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg3ei16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vloxseg3ei16_v_bf16mf2x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vloxseg3.mask.nxv2bf16.nxv2i16.i64( poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16mf2x3_t test_vloxseg3ei16_v_bf16mf2x3_m(vbool32_t vm, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg3ei16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vloxseg3ei16_v_bf16m1x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vloxseg3.mask.nxv4bf16.nxv4i16.i64( poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16m1x3_t test_vloxseg3ei16_v_bf16m1x3_m(vbool16_t vm, const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg3ei16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vloxseg3ei16_v_bf16m2x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vloxseg3.mask.nxv8bf16.nxv8i16.i64( poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16m2x3_t test_vloxseg3ei16_v_bf16m2x3_m(vbool8_t vm, const __bf16 *rs1, + vuint16m2_t rs2, size_t vl) { + return __riscv_vloxseg3ei16(vm, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vloxseg4ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vloxseg4ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..3351c42c25c171a82433c293619144e4c8b7a028 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vloxseg4ei16.c @@ -0,0 +1,99 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vloxseg4ei16_v_bf16mf4x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vloxseg4.nxv1bf16.nxv1i16.i64( poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16mf4x4_t test_vloxseg4ei16_v_bf16mf4x4(const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg4ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vloxseg4ei16_v_bf16mf2x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vloxseg4.nxv2bf16.nxv2i16.i64( poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16mf2x4_t test_vloxseg4ei16_v_bf16mf2x4(const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg4ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vloxseg4ei16_v_bf16m1x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vloxseg4.nxv4bf16.nxv4i16.i64( poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16m1x4_t test_vloxseg4ei16_v_bf16m1x4(const __bf16 *rs1, vuint16m1_t rs2, + size_t vl) { + return __riscv_vloxseg4ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vloxseg4ei16_v_bf16m2x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vloxseg4.nxv8bf16.nxv8i16.i64( poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16m2x4_t test_vloxseg4ei16_v_bf16m2x4(const __bf16 *rs1, vuint16m2_t rs2, + size_t vl) { + return __riscv_vloxseg4ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vloxseg4ei16_v_bf16mf4x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vloxseg4.mask.nxv1bf16.nxv1i16.i64( poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16mf4x4_t test_vloxseg4ei16_v_bf16mf4x4_m(vbool64_t vm, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg4ei16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vloxseg4ei16_v_bf16mf2x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vloxseg4.mask.nxv2bf16.nxv2i16.i64( poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16mf2x4_t test_vloxseg4ei16_v_bf16mf2x4_m(vbool32_t vm, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg4ei16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vloxseg4ei16_v_bf16m1x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vloxseg4.mask.nxv4bf16.nxv4i16.i64( poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16m1x4_t test_vloxseg4ei16_v_bf16m1x4_m(vbool16_t vm, const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg4ei16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vloxseg4ei16_v_bf16m2x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vloxseg4.mask.nxv8bf16.nxv8i16.i64( poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16m2x4_t test_vloxseg4ei16_v_bf16m2x4_m(vbool8_t vm, const __bf16 *rs1, + vuint16m2_t rs2, size_t vl) { + return __riscv_vloxseg4ei16(vm, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vloxseg5ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vloxseg5ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..4651c0ecad853cfd5e8f583e7f91036a1557992d --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vloxseg5ei16.c @@ -0,0 +1,77 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vloxseg5ei16_v_bf16mf4x5( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , } @llvm.riscv.vloxseg5.nxv1bf16.nxv1i16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP0]] +// +vbfloat16mf4x5_t test_vloxseg5ei16_v_bf16mf4x5(const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg5ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vloxseg5ei16_v_bf16mf2x5( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , } @llvm.riscv.vloxseg5.nxv2bf16.nxv2i16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP0]] +// +vbfloat16mf2x5_t test_vloxseg5ei16_v_bf16mf2x5(const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg5ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vloxseg5ei16_v_bf16m1x5( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , } @llvm.riscv.vloxseg5.nxv4bf16.nxv4i16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP0]] +// +vbfloat16m1x5_t test_vloxseg5ei16_v_bf16m1x5(const __bf16 *rs1, vuint16m1_t rs2, + size_t vl) { + return __riscv_vloxseg5ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vloxseg5ei16_v_bf16mf4x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , } @llvm.riscv.vloxseg5.mask.nxv1bf16.nxv1i16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP0]] +// +vbfloat16mf4x5_t test_vloxseg5ei16_v_bf16mf4x5_m(vbool64_t vm, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg5ei16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vloxseg5ei16_v_bf16mf2x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , } @llvm.riscv.vloxseg5.mask.nxv2bf16.nxv2i16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP0]] +// +vbfloat16mf2x5_t test_vloxseg5ei16_v_bf16mf2x5_m(vbool32_t vm, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg5ei16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vloxseg5ei16_v_bf16m1x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , } @llvm.riscv.vloxseg5.mask.nxv4bf16.nxv4i16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP0]] +// +vbfloat16m1x5_t test_vloxseg5ei16_v_bf16m1x5_m(vbool16_t vm, const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg5ei16(vm, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vloxseg6ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vloxseg6ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..c70b924c5cab75fc96cf879a6483c60baf38efbc --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vloxseg6ei16.c @@ -0,0 +1,77 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vloxseg6ei16_v_bf16mf4x6( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , } @llvm.riscv.vloxseg6.nxv1bf16.nxv1i16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP0]] +// +vbfloat16mf4x6_t test_vloxseg6ei16_v_bf16mf4x6(const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg6ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vloxseg6ei16_v_bf16mf2x6( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , } @llvm.riscv.vloxseg6.nxv2bf16.nxv2i16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP0]] +// +vbfloat16mf2x6_t test_vloxseg6ei16_v_bf16mf2x6(const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg6ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vloxseg6ei16_v_bf16m1x6( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , } @llvm.riscv.vloxseg6.nxv4bf16.nxv4i16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP0]] +// +vbfloat16m1x6_t test_vloxseg6ei16_v_bf16m1x6(const __bf16 *rs1, vuint16m1_t rs2, + size_t vl) { + return __riscv_vloxseg6ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vloxseg6ei16_v_bf16mf4x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , } @llvm.riscv.vloxseg6.mask.nxv1bf16.nxv1i16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP0]] +// +vbfloat16mf4x6_t test_vloxseg6ei16_v_bf16mf4x6_m(vbool64_t vm, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg6ei16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vloxseg6ei16_v_bf16mf2x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , } @llvm.riscv.vloxseg6.mask.nxv2bf16.nxv2i16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP0]] +// +vbfloat16mf2x6_t test_vloxseg6ei16_v_bf16mf2x6_m(vbool32_t vm, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg6ei16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vloxseg6ei16_v_bf16m1x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , } @llvm.riscv.vloxseg6.mask.nxv4bf16.nxv4i16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP0]] +// +vbfloat16m1x6_t test_vloxseg6ei16_v_bf16m1x6_m(vbool16_t vm, const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg6ei16(vm, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vloxseg7ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vloxseg7ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..985b0053362f445690911b5b259d5e5e0c96d68f --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vloxseg7ei16.c @@ -0,0 +1,77 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vloxseg7ei16_v_bf16mf4x7( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , } @llvm.riscv.vloxseg7.nxv1bf16.nxv1i16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP0]] +// +vbfloat16mf4x7_t test_vloxseg7ei16_v_bf16mf4x7(const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg7ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vloxseg7ei16_v_bf16mf2x7( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , } @llvm.riscv.vloxseg7.nxv2bf16.nxv2i16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP0]] +// +vbfloat16mf2x7_t test_vloxseg7ei16_v_bf16mf2x7(const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg7ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vloxseg7ei16_v_bf16m1x7( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , } @llvm.riscv.vloxseg7.nxv4bf16.nxv4i16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP0]] +// +vbfloat16m1x7_t test_vloxseg7ei16_v_bf16m1x7(const __bf16 *rs1, vuint16m1_t rs2, + size_t vl) { + return __riscv_vloxseg7ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vloxseg7ei16_v_bf16mf4x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , } @llvm.riscv.vloxseg7.mask.nxv1bf16.nxv1i16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP0]] +// +vbfloat16mf4x7_t test_vloxseg7ei16_v_bf16mf4x7_m(vbool64_t vm, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg7ei16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vloxseg7ei16_v_bf16mf2x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , } @llvm.riscv.vloxseg7.mask.nxv2bf16.nxv2i16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP0]] +// +vbfloat16mf2x7_t test_vloxseg7ei16_v_bf16mf2x7_m(vbool32_t vm, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg7ei16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vloxseg7ei16_v_bf16m1x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , } @llvm.riscv.vloxseg7.mask.nxv4bf16.nxv4i16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP0]] +// +vbfloat16m1x7_t test_vloxseg7ei16_v_bf16m1x7_m(vbool16_t vm, const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg7ei16(vm, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vloxseg8ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vloxseg8ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..413773b1657a29e6ef3103ff7619863861e7cf1b --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vloxseg8ei16.c @@ -0,0 +1,77 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vloxseg8ei16_v_bf16mf4x8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , } @llvm.riscv.vloxseg8.nxv1bf16.nxv1i16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP0]] +// +vbfloat16mf4x8_t test_vloxseg8ei16_v_bf16mf4x8(const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg8ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vloxseg8ei16_v_bf16mf2x8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , } @llvm.riscv.vloxseg8.nxv2bf16.nxv2i16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP0]] +// +vbfloat16mf2x8_t test_vloxseg8ei16_v_bf16mf2x8(const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg8ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vloxseg8ei16_v_bf16m1x8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , } @llvm.riscv.vloxseg8.nxv4bf16.nxv4i16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP0]] +// +vbfloat16m1x8_t test_vloxseg8ei16_v_bf16m1x8(const __bf16 *rs1, vuint16m1_t rs2, + size_t vl) { + return __riscv_vloxseg8ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vloxseg8ei16_v_bf16mf4x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , } @llvm.riscv.vloxseg8.mask.nxv1bf16.nxv1i16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP0]] +// +vbfloat16mf4x8_t test_vloxseg8ei16_v_bf16mf4x8_m(vbool64_t vm, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg8ei16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vloxseg8ei16_v_bf16mf2x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , } @llvm.riscv.vloxseg8.mask.nxv2bf16.nxv2i16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP0]] +// +vbfloat16mf2x8_t test_vloxseg8ei16_v_bf16mf2x8_m(vbool32_t vm, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg8ei16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vloxseg8ei16_v_bf16m1x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , } @llvm.riscv.vloxseg8.mask.nxv4bf16.nxv4i16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP0]] +// +vbfloat16m1x8_t test_vloxseg8ei16_v_bf16m1x8_m(vbool16_t vm, const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg8ei16(vm, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlse16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlse16.c new file mode 100644 index 0000000000000000000000000000000000000000..300100a94371e2141dda000821281998a4ba9451 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlse16.c @@ -0,0 +1,75 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16mf4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.mask.nxv1bf16.i64( poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vlse16_v_bf16mf4_m(vbool64_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlse16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16mf2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.mask.nxv2bf16.i64( poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vlse16_v_bf16mf2_m(vbool32_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlse16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16m1_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.mask.nxv4bf16.i64( poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vlse16_v_bf16m1_m(vbool16_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlse16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16m2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.mask.nxv8bf16.i64( poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vlse16_v_bf16m2_m(vbool8_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlse16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16m4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.mask.nxv16bf16.i64( poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vlse16_v_bf16m4_m(vbool4_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlse16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16m8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.mask.nxv32bf16.i64( poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vlse16_v_bf16m8_m(vbool2_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlse16(vm, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlseg2e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlseg2e16.c new file mode 100644 index 0000000000000000000000000000000000000000..2304cc3a7cddab4af991e692fcca0efaa8ee7b71 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlseg2e16.c @@ -0,0 +1,64 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16mf4x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vlseg2.mask.nxv1bf16.i64( poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16mf4x2_t test_vlseg2e16_v_bf16mf4x2_m(vbool64_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg2e16(vm, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16mf2x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vlseg2.mask.nxv2bf16.i64( poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16mf2x2_t test_vlseg2e16_v_bf16mf2x2_m(vbool32_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg2e16(vm, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16m1x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vlseg2.mask.nxv4bf16.i64( poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16m1x2_t test_vlseg2e16_v_bf16m1x2_m(vbool16_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg2e16(vm, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16m2x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vlseg2.mask.nxv8bf16.i64( poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16m2x2_t test_vlseg2e16_v_bf16m2x2_m(vbool8_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg2e16(vm, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16m4x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vlseg2.mask.nxv16bf16.i64( poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16m4x2_t test_vlseg2e16_v_bf16m4x2_m(vbool4_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg2e16(vm, rs1, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlseg2e16ff.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlseg2e16ff.c new file mode 100644 index 0000000000000000000000000000000000000000..f645d5872c269601d6095fa43a61f3cbbc5983df --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlseg2e16ff.c @@ -0,0 +1,94 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16mf4x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.mask.nxv1bf16.i64( poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP5]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP4]] +// +vbfloat16mf4x2_t test_vlseg2e16ff_v_bf16mf4x2_m(vbool64_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff(vm, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16mf2x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.mask.nxv2bf16.i64( poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP5]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP4]] +// +vbfloat16mf2x2_t test_vlseg2e16ff_v_bf16mf2x2_m(vbool32_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff(vm, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16m1x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.mask.nxv4bf16.i64( poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP5]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP4]] +// +vbfloat16m1x2_t test_vlseg2e16ff_v_bf16m1x2_m(vbool16_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff(vm, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16m2x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.mask.nxv8bf16.i64( poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP5]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP4]] +// +vbfloat16m2x2_t test_vlseg2e16ff_v_bf16m2x2_m(vbool8_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff(vm, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16m4x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.mask.nxv16bf16.i64( poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP5]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP4]] +// +vbfloat16m4x2_t test_vlseg2e16ff_v_bf16m4x2_m(vbool4_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff(vm, rs1, new_vl, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlseg3e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlseg3e16.c new file mode 100644 index 0000000000000000000000000000000000000000..0ce174b2402aa6547ab8ac6bbc13ef80424b07da --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlseg3e16.c @@ -0,0 +1,53 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16_v_bf16mf4x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vlseg3.mask.nxv1bf16.i64( poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16mf4x3_t test_vlseg3e16_v_bf16mf4x3_m(vbool64_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg3e16(vm, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16_v_bf16mf2x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vlseg3.mask.nxv2bf16.i64( poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16mf2x3_t test_vlseg3e16_v_bf16mf2x3_m(vbool32_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg3e16(vm, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16_v_bf16m1x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vlseg3.mask.nxv4bf16.i64( poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16m1x3_t test_vlseg3e16_v_bf16m1x3_m(vbool16_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg3e16(vm, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16_v_bf16m2x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vlseg3.mask.nxv8bf16.i64( poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16m2x3_t test_vlseg3e16_v_bf16m2x3_m(vbool8_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg3e16(vm, rs1, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlseg3e16ff.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlseg3e16ff.c new file mode 100644 index 0000000000000000000000000000000000000000..3545a54199a7ff29abf24aed7739a85a96fddbbb --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlseg3e16ff.c @@ -0,0 +1,85 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16ff_v_bf16mf4x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , i64 } @llvm.riscv.vlseg3ff.mask.nxv1bf16.i64( poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , } [[TMP6]] +// +vbfloat16mf4x3_t test_vlseg3e16ff_v_bf16mf4x3_m(vbool64_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg3e16ff(vm, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16ff_v_bf16mf2x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , i64 } @llvm.riscv.vlseg3ff.mask.nxv2bf16.i64( poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , } [[TMP6]] +// +vbfloat16mf2x3_t test_vlseg3e16ff_v_bf16mf2x3_m(vbool32_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg3e16ff(vm, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16ff_v_bf16m1x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , i64 } @llvm.riscv.vlseg3ff.mask.nxv4bf16.i64( poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , } [[TMP6]] +// +vbfloat16m1x3_t test_vlseg3e16ff_v_bf16m1x3_m(vbool16_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg3e16ff(vm, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16ff_v_bf16m2x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , i64 } @llvm.riscv.vlseg3ff.mask.nxv8bf16.i64( poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , } [[TMP6]] +// +vbfloat16m2x3_t test_vlseg3e16ff_v_bf16m2x3_m(vbool8_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg3e16ff(vm, rs1, new_vl, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlseg4e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlseg4e16.c new file mode 100644 index 0000000000000000000000000000000000000000..c17b1eab338b588be9b8e755b672d27de9506392 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlseg4e16.c @@ -0,0 +1,53 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16_v_bf16mf4x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vlseg4.mask.nxv1bf16.i64( poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16mf4x4_t test_vlseg4e16_v_bf16mf4x4_m(vbool64_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg4e16(vm, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16_v_bf16mf2x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vlseg4.mask.nxv2bf16.i64( poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16mf2x4_t test_vlseg4e16_v_bf16mf2x4_m(vbool32_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg4e16(vm, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16_v_bf16m1x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vlseg4.mask.nxv4bf16.i64( poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16m1x4_t test_vlseg4e16_v_bf16m1x4_m(vbool16_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg4e16(vm, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16_v_bf16m2x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vlseg4.mask.nxv8bf16.i64( poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16m2x4_t test_vlseg4e16_v_bf16m2x4_m(vbool8_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg4e16(vm, rs1, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlseg4e16ff.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlseg4e16ff.c new file mode 100644 index 0000000000000000000000000000000000000000..3aadacfd62eb23f377606e17030e848c6ad2dd46 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlseg4e16ff.c @@ -0,0 +1,93 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16ff_v_bf16mf4x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , i64 } @llvm.riscv.vlseg4ff.mask.nxv1bf16.i64( poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , } [[TMP6]], [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 4 +// CHECK-RV64-NEXT: store i64 [[TMP9]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , } [[TMP8]] +// +vbfloat16mf4x4_t test_vlseg4e16ff_v_bf16mf4x4_m(vbool64_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg4e16ff(vm, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16ff_v_bf16mf2x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , i64 } @llvm.riscv.vlseg4ff.mask.nxv2bf16.i64( poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , } [[TMP6]], [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 4 +// CHECK-RV64-NEXT: store i64 [[TMP9]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , } [[TMP8]] +// +vbfloat16mf2x4_t test_vlseg4e16ff_v_bf16mf2x4_m(vbool32_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg4e16ff(vm, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16ff_v_bf16m1x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , i64 } @llvm.riscv.vlseg4ff.mask.nxv4bf16.i64( poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , } [[TMP6]], [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 4 +// CHECK-RV64-NEXT: store i64 [[TMP9]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , } [[TMP8]] +// +vbfloat16m1x4_t test_vlseg4e16ff_v_bf16m1x4_m(vbool16_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg4e16ff(vm, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16ff_v_bf16m2x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , i64 } @llvm.riscv.vlseg4ff.mask.nxv8bf16.i64( poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , } [[TMP6]], [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , i64 } [[TMP0]], 4 +// CHECK-RV64-NEXT: store i64 [[TMP9]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , } [[TMP8]] +// +vbfloat16m2x4_t test_vlseg4e16ff_v_bf16m2x4_m(vbool8_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg4e16ff(vm, rs1, new_vl, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlseg5e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlseg5e16.c new file mode 100644 index 0000000000000000000000000000000000000000..029916fde042ac22bd76adc2ddcaabdb04718c39 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlseg5e16.c @@ -0,0 +1,42 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16_v_bf16mf4x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , } @llvm.riscv.vlseg5.mask.nxv1bf16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP0]] +// +vbfloat16mf4x5_t test_vlseg5e16_v_bf16mf4x5_m(vbool64_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg5e16(vm, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16_v_bf16mf2x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , } @llvm.riscv.vlseg5.mask.nxv2bf16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP0]] +// +vbfloat16mf2x5_t test_vlseg5e16_v_bf16mf2x5_m(vbool32_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg5e16(vm, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16_v_bf16m1x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , } @llvm.riscv.vlseg5.mask.nxv4bf16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP0]] +// +vbfloat16m1x5_t test_vlseg5e16_v_bf16m1x5_m(vbool16_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg5e16(vm, rs1, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlseg5e16ff.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlseg5e16ff.c new file mode 100644 index 0000000000000000000000000000000000000000..d1c991ed2cee37ac24f15a50546ae691fc0edcc2 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlseg5e16ff.c @@ -0,0 +1,78 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16ff_v_bf16mf4x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , i64 } @llvm.riscv.vlseg5ff.mask.nxv1bf16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , } [[TMP6]], [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 4 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , } [[TMP8]], [[TMP9]], 4 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 5 +// CHECK-RV64-NEXT: store i64 [[TMP11]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , } [[TMP10]] +// +vbfloat16mf4x5_t test_vlseg5e16ff_v_bf16mf4x5_m(vbool64_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg5e16ff(vm, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16ff_v_bf16mf2x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , i64 } @llvm.riscv.vlseg5ff.mask.nxv2bf16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , } [[TMP6]], [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 4 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , } [[TMP8]], [[TMP9]], 4 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 5 +// CHECK-RV64-NEXT: store i64 [[TMP11]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , } [[TMP10]] +// +vbfloat16mf2x5_t test_vlseg5e16ff_v_bf16mf2x5_m(vbool32_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg5e16ff(vm, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16ff_v_bf16m1x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , i64 } @llvm.riscv.vlseg5ff.mask.nxv4bf16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , } [[TMP6]], [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 4 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , } [[TMP8]], [[TMP9]], 4 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , i64 } [[TMP0]], 5 +// CHECK-RV64-NEXT: store i64 [[TMP11]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , } [[TMP10]] +// +vbfloat16m1x5_t test_vlseg5e16ff_v_bf16m1x5_m(vbool16_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg5e16ff(vm, rs1, new_vl, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlseg6e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlseg6e16.c new file mode 100644 index 0000000000000000000000000000000000000000..33ecd52a6e66dce9ee924001f23db58ec7d38ac7 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlseg6e16.c @@ -0,0 +1,42 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16_v_bf16mf4x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , } @llvm.riscv.vlseg6.mask.nxv1bf16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP0]] +// +vbfloat16mf4x6_t test_vlseg6e16_v_bf16mf4x6_m(vbool64_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg6e16(vm, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16_v_bf16mf2x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , } @llvm.riscv.vlseg6.mask.nxv2bf16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP0]] +// +vbfloat16mf2x6_t test_vlseg6e16_v_bf16mf2x6_m(vbool32_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg6e16(vm, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16_v_bf16m1x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , } @llvm.riscv.vlseg6.mask.nxv4bf16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP0]] +// +vbfloat16m1x6_t test_vlseg6e16_v_bf16m1x6_m(vbool16_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg6e16(vm, rs1, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlseg6e16ff.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlseg6e16ff.c new file mode 100644 index 0000000000000000000000000000000000000000..5bc58996f14b7b5e6d22257e7a06b6a58849bebe --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlseg6e16ff.c @@ -0,0 +1,84 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16ff_v_bf16mf4x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , i64 } @llvm.riscv.vlseg6ff.mask.nxv1bf16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , } [[TMP6]], [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 4 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , } [[TMP8]], [[TMP9]], 4 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 5 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , } [[TMP10]], [[TMP11]], 5 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 6 +// CHECK-RV64-NEXT: store i64 [[TMP13]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP12]] +// +vbfloat16mf4x6_t test_vlseg6e16ff_v_bf16mf4x6_m(vbool64_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg6e16ff(vm, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16ff_v_bf16mf2x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , i64 } @llvm.riscv.vlseg6ff.mask.nxv2bf16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , } [[TMP6]], [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 4 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , } [[TMP8]], [[TMP9]], 4 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 5 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , } [[TMP10]], [[TMP11]], 5 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 6 +// CHECK-RV64-NEXT: store i64 [[TMP13]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP12]] +// +vbfloat16mf2x6_t test_vlseg6e16ff_v_bf16mf2x6_m(vbool32_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg6e16ff(vm, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16ff_v_bf16m1x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , i64 } @llvm.riscv.vlseg6ff.mask.nxv4bf16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , } [[TMP6]], [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 4 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , } [[TMP8]], [[TMP9]], 4 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 5 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , } [[TMP10]], [[TMP11]], 5 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , i64 } [[TMP0]], 6 +// CHECK-RV64-NEXT: store i64 [[TMP13]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP12]] +// +vbfloat16m1x6_t test_vlseg6e16ff_v_bf16m1x6_m(vbool16_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg6e16ff(vm, rs1, new_vl, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlseg7e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlseg7e16.c new file mode 100644 index 0000000000000000000000000000000000000000..9804f5edac6132da1099ccb158ba46ed4e95b6f6 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlseg7e16.c @@ -0,0 +1,42 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16_v_bf16mf4x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , } @llvm.riscv.vlseg7.mask.nxv1bf16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP0]] +// +vbfloat16mf4x7_t test_vlseg7e16_v_bf16mf4x7_m(vbool64_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg7e16(vm, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16_v_bf16mf2x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , } @llvm.riscv.vlseg7.mask.nxv2bf16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP0]] +// +vbfloat16mf2x7_t test_vlseg7e16_v_bf16mf2x7_m(vbool32_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg7e16(vm, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16_v_bf16m1x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , } @llvm.riscv.vlseg7.mask.nxv4bf16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP0]] +// +vbfloat16m1x7_t test_vlseg7e16_v_bf16m1x7_m(vbool16_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg7e16(vm, rs1, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlseg7e16ff.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlseg7e16ff.c new file mode 100644 index 0000000000000000000000000000000000000000..646c177806cfe89fa5889ca025b84d76c8ab412b --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlseg7e16ff.c @@ -0,0 +1,90 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16ff_v_bf16mf4x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , i64 } @llvm.riscv.vlseg7ff.mask.nxv1bf16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , , , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , , , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , , , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , , } [[TMP6]], [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 4 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , , } [[TMP8]], [[TMP9]], 4 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 5 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , , } [[TMP10]], [[TMP11]], 5 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 6 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , , } [[TMP12]], [[TMP13]], 6 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 7 +// CHECK-RV64-NEXT: store i64 [[TMP15]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP14]] +// +vbfloat16mf4x7_t test_vlseg7e16ff_v_bf16mf4x7_m(vbool64_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg7e16ff(vm, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16ff_v_bf16mf2x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , i64 } @llvm.riscv.vlseg7ff.mask.nxv2bf16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , , , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , , , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , , , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , , } [[TMP6]], [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 4 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , , } [[TMP8]], [[TMP9]], 4 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 5 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , , } [[TMP10]], [[TMP11]], 5 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 6 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , , } [[TMP12]], [[TMP13]], 6 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 7 +// CHECK-RV64-NEXT: store i64 [[TMP15]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP14]] +// +vbfloat16mf2x7_t test_vlseg7e16ff_v_bf16mf2x7_m(vbool32_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg7e16ff(vm, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16ff_v_bf16m1x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , i64 } @llvm.riscv.vlseg7ff.mask.nxv4bf16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , , , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , , , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , , , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , , } [[TMP6]], [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 4 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , , } [[TMP8]], [[TMP9]], 4 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 5 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , , } [[TMP10]], [[TMP11]], 5 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 6 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , , } [[TMP12]], [[TMP13]], 6 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , , i64 } [[TMP0]], 7 +// CHECK-RV64-NEXT: store i64 [[TMP15]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP14]] +// +vbfloat16m1x7_t test_vlseg7e16ff_v_bf16m1x7_m(vbool16_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg7e16ff(vm, rs1, new_vl, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlseg8e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlseg8e16.c new file mode 100644 index 0000000000000000000000000000000000000000..a969317f246d3fc2556273b6bdc96eb7ff4ead37 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlseg8e16.c @@ -0,0 +1,42 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16_v_bf16mf4x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , } @llvm.riscv.vlseg8.mask.nxv1bf16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP0]] +// +vbfloat16mf4x8_t test_vlseg8e16_v_bf16mf4x8_m(vbool64_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg8e16(vm, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16_v_bf16mf2x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , } @llvm.riscv.vlseg8.mask.nxv2bf16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP0]] +// +vbfloat16mf2x8_t test_vlseg8e16_v_bf16mf2x8_m(vbool32_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg8e16(vm, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16_v_bf16m1x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , } @llvm.riscv.vlseg8.mask.nxv4bf16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP0]] +// +vbfloat16m1x8_t test_vlseg8e16_v_bf16m1x8_m(vbool16_t vm, const __bf16 *rs1, + size_t vl) { + return __riscv_vlseg8e16(vm, rs1, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlseg8e16ff.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlseg8e16ff.c new file mode 100644 index 0000000000000000000000000000000000000000..bec9006b8afc8943a14a347385c3e11f6bde4a47 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlseg8e16ff.c @@ -0,0 +1,96 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16ff_v_bf16mf4x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , , i64 } @llvm.riscv.vlseg8ff.mask.nxv1bf16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , , , , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , , , , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , , , , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , , , } [[TMP6]], [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 4 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , , , } [[TMP8]], [[TMP9]], 4 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 5 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , , , } [[TMP10]], [[TMP11]], 5 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 6 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , , , } [[TMP12]], [[TMP13]], 6 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 7 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , , , } [[TMP14]], [[TMP15]], 7 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 8 +// CHECK-RV64-NEXT: store i64 [[TMP17]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP16]] +// +vbfloat16mf4x8_t test_vlseg8e16ff_v_bf16mf4x8_m(vbool64_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg8e16ff(vm, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16ff_v_bf16mf2x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , , i64 } @llvm.riscv.vlseg8ff.mask.nxv2bf16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , , , , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , , , , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , , , , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , , , } [[TMP6]], [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 4 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , , , } [[TMP8]], [[TMP9]], 4 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 5 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , , , } [[TMP10]], [[TMP11]], 5 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 6 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , , , } [[TMP12]], [[TMP13]], 6 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 7 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , , , } [[TMP14]], [[TMP15]], 7 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 8 +// CHECK-RV64-NEXT: store i64 [[TMP17]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP16]] +// +vbfloat16mf2x8_t test_vlseg8e16ff_v_bf16mf2x8_m(vbool32_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg8e16ff(vm, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16ff_v_bf16m1x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , , i64 } @llvm.riscv.vlseg8ff.mask.nxv4bf16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = insertvalue { , , , , , , , } poison, [[TMP1]], 0 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , , , , , , , } [[TMP2]], [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 2 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , , , , , } [[TMP4]], [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 3 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , , , } [[TMP6]], [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 4 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , , , } [[TMP8]], [[TMP9]], 4 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 5 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , , , } [[TMP10]], [[TMP11]], 5 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 6 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , , , } [[TMP12]], [[TMP13]], 6 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 7 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , , , } [[TMP14]], [[TMP15]], 7 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP0]], 8 +// CHECK-RV64-NEXT: store i64 [[TMP17]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP16]] +// +vbfloat16m1x8_t test_vlseg8e16ff_v_bf16m1x8_m(vbool16_t vm, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg8e16ff(vm, rs1, new_vl, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlsseg2e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlsseg2e16.c new file mode 100644 index 0000000000000000000000000000000000000000..ba5cf455287e055e48cd1e72c89b770157d2360f --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlsseg2e16.c @@ -0,0 +1,64 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16mf4x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vlsseg2.mask.nxv1bf16.i64( poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16mf4x2_t test_vlsseg2e16_v_bf16mf4x2_m(vbool64_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg2e16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16mf2x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vlsseg2.mask.nxv2bf16.i64( poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16mf2x2_t test_vlsseg2e16_v_bf16mf2x2_m(vbool32_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg2e16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16m1x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vlsseg2.mask.nxv4bf16.i64( poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16m1x2_t test_vlsseg2e16_v_bf16m1x2_m(vbool16_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg2e16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16m2x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vlsseg2.mask.nxv8bf16.i64( poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16m2x2_t test_vlsseg2e16_v_bf16m2x2_m(vbool8_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg2e16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16m4x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vlsseg2.mask.nxv16bf16.i64( poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16m4x2_t test_vlsseg2e16_v_bf16m4x2_m(vbool4_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg2e16(vm, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlsseg3e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlsseg3e16.c new file mode 100644 index 0000000000000000000000000000000000000000..0cdad1c52725dc8ba6391059491efc185a7fe6e3 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlsseg3e16.c @@ -0,0 +1,53 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlsseg3e16_v_bf16mf4x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vlsseg3.mask.nxv1bf16.i64( poison, poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16mf4x3_t test_vlsseg3e16_v_bf16mf4x3_m(vbool64_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg3e16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlsseg3e16_v_bf16mf2x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vlsseg3.mask.nxv2bf16.i64( poison, poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16mf2x3_t test_vlsseg3e16_v_bf16mf2x3_m(vbool32_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg3e16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlsseg3e16_v_bf16m1x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vlsseg3.mask.nxv4bf16.i64( poison, poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16m1x3_t test_vlsseg3e16_v_bf16m1x3_m(vbool16_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg3e16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlsseg3e16_v_bf16m2x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vlsseg3.mask.nxv8bf16.i64( poison, poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16m2x3_t test_vlsseg3e16_v_bf16m2x3_m(vbool8_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg3e16(vm, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlsseg4e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlsseg4e16.c new file mode 100644 index 0000000000000000000000000000000000000000..d45e46fd9326f2bee57dfbb584cd41785a68b0a4 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlsseg4e16.c @@ -0,0 +1,53 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlsseg4e16_v_bf16mf4x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vlsseg4.mask.nxv1bf16.i64( poison, poison, poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16mf4x4_t test_vlsseg4e16_v_bf16mf4x4_m(vbool64_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg4e16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlsseg4e16_v_bf16mf2x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vlsseg4.mask.nxv2bf16.i64( poison, poison, poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16mf2x4_t test_vlsseg4e16_v_bf16mf2x4_m(vbool32_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg4e16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlsseg4e16_v_bf16m1x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vlsseg4.mask.nxv4bf16.i64( poison, poison, poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16m1x4_t test_vlsseg4e16_v_bf16m1x4_m(vbool16_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg4e16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlsseg4e16_v_bf16m2x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vlsseg4.mask.nxv8bf16.i64( poison, poison, poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16m2x4_t test_vlsseg4e16_v_bf16m2x4_m(vbool8_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg4e16(vm, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlsseg5e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlsseg5e16.c new file mode 100644 index 0000000000000000000000000000000000000000..d7484e5e6e6dd111db5cef238f7544e5fe2e00b1 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlsseg5e16.c @@ -0,0 +1,42 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlsseg5e16_v_bf16mf4x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , } @llvm.riscv.vlsseg5.mask.nxv1bf16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP0]] +// +vbfloat16mf4x5_t test_vlsseg5e16_v_bf16mf4x5_m(vbool64_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg5e16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlsseg5e16_v_bf16mf2x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , } @llvm.riscv.vlsseg5.mask.nxv2bf16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP0]] +// +vbfloat16mf2x5_t test_vlsseg5e16_v_bf16mf2x5_m(vbool32_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg5e16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlsseg5e16_v_bf16m1x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , } @llvm.riscv.vlsseg5.mask.nxv4bf16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP0]] +// +vbfloat16m1x5_t test_vlsseg5e16_v_bf16m1x5_m(vbool16_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg5e16(vm, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlsseg6e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlsseg6e16.c new file mode 100644 index 0000000000000000000000000000000000000000..9bbdc186f0f59a212b6ae071ab7a08761cc08ae7 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlsseg6e16.c @@ -0,0 +1,42 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlsseg6e16_v_bf16mf4x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , } @llvm.riscv.vlsseg6.mask.nxv1bf16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP0]] +// +vbfloat16mf4x6_t test_vlsseg6e16_v_bf16mf4x6_m(vbool64_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg6e16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlsseg6e16_v_bf16mf2x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , } @llvm.riscv.vlsseg6.mask.nxv2bf16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP0]] +// +vbfloat16mf2x6_t test_vlsseg6e16_v_bf16mf2x6_m(vbool32_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg6e16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlsseg6e16_v_bf16m1x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , } @llvm.riscv.vlsseg6.mask.nxv4bf16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP0]] +// +vbfloat16m1x6_t test_vlsseg6e16_v_bf16m1x6_m(vbool16_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg6e16(vm, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlsseg7e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlsseg7e16.c new file mode 100644 index 0000000000000000000000000000000000000000..364d664525fdfdda38a52f521dd9a0f009e8daab --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlsseg7e16.c @@ -0,0 +1,42 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlsseg7e16_v_bf16mf4x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , } @llvm.riscv.vlsseg7.mask.nxv1bf16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP0]] +// +vbfloat16mf4x7_t test_vlsseg7e16_v_bf16mf4x7_m(vbool64_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg7e16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlsseg7e16_v_bf16mf2x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , } @llvm.riscv.vlsseg7.mask.nxv2bf16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP0]] +// +vbfloat16mf2x7_t test_vlsseg7e16_v_bf16mf2x7_m(vbool32_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg7e16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlsseg7e16_v_bf16m1x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , } @llvm.riscv.vlsseg7.mask.nxv4bf16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP0]] +// +vbfloat16m1x7_t test_vlsseg7e16_v_bf16m1x7_m(vbool16_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg7e16(vm, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlsseg8e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlsseg8e16.c new file mode 100644 index 0000000000000000000000000000000000000000..0d6a391b2ea70c39bb8f5788bbd63978647c6019 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vlsseg8e16.c @@ -0,0 +1,42 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlsseg8e16_v_bf16mf4x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , } @llvm.riscv.vlsseg8.mask.nxv1bf16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP0]] +// +vbfloat16mf4x8_t test_vlsseg8e16_v_bf16mf4x8_m(vbool64_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg8e16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlsseg8e16_v_bf16mf2x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , } @llvm.riscv.vlsseg8.mask.nxv2bf16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP0]] +// +vbfloat16mf2x8_t test_vlsseg8e16_v_bf16mf2x8_m(vbool32_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg8e16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlsseg8e16_v_bf16m1x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , } @llvm.riscv.vlsseg8.mask.nxv4bf16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP0]] +// +vbfloat16m1x8_t test_vlsseg8e16_v_bf16m1x8_m(vbool16_t vm, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg8e16(vm, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vluxei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vluxei16.c new file mode 100644 index 0000000000000000000000000000000000000000..2654821297402e9dc64503a8fb9cbbdf2f07f506 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vluxei16.c @@ -0,0 +1,141 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16mf4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.nxv1bf16.nxv1i16.i64( poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vluxei16_v_bf16mf4(const __bf16 *rs1, vuint16mf4_t rs2, + size_t vl) { + return __riscv_vluxei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16mf2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.nxv2bf16.nxv2i16.i64( poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vluxei16_v_bf16mf2(const __bf16 *rs1, vuint16mf2_t rs2, + size_t vl) { + return __riscv_vluxei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16m1( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.nxv4bf16.nxv4i16.i64( poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vluxei16_v_bf16m1(const __bf16 *rs1, vuint16m1_t rs2, + size_t vl) { + return __riscv_vluxei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16m2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.nxv8bf16.nxv8i16.i64( poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vluxei16_v_bf16m2(const __bf16 *rs1, vuint16m2_t rs2, + size_t vl) { + return __riscv_vluxei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16m4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.nxv16bf16.nxv16i16.i64( poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vluxei16_v_bf16m4(const __bf16 *rs1, vuint16m4_t rs2, + size_t vl) { + return __riscv_vluxei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16m8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.nxv32bf16.nxv32i16.i64( poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vluxei16_v_bf16m8(const __bf16 *rs1, vuint16m8_t rs2, + size_t vl) { + return __riscv_vluxei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16mf4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.mask.nxv1bf16.nxv1i16.i64( poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vluxei16_v_bf16mf4_m(vbool64_t vm, const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxei16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16mf2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.mask.nxv2bf16.nxv2i16.i64( poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vluxei16_v_bf16mf2_m(vbool32_t vm, const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxei16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16m1_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.mask.nxv4bf16.nxv4i16.i64( poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vluxei16_v_bf16m1_m(vbool16_t vm, const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vluxei16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16m2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.mask.nxv8bf16.nxv8i16.i64( poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vluxei16_v_bf16m2_m(vbool8_t vm, const __bf16 *rs1, + vuint16m2_t rs2, size_t vl) { + return __riscv_vluxei16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16m4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.mask.nxv16bf16.nxv16i16.i64( poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vluxei16_v_bf16m4_m(vbool4_t vm, const __bf16 *rs1, + vuint16m4_t rs2, size_t vl) { + return __riscv_vluxei16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16m8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.mask.nxv32bf16.nxv32i16.i64( poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vluxei16_v_bf16m8_m(vbool2_t vm, const __bf16 *rs1, + vuint16m8_t rs2, size_t vl) { + return __riscv_vluxei16(vm, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vluxseg2ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vluxseg2ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..b862aae053dac34a869850b584c367e8c36e9364 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vluxseg2ei16.c @@ -0,0 +1,121 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16mf4x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vluxseg2.nxv1bf16.nxv1i16.i64( poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16mf4x2_t test_vluxseg2ei16_v_bf16mf4x2(const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg2ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16mf2x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vluxseg2.nxv2bf16.nxv2i16.i64( poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16mf2x2_t test_vluxseg2ei16_v_bf16mf2x2(const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg2ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16m1x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vluxseg2.nxv4bf16.nxv4i16.i64( poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16m1x2_t test_vluxseg2ei16_v_bf16m1x2(const __bf16 *rs1, vuint16m1_t rs2, + size_t vl) { + return __riscv_vluxseg2ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16m2x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vluxseg2.nxv8bf16.nxv8i16.i64( poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16m2x2_t test_vluxseg2ei16_v_bf16m2x2(const __bf16 *rs1, vuint16m2_t rs2, + size_t vl) { + return __riscv_vluxseg2ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16m4x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vluxseg2.nxv16bf16.nxv16i16.i64( poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16m4x2_t test_vluxseg2ei16_v_bf16m4x2(const __bf16 *rs1, vuint16m4_t rs2, + size_t vl) { + return __riscv_vluxseg2ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16mf4x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vluxseg2.mask.nxv1bf16.nxv1i16.i64( poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16mf4x2_t test_vluxseg2ei16_v_bf16mf4x2_m(vbool64_t vm, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg2ei16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16mf2x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vluxseg2.mask.nxv2bf16.nxv2i16.i64( poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16mf2x2_t test_vluxseg2ei16_v_bf16mf2x2_m(vbool32_t vm, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg2ei16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16m1x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vluxseg2.mask.nxv4bf16.nxv4i16.i64( poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16m1x2_t test_vluxseg2ei16_v_bf16m1x2_m(vbool16_t vm, const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg2ei16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16m2x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vluxseg2.mask.nxv8bf16.nxv8i16.i64( poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16m2x2_t test_vluxseg2ei16_v_bf16m2x2_m(vbool8_t vm, const __bf16 *rs1, + vuint16m2_t rs2, size_t vl) { + return __riscv_vluxseg2ei16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16m4x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , } @llvm.riscv.vluxseg2.mask.nxv16bf16.nxv16i16.i64( poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16m4x2_t test_vluxseg2ei16_v_bf16m4x2_m(vbool4_t vm, const __bf16 *rs1, + vuint16m4_t rs2, size_t vl) { + return __riscv_vluxseg2ei16(vm, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vluxseg3ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vluxseg3ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..372523aebc995c02a902c481234d921b2d925320 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vluxseg3ei16.c @@ -0,0 +1,99 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vluxseg3ei16_v_bf16mf4x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vluxseg3.nxv1bf16.nxv1i16.i64( poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16mf4x3_t test_vluxseg3ei16_v_bf16mf4x3(const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg3ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vluxseg3ei16_v_bf16mf2x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vluxseg3.nxv2bf16.nxv2i16.i64( poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16mf2x3_t test_vluxseg3ei16_v_bf16mf2x3(const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg3ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vluxseg3ei16_v_bf16m1x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vluxseg3.nxv4bf16.nxv4i16.i64( poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16m1x3_t test_vluxseg3ei16_v_bf16m1x3(const __bf16 *rs1, vuint16m1_t rs2, + size_t vl) { + return __riscv_vluxseg3ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vluxseg3ei16_v_bf16m2x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vluxseg3.nxv8bf16.nxv8i16.i64( poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16m2x3_t test_vluxseg3ei16_v_bf16m2x3(const __bf16 *rs1, vuint16m2_t rs2, + size_t vl) { + return __riscv_vluxseg3ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vluxseg3ei16_v_bf16mf4x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vluxseg3.mask.nxv1bf16.nxv1i16.i64( poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16mf4x3_t test_vluxseg3ei16_v_bf16mf4x3_m(vbool64_t vm, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg3ei16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vluxseg3ei16_v_bf16mf2x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vluxseg3.mask.nxv2bf16.nxv2i16.i64( poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16mf2x3_t test_vluxseg3ei16_v_bf16mf2x3_m(vbool32_t vm, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg3ei16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vluxseg3ei16_v_bf16m1x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vluxseg3.mask.nxv4bf16.nxv4i16.i64( poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16m1x3_t test_vluxseg3ei16_v_bf16m1x3_m(vbool16_t vm, const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg3ei16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vluxseg3ei16_v_bf16m2x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , } @llvm.riscv.vluxseg3.mask.nxv8bf16.nxv8i16.i64( poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16m2x3_t test_vluxseg3ei16_v_bf16m2x3_m(vbool8_t vm, const __bf16 *rs1, + vuint16m2_t rs2, size_t vl) { + return __riscv_vluxseg3ei16(vm, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vluxseg4ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vluxseg4ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..dda3615cd2042292440e7d4f86b33012c4179954 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vluxseg4ei16.c @@ -0,0 +1,99 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vluxseg4ei16_v_bf16mf4x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vluxseg4.nxv1bf16.nxv1i16.i64( poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16mf4x4_t test_vluxseg4ei16_v_bf16mf4x4(const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg4ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vluxseg4ei16_v_bf16mf2x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vluxseg4.nxv2bf16.nxv2i16.i64( poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16mf2x4_t test_vluxseg4ei16_v_bf16mf2x4(const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg4ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vluxseg4ei16_v_bf16m1x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vluxseg4.nxv4bf16.nxv4i16.i64( poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16m1x4_t test_vluxseg4ei16_v_bf16m1x4(const __bf16 *rs1, vuint16m1_t rs2, + size_t vl) { + return __riscv_vluxseg4ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vluxseg4ei16_v_bf16m2x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vluxseg4.nxv8bf16.nxv8i16.i64( poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16m2x4_t test_vluxseg4ei16_v_bf16m2x4(const __bf16 *rs1, vuint16m2_t rs2, + size_t vl) { + return __riscv_vluxseg4ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vluxseg4ei16_v_bf16mf4x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vluxseg4.mask.nxv1bf16.nxv1i16.i64( poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16mf4x4_t test_vluxseg4ei16_v_bf16mf4x4_m(vbool64_t vm, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg4ei16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vluxseg4ei16_v_bf16mf2x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vluxseg4.mask.nxv2bf16.nxv2i16.i64( poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16mf2x4_t test_vluxseg4ei16_v_bf16mf2x4_m(vbool32_t vm, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg4ei16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vluxseg4ei16_v_bf16m1x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vluxseg4.mask.nxv4bf16.nxv4i16.i64( poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16m1x4_t test_vluxseg4ei16_v_bf16m1x4_m(vbool16_t vm, const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg4ei16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vluxseg4ei16_v_bf16m2x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , } @llvm.riscv.vluxseg4.mask.nxv8bf16.nxv8i16.i64( poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16m2x4_t test_vluxseg4ei16_v_bf16m2x4_m(vbool8_t vm, const __bf16 *rs1, + vuint16m2_t rs2, size_t vl) { + return __riscv_vluxseg4ei16(vm, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vluxseg5ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vluxseg5ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..52dbe05328d84b02c49733bc979c3198dc9d68ad --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vluxseg5ei16.c @@ -0,0 +1,77 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vluxseg5ei16_v_bf16mf4x5( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , } @llvm.riscv.vluxseg5.nxv1bf16.nxv1i16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP0]] +// +vbfloat16mf4x5_t test_vluxseg5ei16_v_bf16mf4x5(const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg5ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vluxseg5ei16_v_bf16mf2x5( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , } @llvm.riscv.vluxseg5.nxv2bf16.nxv2i16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP0]] +// +vbfloat16mf2x5_t test_vluxseg5ei16_v_bf16mf2x5(const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg5ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vluxseg5ei16_v_bf16m1x5( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , } @llvm.riscv.vluxseg5.nxv4bf16.nxv4i16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP0]] +// +vbfloat16m1x5_t test_vluxseg5ei16_v_bf16m1x5(const __bf16 *rs1, vuint16m1_t rs2, + size_t vl) { + return __riscv_vluxseg5ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vluxseg5ei16_v_bf16mf4x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , } @llvm.riscv.vluxseg5.mask.nxv1bf16.nxv1i16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP0]] +// +vbfloat16mf4x5_t test_vluxseg5ei16_v_bf16mf4x5_m(vbool64_t vm, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg5ei16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vluxseg5ei16_v_bf16mf2x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , } @llvm.riscv.vluxseg5.mask.nxv2bf16.nxv2i16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP0]] +// +vbfloat16mf2x5_t test_vluxseg5ei16_v_bf16mf2x5_m(vbool32_t vm, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg5ei16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vluxseg5ei16_v_bf16m1x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , } @llvm.riscv.vluxseg5.mask.nxv4bf16.nxv4i16.i64( poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP0]] +// +vbfloat16m1x5_t test_vluxseg5ei16_v_bf16m1x5_m(vbool16_t vm, const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg5ei16(vm, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vluxseg6ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vluxseg6ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..40cb79b3684e2713fc9ba9ee9138c1b471164adc --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vluxseg6ei16.c @@ -0,0 +1,77 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vluxseg6ei16_v_bf16mf4x6( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , } @llvm.riscv.vluxseg6.nxv1bf16.nxv1i16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP0]] +// +vbfloat16mf4x6_t test_vluxseg6ei16_v_bf16mf4x6(const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg6ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vluxseg6ei16_v_bf16mf2x6( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , } @llvm.riscv.vluxseg6.nxv2bf16.nxv2i16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP0]] +// +vbfloat16mf2x6_t test_vluxseg6ei16_v_bf16mf2x6(const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg6ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vluxseg6ei16_v_bf16m1x6( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , } @llvm.riscv.vluxseg6.nxv4bf16.nxv4i16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP0]] +// +vbfloat16m1x6_t test_vluxseg6ei16_v_bf16m1x6(const __bf16 *rs1, vuint16m1_t rs2, + size_t vl) { + return __riscv_vluxseg6ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vluxseg6ei16_v_bf16mf4x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , } @llvm.riscv.vluxseg6.mask.nxv1bf16.nxv1i16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP0]] +// +vbfloat16mf4x6_t test_vluxseg6ei16_v_bf16mf4x6_m(vbool64_t vm, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg6ei16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vluxseg6ei16_v_bf16mf2x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , } @llvm.riscv.vluxseg6.mask.nxv2bf16.nxv2i16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP0]] +// +vbfloat16mf2x6_t test_vluxseg6ei16_v_bf16mf2x6_m(vbool32_t vm, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg6ei16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vluxseg6ei16_v_bf16m1x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , } @llvm.riscv.vluxseg6.mask.nxv4bf16.nxv4i16.i64( poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP0]] +// +vbfloat16m1x6_t test_vluxseg6ei16_v_bf16m1x6_m(vbool16_t vm, const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg6ei16(vm, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vluxseg7ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vluxseg7ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..00bea1db887928340c88b8baf29620b52f122ee3 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vluxseg7ei16.c @@ -0,0 +1,77 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vluxseg7ei16_v_bf16mf4x7( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , } @llvm.riscv.vluxseg7.nxv1bf16.nxv1i16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP0]] +// +vbfloat16mf4x7_t test_vluxseg7ei16_v_bf16mf4x7(const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg7ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vluxseg7ei16_v_bf16mf2x7( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , } @llvm.riscv.vluxseg7.nxv2bf16.nxv2i16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP0]] +// +vbfloat16mf2x7_t test_vluxseg7ei16_v_bf16mf2x7(const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg7ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vluxseg7ei16_v_bf16m1x7( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , } @llvm.riscv.vluxseg7.nxv4bf16.nxv4i16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP0]] +// +vbfloat16m1x7_t test_vluxseg7ei16_v_bf16m1x7(const __bf16 *rs1, vuint16m1_t rs2, + size_t vl) { + return __riscv_vluxseg7ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vluxseg7ei16_v_bf16mf4x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , } @llvm.riscv.vluxseg7.mask.nxv1bf16.nxv1i16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP0]] +// +vbfloat16mf4x7_t test_vluxseg7ei16_v_bf16mf4x7_m(vbool64_t vm, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg7ei16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vluxseg7ei16_v_bf16mf2x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , } @llvm.riscv.vluxseg7.mask.nxv2bf16.nxv2i16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP0]] +// +vbfloat16mf2x7_t test_vluxseg7ei16_v_bf16mf2x7_m(vbool32_t vm, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg7ei16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vluxseg7ei16_v_bf16m1x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , } @llvm.riscv.vluxseg7.mask.nxv4bf16.nxv4i16.i64( poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP0]] +// +vbfloat16m1x7_t test_vluxseg7ei16_v_bf16m1x7_m(vbool16_t vm, const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg7ei16(vm, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vluxseg8ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vluxseg8ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..29fa54d073995867a8076606db5d920cf4569012 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vluxseg8ei16.c @@ -0,0 +1,77 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vluxseg8ei16_v_bf16mf4x8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , } @llvm.riscv.vluxseg8.nxv1bf16.nxv1i16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP0]] +// +vbfloat16mf4x8_t test_vluxseg8ei16_v_bf16mf4x8(const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg8ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vluxseg8ei16_v_bf16mf2x8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , } @llvm.riscv.vluxseg8.nxv2bf16.nxv2i16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP0]] +// +vbfloat16mf2x8_t test_vluxseg8ei16_v_bf16mf2x8(const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg8ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vluxseg8ei16_v_bf16m1x8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , } @llvm.riscv.vluxseg8.nxv4bf16.nxv4i16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP0]] +// +vbfloat16m1x8_t test_vluxseg8ei16_v_bf16m1x8(const __bf16 *rs1, vuint16m1_t rs2, + size_t vl) { + return __riscv_vluxseg8ei16(rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vluxseg8ei16_v_bf16mf4x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , } @llvm.riscv.vluxseg8.mask.nxv1bf16.nxv1i16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP0]] +// +vbfloat16mf4x8_t test_vluxseg8ei16_v_bf16mf4x8_m(vbool64_t vm, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg8ei16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vluxseg8ei16_v_bf16mf2x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , } @llvm.riscv.vluxseg8.mask.nxv2bf16.nxv2i16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP0]] +// +vbfloat16mf2x8_t test_vluxseg8ei16_v_bf16mf2x8_m(vbool32_t vm, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg8ei16(vm, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vluxseg8ei16_v_bf16m1x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , , , , , , , } @llvm.riscv.vluxseg8.mask.nxv4bf16.nxv4i16.i64( poison, poison, poison, poison, poison, poison, poison, poison, ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 3) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP0]] +// +vbfloat16m1x8_t test_vluxseg8ei16_v_bf16m1x8_m(vbool16_t vm, const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg8ei16(vm, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vreinterpret.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vreinterpret.c new file mode 100644 index 0000000000000000000000000000000000000000..2e14f42fa34603b7d1d9a66422866815ffb08468 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vreinterpret.c @@ -0,0 +1,249 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local @test_vreinterpret_v_i16mf4_bf16mf4( +// CHECK-RV64-SAME: [[SRC:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = bitcast [[SRC]] to +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vreinterpret_v_i16mf4_bf16mf4(vint16mf4_t src) { + return __riscv_vreinterpret_bf16mf4(src); +} + +// CHECK-RV64-LABEL: define dso_local @test_vreinterpret_v_i16mf2_bf16mf2( +// CHECK-RV64-SAME: [[SRC:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = bitcast [[SRC]] to +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vreinterpret_v_i16mf2_bf16mf2(vint16mf2_t src) { + return __riscv_vreinterpret_bf16mf2(src); +} + +// CHECK-RV64-LABEL: define dso_local @test_vreinterpret_v_i16m1_bf16m1( +// CHECK-RV64-SAME: [[SRC:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = bitcast [[SRC]] to +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vreinterpret_v_i16m1_bf16m1(vint16m1_t src) { + return __riscv_vreinterpret_bf16m1(src); +} + +// CHECK-RV64-LABEL: define dso_local @test_vreinterpret_v_i16m2_bf16m2( +// CHECK-RV64-SAME: [[SRC:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = bitcast [[SRC]] to +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vreinterpret_v_i16m2_bf16m2(vint16m2_t src) { + return __riscv_vreinterpret_bf16m2(src); +} + +// CHECK-RV64-LABEL: define dso_local @test_vreinterpret_v_i16m4_bf16m4( +// CHECK-RV64-SAME: [[SRC:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = bitcast [[SRC]] to +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vreinterpret_v_i16m4_bf16m4(vint16m4_t src) { + return __riscv_vreinterpret_bf16m4(src); +} + +// CHECK-RV64-LABEL: define dso_local @test_vreinterpret_v_i16m8_bf16m8( +// CHECK-RV64-SAME: [[SRC:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = bitcast [[SRC]] to +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vreinterpret_v_i16m8_bf16m8(vint16m8_t src) { + return __riscv_vreinterpret_bf16m8(src); +} + +// CHECK-RV64-LABEL: define dso_local @test_vreinterpret_v_u16mf4_bf16mf4( +// CHECK-RV64-SAME: [[SRC:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = bitcast [[SRC]] to +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vreinterpret_v_u16mf4_bf16mf4(vuint16mf4_t src) { + return __riscv_vreinterpret_bf16mf4(src); +} + +// CHECK-RV64-LABEL: define dso_local @test_vreinterpret_v_u16mf2_bf16mf2( +// CHECK-RV64-SAME: [[SRC:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = bitcast [[SRC]] to +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vreinterpret_v_u16mf2_bf16mf2(vuint16mf2_t src) { + return __riscv_vreinterpret_bf16mf2(src); +} + +// CHECK-RV64-LABEL: define dso_local @test_vreinterpret_v_u16m1_bf16m1( +// CHECK-RV64-SAME: [[SRC:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = bitcast [[SRC]] to +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vreinterpret_v_u16m1_bf16m1(vuint16m1_t src) { + return __riscv_vreinterpret_bf16m1(src); +} + +// CHECK-RV64-LABEL: define dso_local @test_vreinterpret_v_u16m2_bf16m2( +// CHECK-RV64-SAME: [[SRC:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = bitcast [[SRC]] to +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vreinterpret_v_u16m2_bf16m2(vuint16m2_t src) { + return __riscv_vreinterpret_bf16m2(src); +} + +// CHECK-RV64-LABEL: define dso_local @test_vreinterpret_v_u16m4_bf16m4( +// CHECK-RV64-SAME: [[SRC:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = bitcast [[SRC]] to +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vreinterpret_v_u16m4_bf16m4(vuint16m4_t src) { + return __riscv_vreinterpret_bf16m4(src); +} + +// CHECK-RV64-LABEL: define dso_local @test_vreinterpret_v_u16m8_bf16m8( +// CHECK-RV64-SAME: [[SRC:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = bitcast [[SRC]] to +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vreinterpret_v_u16m8_bf16m8(vuint16m8_t src) { + return __riscv_vreinterpret_bf16m8(src); +} + +// CHECK-RV64-LABEL: define dso_local @test_vreinterpret_v_bf16mf4_i16mf4( +// CHECK-RV64-SAME: [[SRC:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = bitcast [[SRC]] to +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vint16mf4_t test_vreinterpret_v_bf16mf4_i16mf4(vbfloat16mf4_t src) { + return __riscv_vreinterpret_i16mf4(src); +} + +// CHECK-RV64-LABEL: define dso_local @test_vreinterpret_v_bf16mf2_i16mf2( +// CHECK-RV64-SAME: [[SRC:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = bitcast [[SRC]] to +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vint16mf2_t test_vreinterpret_v_bf16mf2_i16mf2(vbfloat16mf2_t src) { + return __riscv_vreinterpret_i16mf2(src); +} + +// CHECK-RV64-LABEL: define dso_local @test_vreinterpret_v_bf16m1_i16m1( +// CHECK-RV64-SAME: [[SRC:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = bitcast [[SRC]] to +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vint16m1_t test_vreinterpret_v_bf16m1_i16m1(vbfloat16m1_t src) { + return __riscv_vreinterpret_i16m1(src); +} + +// CHECK-RV64-LABEL: define dso_local @test_vreinterpret_v_bf16m2_i16m2( +// CHECK-RV64-SAME: [[SRC:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = bitcast [[SRC]] to +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vint16m2_t test_vreinterpret_v_bf16m2_i16m2(vbfloat16m2_t src) { + return __riscv_vreinterpret_i16m2(src); +} + +// CHECK-RV64-LABEL: define dso_local @test_vreinterpret_v_bf16m4_i16m4( +// CHECK-RV64-SAME: [[SRC:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = bitcast [[SRC]] to +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vint16m4_t test_vreinterpret_v_bf16m4_i16m4(vbfloat16m4_t src) { + return __riscv_vreinterpret_i16m4(src); +} + +// CHECK-RV64-LABEL: define dso_local @test_vreinterpret_v_bf16m8_i16m8( +// CHECK-RV64-SAME: [[SRC:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = bitcast [[SRC]] to +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vint16m8_t test_vreinterpret_v_bf16m8_i16m8(vbfloat16m8_t src) { + return __riscv_vreinterpret_i16m8(src); +} + +// CHECK-RV64-LABEL: define dso_local @test_vreinterpret_v_bf16mf4_u16mf4( +// CHECK-RV64-SAME: [[SRC:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = bitcast [[SRC]] to +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vuint16mf4_t test_vreinterpret_v_bf16mf4_u16mf4(vbfloat16mf4_t src) { + return __riscv_vreinterpret_u16mf4(src); +} + +// CHECK-RV64-LABEL: define dso_local @test_vreinterpret_v_bf16mf2_u16mf2( +// CHECK-RV64-SAME: [[SRC:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = bitcast [[SRC]] to +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vuint16mf2_t test_vreinterpret_v_bf16mf2_u16mf2(vbfloat16mf2_t src) { + return __riscv_vreinterpret_u16mf2(src); +} + +// CHECK-RV64-LABEL: define dso_local @test_vreinterpret_v_bf16m1_u16m1( +// CHECK-RV64-SAME: [[SRC:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = bitcast [[SRC]] to +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vuint16m1_t test_vreinterpret_v_bf16m1_u16m1(vbfloat16m1_t src) { + return __riscv_vreinterpret_u16m1(src); +} + +// CHECK-RV64-LABEL: define dso_local @test_vreinterpret_v_bf16m2_u16m2( +// CHECK-RV64-SAME: [[SRC:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = bitcast [[SRC]] to +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vuint16m2_t test_vreinterpret_v_bf16m2_u16m2(vbfloat16m2_t src) { + return __riscv_vreinterpret_u16m2(src); +} + +// CHECK-RV64-LABEL: define dso_local @test_vreinterpret_v_bf16m4_u16m4( +// CHECK-RV64-SAME: [[SRC:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = bitcast [[SRC]] to +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vuint16m4_t test_vreinterpret_v_bf16m4_u16m4(vbfloat16m4_t src) { + return __riscv_vreinterpret_u16m4(src); +} + +// CHECK-RV64-LABEL: define dso_local @test_vreinterpret_v_bf16m8_u16m8( +// CHECK-RV64-SAME: [[SRC:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = bitcast [[SRC]] to +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vuint16m8_t test_vreinterpret_v_bf16m8_u16m8(vbfloat16m8_t src) { + return __riscv_vreinterpret_u16m8(src); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vse16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vse16.c new file mode 100644 index 0000000000000000000000000000000000000000..0fe9076b1f10e3817c8010597504f673b77a76ce --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vse16.c @@ -0,0 +1,135 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vse16_v_bf16mf4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vse.nxv1bf16.i64( [[VS3]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vse16_v_bf16mf4(__bf16 *rs1, vbfloat16mf4_t vs3, size_t vl) { + return __riscv_vse16(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vse16_v_bf16mf2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vse.nxv2bf16.i64( [[VS3]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vse16_v_bf16mf2(__bf16 *rs1, vbfloat16mf2_t vs3, size_t vl) { + return __riscv_vse16(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vse16_v_bf16m1( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vse.nxv4bf16.i64( [[VS3]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vse16_v_bf16m1(__bf16 *rs1, vbfloat16m1_t vs3, size_t vl) { + return __riscv_vse16(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vse16_v_bf16m2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vse.nxv8bf16.i64( [[VS3]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vse16_v_bf16m2(__bf16 *rs1, vbfloat16m2_t vs3, size_t vl) { + return __riscv_vse16(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vse16_v_bf16m4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vse.nxv16bf16.i64( [[VS3]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vse16_v_bf16m4(__bf16 *rs1, vbfloat16m4_t vs3, size_t vl) { + return __riscv_vse16(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vse16_v_bf16m8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vse.nxv32bf16.i64( [[VS3]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vse16_v_bf16m8(__bf16 *rs1, vbfloat16m8_t vs3, size_t vl) { + return __riscv_vse16(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vse16_v_bf16mf4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vse.mask.nxv1bf16.i64( [[VS3]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vse16_v_bf16mf4_m(vbool64_t vm, __bf16 *rs1, vbfloat16mf4_t vs3, + size_t vl) { + return __riscv_vse16(vm, rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vse16_v_bf16mf2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vse.mask.nxv2bf16.i64( [[VS3]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vse16_v_bf16mf2_m(vbool32_t vm, __bf16 *rs1, vbfloat16mf2_t vs3, + size_t vl) { + return __riscv_vse16(vm, rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vse16_v_bf16m1_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vse.mask.nxv4bf16.i64( [[VS3]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vse16_v_bf16m1_m(vbool16_t vm, __bf16 *rs1, vbfloat16m1_t vs3, + size_t vl) { + return __riscv_vse16(vm, rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vse16_v_bf16m2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vse.mask.nxv8bf16.i64( [[VS3]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vse16_v_bf16m2_m(vbool8_t vm, __bf16 *rs1, vbfloat16m2_t vs3, + size_t vl) { + return __riscv_vse16(vm, rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vse16_v_bf16m4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vse.mask.nxv16bf16.i64( [[VS3]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vse16_v_bf16m4_m(vbool4_t vm, __bf16 *rs1, vbfloat16m4_t vs3, + size_t vl) { + return __riscv_vse16(vm, rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vse16_v_bf16m8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vse.mask.nxv32bf16.i64( [[VS3]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vse16_v_bf16m8_m(vbool2_t vm, __bf16 *rs1, vbfloat16m8_t vs3, + size_t vl) { + return __riscv_vse16(vm, rs1, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vset.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vset.c new file mode 100644 index 0000000000000000000000000000000000000000..67fb436bf22a704efddad9a40984fe84ff77c678 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vset.c @@ -0,0 +1,364 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local @test_vset_v_bf16m1_bf16m2( +// CHECK-RV64-SAME: [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.insert.nxv8bf16.nxv4bf16( [[DEST]], [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vset_v_bf16m1_bf16m2(vbfloat16m2_t dest, size_t index, + vbfloat16m1_t value) { + return __riscv_vset(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vset_v_bf16m1_bf16m4( +// CHECK-RV64-SAME: [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.insert.nxv16bf16.nxv4bf16( [[DEST]], [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vset_v_bf16m1_bf16m4(vbfloat16m4_t dest, size_t index, + vbfloat16m1_t value) { + return __riscv_vset(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vset_v_bf16m2_bf16m4( +// CHECK-RV64-SAME: [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.insert.nxv16bf16.nxv8bf16( [[DEST]], [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vset_v_bf16m2_bf16m4(vbfloat16m4_t dest, size_t index, + vbfloat16m2_t value) { + return __riscv_vset(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vset_v_bf16m1_bf16m8( +// CHECK-RV64-SAME: [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.insert.nxv32bf16.nxv4bf16( [[DEST]], [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vset_v_bf16m1_bf16m8(vbfloat16m8_t dest, size_t index, + vbfloat16m1_t value) { + return __riscv_vset(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vset_v_bf16m2_bf16m8( +// CHECK-RV64-SAME: [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.insert.nxv32bf16.nxv8bf16( [[DEST]], [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vset_v_bf16m2_bf16m8(vbfloat16m8_t dest, size_t index, + vbfloat16m2_t value) { + return __riscv_vset(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local @test_vset_v_bf16m4_bf16m8( +// CHECK-RV64-SAME: [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.vector.insert.nxv32bf16.nxv16bf16( [[DEST]], [[VALUE]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vset_v_bf16m4_bf16m8(vbfloat16m8_t dest, size_t index, + vbfloat16m4_t value) { + return __riscv_vset(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vset_v_bf16mf4_bf16mf4x2( +// CHECK-RV64-SAME: { , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16mf4x2_t test_vset_v_bf16mf4_bf16mf4x2(vbfloat16mf4x2_t dest, + size_t index, + vbfloat16mf4_t value) { + return __riscv_vset(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vset_v_bf16mf4_bf16mf4x3( +// CHECK-RV64-SAME: { , , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16mf4x3_t test_vset_v_bf16mf4_bf16mf4x3(vbfloat16mf4x3_t dest, + size_t index, + vbfloat16mf4_t value) { + return __riscv_vset(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vset_v_bf16mf4_bf16mf4x4( +// CHECK-RV64-SAME: { , , , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16mf4x4_t test_vset_v_bf16mf4_bf16mf4x4(vbfloat16mf4x4_t dest, + size_t index, + vbfloat16mf4_t value) { + return __riscv_vset(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vset_v_bf16mf4_bf16mf4x5( +// CHECK-RV64-SAME: { , , , , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , , , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , , , , } [[TMP0]] +// +vbfloat16mf4x5_t test_vset_v_bf16mf4_bf16mf4x5(vbfloat16mf4x5_t dest, + size_t index, + vbfloat16mf4_t value) { + return __riscv_vset(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vset_v_bf16mf4_bf16mf4x6( +// CHECK-RV64-SAME: { , , , , , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , , , , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP0]] +// +vbfloat16mf4x6_t test_vset_v_bf16mf4_bf16mf4x6(vbfloat16mf4x6_t dest, + size_t index, + vbfloat16mf4_t value) { + return __riscv_vset(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vset_v_bf16mf4_bf16mf4x7( +// CHECK-RV64-SAME: { , , , , , , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , , , , , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP0]] +// +vbfloat16mf4x7_t test_vset_v_bf16mf4_bf16mf4x7(vbfloat16mf4x7_t dest, + size_t index, + vbfloat16mf4_t value) { + return __riscv_vset(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vset_v_bf16mf4_bf16mf4x8( +// CHECK-RV64-SAME: { , , , , , , , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , , , , , , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP0]] +// +vbfloat16mf4x8_t test_vset_v_bf16mf4_bf16mf4x8(vbfloat16mf4x8_t dest, + size_t index, + vbfloat16mf4_t value) { + return __riscv_vset(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vset_v_bf16mf2_bf16mf2x2( +// CHECK-RV64-SAME: { , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16mf2x2_t test_vset_v_bf16mf2_bf16mf2x2(vbfloat16mf2x2_t dest, + size_t index, + vbfloat16mf2_t value) { + return __riscv_vset(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vset_v_bf16mf2_bf16mf2x3( +// CHECK-RV64-SAME: { , , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16mf2x3_t test_vset_v_bf16mf2_bf16mf2x3(vbfloat16mf2x3_t dest, + size_t index, + vbfloat16mf2_t value) { + return __riscv_vset(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vset_v_bf16mf2_bf16mf2x4( +// CHECK-RV64-SAME: { , , , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16mf2x4_t test_vset_v_bf16mf2_bf16mf2x4(vbfloat16mf2x4_t dest, + size_t index, + vbfloat16mf2_t value) { + return __riscv_vset(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vset_v_bf16mf2_bf16mf2x5( +// CHECK-RV64-SAME: { , , , , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , , , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , , , , } [[TMP0]] +// +vbfloat16mf2x5_t test_vset_v_bf16mf2_bf16mf2x5(vbfloat16mf2x5_t dest, + size_t index, + vbfloat16mf2_t value) { + return __riscv_vset(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vset_v_bf16mf2_bf16mf2x6( +// CHECK-RV64-SAME: { , , , , , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , , , , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP0]] +// +vbfloat16mf2x6_t test_vset_v_bf16mf2_bf16mf2x6(vbfloat16mf2x6_t dest, + size_t index, + vbfloat16mf2_t value) { + return __riscv_vset(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vset_v_bf16mf2_bf16mf2x7( +// CHECK-RV64-SAME: { , , , , , , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , , , , , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP0]] +// +vbfloat16mf2x7_t test_vset_v_bf16mf2_bf16mf2x7(vbfloat16mf2x7_t dest, + size_t index, + vbfloat16mf2_t value) { + return __riscv_vset(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vset_v_bf16mf2_bf16mf2x8( +// CHECK-RV64-SAME: { , , , , , , , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , , , , , , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP0]] +// +vbfloat16mf2x8_t test_vset_v_bf16mf2_bf16mf2x8(vbfloat16mf2x8_t dest, + size_t index, + vbfloat16mf2_t value) { + return __riscv_vset(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vset_v_bf16m1_bf16m1x2( +// CHECK-RV64-SAME: { , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16m1x2_t test_vset_v_bf16m1_bf16m1x2(vbfloat16m1x2_t dest, size_t index, + vbfloat16m1_t value) { + return __riscv_vset(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vset_v_bf16m1_bf16m1x3( +// CHECK-RV64-SAME: { , , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16m1x3_t test_vset_v_bf16m1_bf16m1x3(vbfloat16m1x3_t dest, size_t index, + vbfloat16m1_t value) { + return __riscv_vset(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vset_v_bf16m1_bf16m1x4( +// CHECK-RV64-SAME: { , , , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16m1x4_t test_vset_v_bf16m1_bf16m1x4(vbfloat16m1x4_t dest, size_t index, + vbfloat16m1_t value) { + return __riscv_vset(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vset_v_bf16m1_bf16m1x5( +// CHECK-RV64-SAME: { , , , , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , , , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , , , , } [[TMP0]] +// +vbfloat16m1x5_t test_vset_v_bf16m1_bf16m1x5(vbfloat16m1x5_t dest, size_t index, + vbfloat16m1_t value) { + return __riscv_vset(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vset_v_bf16m1_bf16m1x6( +// CHECK-RV64-SAME: { , , , , , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , , , , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP0]] +// +vbfloat16m1x6_t test_vset_v_bf16m1_bf16m1x6(vbfloat16m1x6_t dest, size_t index, + vbfloat16m1_t value) { + return __riscv_vset(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vset_v_bf16m1_bf16m1x7( +// CHECK-RV64-SAME: { , , , , , , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , , , , , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP0]] +// +vbfloat16m1x7_t test_vset_v_bf16m1_bf16m1x7(vbfloat16m1x7_t dest, size_t index, + vbfloat16m1_t value) { + return __riscv_vset(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vset_v_bf16m1_bf16m1x8( +// CHECK-RV64-SAME: { , , , , , , , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , , , , , , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP0]] +// +vbfloat16m1x8_t test_vset_v_bf16m1_bf16m1x8(vbfloat16m1x8_t dest, size_t index, + vbfloat16m1_t value) { + return __riscv_vset(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vset_v_bf16m2_bf16m2x2( +// CHECK-RV64-SAME: { , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16m2x2_t test_vset_v_bf16m2_bf16m2x2(vbfloat16m2x2_t dest, size_t index, + vbfloat16m2_t value) { + return __riscv_vset(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vset_v_bf16m2_bf16m2x3( +// CHECK-RV64-SAME: { , , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , , } [[TMP0]] +// +vbfloat16m2x3_t test_vset_v_bf16m2_bf16m2x3(vbfloat16m2x3_t dest, size_t index, + vbfloat16m2_t value) { + return __riscv_vset(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vset_v_bf16m2_bf16m2x4( +// CHECK-RV64-SAME: { , , , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , , , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , , , } [[TMP0]] +// +vbfloat16m2x4_t test_vset_v_bf16m2_bf16m2x4(vbfloat16m2x4_t dest, size_t index, + vbfloat16m2_t value) { + return __riscv_vset(dest, 0, value); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vset_v_bf16m4_bf16m4x2( +// CHECK-RV64-SAME: { , } [[DEST:%.*]], i64 noundef [[INDEX:%.*]], [[VALUE:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = insertvalue { , } [[DEST]], [[VALUE]], 0 +// CHECK-RV64-NEXT: ret { , } [[TMP0]] +// +vbfloat16m4x2_t test_vset_v_bf16m4_bf16m4x2(vbfloat16m4x2_t dest, size_t index, + vbfloat16m4_t value) { + return __riscv_vset(dest, 0, value); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsoxei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsoxei16.c new file mode 100644 index 0000000000000000000000000000000000000000..a374e019665c7afb63be5f94452187ec25611728 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsoxei16.c @@ -0,0 +1,141 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxei16_v_bf16mf4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxei.nxv1bf16.nxv1i16.i64( [[VS3]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxei16_v_bf16mf4(__bf16 *rs1, vuint16mf4_t rs2, vbfloat16mf4_t vs3, + size_t vl) { + return __riscv_vsoxei16(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxei16_v_bf16mf2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxei.nxv2bf16.nxv2i16.i64( [[VS3]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxei16_v_bf16mf2(__bf16 *rs1, vuint16mf2_t rs2, vbfloat16mf2_t vs3, + size_t vl) { + return __riscv_vsoxei16(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxei16_v_bf16m1( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxei.nxv4bf16.nxv4i16.i64( [[VS3]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxei16_v_bf16m1(__bf16 *rs1, vuint16m1_t rs2, vbfloat16m1_t vs3, + size_t vl) { + return __riscv_vsoxei16(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxei16_v_bf16m2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxei.nxv8bf16.nxv8i16.i64( [[VS3]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxei16_v_bf16m2(__bf16 *rs1, vuint16m2_t rs2, vbfloat16m2_t vs3, + size_t vl) { + return __riscv_vsoxei16(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxei16_v_bf16m4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxei.nxv16bf16.nxv16i16.i64( [[VS3]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxei16_v_bf16m4(__bf16 *rs1, vuint16m4_t rs2, vbfloat16m4_t vs3, + size_t vl) { + return __riscv_vsoxei16(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxei16_v_bf16m8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxei.nxv32bf16.nxv32i16.i64( [[VS3]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxei16_v_bf16m8(__bf16 *rs1, vuint16m8_t rs2, vbfloat16m8_t vs3, + size_t vl) { + return __riscv_vsoxei16(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxei16_v_bf16mf4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxei.mask.nxv1bf16.nxv1i16.i64( [[VS3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxei16_v_bf16mf4_m(vbool64_t vm, __bf16 *rs1, vuint16mf4_t rs2, + vbfloat16mf4_t vs3, size_t vl) { + return __riscv_vsoxei16(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxei16_v_bf16mf2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxei.mask.nxv2bf16.nxv2i16.i64( [[VS3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxei16_v_bf16mf2_m(vbool32_t vm, __bf16 *rs1, vuint16mf2_t rs2, + vbfloat16mf2_t vs3, size_t vl) { + return __riscv_vsoxei16(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxei16_v_bf16m1_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxei.mask.nxv4bf16.nxv4i16.i64( [[VS3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxei16_v_bf16m1_m(vbool16_t vm, __bf16 *rs1, vuint16m1_t rs2, + vbfloat16m1_t vs3, size_t vl) { + return __riscv_vsoxei16(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxei16_v_bf16m2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxei.mask.nxv8bf16.nxv8i16.i64( [[VS3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxei16_v_bf16m2_m(vbool8_t vm, __bf16 *rs1, vuint16m2_t rs2, + vbfloat16m2_t vs3, size_t vl) { + return __riscv_vsoxei16(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxei16_v_bf16m4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxei.mask.nxv16bf16.nxv16i16.i64( [[VS3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxei16_v_bf16m4_m(vbool4_t vm, __bf16 *rs1, vuint16m4_t rs2, + vbfloat16m4_t vs3, size_t vl) { + return __riscv_vsoxei16(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxei16_v_bf16m8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxei.mask.nxv32bf16.nxv32i16.i64( [[VS3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxei16_v_bf16m8_m(vbool2_t vm, __bf16 *rs1, vuint16m8_t rs2, + vbfloat16m8_t vs3, size_t vl) { + return __riscv_vsoxei16(vm, rs1, rs2, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsoxseg2ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsoxseg2ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..088ef855cd1c52ee251b34e5963a9cb54c323636 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsoxseg2ei16.c @@ -0,0 +1,141 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg2ei16_v_bf16mf4x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg2.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg2ei16_v_bf16mf4x2(__bf16 *rs1, vuint16mf4_t vs2, + vbfloat16mf4x2_t vs3, size_t vl) { + return __riscv_vsoxseg2ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg2ei16_v_bf16mf2x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg2.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg2ei16_v_bf16mf2x2(__bf16 *rs1, vuint16mf2_t vs2, + vbfloat16mf2x2_t vs3, size_t vl) { + return __riscv_vsoxseg2ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg2ei16_v_bf16m1x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg2.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg2ei16_v_bf16m1x2(__bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x2_t vs3, size_t vl) { + return __riscv_vsoxseg2ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg2ei16_v_bf16m2x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg2.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg2ei16_v_bf16m2x2(__bf16 *rs1, vuint16m2_t vs2, + vbfloat16m2x2_t vs3, size_t vl) { + return __riscv_vsoxseg2ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg2ei16_v_bf16m4x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg2.nxv16bf16.nxv16i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg2ei16_v_bf16m4x2(__bf16 *rs1, vuint16m4_t vs2, + vbfloat16m4x2_t vs3, size_t vl) { + return __riscv_vsoxseg2ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg2ei16_v_bf16mf4x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg2.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg2ei16_v_bf16mf4x2_m(vbool64_t vm, __bf16 *rs1, + vuint16mf4_t vs2, vbfloat16mf4x2_t vs3, + size_t vl) { + return __riscv_vsoxseg2ei16(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg2ei16_v_bf16mf2x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg2.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg2ei16_v_bf16mf2x2_m(vbool32_t vm, __bf16 *rs1, + vuint16mf2_t vs2, vbfloat16mf2x2_t vs3, + size_t vl) { + return __riscv_vsoxseg2ei16(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg2ei16_v_bf16m1x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg2.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg2ei16_v_bf16m1x2_m(vbool16_t vm, __bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x2_t vs3, size_t vl) { + return __riscv_vsoxseg2ei16(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg2ei16_v_bf16m2x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg2.mask.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg2ei16_v_bf16m2x2_m(vbool8_t vm, __bf16 *rs1, vuint16m2_t vs2, + vbfloat16m2x2_t vs3, size_t vl) { + return __riscv_vsoxseg2ei16(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg2ei16_v_bf16m4x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg2.mask.nxv16bf16.nxv16i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg2ei16_v_bf16m4x2_m(vbool4_t vm, __bf16 *rs1, vuint16m4_t vs2, + vbfloat16m4x2_t vs3, size_t vl) { + return __riscv_vsoxseg2ei16(vm, rs1, vs2, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsoxseg3ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsoxseg3ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..aee2c3ce96af04d5ffb1d23fdb949170f7cfa873 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsoxseg3ei16.c @@ -0,0 +1,123 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg3ei16_v_bf16mf4x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg3.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg3ei16_v_bf16mf4x3(__bf16 *rs1, vuint16mf4_t vs2, + vbfloat16mf4x3_t vs3, size_t vl) { + return __riscv_vsoxseg3ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg3ei16_v_bf16mf2x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg3.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg3ei16_v_bf16mf2x3(__bf16 *rs1, vuint16mf2_t vs2, + vbfloat16mf2x3_t vs3, size_t vl) { + return __riscv_vsoxseg3ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg3ei16_v_bf16m1x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg3.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg3ei16_v_bf16m1x3(__bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x3_t vs3, size_t vl) { + return __riscv_vsoxseg3ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg3ei16_v_bf16m2x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg3.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg3ei16_v_bf16m2x3(__bf16 *rs1, vuint16m2_t vs2, + vbfloat16m2x3_t vs3, size_t vl) { + return __riscv_vsoxseg3ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg3ei16_v_bf16mf4x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg3.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg3ei16_v_bf16mf4x3_m(vbool64_t vm, __bf16 *rs1, + vuint16mf4_t vs2, vbfloat16mf4x3_t vs3, + size_t vl) { + return __riscv_vsoxseg3ei16(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg3ei16_v_bf16mf2x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg3.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg3ei16_v_bf16mf2x3_m(vbool32_t vm, __bf16 *rs1, + vuint16mf2_t vs2, vbfloat16mf2x3_t vs3, + size_t vl) { + return __riscv_vsoxseg3ei16(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg3ei16_v_bf16m1x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg3.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg3ei16_v_bf16m1x3_m(vbool16_t vm, __bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x3_t vs3, size_t vl) { + return __riscv_vsoxseg3ei16(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg3ei16_v_bf16m2x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg3.mask.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg3ei16_v_bf16m2x3_m(vbool8_t vm, __bf16 *rs1, vuint16m2_t vs2, + vbfloat16m2x3_t vs3, size_t vl) { + return __riscv_vsoxseg3ei16(vm, rs1, vs2, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsoxseg4ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsoxseg4ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..4d2232129c4e43cf4ad70ca0fd9b1593fb71001d --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsoxseg4ei16.c @@ -0,0 +1,131 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg4ei16_v_bf16mf4x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg4.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg4ei16_v_bf16mf4x4(__bf16 *rs1, vuint16mf4_t vs2, + vbfloat16mf4x4_t vs3, size_t vl) { + return __riscv_vsoxseg4ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg4ei16_v_bf16mf2x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg4.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg4ei16_v_bf16mf2x4(__bf16 *rs1, vuint16mf2_t vs2, + vbfloat16mf2x4_t vs3, size_t vl) { + return __riscv_vsoxseg4ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg4ei16_v_bf16m1x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg4.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg4ei16_v_bf16m1x4(__bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x4_t vs3, size_t vl) { + return __riscv_vsoxseg4ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg4ei16_v_bf16m2x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg4.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg4ei16_v_bf16m2x4(__bf16 *rs1, vuint16m2_t vs2, + vbfloat16m2x4_t vs3, size_t vl) { + return __riscv_vsoxseg4ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg4ei16_v_bf16mf4x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg4.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg4ei16_v_bf16mf4x4_m(vbool64_t vm, __bf16 *rs1, + vuint16mf4_t vs2, vbfloat16mf4x4_t vs3, + size_t vl) { + return __riscv_vsoxseg4ei16(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg4ei16_v_bf16mf2x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg4.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg4ei16_v_bf16mf2x4_m(vbool32_t vm, __bf16 *rs1, + vuint16mf2_t vs2, vbfloat16mf2x4_t vs3, + size_t vl) { + return __riscv_vsoxseg4ei16(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg4ei16_v_bf16m1x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg4.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg4ei16_v_bf16m1x4_m(vbool16_t vm, __bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x4_t vs3, size_t vl) { + return __riscv_vsoxseg4ei16(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg4ei16_v_bf16m2x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg4.mask.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg4ei16_v_bf16m2x4_m(vbool8_t vm, __bf16 *rs1, vuint16m2_t vs2, + vbfloat16m2x4_t vs3, size_t vl) { + return __riscv_vsoxseg4ei16(vm, rs1, vs2, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsoxseg5ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsoxseg5ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..5975ed0cc17938dade702966469ebca9f78c2f64 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsoxseg5ei16.c @@ -0,0 +1,107 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg5ei16_v_bf16mf4x5( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg5.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg5ei16_v_bf16mf4x5(__bf16 *rs1, vuint16mf4_t vs2, + vbfloat16mf4x5_t vs3, size_t vl) { + return __riscv_vsoxseg5ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg5ei16_v_bf16mf2x5( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg5.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg5ei16_v_bf16mf2x5(__bf16 *rs1, vuint16mf2_t vs2, + vbfloat16mf2x5_t vs3, size_t vl) { + return __riscv_vsoxseg5ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg5ei16_v_bf16m1x5( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg5.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg5ei16_v_bf16m1x5(__bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x5_t vs3, size_t vl) { + return __riscv_vsoxseg5ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg5ei16_v_bf16mf4x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg5.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg5ei16_v_bf16mf4x5_m(vbool64_t vm, __bf16 *rs1, + vuint16mf4_t vs2, vbfloat16mf4x5_t vs3, + size_t vl) { + return __riscv_vsoxseg5ei16(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg5ei16_v_bf16mf2x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg5.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg5ei16_v_bf16mf2x5_m(vbool32_t vm, __bf16 *rs1, + vuint16mf2_t vs2, vbfloat16mf2x5_t vs3, + size_t vl) { + return __riscv_vsoxseg5ei16(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg5ei16_v_bf16m1x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg5.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg5ei16_v_bf16m1x5_m(vbool16_t vm, __bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x5_t vs3, size_t vl) { + return __riscv_vsoxseg5ei16(vm, rs1, vs2, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsoxseg6ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsoxseg6ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..cca77d6dc66876709cc207b44f1ad62b25da328a --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsoxseg6ei16.c @@ -0,0 +1,113 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg6ei16_v_bf16mf4x6( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg6.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg6ei16_v_bf16mf4x6(__bf16 *rs1, vuint16mf4_t vs2, + vbfloat16mf4x6_t vs3, size_t vl) { + return __riscv_vsoxseg6ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg6ei16_v_bf16mf2x6( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg6.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg6ei16_v_bf16mf2x6(__bf16 *rs1, vuint16mf2_t vs2, + vbfloat16mf2x6_t vs3, size_t vl) { + return __riscv_vsoxseg6ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg6ei16_v_bf16m1x6( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg6.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg6ei16_v_bf16m1x6(__bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x6_t vs3, size_t vl) { + return __riscv_vsoxseg6ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg6ei16_v_bf16mf4x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg6.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg6ei16_v_bf16mf4x6_m(vbool64_t vm, __bf16 *rs1, + vuint16mf4_t vs2, vbfloat16mf4x6_t vs3, + size_t vl) { + return __riscv_vsoxseg6ei16(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg6ei16_v_bf16mf2x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg6.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg6ei16_v_bf16mf2x6_m(vbool32_t vm, __bf16 *rs1, + vuint16mf2_t vs2, vbfloat16mf2x6_t vs3, + size_t vl) { + return __riscv_vsoxseg6ei16(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg6ei16_v_bf16m1x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg6.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg6ei16_v_bf16m1x6_m(vbool16_t vm, __bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x6_t vs3, size_t vl) { + return __riscv_vsoxseg6ei16(vm, rs1, vs2, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsoxseg7ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsoxseg7ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..f258f74f4b259fd4b11f7eff55960b39d25872b1 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsoxseg7ei16.c @@ -0,0 +1,119 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg7ei16_v_bf16mf4x7( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg7.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg7ei16_v_bf16mf4x7(__bf16 *rs1, vuint16mf4_t vs2, + vbfloat16mf4x7_t vs3, size_t vl) { + return __riscv_vsoxseg7ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg7ei16_v_bf16mf2x7( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg7.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg7ei16_v_bf16mf2x7(__bf16 *rs1, vuint16mf2_t vs2, + vbfloat16mf2x7_t vs3, size_t vl) { + return __riscv_vsoxseg7ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg7ei16_v_bf16m1x7( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg7.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg7ei16_v_bf16m1x7(__bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x7_t vs3, size_t vl) { + return __riscv_vsoxseg7ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg7ei16_v_bf16mf4x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg7.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg7ei16_v_bf16mf4x7_m(vbool64_t vm, __bf16 *rs1, + vuint16mf4_t vs2, vbfloat16mf4x7_t vs3, + size_t vl) { + return __riscv_vsoxseg7ei16(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg7ei16_v_bf16mf2x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg7.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg7ei16_v_bf16mf2x7_m(vbool32_t vm, __bf16 *rs1, + vuint16mf2_t vs2, vbfloat16mf2x7_t vs3, + size_t vl) { + return __riscv_vsoxseg7ei16(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg7ei16_v_bf16m1x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg7.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg7ei16_v_bf16m1x7_m(vbool16_t vm, __bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x7_t vs3, size_t vl) { + return __riscv_vsoxseg7ei16(vm, rs1, vs2, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsoxseg8ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsoxseg8ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..8f718ac3b730087395f6c7d189a086aa1b2bab2e --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsoxseg8ei16.c @@ -0,0 +1,125 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg8ei16_v_bf16mf4x8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VS3]], 7 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg8.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg8ei16_v_bf16mf4x8(__bf16 *rs1, vuint16mf4_t vs2, + vbfloat16mf4x8_t vs3, size_t vl) { + return __riscv_vsoxseg8ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg8ei16_v_bf16mf2x8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VS3]], 7 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg8.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg8ei16_v_bf16mf2x8(__bf16 *rs1, vuint16mf2_t vs2, + vbfloat16mf2x8_t vs3, size_t vl) { + return __riscv_vsoxseg8ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg8ei16_v_bf16m1x8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VS3]], 7 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg8.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg8ei16_v_bf16m1x8(__bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x8_t vs3, size_t vl) { + return __riscv_vsoxseg8ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg8ei16_v_bf16mf4x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VS3]], 7 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg8.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg8ei16_v_bf16mf4x8_m(vbool64_t vm, __bf16 *rs1, + vuint16mf4_t vs2, vbfloat16mf4x8_t vs3, + size_t vl) { + return __riscv_vsoxseg8ei16(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg8ei16_v_bf16mf2x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VS3]], 7 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg8.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg8ei16_v_bf16mf2x8_m(vbool32_t vm, __bf16 *rs1, + vuint16mf2_t vs2, vbfloat16mf2x8_t vs3, + size_t vl) { + return __riscv_vsoxseg8ei16(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsoxseg8ei16_v_bf16m1x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VS3]], 7 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsoxseg8.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsoxseg8ei16_v_bf16m1x8_m(vbool16_t vm, __bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x8_t vs3, size_t vl) { + return __riscv_vsoxseg8ei16(vm, rs1, vs2, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsse16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsse16.c new file mode 100644 index 0000000000000000000000000000000000000000..103d2bff32288e622c472f4896a6e99936f21cbd --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsse16.c @@ -0,0 +1,141 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vsse16_v_bf16mf4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsse.nxv1bf16.i64( [[VS3]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsse16_v_bf16mf4(__bf16 *rs1, ptrdiff_t rs2, vbfloat16mf4_t vs3, + size_t vl) { + return __riscv_vsse16(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsse16_v_bf16mf2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsse.nxv2bf16.i64( [[VS3]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsse16_v_bf16mf2(__bf16 *rs1, ptrdiff_t rs2, vbfloat16mf2_t vs3, + size_t vl) { + return __riscv_vsse16(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsse16_v_bf16m1( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsse.nxv4bf16.i64( [[VS3]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsse16_v_bf16m1(__bf16 *rs1, ptrdiff_t rs2, vbfloat16m1_t vs3, + size_t vl) { + return __riscv_vsse16(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsse16_v_bf16m2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsse.nxv8bf16.i64( [[VS3]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsse16_v_bf16m2(__bf16 *rs1, ptrdiff_t rs2, vbfloat16m2_t vs3, + size_t vl) { + return __riscv_vsse16(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsse16_v_bf16m4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsse.nxv16bf16.i64( [[VS3]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsse16_v_bf16m4(__bf16 *rs1, ptrdiff_t rs2, vbfloat16m4_t vs3, + size_t vl) { + return __riscv_vsse16(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsse16_v_bf16m8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsse.nxv32bf16.i64( [[VS3]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsse16_v_bf16m8(__bf16 *rs1, ptrdiff_t rs2, vbfloat16m8_t vs3, + size_t vl) { + return __riscv_vsse16(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsse16_v_bf16mf4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsse.mask.nxv1bf16.i64( [[VS3]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsse16_v_bf16mf4_m(vbool64_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf4_t vs3, size_t vl) { + return __riscv_vsse16(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsse16_v_bf16mf2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsse.mask.nxv2bf16.i64( [[VS3]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsse16_v_bf16mf2_m(vbool32_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf2_t vs3, size_t vl) { + return __riscv_vsse16(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsse16_v_bf16m1_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsse.mask.nxv4bf16.i64( [[VS3]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsse16_v_bf16m1_m(vbool16_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16m1_t vs3, size_t vl) { + return __riscv_vsse16(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsse16_v_bf16m2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsse.mask.nxv8bf16.i64( [[VS3]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsse16_v_bf16m2_m(vbool8_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16m2_t vs3, size_t vl) { + return __riscv_vsse16(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsse16_v_bf16m4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsse.mask.nxv16bf16.i64( [[VS3]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsse16_v_bf16m4_m(vbool4_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16m4_t vs3, size_t vl) { + return __riscv_vsse16(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsse16_v_bf16m8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsse.mask.nxv32bf16.i64( [[VS3]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsse16_v_bf16m8_m(vbool2_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16m8_t vs3, size_t vl) { + return __riscv_vsse16(vm, rs1, rs2, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsseg2e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsseg2e16.c new file mode 100644 index 0000000000000000000000000000000000000000..c302d828fd0523b0e456f9c3d67c3f02e995c96c --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsseg2e16.c @@ -0,0 +1,134 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg2e16_v_bf16mf4x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg2.nxv1bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg2e16_v_bf16mf4x2(__bf16 *rs1, vbfloat16mf4x2_t vs3, size_t vl) { + return __riscv_vsseg2e16(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg2e16_v_bf16mf2x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg2.nxv2bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg2e16_v_bf16mf2x2(__bf16 *rs1, vbfloat16mf2x2_t vs3, size_t vl) { + return __riscv_vsseg2e16(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg2e16_v_bf16m1x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg2.nxv4bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg2e16_v_bf16m1x2(__bf16 *rs1, vbfloat16m1x2_t vs3, size_t vl) { + return __riscv_vsseg2e16(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg2e16_v_bf16m2x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg2.nxv8bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg2e16_v_bf16m2x2(__bf16 *rs1, vbfloat16m2x2_t vs3, size_t vl) { + return __riscv_vsseg2e16(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg2e16_v_bf16m4x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg2.nxv16bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg2e16_v_bf16m4x2(__bf16 *rs1, vbfloat16m4x2_t vs3, size_t vl) { + return __riscv_vsseg2e16(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg2e16_v_bf16mf4x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg2.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg2e16_v_bf16mf4x2_m(vbool64_t vm, __bf16 *rs1, + vbfloat16mf4x2_t vs3, size_t vl) { + return __riscv_vsseg2e16(vm, rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg2e16_v_bf16mf2x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg2.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg2e16_v_bf16mf2x2_m(vbool32_t vm, __bf16 *rs1, + vbfloat16mf2x2_t vs3, size_t vl) { + return __riscv_vsseg2e16(vm, rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg2e16_v_bf16m1x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg2.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg2e16_v_bf16m1x2_m(vbool16_t vm, __bf16 *rs1, vbfloat16m1x2_t vs3, + size_t vl) { + return __riscv_vsseg2e16(vm, rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg2e16_v_bf16m2x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg2.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg2e16_v_bf16m2x2_m(vbool8_t vm, __bf16 *rs1, vbfloat16m2x2_t vs3, + size_t vl) { + return __riscv_vsseg2e16(vm, rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg2e16_v_bf16m4x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg2.mask.nxv16bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg2e16_v_bf16m4x2_m(vbool4_t vm, __bf16 *rs1, vbfloat16m4x2_t vs3, + size_t vl) { + return __riscv_vsseg2e16(vm, rs1, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsseg3e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsseg3e16.c new file mode 100644 index 0000000000000000000000000000000000000000..644d2145dc11862f1fdfc539dc4a13b6a582afde --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsseg3e16.c @@ -0,0 +1,117 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg3e16_v_bf16mf4x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg3.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg3e16_v_bf16mf4x3(__bf16 *rs1, vbfloat16mf4x3_t vs3, size_t vl) { + return __riscv_vsseg3e16(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg3e16_v_bf16mf2x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg3.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg3e16_v_bf16mf2x3(__bf16 *rs1, vbfloat16mf2x3_t vs3, size_t vl) { + return __riscv_vsseg3e16(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg3e16_v_bf16m1x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg3.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg3e16_v_bf16m1x3(__bf16 *rs1, vbfloat16m1x3_t vs3, size_t vl) { + return __riscv_vsseg3e16(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg3e16_v_bf16m2x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg3.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg3e16_v_bf16m2x3(__bf16 *rs1, vbfloat16m2x3_t vs3, size_t vl) { + return __riscv_vsseg3e16(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg3e16_v_bf16mf4x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg3.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg3e16_v_bf16mf4x3_m(vbool64_t vm, __bf16 *rs1, + vbfloat16mf4x3_t vs3, size_t vl) { + return __riscv_vsseg3e16(vm, rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg3e16_v_bf16mf2x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg3.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg3e16_v_bf16mf2x3_m(vbool32_t vm, __bf16 *rs1, + vbfloat16mf2x3_t vs3, size_t vl) { + return __riscv_vsseg3e16(vm, rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg3e16_v_bf16m1x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg3.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg3e16_v_bf16m1x3_m(vbool16_t vm, __bf16 *rs1, vbfloat16m1x3_t vs3, + size_t vl) { + return __riscv_vsseg3e16(vm, rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg3e16_v_bf16m2x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg3.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg3e16_v_bf16m2x3_m(vbool8_t vm, __bf16 *rs1, vbfloat16m2x3_t vs3, + size_t vl) { + return __riscv_vsseg3e16(vm, rs1, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsseg4e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsseg4e16.c new file mode 100644 index 0000000000000000000000000000000000000000..7dbd0577278522f6550fdc559a33d89be6e32ba3 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsseg4e16.c @@ -0,0 +1,125 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg4e16_v_bf16mf4x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg4.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg4e16_v_bf16mf4x4(__bf16 *rs1, vbfloat16mf4x4_t vs3, size_t vl) { + return __riscv_vsseg4e16(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg4e16_v_bf16mf2x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg4.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg4e16_v_bf16mf2x4(__bf16 *rs1, vbfloat16mf2x4_t vs3, size_t vl) { + return __riscv_vsseg4e16(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg4e16_v_bf16m1x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg4.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg4e16_v_bf16m1x4(__bf16 *rs1, vbfloat16m1x4_t vs3, size_t vl) { + return __riscv_vsseg4e16(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg4e16_v_bf16m2x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg4.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg4e16_v_bf16m2x4(__bf16 *rs1, vbfloat16m2x4_t vs3, size_t vl) { + return __riscv_vsseg4e16(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg4e16_v_bf16mf4x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg4.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg4e16_v_bf16mf4x4_m(vbool64_t vm, __bf16 *rs1, + vbfloat16mf4x4_t vs3, size_t vl) { + return __riscv_vsseg4e16(vm, rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg4e16_v_bf16mf2x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg4.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg4e16_v_bf16mf2x4_m(vbool32_t vm, __bf16 *rs1, + vbfloat16mf2x4_t vs3, size_t vl) { + return __riscv_vsseg4e16(vm, rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg4e16_v_bf16m1x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg4.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg4e16_v_bf16m1x4_m(vbool16_t vm, __bf16 *rs1, vbfloat16m1x4_t vs3, + size_t vl) { + return __riscv_vsseg4e16(vm, rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg4e16_v_bf16m2x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg4.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg4e16_v_bf16m2x4_m(vbool8_t vm, __bf16 *rs1, vbfloat16m2x4_t vs3, + size_t vl) { + return __riscv_vsseg4e16(vm, rs1, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsseg5e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsseg5e16.c new file mode 100644 index 0000000000000000000000000000000000000000..be8a12c0507877360c335660af174c042ca30634 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsseg5e16.c @@ -0,0 +1,102 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg5e16_v_bf16mf4x5( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg5.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg5e16_v_bf16mf4x5(__bf16 *rs1, vbfloat16mf4x5_t vs3, size_t vl) { + return __riscv_vsseg5e16(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg5e16_v_bf16mf2x5( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg5.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg5e16_v_bf16mf2x5(__bf16 *rs1, vbfloat16mf2x5_t vs3, size_t vl) { + return __riscv_vsseg5e16(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg5e16_v_bf16m1x5( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg5.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg5e16_v_bf16m1x5(__bf16 *rs1, vbfloat16m1x5_t vs3, size_t vl) { + return __riscv_vsseg5e16(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg5e16_v_bf16mf4x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg5.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg5e16_v_bf16mf4x5_m(vbool64_t vm, __bf16 *rs1, + vbfloat16mf4x5_t vs3, size_t vl) { + return __riscv_vsseg5e16(vm, rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg5e16_v_bf16mf2x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg5.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg5e16_v_bf16mf2x5_m(vbool32_t vm, __bf16 *rs1, + vbfloat16mf2x5_t vs3, size_t vl) { + return __riscv_vsseg5e16(vm, rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg5e16_v_bf16m1x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg5.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg5e16_v_bf16m1x5_m(vbool16_t vm, __bf16 *rs1, vbfloat16m1x5_t vs3, + size_t vl) { + return __riscv_vsseg5e16(vm, rs1, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsseg6e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsseg6e16.c new file mode 100644 index 0000000000000000000000000000000000000000..4de257158927032b33e3c5cde44a33b063509755 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsseg6e16.c @@ -0,0 +1,108 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg6e16_v_bf16mf4x6( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg6.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg6e16_v_bf16mf4x6(__bf16 *rs1, vbfloat16mf4x6_t vs3, size_t vl) { + return __riscv_vsseg6e16(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg6e16_v_bf16mf2x6( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg6.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg6e16_v_bf16mf2x6(__bf16 *rs1, vbfloat16mf2x6_t vs3, size_t vl) { + return __riscv_vsseg6e16(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg6e16_v_bf16m1x6( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg6.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg6e16_v_bf16m1x6(__bf16 *rs1, vbfloat16m1x6_t vs3, size_t vl) { + return __riscv_vsseg6e16(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg6e16_v_bf16mf4x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg6.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg6e16_v_bf16mf4x6_m(vbool64_t vm, __bf16 *rs1, + vbfloat16mf4x6_t vs3, size_t vl) { + return __riscv_vsseg6e16(vm, rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg6e16_v_bf16mf2x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg6.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg6e16_v_bf16mf2x6_m(vbool32_t vm, __bf16 *rs1, + vbfloat16mf2x6_t vs3, size_t vl) { + return __riscv_vsseg6e16(vm, rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg6e16_v_bf16m1x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg6.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg6e16_v_bf16m1x6_m(vbool16_t vm, __bf16 *rs1, vbfloat16m1x6_t vs3, + size_t vl) { + return __riscv_vsseg6e16(vm, rs1, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsseg7e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsseg7e16.c new file mode 100644 index 0000000000000000000000000000000000000000..24252fe479402411fce2527120076de59440d8d1 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsseg7e16.c @@ -0,0 +1,114 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg7e16_v_bf16mf4x7( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg7.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg7e16_v_bf16mf4x7(__bf16 *rs1, vbfloat16mf4x7_t vs3, size_t vl) { + return __riscv_vsseg7e16(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg7e16_v_bf16mf2x7( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg7.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg7e16_v_bf16mf2x7(__bf16 *rs1, vbfloat16mf2x7_t vs3, size_t vl) { + return __riscv_vsseg7e16(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg7e16_v_bf16m1x7( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg7.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg7e16_v_bf16m1x7(__bf16 *rs1, vbfloat16m1x7_t vs3, size_t vl) { + return __riscv_vsseg7e16(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg7e16_v_bf16mf4x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg7.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg7e16_v_bf16mf4x7_m(vbool64_t vm, __bf16 *rs1, + vbfloat16mf4x7_t vs3, size_t vl) { + return __riscv_vsseg7e16(vm, rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg7e16_v_bf16mf2x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg7.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg7e16_v_bf16mf2x7_m(vbool32_t vm, __bf16 *rs1, + vbfloat16mf2x7_t vs3, size_t vl) { + return __riscv_vsseg7e16(vm, rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg7e16_v_bf16m1x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg7.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg7e16_v_bf16m1x7_m(vbool16_t vm, __bf16 *rs1, vbfloat16m1x7_t vs3, + size_t vl) { + return __riscv_vsseg7e16(vm, rs1, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsseg8e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsseg8e16.c new file mode 100644 index 0000000000000000000000000000000000000000..c6f5e5db5d9c794c22b3f230337d8cfcf78980a5 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsseg8e16.c @@ -0,0 +1,120 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg8e16_v_bf16mf4x8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VS3]], 7 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg8.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg8e16_v_bf16mf4x8(__bf16 *rs1, vbfloat16mf4x8_t vs3, size_t vl) { + return __riscv_vsseg8e16(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg8e16_v_bf16mf2x8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VS3]], 7 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg8.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg8e16_v_bf16mf2x8(__bf16 *rs1, vbfloat16mf2x8_t vs3, size_t vl) { + return __riscv_vsseg8e16(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg8e16_v_bf16m1x8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], { , , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VS3]], 7 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg8.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg8e16_v_bf16m1x8(__bf16 *rs1, vbfloat16m1x8_t vs3, size_t vl) { + return __riscv_vsseg8e16(rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg8e16_v_bf16mf4x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VS3]], 7 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg8.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg8e16_v_bf16mf4x8_m(vbool64_t vm, __bf16 *rs1, + vbfloat16mf4x8_t vs3, size_t vl) { + return __riscv_vsseg8e16(vm, rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg8e16_v_bf16mf2x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VS3]], 7 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg8.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg8e16_v_bf16mf2x8_m(vbool32_t vm, __bf16 *rs1, + vbfloat16mf2x8_t vs3, size_t vl) { + return __riscv_vsseg8e16(vm, rs1, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsseg8e16_v_bf16m1x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], { , , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VS3]], 7 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsseg8.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsseg8e16_v_bf16m1x8_m(vbool16_t vm, __bf16 *rs1, vbfloat16m1x8_t vs3, + size_t vl) { + return __riscv_vsseg8e16(vm, rs1, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vssseg2e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vssseg2e16.c new file mode 100644 index 0000000000000000000000000000000000000000..ee6d701667dd46dfcac386dff147c498604f681c --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vssseg2e16.c @@ -0,0 +1,139 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg2e16_v_bf16mf4x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg2.nxv1bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg2e16_v_bf16mf4x2(__bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf4x2_t vs3, size_t vl) { + return __riscv_vssseg2e16(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg2e16_v_bf16mf2x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg2.nxv2bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg2e16_v_bf16mf2x2(__bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf2x2_t vs3, size_t vl) { + return __riscv_vssseg2e16(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg2e16_v_bf16m1x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg2.nxv4bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg2e16_v_bf16m1x2(__bf16 *rs1, ptrdiff_t rs2, vbfloat16m1x2_t vs3, + size_t vl) { + return __riscv_vssseg2e16(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg2e16_v_bf16m2x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg2.nxv8bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg2e16_v_bf16m2x2(__bf16 *rs1, ptrdiff_t rs2, vbfloat16m2x2_t vs3, + size_t vl) { + return __riscv_vssseg2e16(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg2e16_v_bf16m4x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg2.nxv16bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg2e16_v_bf16m4x2(__bf16 *rs1, ptrdiff_t rs2, vbfloat16m4x2_t vs3, + size_t vl) { + return __riscv_vssseg2e16(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg2e16_v_bf16mf4x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg2.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg2e16_v_bf16mf4x2_m(vbool64_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf4x2_t vs3, size_t vl) { + return __riscv_vssseg2e16(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg2e16_v_bf16mf2x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg2.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg2e16_v_bf16mf2x2_m(vbool32_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf2x2_t vs3, size_t vl) { + return __riscv_vssseg2e16(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg2e16_v_bf16m1x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg2.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg2e16_v_bf16m1x2_m(vbool16_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16m1x2_t vs3, size_t vl) { + return __riscv_vssseg2e16(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg2e16_v_bf16m2x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg2.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg2e16_v_bf16m2x2_m(vbool8_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16m2x2_t vs3, size_t vl) { + return __riscv_vssseg2e16(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg2e16_v_bf16m4x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg2.mask.nxv16bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg2e16_v_bf16m4x2_m(vbool4_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16m4x2_t vs3, size_t vl) { + return __riscv_vssseg2e16(vm, rs1, rs2, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vssseg3e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vssseg3e16.c new file mode 100644 index 0000000000000000000000000000000000000000..c8562ff453642e7902fc850ddaaee2e3ed9be39f --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vssseg3e16.c @@ -0,0 +1,121 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg3e16_v_bf16mf4x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg3.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg3e16_v_bf16mf4x3(__bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf4x3_t vs3, size_t vl) { + return __riscv_vssseg3e16(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg3e16_v_bf16mf2x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg3.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg3e16_v_bf16mf2x3(__bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf2x3_t vs3, size_t vl) { + return __riscv_vssseg3e16(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg3e16_v_bf16m1x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg3.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg3e16_v_bf16m1x3(__bf16 *rs1, ptrdiff_t rs2, vbfloat16m1x3_t vs3, + size_t vl) { + return __riscv_vssseg3e16(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg3e16_v_bf16m2x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg3.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg3e16_v_bf16m2x3(__bf16 *rs1, ptrdiff_t rs2, vbfloat16m2x3_t vs3, + size_t vl) { + return __riscv_vssseg3e16(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg3e16_v_bf16mf4x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg3.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg3e16_v_bf16mf4x3_m(vbool64_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf4x3_t vs3, size_t vl) { + return __riscv_vssseg3e16(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg3e16_v_bf16mf2x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg3.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg3e16_v_bf16mf2x3_m(vbool32_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf2x3_t vs3, size_t vl) { + return __riscv_vssseg3e16(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg3e16_v_bf16m1x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg3.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg3e16_v_bf16m1x3_m(vbool16_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16m1x3_t vs3, size_t vl) { + return __riscv_vssseg3e16(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg3e16_v_bf16m2x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg3.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg3e16_v_bf16m2x3_m(vbool8_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16m2x3_t vs3, size_t vl) { + return __riscv_vssseg3e16(vm, rs1, rs2, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vssseg4e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vssseg4e16.c new file mode 100644 index 0000000000000000000000000000000000000000..64069bdc03baa4aee73f25c3216030a99eadffb8 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vssseg4e16.c @@ -0,0 +1,129 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg4e16_v_bf16mf4x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg4.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg4e16_v_bf16mf4x4(__bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf4x4_t vs3, size_t vl) { + return __riscv_vssseg4e16(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg4e16_v_bf16mf2x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg4.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg4e16_v_bf16mf2x4(__bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf2x4_t vs3, size_t vl) { + return __riscv_vssseg4e16(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg4e16_v_bf16m1x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg4.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg4e16_v_bf16m1x4(__bf16 *rs1, ptrdiff_t rs2, vbfloat16m1x4_t vs3, + size_t vl) { + return __riscv_vssseg4e16(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg4e16_v_bf16m2x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg4.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg4e16_v_bf16m2x4(__bf16 *rs1, ptrdiff_t rs2, vbfloat16m2x4_t vs3, + size_t vl) { + return __riscv_vssseg4e16(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg4e16_v_bf16mf4x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg4.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg4e16_v_bf16mf4x4_m(vbool64_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf4x4_t vs3, size_t vl) { + return __riscv_vssseg4e16(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg4e16_v_bf16mf2x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg4.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg4e16_v_bf16mf2x4_m(vbool32_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf2x4_t vs3, size_t vl) { + return __riscv_vssseg4e16(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg4e16_v_bf16m1x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg4.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg4e16_v_bf16m1x4_m(vbool16_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16m1x4_t vs3, size_t vl) { + return __riscv_vssseg4e16(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg4e16_v_bf16m2x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg4.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg4e16_v_bf16m2x4_m(vbool8_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16m2x4_t vs3, size_t vl) { + return __riscv_vssseg4e16(vm, rs1, rs2, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vssseg5e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vssseg5e16.c new file mode 100644 index 0000000000000000000000000000000000000000..00cc1066474b019593ebd5188afa83420c23d12c --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vssseg5e16.c @@ -0,0 +1,105 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg5e16_v_bf16mf4x5( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg5.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg5e16_v_bf16mf4x5(__bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf4x5_t vs3, size_t vl) { + return __riscv_vssseg5e16(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg5e16_v_bf16mf2x5( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg5.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg5e16_v_bf16mf2x5(__bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf2x5_t vs3, size_t vl) { + return __riscv_vssseg5e16(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg5e16_v_bf16m1x5( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg5.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg5e16_v_bf16m1x5(__bf16 *rs1, ptrdiff_t rs2, vbfloat16m1x5_t vs3, + size_t vl) { + return __riscv_vssseg5e16(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg5e16_v_bf16mf4x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg5.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg5e16_v_bf16mf4x5_m(vbool64_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf4x5_t vs3, size_t vl) { + return __riscv_vssseg5e16(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg5e16_v_bf16mf2x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg5.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg5e16_v_bf16mf2x5_m(vbool32_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf2x5_t vs3, size_t vl) { + return __riscv_vssseg5e16(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg5e16_v_bf16m1x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg5.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg5e16_v_bf16m1x5_m(vbool16_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16m1x5_t vs3, size_t vl) { + return __riscv_vssseg5e16(vm, rs1, rs2, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vssseg6e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vssseg6e16.c new file mode 100644 index 0000000000000000000000000000000000000000..8be7e9fe56aadb8422af7d57b15d5fc05777452c --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vssseg6e16.c @@ -0,0 +1,111 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg6e16_v_bf16mf4x6( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg6.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg6e16_v_bf16mf4x6(__bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf4x6_t vs3, size_t vl) { + return __riscv_vssseg6e16(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg6e16_v_bf16mf2x6( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg6.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg6e16_v_bf16mf2x6(__bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf2x6_t vs3, size_t vl) { + return __riscv_vssseg6e16(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg6e16_v_bf16m1x6( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg6.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg6e16_v_bf16m1x6(__bf16 *rs1, ptrdiff_t rs2, vbfloat16m1x6_t vs3, + size_t vl) { + return __riscv_vssseg6e16(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg6e16_v_bf16mf4x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg6.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg6e16_v_bf16mf4x6_m(vbool64_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf4x6_t vs3, size_t vl) { + return __riscv_vssseg6e16(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg6e16_v_bf16mf2x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg6.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg6e16_v_bf16mf2x6_m(vbool32_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf2x6_t vs3, size_t vl) { + return __riscv_vssseg6e16(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg6e16_v_bf16m1x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg6.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg6e16_v_bf16m1x6_m(vbool16_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16m1x6_t vs3, size_t vl) { + return __riscv_vssseg6e16(vm, rs1, rs2, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vssseg7e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vssseg7e16.c new file mode 100644 index 0000000000000000000000000000000000000000..28c17de2ea1d9aa6cca2a1280a47b6c27640b117 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vssseg7e16.c @@ -0,0 +1,117 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg7e16_v_bf16mf4x7( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg7.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg7e16_v_bf16mf4x7(__bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf4x7_t vs3, size_t vl) { + return __riscv_vssseg7e16(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg7e16_v_bf16mf2x7( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg7.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg7e16_v_bf16mf2x7(__bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf2x7_t vs3, size_t vl) { + return __riscv_vssseg7e16(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg7e16_v_bf16m1x7( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg7.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg7e16_v_bf16m1x7(__bf16 *rs1, ptrdiff_t rs2, vbfloat16m1x7_t vs3, + size_t vl) { + return __riscv_vssseg7e16(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg7e16_v_bf16mf4x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg7.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg7e16_v_bf16mf4x7_m(vbool64_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf4x7_t vs3, size_t vl) { + return __riscv_vssseg7e16(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg7e16_v_bf16mf2x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg7.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg7e16_v_bf16mf2x7_m(vbool32_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf2x7_t vs3, size_t vl) { + return __riscv_vssseg7e16(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg7e16_v_bf16m1x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg7.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg7e16_v_bf16m1x7_m(vbool16_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16m1x7_t vs3, size_t vl) { + return __riscv_vssseg7e16(vm, rs1, rs2, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vssseg8e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vssseg8e16.c new file mode 100644 index 0000000000000000000000000000000000000000..90f0e46cf9766674d35ca8ef6b116d2cbc4996e5 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vssseg8e16.c @@ -0,0 +1,123 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg8e16_v_bf16mf4x8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VS3]], 7 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg8.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg8e16_v_bf16mf4x8(__bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf4x8_t vs3, size_t vl) { + return __riscv_vssseg8e16(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg8e16_v_bf16mf2x8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VS3]], 7 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg8.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg8e16_v_bf16mf2x8(__bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf2x8_t vs3, size_t vl) { + return __riscv_vssseg8e16(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg8e16_v_bf16m1x8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VS3]], 7 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg8.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg8e16_v_bf16m1x8(__bf16 *rs1, ptrdiff_t rs2, vbfloat16m1x8_t vs3, + size_t vl) { + return __riscv_vssseg8e16(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg8e16_v_bf16mf4x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VS3]], 7 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg8.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg8e16_v_bf16mf4x8_m(vbool64_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf4x8_t vs3, size_t vl) { + return __riscv_vssseg8e16(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg8e16_v_bf16mf2x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VS3]], 7 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg8.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg8e16_v_bf16mf2x8_m(vbool32_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16mf2x8_t vs3, size_t vl) { + return __riscv_vssseg8e16(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vssseg8e16_v_bf16m1x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], { , , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VS3]], 7 +// CHECK-RV64-NEXT: call void @llvm.riscv.vssseg8.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vssseg8e16_v_bf16m1x8_m(vbool16_t vm, __bf16 *rs1, ptrdiff_t rs2, + vbfloat16m1x8_t vs3, size_t vl) { + return __riscv_vssseg8e16(vm, rs1, rs2, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsuxei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsuxei16.c new file mode 100644 index 0000000000000000000000000000000000000000..ef8083df5cfb78988582d8d4fa017d16a89ac760 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsuxei16.c @@ -0,0 +1,141 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxei16_v_bf16mf4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxei.nxv1bf16.nxv1i16.i64( [[VS3]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxei16_v_bf16mf4(__bf16 *rs1, vuint16mf4_t rs2, vbfloat16mf4_t vs3, + size_t vl) { + return __riscv_vsuxei16(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxei16_v_bf16mf2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxei.nxv2bf16.nxv2i16.i64( [[VS3]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxei16_v_bf16mf2(__bf16 *rs1, vuint16mf2_t rs2, vbfloat16mf2_t vs3, + size_t vl) { + return __riscv_vsuxei16(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxei16_v_bf16m1( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxei.nxv4bf16.nxv4i16.i64( [[VS3]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxei16_v_bf16m1(__bf16 *rs1, vuint16m1_t rs2, vbfloat16m1_t vs3, + size_t vl) { + return __riscv_vsuxei16(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxei16_v_bf16m2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxei.nxv8bf16.nxv8i16.i64( [[VS3]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxei16_v_bf16m2(__bf16 *rs1, vuint16m2_t rs2, vbfloat16m2_t vs3, + size_t vl) { + return __riscv_vsuxei16(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxei16_v_bf16m4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxei.nxv16bf16.nxv16i16.i64( [[VS3]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxei16_v_bf16m4(__bf16 *rs1, vuint16m4_t rs2, vbfloat16m4_t vs3, + size_t vl) { + return __riscv_vsuxei16(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxei16_v_bf16m8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxei.nxv32bf16.nxv32i16.i64( [[VS3]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxei16_v_bf16m8(__bf16 *rs1, vuint16m8_t rs2, vbfloat16m8_t vs3, + size_t vl) { + return __riscv_vsuxei16(rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxei16_v_bf16mf4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxei.mask.nxv1bf16.nxv1i16.i64( [[VS3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxei16_v_bf16mf4_m(vbool64_t vm, __bf16 *rs1, vuint16mf4_t rs2, + vbfloat16mf4_t vs3, size_t vl) { + return __riscv_vsuxei16(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxei16_v_bf16mf2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxei.mask.nxv2bf16.nxv2i16.i64( [[VS3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxei16_v_bf16mf2_m(vbool32_t vm, __bf16 *rs1, vuint16mf2_t rs2, + vbfloat16mf2_t vs3, size_t vl) { + return __riscv_vsuxei16(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxei16_v_bf16m1_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxei.mask.nxv4bf16.nxv4i16.i64( [[VS3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxei16_v_bf16m1_m(vbool16_t vm, __bf16 *rs1, vuint16m1_t rs2, + vbfloat16m1_t vs3, size_t vl) { + return __riscv_vsuxei16(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxei16_v_bf16m2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxei.mask.nxv8bf16.nxv8i16.i64( [[VS3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxei16_v_bf16m2_m(vbool8_t vm, __bf16 *rs1, vuint16m2_t rs2, + vbfloat16m2_t vs3, size_t vl) { + return __riscv_vsuxei16(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxei16_v_bf16m4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxei.mask.nxv16bf16.nxv16i16.i64( [[VS3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxei16_v_bf16m4_m(vbool4_t vm, __bf16 *rs1, vuint16m4_t rs2, + vbfloat16m4_t vs3, size_t vl) { + return __riscv_vsuxei16(vm, rs1, rs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxei16_v_bf16m8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxei.mask.nxv32bf16.nxv32i16.i64( [[VS3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxei16_v_bf16m8_m(vbool2_t vm, __bf16 *rs1, vuint16m8_t rs2, + vbfloat16m8_t vs3, size_t vl) { + return __riscv_vsuxei16(vm, rs1, rs2, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsuxseg2ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsuxseg2ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..0ca9429723694c8be6607ba484675178f22d358d --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsuxseg2ei16.c @@ -0,0 +1,141 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg2ei16_v_bf16mf4x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg2.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg2ei16_v_bf16mf4x2(__bf16 *rs1, vuint16mf4_t vs2, + vbfloat16mf4x2_t vs3, size_t vl) { + return __riscv_vsuxseg2ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg2ei16_v_bf16mf2x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg2.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg2ei16_v_bf16mf2x2(__bf16 *rs1, vuint16mf2_t vs2, + vbfloat16mf2x2_t vs3, size_t vl) { + return __riscv_vsuxseg2ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg2ei16_v_bf16m1x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg2.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg2ei16_v_bf16m1x2(__bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x2_t vs3, size_t vl) { + return __riscv_vsuxseg2ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg2ei16_v_bf16m2x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg2.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg2ei16_v_bf16m2x2(__bf16 *rs1, vuint16m2_t vs2, + vbfloat16m2x2_t vs3, size_t vl) { + return __riscv_vsuxseg2ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg2ei16_v_bf16m4x2( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg2.nxv16bf16.nxv16i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg2ei16_v_bf16m4x2(__bf16 *rs1, vuint16m4_t vs2, + vbfloat16m4x2_t vs3, size_t vl) { + return __riscv_vsuxseg2ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg2ei16_v_bf16mf4x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg2.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg2ei16_v_bf16mf4x2_m(vbool64_t vm, __bf16 *rs1, + vuint16mf4_t vs2, vbfloat16mf4x2_t vs3, + size_t vl) { + return __riscv_vsuxseg2ei16(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg2ei16_v_bf16mf2x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg2.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg2ei16_v_bf16mf2x2_m(vbool32_t vm, __bf16 *rs1, + vuint16mf2_t vs2, vbfloat16mf2x2_t vs3, + size_t vl) { + return __riscv_vsuxseg2ei16(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg2ei16_v_bf16m1x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg2.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg2ei16_v_bf16m1x2_m(vbool16_t vm, __bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x2_t vs3, size_t vl) { + return __riscv_vsuxseg2ei16(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg2ei16_v_bf16m2x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg2.mask.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg2ei16_v_bf16m2x2_m(vbool8_t vm, __bf16 *rs1, vuint16m2_t vs2, + vbfloat16m2x2_t vs3, size_t vl) { + return __riscv_vsuxseg2ei16(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg2ei16_v_bf16m4x2_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VS3]], 1 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg2.mask.nxv16bf16.nxv16i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg2ei16_v_bf16m4x2_m(vbool4_t vm, __bf16 *rs1, vuint16m4_t vs2, + vbfloat16m4x2_t vs3, size_t vl) { + return __riscv_vsuxseg2ei16(vm, rs1, vs2, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsuxseg3ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsuxseg3ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..873af1b1a1d802293da4b113d225a16b014365e6 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsuxseg3ei16.c @@ -0,0 +1,123 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg3ei16_v_bf16mf4x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg3.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg3ei16_v_bf16mf4x3(__bf16 *rs1, vuint16mf4_t vs2, + vbfloat16mf4x3_t vs3, size_t vl) { + return __riscv_vsuxseg3ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg3ei16_v_bf16mf2x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg3.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg3ei16_v_bf16mf2x3(__bf16 *rs1, vuint16mf2_t vs2, + vbfloat16mf2x3_t vs3, size_t vl) { + return __riscv_vsuxseg3ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg3ei16_v_bf16m1x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg3.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg3ei16_v_bf16m1x3(__bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x3_t vs3, size_t vl) { + return __riscv_vsuxseg3ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg3ei16_v_bf16m2x3( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg3.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg3ei16_v_bf16m2x3(__bf16 *rs1, vuint16m2_t vs2, + vbfloat16m2x3_t vs3, size_t vl) { + return __riscv_vsuxseg3ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg3ei16_v_bf16mf4x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg3.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg3ei16_v_bf16mf4x3_m(vbool64_t vm, __bf16 *rs1, + vuint16mf4_t vs2, vbfloat16mf4x3_t vs3, + size_t vl) { + return __riscv_vsuxseg3ei16(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg3ei16_v_bf16mf2x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg3.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg3ei16_v_bf16mf2x3_m(vbool32_t vm, __bf16 *rs1, + vuint16mf2_t vs2, vbfloat16mf2x3_t vs3, + size_t vl) { + return __riscv_vsuxseg3ei16(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg3ei16_v_bf16m1x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg3.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg3ei16_v_bf16m1x3_m(vbool16_t vm, __bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x3_t vs3, size_t vl) { + return __riscv_vsuxseg3ei16(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg3ei16_v_bf16m2x3_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VS3]], 2 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg3.mask.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg3ei16_v_bf16m2x3_m(vbool8_t vm, __bf16 *rs1, vuint16m2_t vs2, + vbfloat16m2x3_t vs3, size_t vl) { + return __riscv_vsuxseg3ei16(vm, rs1, vs2, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsuxseg4ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsuxseg4ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..f0c497e107979e5d68925ba27b1ab9d12dfc6eef --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsuxseg4ei16.c @@ -0,0 +1,131 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg4ei16_v_bf16mf4x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg4.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg4ei16_v_bf16mf4x4(__bf16 *rs1, vuint16mf4_t vs2, + vbfloat16mf4x4_t vs3, size_t vl) { + return __riscv_vsuxseg4ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg4ei16_v_bf16mf2x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg4.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg4ei16_v_bf16mf2x4(__bf16 *rs1, vuint16mf2_t vs2, + vbfloat16mf2x4_t vs3, size_t vl) { + return __riscv_vsuxseg4ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg4ei16_v_bf16m1x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg4.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg4ei16_v_bf16m1x4(__bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x4_t vs3, size_t vl) { + return __riscv_vsuxseg4ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg4ei16_v_bf16m2x4( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg4.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg4ei16_v_bf16m2x4(__bf16 *rs1, vuint16m2_t vs2, + vbfloat16m2x4_t vs3, size_t vl) { + return __riscv_vsuxseg4ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg4ei16_v_bf16mf4x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg4.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg4ei16_v_bf16mf4x4_m(vbool64_t vm, __bf16 *rs1, + vuint16mf4_t vs2, vbfloat16mf4x4_t vs3, + size_t vl) { + return __riscv_vsuxseg4ei16(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg4ei16_v_bf16mf2x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg4.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg4ei16_v_bf16mf2x4_m(vbool32_t vm, __bf16 *rs1, + vuint16mf2_t vs2, vbfloat16mf2x4_t vs3, + size_t vl) { + return __riscv_vsuxseg4ei16(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg4ei16_v_bf16m1x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg4.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg4ei16_v_bf16m1x4_m(vbool16_t vm, __bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x4_t vs3, size_t vl) { + return __riscv_vsuxseg4ei16(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg4ei16_v_bf16m2x4_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg4.mask.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg4ei16_v_bf16m2x4_m(vbool8_t vm, __bf16 *rs1, vuint16m2_t vs2, + vbfloat16m2x4_t vs3, size_t vl) { + return __riscv_vsuxseg4ei16(vm, rs1, vs2, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsuxseg5ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsuxseg5ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..6a2ce44b869d0e1cb26b726a30ebf23c7f8b2353 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsuxseg5ei16.c @@ -0,0 +1,107 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg5ei16_v_bf16mf4x5( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg5.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg5ei16_v_bf16mf4x5(__bf16 *rs1, vuint16mf4_t vs2, + vbfloat16mf4x5_t vs3, size_t vl) { + return __riscv_vsuxseg5ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg5ei16_v_bf16mf2x5( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg5.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg5ei16_v_bf16mf2x5(__bf16 *rs1, vuint16mf2_t vs2, + vbfloat16mf2x5_t vs3, size_t vl) { + return __riscv_vsuxseg5ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg5ei16_v_bf16m1x5( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg5.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg5ei16_v_bf16m1x5(__bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x5_t vs3, size_t vl) { + return __riscv_vsuxseg5ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg5ei16_v_bf16mf4x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg5.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg5ei16_v_bf16mf4x5_m(vbool64_t vm, __bf16 *rs1, + vuint16mf4_t vs2, vbfloat16mf4x5_t vs3, + size_t vl) { + return __riscv_vsuxseg5ei16(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg5ei16_v_bf16mf2x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg5.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg5ei16_v_bf16mf2x5_m(vbool32_t vm, __bf16 *rs1, + vuint16mf2_t vs2, vbfloat16mf2x5_t vs3, + size_t vl) { + return __riscv_vsuxseg5ei16(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg5ei16_v_bf16m1x5_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg5.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg5ei16_v_bf16m1x5_m(vbool16_t vm, __bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x5_t vs3, size_t vl) { + return __riscv_vsuxseg5ei16(vm, rs1, vs2, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsuxseg6ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsuxseg6ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..84827b645e34d6ed526cf830ec8d557ab0a854d3 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsuxseg6ei16.c @@ -0,0 +1,113 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg6ei16_v_bf16mf4x6( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg6.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg6ei16_v_bf16mf4x6(__bf16 *rs1, vuint16mf4_t vs2, + vbfloat16mf4x6_t vs3, size_t vl) { + return __riscv_vsuxseg6ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg6ei16_v_bf16mf2x6( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg6.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg6ei16_v_bf16mf2x6(__bf16 *rs1, vuint16mf2_t vs2, + vbfloat16mf2x6_t vs3, size_t vl) { + return __riscv_vsuxseg6ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg6ei16_v_bf16m1x6( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg6.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg6ei16_v_bf16m1x6(__bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x6_t vs3, size_t vl) { + return __riscv_vsuxseg6ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg6ei16_v_bf16mf4x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg6.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg6ei16_v_bf16mf4x6_m(vbool64_t vm, __bf16 *rs1, + vuint16mf4_t vs2, vbfloat16mf4x6_t vs3, + size_t vl) { + return __riscv_vsuxseg6ei16(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg6ei16_v_bf16mf2x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg6.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg6ei16_v_bf16mf2x6_m(vbool32_t vm, __bf16 *rs1, + vuint16mf2_t vs2, vbfloat16mf2x6_t vs3, + size_t vl) { + return __riscv_vsuxseg6ei16(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg6ei16_v_bf16m1x6_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg6.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg6ei16_v_bf16m1x6_m(vbool16_t vm, __bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x6_t vs3, size_t vl) { + return __riscv_vsuxseg6ei16(vm, rs1, vs2, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsuxseg7ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsuxseg7ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..e8c00aaebe86db2e49765095c4c8db25c5fd6ed6 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsuxseg7ei16.c @@ -0,0 +1,119 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg7ei16_v_bf16mf4x7( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg7.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg7ei16_v_bf16mf4x7(__bf16 *rs1, vuint16mf4_t vs2, + vbfloat16mf4x7_t vs3, size_t vl) { + return __riscv_vsuxseg7ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg7ei16_v_bf16mf2x7( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg7.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg7ei16_v_bf16mf2x7(__bf16 *rs1, vuint16mf2_t vs2, + vbfloat16mf2x7_t vs3, size_t vl) { + return __riscv_vsuxseg7ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg7ei16_v_bf16m1x7( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg7.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg7ei16_v_bf16m1x7(__bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x7_t vs3, size_t vl) { + return __riscv_vsuxseg7ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg7ei16_v_bf16mf4x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg7.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg7ei16_v_bf16mf4x7_m(vbool64_t vm, __bf16 *rs1, + vuint16mf4_t vs2, vbfloat16mf4x7_t vs3, + size_t vl) { + return __riscv_vsuxseg7ei16(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg7ei16_v_bf16mf2x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg7.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg7ei16_v_bf16mf2x7_m(vbool32_t vm, __bf16 *rs1, + vuint16mf2_t vs2, vbfloat16mf2x7_t vs3, + size_t vl) { + return __riscv_vsuxseg7ei16(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg7ei16_v_bf16m1x7_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg7.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg7ei16_v_bf16m1x7_m(vbool16_t vm, __bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x7_t vs3, size_t vl) { + return __riscv_vsuxseg7ei16(vm, rs1, vs2, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsuxseg8ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsuxseg8ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..ff96cef336ea12fc228a0cd59cba7bba770c5150 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/bfloat16/vsuxseg8ei16.c @@ -0,0 +1,125 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg8ei16_v_bf16mf4x8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VS3]], 7 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg8.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg8ei16_v_bf16mf4x8(__bf16 *rs1, vuint16mf4_t vs2, + vbfloat16mf4x8_t vs3, size_t vl) { + return __riscv_vsuxseg8ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg8ei16_v_bf16mf2x8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VS3]], 7 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg8.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg8ei16_v_bf16mf2x8(__bf16 *rs1, vuint16mf2_t vs2, + vbfloat16mf2x8_t vs3, size_t vl) { + return __riscv_vsuxseg8ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg8ei16_v_bf16m1x8( +// CHECK-RV64-SAME: ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VS3]], 7 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg8.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg8ei16_v_bf16m1x8(__bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x8_t vs3, size_t vl) { + return __riscv_vsuxseg8ei16(rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg8ei16_v_bf16mf4x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VS3]], 7 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg8.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg8ei16_v_bf16mf4x8_m(vbool64_t vm, __bf16 *rs1, + vuint16mf4_t vs2, vbfloat16mf4x8_t vs3, + size_t vl) { + return __riscv_vsuxseg8ei16(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg8ei16_v_bf16mf2x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VS3]], 7 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg8.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg8ei16_v_bf16mf2x8_m(vbool32_t vm, __bf16 *rs1, + vuint16mf2_t vs2, vbfloat16mf2x8_t vs3, + size_t vl) { + return __riscv_vsuxseg8ei16(vm, rs1, vs2, vs3, vl); +} + +// CHECK-RV64-LABEL: define dso_local void @test_vsuxseg8ei16_v_bf16m1x8_m( +// CHECK-RV64-SAME: [[VM:%.*]], ptr noundef [[RS1:%.*]], [[VS2:%.*]], { , , , , , , , } [[VS3:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VS3]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VS3]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VS3]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VS3]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VS3]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VS3]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VS3]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VS3]], 7 +// CHECK-RV64-NEXT: call void @llvm.riscv.vsuxseg8.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VS2]], [[VM]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret void +// +void test_vsuxseg8ei16_v_bf16m1x8_m(vbool16_t vm, __bf16 *rs1, vuint16m1_t vs2, + vbfloat16m1x8_t vs3, size_t vl) { + return __riscv_vsuxseg8ei16(vm, rs1, vs2, vs3, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/vaesdf.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/vaesdf.c index 9c91d2a1192d569001b459eb37bfe0d8ddc2a0ed..ec3cd1a5a6968ddb4df6bcfd0889492a7c7b74e7 100644 --- a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/vaesdf.c +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/vaesdf.c @@ -206,13 +206,3 @@ vuint32m8_t test_vaesdf_vv_u32m8(vuint32m8_t vd, vuint32m8_t vs2, size_t vl) { return __riscv_vaesdf_vv(vd, vs2, vl); } -// CHECK-RV64-LABEL: define dso_local @test_vaesdf_vs_u32m8_u32m8 -// CHECK-RV64-SAME: ( [[VD:%.*]], [[VS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { -// CHECK-RV64-NEXT: entry: -// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vaesdf.vs.nxv16i32.nxv16i32.i64( [[VD]], [[VS2]], i64 [[VL]], i64 3) -// CHECK-RV64-NEXT: ret [[TMP0]] -// -vuint32m8_t test_vaesdf_vs_u32m8_u32m8(vuint32m8_t vd, vuint32m8_t vs2, size_t vl) { - return __riscv_vaesdf_vs(vd, vs2, vl); -} - diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/vaesdm.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/vaesdm.c index dac9eb38713b4d1cda1e01303af096593bc07dd7..85d452543db2bc3d5503d82276ddaae23fc530e0 100644 --- a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/vaesdm.c +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/vaesdm.c @@ -206,13 +206,3 @@ vuint32m8_t test_vaesdm_vv_u32m8(vuint32m8_t vd, vuint32m8_t vs2, size_t vl) { return __riscv_vaesdm_vv(vd, vs2, vl); } -// CHECK-RV64-LABEL: define dso_local @test_vaesdm_vs_u32m8_u32m8 -// CHECK-RV64-SAME: ( [[VD:%.*]], [[VS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { -// CHECK-RV64-NEXT: entry: -// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vaesdm.vs.nxv16i32.nxv16i32.i64( [[VD]], [[VS2]], i64 [[VL]], i64 3) -// CHECK-RV64-NEXT: ret [[TMP0]] -// -vuint32m8_t test_vaesdm_vs_u32m8_u32m8(vuint32m8_t vd, vuint32m8_t vs2, size_t vl) { - return __riscv_vaesdm_vs(vd, vs2, vl); -} - diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/vaesef.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/vaesef.c index 01875afa525efc08e40241fb75cd06a2c94aaa6e..6727ff24b83d3f50366e00c4a0c894ed178c3a43 100644 --- a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/vaesef.c +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/vaesef.c @@ -206,13 +206,3 @@ vuint32m8_t test_vaesef_vv_u32m8(vuint32m8_t vd, vuint32m8_t vs2, size_t vl) { return __riscv_vaesef_vv(vd, vs2, vl); } -// CHECK-RV64-LABEL: define dso_local @test_vaesef_vs_u32m8_u32m8 -// CHECK-RV64-SAME: ( [[VD:%.*]], [[VS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { -// CHECK-RV64-NEXT: entry: -// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vaesef.vs.nxv16i32.nxv16i32.i64( [[VD]], [[VS2]], i64 [[VL]], i64 3) -// CHECK-RV64-NEXT: ret [[TMP0]] -// -vuint32m8_t test_vaesef_vs_u32m8_u32m8(vuint32m8_t vd, vuint32m8_t vs2, size_t vl) { - return __riscv_vaesef_vs(vd, vs2, vl); -} - diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/vaesem.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/vaesem.c index e9a0add21c92d5126ff6a186801884ba3d5b385c..6ebfd5ff4962e4c85c419d3ddd018d6a1037a31d 100644 --- a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/vaesem.c +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/vaesem.c @@ -206,13 +206,3 @@ vuint32m8_t test_vaesem_vv_u32m8(vuint32m8_t vd, vuint32m8_t vs2, size_t vl) { return __riscv_vaesem_vv(vd, vs2, vl); } -// CHECK-RV64-LABEL: define dso_local @test_vaesem_vs_u32m8_u32m8 -// CHECK-RV64-SAME: ( [[VD:%.*]], [[VS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { -// CHECK-RV64-NEXT: entry: -// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vaesem.vs.nxv16i32.nxv16i32.i64( [[VD]], [[VS2]], i64 [[VL]], i64 3) -// CHECK-RV64-NEXT: ret [[TMP0]] -// -vuint32m8_t test_vaesem_vs_u32m8_u32m8(vuint32m8_t vd, vuint32m8_t vs2, size_t vl) { - return __riscv_vaesem_vs(vd, vs2, vl); -} - diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/vaesz.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/vaesz.c index c80e4ebce5e5b782e858f3fb66e8f6b82b9b3853..fe657a603d7b7561458ffdd71df14c59caedaf9a 100644 --- a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/vaesz.c +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/vaesz.c @@ -156,13 +156,3 @@ vuint32m8_t test_vaesz_vs_u32m4_u32m8(vuint32m8_t vd, vuint32m4_t vs2, size_t vl return __riscv_vaesz(vd, vs2, vl); } -// CHECK-RV64-LABEL: define dso_local @test_vaesz_vs_u32m8_u32m8 -// CHECK-RV64-SAME: ( [[VD:%.*]], [[VS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { -// CHECK-RV64-NEXT: entry: -// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vaesz.vs.nxv16i32.nxv16i32.i64( [[VD]], [[VS2]], i64 [[VL]], i64 3) -// CHECK-RV64-NEXT: ret [[TMP0]] -// -vuint32m8_t test_vaesz_vs_u32m8_u32m8(vuint32m8_t vd, vuint32m8_t vs2, size_t vl) { - return __riscv_vaesz(vd, vs2, vl); -} - diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/vsm4r.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/vsm4r.c index cfc8532835eaa3a5252416c6df8d91a9e5eef1f1..82f275af3e5002c029f69a08f837df63db840ecd 100644 --- a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/vsm4r.c +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/non-policy/overloaded/vsm4r.c @@ -206,13 +206,3 @@ vuint32m8_t test_vsm4r_vv_u32m8(vuint32m8_t vd, vuint32m8_t vs2, size_t vl) { return __riscv_vsm4r_vv(vd, vs2, vl); } -// CHECK-RV64-LABEL: define dso_local @test_vsm4r_vs_u32m8_u32m8 -// CHECK-RV64-SAME: ( [[VD:%.*]], [[VS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { -// CHECK-RV64-NEXT: entry: -// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vsm4r.vs.nxv16i32.nxv16i32.i64( [[VD]], [[VS2]], i64 [[VL]], i64 3) -// CHECK-RV64-NEXT: ret [[TMP0]] -// -vuint32m8_t test_vsm4r_vs_u32m8_u32m8(vuint32m8_t vd, vuint32m8_t vs2, size_t vl) { - return __riscv_vsm4r_vs(vd, vs2, vl); -} - diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vle16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vle16.c new file mode 100644 index 0000000000000000000000000000000000000000..53d8b4d625e7bffa0132c840dbb7747678ae0cd0 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vle16.c @@ -0,0 +1,249 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16mf4_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.nxv1bf16.i64( [[VD]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vle16_v_bf16mf4_tu(vbfloat16mf4_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vle16_v_bf16mf4_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16mf2_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.nxv2bf16.i64( [[VD]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vle16_v_bf16mf2_tu(vbfloat16mf2_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vle16_v_bf16mf2_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16m1_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.nxv4bf16.i64( [[VD]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vle16_v_bf16m1_tu(vbfloat16m1_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vle16_v_bf16m1_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16m2_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.nxv8bf16.i64( [[VD]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vle16_v_bf16m2_tu(vbfloat16m2_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vle16_v_bf16m2_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16m4_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.nxv16bf16.i64( [[VD]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vle16_v_bf16m4_tu(vbfloat16m4_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vle16_v_bf16m4_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16m8_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.nxv32bf16.i64( [[VD]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vle16_v_bf16m8_tu(vbfloat16m8_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vle16_v_bf16m8_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16mf4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.mask.nxv1bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vle16_v_bf16mf4_tum(vbool64_t vm, vbfloat16mf4_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vle16_v_bf16mf4_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16mf2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.mask.nxv2bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vle16_v_bf16mf2_tum(vbool32_t vm, vbfloat16mf2_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vle16_v_bf16mf2_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16m1_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.mask.nxv4bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vle16_v_bf16m1_tum(vbool16_t vm, vbfloat16m1_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vle16_v_bf16m1_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16m2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.mask.nxv8bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vle16_v_bf16m2_tum(vbool8_t vm, vbfloat16m2_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vle16_v_bf16m2_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16m4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.mask.nxv16bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vle16_v_bf16m4_tum(vbool4_t vm, vbfloat16m4_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vle16_v_bf16m4_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16m8_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.mask.nxv32bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vle16_v_bf16m8_tum(vbool2_t vm, vbfloat16m8_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vle16_v_bf16m8_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16mf4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.mask.nxv1bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vle16_v_bf16mf4_tumu(vbool64_t vm, vbfloat16mf4_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vle16_v_bf16mf4_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16mf2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.mask.nxv2bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vle16_v_bf16mf2_tumu(vbool32_t vm, vbfloat16mf2_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vle16_v_bf16mf2_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16m1_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.mask.nxv4bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vle16_v_bf16m1_tumu(vbool16_t vm, vbfloat16m1_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vle16_v_bf16m1_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16m2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.mask.nxv8bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vle16_v_bf16m2_tumu(vbool8_t vm, vbfloat16m2_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vle16_v_bf16m2_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16m4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.mask.nxv16bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vle16_v_bf16m4_tumu(vbool4_t vm, vbfloat16m4_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vle16_v_bf16m4_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16m8_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.mask.nxv32bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vle16_v_bf16m8_tumu(vbool2_t vm, vbfloat16m8_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vle16_v_bf16m8_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16mf4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.mask.nxv1bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vle16_v_bf16mf4_mu(vbool64_t vm, vbfloat16mf4_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vle16_v_bf16mf4_mu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16mf2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.mask.nxv2bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vle16_v_bf16mf2_mu(vbool32_t vm, vbfloat16mf2_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vle16_v_bf16mf2_mu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16m1_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.mask.nxv4bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vle16_v_bf16m1_mu(vbool16_t vm, vbfloat16m1_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vle16_v_bf16m1_mu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16m2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.mask.nxv8bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vle16_v_bf16m2_mu(vbool8_t vm, vbfloat16m2_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vle16_v_bf16m2_mu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16m4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.mask.nxv16bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vle16_v_bf16m4_mu(vbool4_t vm, vbfloat16m4_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vle16_v_bf16m4_mu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16m8_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.mask.nxv32bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vle16_v_bf16m8_mu(vbool2_t vm, vbfloat16m8_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vle16_v_bf16m8_mu(vm, vd, rs1, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vle16ff.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vle16ff.c new file mode 100644 index 0000000000000000000000000000000000000000..b7e689e00ada59e746d056e5931efbd53c98da2d --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vle16ff.c @@ -0,0 +1,321 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16mf4_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.nxv1bf16.i64( [[VD]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 2 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16mf4_t test_vle16ff_v_bf16mf4_tu(vbfloat16mf4_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vle16ff_v_bf16mf4_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16mf2_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.nxv2bf16.i64( [[VD]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 2 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16mf2_t test_vle16ff_v_bf16mf2_tu(vbfloat16mf2_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vle16ff_v_bf16mf2_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16m1_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.nxv4bf16.i64( [[VD]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 2 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16m1_t test_vle16ff_v_bf16m1_tu(vbfloat16m1_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vle16ff_v_bf16m1_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16m2_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.nxv8bf16.i64( [[VD]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 2 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16m2_t test_vle16ff_v_bf16m2_tu(vbfloat16m2_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vle16ff_v_bf16m2_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16m4_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.nxv16bf16.i64( [[VD]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 2 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16m4_t test_vle16ff_v_bf16m4_tu(vbfloat16m4_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vle16ff_v_bf16m4_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16m8_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.nxv32bf16.i64( [[VD]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 2 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16m8_t test_vle16ff_v_bf16m8_tu(vbfloat16m8_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vle16ff_v_bf16m8_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16mf4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.mask.nxv1bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16mf4_t test_vle16ff_v_bf16mf4_tum(vbool64_t vm, vbfloat16mf4_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vle16ff_v_bf16mf4_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16mf2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.mask.nxv2bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16mf2_t test_vle16ff_v_bf16mf2_tum(vbool32_t vm, vbfloat16mf2_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vle16ff_v_bf16mf2_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16m1_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.mask.nxv4bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16m1_t test_vle16ff_v_bf16m1_tum(vbool16_t vm, vbfloat16m1_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vle16ff_v_bf16m1_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16m2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.mask.nxv8bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16m2_t test_vle16ff_v_bf16m2_tum(vbool8_t vm, vbfloat16m2_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vle16ff_v_bf16m2_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16m4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.mask.nxv16bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16m4_t test_vle16ff_v_bf16m4_tum(vbool4_t vm, vbfloat16m4_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vle16ff_v_bf16m4_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16m8_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.mask.nxv32bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16m8_t test_vle16ff_v_bf16m8_tum(vbool2_t vm, vbfloat16m8_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vle16ff_v_bf16m8_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16mf4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.mask.nxv1bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16mf4_t test_vle16ff_v_bf16mf4_tumu(vbool64_t vm, vbfloat16mf4_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vle16ff_v_bf16mf4_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16mf2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.mask.nxv2bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16mf2_t test_vle16ff_v_bf16mf2_tumu(vbool32_t vm, vbfloat16mf2_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vle16ff_v_bf16mf2_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16m1_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.mask.nxv4bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16m1_t test_vle16ff_v_bf16m1_tumu(vbool16_t vm, vbfloat16m1_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vle16ff_v_bf16m1_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16m2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.mask.nxv8bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16m2_t test_vle16ff_v_bf16m2_tumu(vbool8_t vm, vbfloat16m2_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vle16ff_v_bf16m2_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16m4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.mask.nxv16bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16m4_t test_vle16ff_v_bf16m4_tumu(vbool4_t vm, vbfloat16m4_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vle16ff_v_bf16m4_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16m8_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.mask.nxv32bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16m8_t test_vle16ff_v_bf16m8_tumu(vbool2_t vm, vbfloat16m8_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vle16ff_v_bf16m8_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16mf4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.mask.nxv1bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16mf4_t test_vle16ff_v_bf16mf4_mu(vbool64_t vm, vbfloat16mf4_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vle16ff_v_bf16mf4_mu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16mf2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.mask.nxv2bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16mf2_t test_vle16ff_v_bf16mf2_mu(vbool32_t vm, vbfloat16mf2_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vle16ff_v_bf16mf2_mu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16m1_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.mask.nxv4bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16m1_t test_vle16ff_v_bf16m1_mu(vbool16_t vm, vbfloat16m1_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vle16ff_v_bf16m1_mu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16m2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.mask.nxv8bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16m2_t test_vle16ff_v_bf16m2_mu(vbool8_t vm, vbfloat16m2_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vle16ff_v_bf16m2_mu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16m4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.mask.nxv16bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16m4_t test_vle16ff_v_bf16m4_mu(vbool4_t vm, vbfloat16m4_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vle16ff_v_bf16m4_mu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16m8_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.mask.nxv32bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16m8_t test_vle16ff_v_bf16m8_mu(vbool2_t vm, vbfloat16m8_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vle16ff_v_bf16m8_mu(vm, vd, rs1, new_vl, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vloxei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vloxei16.c new file mode 100644 index 0000000000000000000000000000000000000000..c0cacbf48d01d09728c44d7b0f6173375ca92882 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vloxei16.c @@ -0,0 +1,249 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16mf4_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.nxv1bf16.nxv1i16.i64( [[VD]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vloxei16_v_bf16mf4_tu(vbfloat16mf4_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxei16_v_bf16mf4_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16mf2_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.nxv2bf16.nxv2i16.i64( [[VD]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vloxei16_v_bf16mf2_tu(vbfloat16mf2_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxei16_v_bf16mf2_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16m1_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.nxv4bf16.nxv4i16.i64( [[VD]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vloxei16_v_bf16m1_tu(vbfloat16m1_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vloxei16_v_bf16m1_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16m2_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.nxv8bf16.nxv8i16.i64( [[VD]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vloxei16_v_bf16m2_tu(vbfloat16m2_t vd, const __bf16 *rs1, vuint16m2_t rs2, size_t vl) { + return __riscv_vloxei16_v_bf16m2_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16m4_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.nxv16bf16.nxv16i16.i64( [[VD]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vloxei16_v_bf16m4_tu(vbfloat16m4_t vd, const __bf16 *rs1, vuint16m4_t rs2, size_t vl) { + return __riscv_vloxei16_v_bf16m4_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16m8_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.nxv32bf16.nxv32i16.i64( [[VD]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vloxei16_v_bf16m8_tu(vbfloat16m8_t vd, const __bf16 *rs1, vuint16m8_t rs2, size_t vl) { + return __riscv_vloxei16_v_bf16m8_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16mf4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.mask.nxv1bf16.nxv1i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vloxei16_v_bf16mf4_tum(vbool64_t vm, vbfloat16mf4_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxei16_v_bf16mf4_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16mf2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.mask.nxv2bf16.nxv2i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vloxei16_v_bf16mf2_tum(vbool32_t vm, vbfloat16mf2_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxei16_v_bf16mf2_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16m1_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.mask.nxv4bf16.nxv4i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vloxei16_v_bf16m1_tum(vbool16_t vm, vbfloat16m1_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vloxei16_v_bf16m1_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16m2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.mask.nxv8bf16.nxv8i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vloxei16_v_bf16m2_tum(vbool8_t vm, vbfloat16m2_t vd, const __bf16 *rs1, vuint16m2_t rs2, size_t vl) { + return __riscv_vloxei16_v_bf16m2_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16m4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.mask.nxv16bf16.nxv16i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vloxei16_v_bf16m4_tum(vbool4_t vm, vbfloat16m4_t vd, const __bf16 *rs1, vuint16m4_t rs2, size_t vl) { + return __riscv_vloxei16_v_bf16m4_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16m8_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.mask.nxv32bf16.nxv32i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vloxei16_v_bf16m8_tum(vbool2_t vm, vbfloat16m8_t vd, const __bf16 *rs1, vuint16m8_t rs2, size_t vl) { + return __riscv_vloxei16_v_bf16m8_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16mf4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.mask.nxv1bf16.nxv1i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vloxei16_v_bf16mf4_tumu(vbool64_t vm, vbfloat16mf4_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxei16_v_bf16mf4_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16mf2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.mask.nxv2bf16.nxv2i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vloxei16_v_bf16mf2_tumu(vbool32_t vm, vbfloat16mf2_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxei16_v_bf16mf2_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16m1_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.mask.nxv4bf16.nxv4i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vloxei16_v_bf16m1_tumu(vbool16_t vm, vbfloat16m1_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vloxei16_v_bf16m1_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16m2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.mask.nxv8bf16.nxv8i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vloxei16_v_bf16m2_tumu(vbool8_t vm, vbfloat16m2_t vd, const __bf16 *rs1, vuint16m2_t rs2, size_t vl) { + return __riscv_vloxei16_v_bf16m2_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16m4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.mask.nxv16bf16.nxv16i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vloxei16_v_bf16m4_tumu(vbool4_t vm, vbfloat16m4_t vd, const __bf16 *rs1, vuint16m4_t rs2, size_t vl) { + return __riscv_vloxei16_v_bf16m4_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16m8_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.mask.nxv32bf16.nxv32i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vloxei16_v_bf16m8_tumu(vbool2_t vm, vbfloat16m8_t vd, const __bf16 *rs1, vuint16m8_t rs2, size_t vl) { + return __riscv_vloxei16_v_bf16m8_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16mf4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.mask.nxv1bf16.nxv1i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vloxei16_v_bf16mf4_mu(vbool64_t vm, vbfloat16mf4_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxei16_v_bf16mf4_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16mf2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.mask.nxv2bf16.nxv2i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vloxei16_v_bf16mf2_mu(vbool32_t vm, vbfloat16mf2_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxei16_v_bf16mf2_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16m1_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.mask.nxv4bf16.nxv4i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vloxei16_v_bf16m1_mu(vbool16_t vm, vbfloat16m1_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vloxei16_v_bf16m1_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16m2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.mask.nxv8bf16.nxv8i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vloxei16_v_bf16m2_mu(vbool8_t vm, vbfloat16m2_t vd, const __bf16 *rs1, vuint16m2_t rs2, size_t vl) { + return __riscv_vloxei16_v_bf16m2_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16m4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.mask.nxv16bf16.nxv16i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vloxei16_v_bf16m4_mu(vbool4_t vm, vbfloat16m4_t vd, const __bf16 *rs1, vuint16m4_t rs2, size_t vl) { + return __riscv_vloxei16_v_bf16m4_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16m8_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.mask.nxv32bf16.nxv32i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vloxei16_v_bf16m8_mu(vbool2_t vm, vbfloat16m8_t vd, const __bf16 *rs1, vuint16m8_t rs2, size_t vl) { + return __riscv_vloxei16_v_bf16m8_mu(vm, vd, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vloxseg2ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vloxseg2ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..085a3784f87e2724f767ec91d49521c7b769a56d --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vloxseg2ei16.c @@ -0,0 +1,249 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16mf4x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vloxseg2.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf4x2_t test_vloxseg2ei16_v_bf16mf4x2_tu(vbfloat16mf4x2_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg2ei16_v_bf16mf4x2_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16mf2x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vloxseg2.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf2x2_t test_vloxseg2ei16_v_bf16mf2x2_tu(vbfloat16mf2x2_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg2ei16_v_bf16mf2x2_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16m1x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vloxseg2.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m1x2_t test_vloxseg2ei16_v_bf16m1x2_tu(vbfloat16m1x2_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg2ei16_v_bf16m1x2_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16m2x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vloxseg2.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m2x2_t test_vloxseg2ei16_v_bf16m2x2_tu(vbfloat16m2x2_t vd, const __bf16 *rs1, vuint16m2_t rs2, size_t vl) { + return __riscv_vloxseg2ei16_v_bf16m2x2_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16m4x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vloxseg2.nxv16bf16.nxv16i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m4x2_t test_vloxseg2ei16_v_bf16m4x2_tu(vbfloat16m4x2_t vd, const __bf16 *rs1, vuint16m4_t rs2, size_t vl) { + return __riscv_vloxseg2ei16_v_bf16m4x2_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16mf4x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vloxseg2.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf4x2_t test_vloxseg2ei16_v_bf16mf4x2_tum(vbool64_t vm, vbfloat16mf4x2_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg2ei16_v_bf16mf4x2_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16mf2x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vloxseg2.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf2x2_t test_vloxseg2ei16_v_bf16mf2x2_tum(vbool32_t vm, vbfloat16mf2x2_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg2ei16_v_bf16mf2x2_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16m1x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vloxseg2.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m1x2_t test_vloxseg2ei16_v_bf16m1x2_tum(vbool16_t vm, vbfloat16m1x2_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg2ei16_v_bf16m1x2_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16m2x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vloxseg2.mask.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m2x2_t test_vloxseg2ei16_v_bf16m2x2_tum(vbool8_t vm, vbfloat16m2x2_t vd, const __bf16 *rs1, vuint16m2_t rs2, size_t vl) { + return __riscv_vloxseg2ei16_v_bf16m2x2_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16m4x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vloxseg2.mask.nxv16bf16.nxv16i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m4x2_t test_vloxseg2ei16_v_bf16m4x2_tum(vbool4_t vm, vbfloat16m4x2_t vd, const __bf16 *rs1, vuint16m4_t rs2, size_t vl) { + return __riscv_vloxseg2ei16_v_bf16m4x2_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16mf4x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vloxseg2.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf4x2_t test_vloxseg2ei16_v_bf16mf4x2_tumu(vbool64_t vm, vbfloat16mf4x2_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg2ei16_v_bf16mf4x2_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16mf2x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vloxseg2.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf2x2_t test_vloxseg2ei16_v_bf16mf2x2_tumu(vbool32_t vm, vbfloat16mf2x2_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg2ei16_v_bf16mf2x2_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16m1x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vloxseg2.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m1x2_t test_vloxseg2ei16_v_bf16m1x2_tumu(vbool16_t vm, vbfloat16m1x2_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg2ei16_v_bf16m1x2_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16m2x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vloxseg2.mask.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m2x2_t test_vloxseg2ei16_v_bf16m2x2_tumu(vbool8_t vm, vbfloat16m2x2_t vd, const __bf16 *rs1, vuint16m2_t rs2, size_t vl) { + return __riscv_vloxseg2ei16_v_bf16m2x2_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16m4x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vloxseg2.mask.nxv16bf16.nxv16i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m4x2_t test_vloxseg2ei16_v_bf16m4x2_tumu(vbool4_t vm, vbfloat16m4x2_t vd, const __bf16 *rs1, vuint16m4_t rs2, size_t vl) { + return __riscv_vloxseg2ei16_v_bf16m4x2_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16mf4x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vloxseg2.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf4x2_t test_vloxseg2ei16_v_bf16mf4x2_mu(vbool64_t vm, vbfloat16mf4x2_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg2ei16_v_bf16mf4x2_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16mf2x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vloxseg2.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf2x2_t test_vloxseg2ei16_v_bf16mf2x2_mu(vbool32_t vm, vbfloat16mf2x2_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg2ei16_v_bf16mf2x2_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16m1x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vloxseg2.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m1x2_t test_vloxseg2ei16_v_bf16m1x2_mu(vbool16_t vm, vbfloat16m1x2_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg2ei16_v_bf16m1x2_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16m2x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vloxseg2.mask.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m2x2_t test_vloxseg2ei16_v_bf16m2x2_mu(vbool8_t vm, vbfloat16m2x2_t vd, const __bf16 *rs1, vuint16m2_t rs2, size_t vl) { + return __riscv_vloxseg2ei16_v_bf16m2x2_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16m4x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vloxseg2.mask.nxv16bf16.nxv16i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m4x2_t test_vloxseg2ei16_v_bf16m4x2_mu(vbool4_t vm, vbfloat16m4x2_t vd, const __bf16 *rs1, vuint16m4_t rs2, size_t vl) { + return __riscv_vloxseg2ei16_v_bf16m4x2_mu(vm, vd, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vloxseg3ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vloxseg3ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..43d21bd63478bc7667786c20c7d2a75a251640bc --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vloxseg3ei16.c @@ -0,0 +1,217 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vloxseg3ei16_v_bf16mf4x3_tu( +// CHECK-RV64-SAME: { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vloxseg3.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf4x3_t test_vloxseg3ei16_v_bf16mf4x3_tu(vbfloat16mf4x3_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg3ei16_v_bf16mf4x3_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vloxseg3ei16_v_bf16mf2x3_tu( +// CHECK-RV64-SAME: { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vloxseg3.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf2x3_t test_vloxseg3ei16_v_bf16mf2x3_tu(vbfloat16mf2x3_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg3ei16_v_bf16mf2x3_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vloxseg3ei16_v_bf16m1x3_tu( +// CHECK-RV64-SAME: { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vloxseg3.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m1x3_t test_vloxseg3ei16_v_bf16m1x3_tu(vbfloat16m1x3_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg3ei16_v_bf16m1x3_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vloxseg3ei16_v_bf16m2x3_tu( +// CHECK-RV64-SAME: { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vloxseg3.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m2x3_t test_vloxseg3ei16_v_bf16m2x3_tu(vbfloat16m2x3_t vd, const __bf16 *rs1, vuint16m2_t rs2, size_t vl) { + return __riscv_vloxseg3ei16_v_bf16m2x3_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vloxseg3ei16_v_bf16mf4x3_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vloxseg3.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf4x3_t test_vloxseg3ei16_v_bf16mf4x3_tum(vbool64_t vm, vbfloat16mf4x3_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg3ei16_v_bf16mf4x3_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vloxseg3ei16_v_bf16mf2x3_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vloxseg3.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf2x3_t test_vloxseg3ei16_v_bf16mf2x3_tum(vbool32_t vm, vbfloat16mf2x3_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg3ei16_v_bf16mf2x3_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vloxseg3ei16_v_bf16m1x3_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vloxseg3.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m1x3_t test_vloxseg3ei16_v_bf16m1x3_tum(vbool16_t vm, vbfloat16m1x3_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg3ei16_v_bf16m1x3_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vloxseg3ei16_v_bf16m2x3_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vloxseg3.mask.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m2x3_t test_vloxseg3ei16_v_bf16m2x3_tum(vbool8_t vm, vbfloat16m2x3_t vd, const __bf16 *rs1, vuint16m2_t rs2, size_t vl) { + return __riscv_vloxseg3ei16_v_bf16m2x3_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vloxseg3ei16_v_bf16mf4x3_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vloxseg3.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf4x3_t test_vloxseg3ei16_v_bf16mf4x3_tumu(vbool64_t vm, vbfloat16mf4x3_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg3ei16_v_bf16mf4x3_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vloxseg3ei16_v_bf16mf2x3_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vloxseg3.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf2x3_t test_vloxseg3ei16_v_bf16mf2x3_tumu(vbool32_t vm, vbfloat16mf2x3_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg3ei16_v_bf16mf2x3_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vloxseg3ei16_v_bf16m1x3_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vloxseg3.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m1x3_t test_vloxseg3ei16_v_bf16m1x3_tumu(vbool16_t vm, vbfloat16m1x3_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg3ei16_v_bf16m1x3_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vloxseg3ei16_v_bf16m2x3_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vloxseg3.mask.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m2x3_t test_vloxseg3ei16_v_bf16m2x3_tumu(vbool8_t vm, vbfloat16m2x3_t vd, const __bf16 *rs1, vuint16m2_t rs2, size_t vl) { + return __riscv_vloxseg3ei16_v_bf16m2x3_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vloxseg3ei16_v_bf16mf4x3_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vloxseg3.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf4x3_t test_vloxseg3ei16_v_bf16mf4x3_mu(vbool64_t vm, vbfloat16mf4x3_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg3ei16_v_bf16mf4x3_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vloxseg3ei16_v_bf16mf2x3_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vloxseg3.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf2x3_t test_vloxseg3ei16_v_bf16mf2x3_mu(vbool32_t vm, vbfloat16mf2x3_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg3ei16_v_bf16mf2x3_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vloxseg3ei16_v_bf16m1x3_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vloxseg3.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m1x3_t test_vloxseg3ei16_v_bf16m1x3_mu(vbool16_t vm, vbfloat16m1x3_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg3ei16_v_bf16m1x3_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vloxseg3ei16_v_bf16m2x3_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vloxseg3.mask.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m2x3_t test_vloxseg3ei16_v_bf16m2x3_mu(vbool8_t vm, vbfloat16m2x3_t vd, const __bf16 *rs1, vuint16m2_t rs2, size_t vl) { + return __riscv_vloxseg3ei16_v_bf16m2x3_mu(vm, vd, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vloxseg4ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vloxseg4ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..43c25cf7d5700cd0a9deb451345f057c037f2d72 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vloxseg4ei16.c @@ -0,0 +1,233 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vloxseg4ei16_v_bf16mf4x4_tu( +// CHECK-RV64-SAME: { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vloxseg4.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf4x4_t test_vloxseg4ei16_v_bf16mf4x4_tu(vbfloat16mf4x4_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg4ei16_v_bf16mf4x4_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vloxseg4ei16_v_bf16mf2x4_tu( +// CHECK-RV64-SAME: { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vloxseg4.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf2x4_t test_vloxseg4ei16_v_bf16mf2x4_tu(vbfloat16mf2x4_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg4ei16_v_bf16mf2x4_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vloxseg4ei16_v_bf16m1x4_tu( +// CHECK-RV64-SAME: { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vloxseg4.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m1x4_t test_vloxseg4ei16_v_bf16m1x4_tu(vbfloat16m1x4_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg4ei16_v_bf16m1x4_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vloxseg4ei16_v_bf16m2x4_tu( +// CHECK-RV64-SAME: { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vloxseg4.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m2x4_t test_vloxseg4ei16_v_bf16m2x4_tu(vbfloat16m2x4_t vd, const __bf16 *rs1, vuint16m2_t rs2, size_t vl) { + return __riscv_vloxseg4ei16_v_bf16m2x4_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vloxseg4ei16_v_bf16mf4x4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vloxseg4.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf4x4_t test_vloxseg4ei16_v_bf16mf4x4_tum(vbool64_t vm, vbfloat16mf4x4_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg4ei16_v_bf16mf4x4_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vloxseg4ei16_v_bf16mf2x4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vloxseg4.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf2x4_t test_vloxseg4ei16_v_bf16mf2x4_tum(vbool32_t vm, vbfloat16mf2x4_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg4ei16_v_bf16mf2x4_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vloxseg4ei16_v_bf16m1x4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vloxseg4.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m1x4_t test_vloxseg4ei16_v_bf16m1x4_tum(vbool16_t vm, vbfloat16m1x4_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg4ei16_v_bf16m1x4_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vloxseg4ei16_v_bf16m2x4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vloxseg4.mask.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m2x4_t test_vloxseg4ei16_v_bf16m2x4_tum(vbool8_t vm, vbfloat16m2x4_t vd, const __bf16 *rs1, vuint16m2_t rs2, size_t vl) { + return __riscv_vloxseg4ei16_v_bf16m2x4_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vloxseg4ei16_v_bf16mf4x4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vloxseg4.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf4x4_t test_vloxseg4ei16_v_bf16mf4x4_tumu(vbool64_t vm, vbfloat16mf4x4_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg4ei16_v_bf16mf4x4_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vloxseg4ei16_v_bf16mf2x4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vloxseg4.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf2x4_t test_vloxseg4ei16_v_bf16mf2x4_tumu(vbool32_t vm, vbfloat16mf2x4_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg4ei16_v_bf16mf2x4_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vloxseg4ei16_v_bf16m1x4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vloxseg4.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m1x4_t test_vloxseg4ei16_v_bf16m1x4_tumu(vbool16_t vm, vbfloat16m1x4_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg4ei16_v_bf16m1x4_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vloxseg4ei16_v_bf16m2x4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vloxseg4.mask.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m2x4_t test_vloxseg4ei16_v_bf16m2x4_tumu(vbool8_t vm, vbfloat16m2x4_t vd, const __bf16 *rs1, vuint16m2_t rs2, size_t vl) { + return __riscv_vloxseg4ei16_v_bf16m2x4_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vloxseg4ei16_v_bf16mf4x4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vloxseg4.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf4x4_t test_vloxseg4ei16_v_bf16mf4x4_mu(vbool64_t vm, vbfloat16mf4x4_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg4ei16_v_bf16mf4x4_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vloxseg4ei16_v_bf16mf2x4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vloxseg4.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf2x4_t test_vloxseg4ei16_v_bf16mf2x4_mu(vbool32_t vm, vbfloat16mf2x4_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg4ei16_v_bf16mf2x4_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vloxseg4ei16_v_bf16m1x4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vloxseg4.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m1x4_t test_vloxseg4ei16_v_bf16m1x4_mu(vbool16_t vm, vbfloat16m1x4_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg4ei16_v_bf16m1x4_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vloxseg4ei16_v_bf16m2x4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vloxseg4.mask.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m2x4_t test_vloxseg4ei16_v_bf16m2x4_mu(vbool8_t vm, vbfloat16m2x4_t vd, const __bf16 *rs1, vuint16m2_t rs2, size_t vl) { + return __riscv_vloxseg4ei16_v_bf16m2x4_mu(vm, vd, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vloxseg5ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vloxseg5ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..9177193a223479950afd0ff9c5347aec690426dd --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vloxseg5ei16.c @@ -0,0 +1,189 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vloxseg5ei16_v_bf16mf4x5_tu( +// CHECK-RV64-SAME: { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vloxseg5.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf4x5_t test_vloxseg5ei16_v_bf16mf4x5_tu(vbfloat16mf4x5_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg5ei16_v_bf16mf4x5_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vloxseg5ei16_v_bf16mf2x5_tu( +// CHECK-RV64-SAME: { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vloxseg5.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf2x5_t test_vloxseg5ei16_v_bf16mf2x5_tu(vbfloat16mf2x5_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg5ei16_v_bf16mf2x5_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vloxseg5ei16_v_bf16m1x5_tu( +// CHECK-RV64-SAME: { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vloxseg5.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16m1x5_t test_vloxseg5ei16_v_bf16m1x5_tu(vbfloat16m1x5_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg5ei16_v_bf16m1x5_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vloxseg5ei16_v_bf16mf4x5_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vloxseg5.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf4x5_t test_vloxseg5ei16_v_bf16mf4x5_tum(vbool64_t vm, vbfloat16mf4x5_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg5ei16_v_bf16mf4x5_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vloxseg5ei16_v_bf16mf2x5_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vloxseg5.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf2x5_t test_vloxseg5ei16_v_bf16mf2x5_tum(vbool32_t vm, vbfloat16mf2x5_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg5ei16_v_bf16mf2x5_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vloxseg5ei16_v_bf16m1x5_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vloxseg5.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16m1x5_t test_vloxseg5ei16_v_bf16m1x5_tum(vbool16_t vm, vbfloat16m1x5_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg5ei16_v_bf16m1x5_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vloxseg5ei16_v_bf16mf4x5_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vloxseg5.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf4x5_t test_vloxseg5ei16_v_bf16mf4x5_tumu(vbool64_t vm, vbfloat16mf4x5_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg5ei16_v_bf16mf4x5_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vloxseg5ei16_v_bf16mf2x5_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vloxseg5.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf2x5_t test_vloxseg5ei16_v_bf16mf2x5_tumu(vbool32_t vm, vbfloat16mf2x5_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg5ei16_v_bf16mf2x5_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vloxseg5ei16_v_bf16m1x5_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vloxseg5.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16m1x5_t test_vloxseg5ei16_v_bf16m1x5_tumu(vbool16_t vm, vbfloat16m1x5_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg5ei16_v_bf16m1x5_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vloxseg5ei16_v_bf16mf4x5_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vloxseg5.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf4x5_t test_vloxseg5ei16_v_bf16mf4x5_mu(vbool64_t vm, vbfloat16mf4x5_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg5ei16_v_bf16mf4x5_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vloxseg5ei16_v_bf16mf2x5_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vloxseg5.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf2x5_t test_vloxseg5ei16_v_bf16mf2x5_mu(vbool32_t vm, vbfloat16mf2x5_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg5ei16_v_bf16mf2x5_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vloxseg5ei16_v_bf16m1x5_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vloxseg5.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16m1x5_t test_vloxseg5ei16_v_bf16m1x5_mu(vbool16_t vm, vbfloat16m1x5_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg5ei16_v_bf16m1x5_mu(vm, vd, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vloxseg6ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vloxseg6ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..6e6ef3a5a254b8c11b9bc7fd35f9e13487cc15ed --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vloxseg6ei16.c @@ -0,0 +1,201 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vloxseg6ei16_v_bf16mf4x6_tu( +// CHECK-RV64-SAME: { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vloxseg6.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf4x6_t test_vloxseg6ei16_v_bf16mf4x6_tu(vbfloat16mf4x6_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg6ei16_v_bf16mf4x6_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vloxseg6ei16_v_bf16mf2x6_tu( +// CHECK-RV64-SAME: { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vloxseg6.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf2x6_t test_vloxseg6ei16_v_bf16mf2x6_tu(vbfloat16mf2x6_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg6ei16_v_bf16mf2x6_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vloxseg6ei16_v_bf16m1x6_tu( +// CHECK-RV64-SAME: { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vloxseg6.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16m1x6_t test_vloxseg6ei16_v_bf16m1x6_tu(vbfloat16m1x6_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg6ei16_v_bf16m1x6_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vloxseg6ei16_v_bf16mf4x6_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vloxseg6.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf4x6_t test_vloxseg6ei16_v_bf16mf4x6_tum(vbool64_t vm, vbfloat16mf4x6_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg6ei16_v_bf16mf4x6_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vloxseg6ei16_v_bf16mf2x6_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vloxseg6.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf2x6_t test_vloxseg6ei16_v_bf16mf2x6_tum(vbool32_t vm, vbfloat16mf2x6_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg6ei16_v_bf16mf2x6_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vloxseg6ei16_v_bf16m1x6_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vloxseg6.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16m1x6_t test_vloxseg6ei16_v_bf16m1x6_tum(vbool16_t vm, vbfloat16m1x6_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg6ei16_v_bf16m1x6_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vloxseg6ei16_v_bf16mf4x6_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vloxseg6.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf4x6_t test_vloxseg6ei16_v_bf16mf4x6_tumu(vbool64_t vm, vbfloat16mf4x6_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg6ei16_v_bf16mf4x6_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vloxseg6ei16_v_bf16mf2x6_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vloxseg6.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf2x6_t test_vloxseg6ei16_v_bf16mf2x6_tumu(vbool32_t vm, vbfloat16mf2x6_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg6ei16_v_bf16mf2x6_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vloxseg6ei16_v_bf16m1x6_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vloxseg6.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16m1x6_t test_vloxseg6ei16_v_bf16m1x6_tumu(vbool16_t vm, vbfloat16m1x6_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg6ei16_v_bf16m1x6_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vloxseg6ei16_v_bf16mf4x6_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vloxseg6.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf4x6_t test_vloxseg6ei16_v_bf16mf4x6_mu(vbool64_t vm, vbfloat16mf4x6_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg6ei16_v_bf16mf4x6_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vloxseg6ei16_v_bf16mf2x6_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vloxseg6.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf2x6_t test_vloxseg6ei16_v_bf16mf2x6_mu(vbool32_t vm, vbfloat16mf2x6_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg6ei16_v_bf16mf2x6_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vloxseg6ei16_v_bf16m1x6_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vloxseg6.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16m1x6_t test_vloxseg6ei16_v_bf16m1x6_mu(vbool16_t vm, vbfloat16m1x6_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg6ei16_v_bf16m1x6_mu(vm, vd, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vloxseg7ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vloxseg7ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..08b013399d3775504cca915b4ad091903b2f0c77 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vloxseg7ei16.c @@ -0,0 +1,213 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vloxseg7ei16_v_bf16mf4x7_tu( +// CHECK-RV64-SAME: { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vloxseg7.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf4x7_t test_vloxseg7ei16_v_bf16mf4x7_tu(vbfloat16mf4x7_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg7ei16_v_bf16mf4x7_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vloxseg7ei16_v_bf16mf2x7_tu( +// CHECK-RV64-SAME: { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vloxseg7.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf2x7_t test_vloxseg7ei16_v_bf16mf2x7_tu(vbfloat16mf2x7_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg7ei16_v_bf16mf2x7_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vloxseg7ei16_v_bf16m1x7_tu( +// CHECK-RV64-SAME: { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vloxseg7.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16m1x7_t test_vloxseg7ei16_v_bf16m1x7_tu(vbfloat16m1x7_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg7ei16_v_bf16m1x7_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vloxseg7ei16_v_bf16mf4x7_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vloxseg7.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf4x7_t test_vloxseg7ei16_v_bf16mf4x7_tum(vbool64_t vm, vbfloat16mf4x7_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg7ei16_v_bf16mf4x7_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vloxseg7ei16_v_bf16mf2x7_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vloxseg7.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf2x7_t test_vloxseg7ei16_v_bf16mf2x7_tum(vbool32_t vm, vbfloat16mf2x7_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg7ei16_v_bf16mf2x7_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vloxseg7ei16_v_bf16m1x7_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vloxseg7.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16m1x7_t test_vloxseg7ei16_v_bf16m1x7_tum(vbool16_t vm, vbfloat16m1x7_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg7ei16_v_bf16m1x7_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vloxseg7ei16_v_bf16mf4x7_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vloxseg7.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf4x7_t test_vloxseg7ei16_v_bf16mf4x7_tumu(vbool64_t vm, vbfloat16mf4x7_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg7ei16_v_bf16mf4x7_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vloxseg7ei16_v_bf16mf2x7_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vloxseg7.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf2x7_t test_vloxseg7ei16_v_bf16mf2x7_tumu(vbool32_t vm, vbfloat16mf2x7_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg7ei16_v_bf16mf2x7_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vloxseg7ei16_v_bf16m1x7_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vloxseg7.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16m1x7_t test_vloxseg7ei16_v_bf16m1x7_tumu(vbool16_t vm, vbfloat16m1x7_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg7ei16_v_bf16m1x7_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vloxseg7ei16_v_bf16mf4x7_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vloxseg7.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf4x7_t test_vloxseg7ei16_v_bf16mf4x7_mu(vbool64_t vm, vbfloat16mf4x7_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg7ei16_v_bf16mf4x7_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vloxseg7ei16_v_bf16mf2x7_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vloxseg7.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf2x7_t test_vloxseg7ei16_v_bf16mf2x7_mu(vbool32_t vm, vbfloat16mf2x7_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg7ei16_v_bf16mf2x7_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vloxseg7ei16_v_bf16m1x7_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vloxseg7.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16m1x7_t test_vloxseg7ei16_v_bf16m1x7_mu(vbool16_t vm, vbfloat16m1x7_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg7ei16_v_bf16m1x7_mu(vm, vd, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vloxseg8ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vloxseg8ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..aa738359fec3f22ef06d4be3f2ec1535b3312190 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vloxseg8ei16.c @@ -0,0 +1,225 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vloxseg8ei16_v_bf16mf4x8_tu( +// CHECK-RV64-SAME: { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vloxseg8.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf4x8_t test_vloxseg8ei16_v_bf16mf4x8_tu(vbfloat16mf4x8_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg8ei16_v_bf16mf4x8_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vloxseg8ei16_v_bf16mf2x8_tu( +// CHECK-RV64-SAME: { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vloxseg8.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf2x8_t test_vloxseg8ei16_v_bf16mf2x8_tu(vbfloat16mf2x8_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg8ei16_v_bf16mf2x8_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vloxseg8ei16_v_bf16m1x8_tu( +// CHECK-RV64-SAME: { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vloxseg8.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16m1x8_t test_vloxseg8ei16_v_bf16m1x8_tu(vbfloat16m1x8_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg8ei16_v_bf16m1x8_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vloxseg8ei16_v_bf16mf4x8_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vloxseg8.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf4x8_t test_vloxseg8ei16_v_bf16mf4x8_tum(vbool64_t vm, vbfloat16mf4x8_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg8ei16_v_bf16mf4x8_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vloxseg8ei16_v_bf16mf2x8_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vloxseg8.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf2x8_t test_vloxseg8ei16_v_bf16mf2x8_tum(vbool32_t vm, vbfloat16mf2x8_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg8ei16_v_bf16mf2x8_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vloxseg8ei16_v_bf16m1x8_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vloxseg8.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16m1x8_t test_vloxseg8ei16_v_bf16m1x8_tum(vbool16_t vm, vbfloat16m1x8_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg8ei16_v_bf16m1x8_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vloxseg8ei16_v_bf16mf4x8_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vloxseg8.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf4x8_t test_vloxseg8ei16_v_bf16mf4x8_tumu(vbool64_t vm, vbfloat16mf4x8_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg8ei16_v_bf16mf4x8_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vloxseg8ei16_v_bf16mf2x8_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vloxseg8.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf2x8_t test_vloxseg8ei16_v_bf16mf2x8_tumu(vbool32_t vm, vbfloat16mf2x8_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg8ei16_v_bf16mf2x8_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vloxseg8ei16_v_bf16m1x8_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vloxseg8.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16m1x8_t test_vloxseg8ei16_v_bf16m1x8_tumu(vbool16_t vm, vbfloat16m1x8_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg8ei16_v_bf16m1x8_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vloxseg8ei16_v_bf16mf4x8_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vloxseg8.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf4x8_t test_vloxseg8ei16_v_bf16mf4x8_mu(vbool64_t vm, vbfloat16mf4x8_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg8ei16_v_bf16mf4x8_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vloxseg8ei16_v_bf16mf2x8_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vloxseg8.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf2x8_t test_vloxseg8ei16_v_bf16mf2x8_mu(vbool32_t vm, vbfloat16mf2x8_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg8ei16_v_bf16mf2x8_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vloxseg8ei16_v_bf16m1x8_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vloxseg8.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16m1x8_t test_vloxseg8ei16_v_bf16m1x8_mu(vbool16_t vm, vbfloat16m1x8_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg8ei16_v_bf16m1x8_mu(vm, vd, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlse16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlse16.c new file mode 100644 index 0000000000000000000000000000000000000000..150d9031b24c703e29591047d70df33c4ec44b9c --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlse16.c @@ -0,0 +1,249 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16mf4_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.nxv1bf16.i64( [[VD]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vlse16_v_bf16mf4_tu(vbfloat16mf4_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlse16_v_bf16mf4_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16mf2_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.nxv2bf16.i64( [[VD]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vlse16_v_bf16mf2_tu(vbfloat16mf2_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlse16_v_bf16mf2_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16m1_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.nxv4bf16.i64( [[VD]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vlse16_v_bf16m1_tu(vbfloat16m1_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlse16_v_bf16m1_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16m2_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.nxv8bf16.i64( [[VD]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vlse16_v_bf16m2_tu(vbfloat16m2_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlse16_v_bf16m2_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16m4_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.nxv16bf16.i64( [[VD]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vlse16_v_bf16m4_tu(vbfloat16m4_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlse16_v_bf16m4_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16m8_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.nxv32bf16.i64( [[VD]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vlse16_v_bf16m8_tu(vbfloat16m8_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlse16_v_bf16m8_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16mf4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.mask.nxv1bf16.i64( [[VD]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vlse16_v_bf16mf4_tum(vbool64_t vm, vbfloat16mf4_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlse16_v_bf16mf4_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16mf2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.mask.nxv2bf16.i64( [[VD]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vlse16_v_bf16mf2_tum(vbool32_t vm, vbfloat16mf2_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlse16_v_bf16mf2_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16m1_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.mask.nxv4bf16.i64( [[VD]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vlse16_v_bf16m1_tum(vbool16_t vm, vbfloat16m1_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlse16_v_bf16m1_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16m2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.mask.nxv8bf16.i64( [[VD]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vlse16_v_bf16m2_tum(vbool8_t vm, vbfloat16m2_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlse16_v_bf16m2_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16m4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.mask.nxv16bf16.i64( [[VD]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vlse16_v_bf16m4_tum(vbool4_t vm, vbfloat16m4_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlse16_v_bf16m4_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16m8_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.mask.nxv32bf16.i64( [[VD]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vlse16_v_bf16m8_tum(vbool2_t vm, vbfloat16m8_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlse16_v_bf16m8_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16mf4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.mask.nxv1bf16.i64( [[VD]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vlse16_v_bf16mf4_tumu(vbool64_t vm, vbfloat16mf4_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlse16_v_bf16mf4_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16mf2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.mask.nxv2bf16.i64( [[VD]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vlse16_v_bf16mf2_tumu(vbool32_t vm, vbfloat16mf2_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlse16_v_bf16mf2_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16m1_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.mask.nxv4bf16.i64( [[VD]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vlse16_v_bf16m1_tumu(vbool16_t vm, vbfloat16m1_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlse16_v_bf16m1_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16m2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.mask.nxv8bf16.i64( [[VD]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vlse16_v_bf16m2_tumu(vbool8_t vm, vbfloat16m2_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlse16_v_bf16m2_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16m4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.mask.nxv16bf16.i64( [[VD]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vlse16_v_bf16m4_tumu(vbool4_t vm, vbfloat16m4_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlse16_v_bf16m4_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16m8_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.mask.nxv32bf16.i64( [[VD]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vlse16_v_bf16m8_tumu(vbool2_t vm, vbfloat16m8_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlse16_v_bf16m8_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16mf4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.mask.nxv1bf16.i64( [[VD]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vlse16_v_bf16mf4_mu(vbool64_t vm, vbfloat16mf4_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlse16_v_bf16mf4_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16mf2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.mask.nxv2bf16.i64( [[VD]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vlse16_v_bf16mf2_mu(vbool32_t vm, vbfloat16mf2_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlse16_v_bf16mf2_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16m1_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.mask.nxv4bf16.i64( [[VD]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vlse16_v_bf16m1_mu(vbool16_t vm, vbfloat16m1_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlse16_v_bf16m1_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16m2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.mask.nxv8bf16.i64( [[VD]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vlse16_v_bf16m2_mu(vbool8_t vm, vbfloat16m2_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlse16_v_bf16m2_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16m4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.mask.nxv16bf16.i64( [[VD]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vlse16_v_bf16m4_mu(vbool4_t vm, vbfloat16m4_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlse16_v_bf16m4_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16m8_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.mask.nxv32bf16.i64( [[VD]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vlse16_v_bf16m8_mu(vbool2_t vm, vbfloat16m8_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlse16_v_bf16m8_mu(vm, vd, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlseg2e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlseg2e16.c new file mode 100644 index 0000000000000000000000000000000000000000..61328eca7ce0cd5e47bd5d36e1c7ebb00ac798eb --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlseg2e16.c @@ -0,0 +1,249 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16mf4x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlseg2.nxv1bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf4x2_t test_vlseg2e16_v_bf16mf4x2_tu(vbfloat16mf4x2_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg2e16_v_bf16mf4x2_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16mf2x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlseg2.nxv2bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf2x2_t test_vlseg2e16_v_bf16mf2x2_tu(vbfloat16mf2x2_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg2e16_v_bf16mf2x2_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16m1x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlseg2.nxv4bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m1x2_t test_vlseg2e16_v_bf16m1x2_tu(vbfloat16m1x2_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg2e16_v_bf16m1x2_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16m2x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlseg2.nxv8bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m2x2_t test_vlseg2e16_v_bf16m2x2_tu(vbfloat16m2x2_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg2e16_v_bf16m2x2_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16m4x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlseg2.nxv16bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m4x2_t test_vlseg2e16_v_bf16m4x2_tu(vbfloat16m4x2_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg2e16_v_bf16m4x2_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16mf4x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlseg2.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf4x2_t test_vlseg2e16_v_bf16mf4x2_tum(vbool64_t vm, vbfloat16mf4x2_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg2e16_v_bf16mf4x2_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16mf2x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlseg2.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf2x2_t test_vlseg2e16_v_bf16mf2x2_tum(vbool32_t vm, vbfloat16mf2x2_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg2e16_v_bf16mf2x2_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16m1x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlseg2.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m1x2_t test_vlseg2e16_v_bf16m1x2_tum(vbool16_t vm, vbfloat16m1x2_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg2e16_v_bf16m1x2_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16m2x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlseg2.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m2x2_t test_vlseg2e16_v_bf16m2x2_tum(vbool8_t vm, vbfloat16m2x2_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg2e16_v_bf16m2x2_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16m4x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlseg2.mask.nxv16bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m4x2_t test_vlseg2e16_v_bf16m4x2_tum(vbool4_t vm, vbfloat16m4x2_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg2e16_v_bf16m4x2_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16mf4x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlseg2.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf4x2_t test_vlseg2e16_v_bf16mf4x2_tumu(vbool64_t vm, vbfloat16mf4x2_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg2e16_v_bf16mf4x2_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16mf2x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlseg2.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf2x2_t test_vlseg2e16_v_bf16mf2x2_tumu(vbool32_t vm, vbfloat16mf2x2_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg2e16_v_bf16mf2x2_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16m1x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlseg2.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m1x2_t test_vlseg2e16_v_bf16m1x2_tumu(vbool16_t vm, vbfloat16m1x2_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg2e16_v_bf16m1x2_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16m2x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlseg2.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m2x2_t test_vlseg2e16_v_bf16m2x2_tumu(vbool8_t vm, vbfloat16m2x2_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg2e16_v_bf16m2x2_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16m4x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlseg2.mask.nxv16bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m4x2_t test_vlseg2e16_v_bf16m4x2_tumu(vbool4_t vm, vbfloat16m4x2_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg2e16_v_bf16m4x2_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16mf4x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlseg2.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf4x2_t test_vlseg2e16_v_bf16mf4x2_mu(vbool64_t vm, vbfloat16mf4x2_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg2e16_v_bf16mf4x2_mu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16mf2x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlseg2.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf2x2_t test_vlseg2e16_v_bf16mf2x2_mu(vbool32_t vm, vbfloat16mf2x2_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg2e16_v_bf16mf2x2_mu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16m1x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlseg2.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m1x2_t test_vlseg2e16_v_bf16m1x2_mu(vbool16_t vm, vbfloat16m1x2_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg2e16_v_bf16m1x2_mu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16m2x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlseg2.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m2x2_t test_vlseg2e16_v_bf16m2x2_mu(vbool8_t vm, vbfloat16m2x2_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg2e16_v_bf16m2x2_mu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16m4x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlseg2.mask.nxv16bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m4x2_t test_vlseg2e16_v_bf16m4x2_mu(vbool4_t vm, vbfloat16m4x2_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg2e16_v_bf16m4x2_mu(vm, vd, rs1, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlseg2e16ff.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlseg2e16ff.c new file mode 100644 index 0000000000000000000000000000000000000000..8a0bfb50c90907a3a255757a606fedca7ce3dfab --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlseg2e16ff.c @@ -0,0 +1,369 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16mf4x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.nxv1bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP2]], 0 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } poison, [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP2]], 1 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , } [[TMP4]], [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , i64 } [[TMP2]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP6]] +// +vbfloat16mf4x2_t test_vlseg2e16ff_v_bf16mf4x2_tu(vbfloat16mf4x2_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff_v_bf16mf4x2_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16mf2x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.nxv2bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP2]], 0 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } poison, [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP2]], 1 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , } [[TMP4]], [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , i64 } [[TMP2]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP6]] +// +vbfloat16mf2x2_t test_vlseg2e16ff_v_bf16mf2x2_tu(vbfloat16mf2x2_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff_v_bf16mf2x2_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16m1x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.nxv4bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP2]], 0 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } poison, [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP2]], 1 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , } [[TMP4]], [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , i64 } [[TMP2]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP6]] +// +vbfloat16m1x2_t test_vlseg2e16ff_v_bf16m1x2_tu(vbfloat16m1x2_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff_v_bf16m1x2_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16m2x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.nxv8bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP2]], 0 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } poison, [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP2]], 1 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , } [[TMP4]], [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , i64 } [[TMP2]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP6]] +// +vbfloat16m2x2_t test_vlseg2e16ff_v_bf16m2x2_tu(vbfloat16m2x2_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff_v_bf16m2x2_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16m4x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.nxv16bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP2]], 0 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } poison, [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP2]], 1 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , } [[TMP4]], [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , i64 } [[TMP2]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP6]] +// +vbfloat16m4x2_t test_vlseg2e16ff_v_bf16m4x2_tu(vbfloat16m4x2_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff_v_bf16m4x2_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16mf4x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP2]], 0 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } poison, [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP2]], 1 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , } [[TMP4]], [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , i64 } [[TMP2]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP6]] +// +vbfloat16mf4x2_t test_vlseg2e16ff_v_bf16mf4x2_tum(vbool64_t vm, vbfloat16mf4x2_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff_v_bf16mf4x2_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16mf2x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP2]], 0 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } poison, [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP2]], 1 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , } [[TMP4]], [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , i64 } [[TMP2]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP6]] +// +vbfloat16mf2x2_t test_vlseg2e16ff_v_bf16mf2x2_tum(vbool32_t vm, vbfloat16mf2x2_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff_v_bf16mf2x2_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16m1x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP2]], 0 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } poison, [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP2]], 1 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , } [[TMP4]], [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , i64 } [[TMP2]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP6]] +// +vbfloat16m1x2_t test_vlseg2e16ff_v_bf16m1x2_tum(vbool16_t vm, vbfloat16m1x2_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff_v_bf16m1x2_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16m2x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP2]], 0 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } poison, [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP2]], 1 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , } [[TMP4]], [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , i64 } [[TMP2]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP6]] +// +vbfloat16m2x2_t test_vlseg2e16ff_v_bf16m2x2_tum(vbool8_t vm, vbfloat16m2x2_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff_v_bf16m2x2_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16m4x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.mask.nxv16bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP2]], 0 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } poison, [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP2]], 1 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , } [[TMP4]], [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , i64 } [[TMP2]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP6]] +// +vbfloat16m4x2_t test_vlseg2e16ff_v_bf16m4x2_tum(vbool4_t vm, vbfloat16m4x2_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff_v_bf16m4x2_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16mf4x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP2]], 0 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } poison, [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP2]], 1 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , } [[TMP4]], [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , i64 } [[TMP2]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP6]] +// +vbfloat16mf4x2_t test_vlseg2e16ff_v_bf16mf4x2_tumu(vbool64_t vm, vbfloat16mf4x2_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff_v_bf16mf4x2_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16mf2x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP2]], 0 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } poison, [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP2]], 1 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , } [[TMP4]], [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , i64 } [[TMP2]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP6]] +// +vbfloat16mf2x2_t test_vlseg2e16ff_v_bf16mf2x2_tumu(vbool32_t vm, vbfloat16mf2x2_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff_v_bf16mf2x2_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16m1x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP2]], 0 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } poison, [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP2]], 1 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , } [[TMP4]], [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , i64 } [[TMP2]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP6]] +// +vbfloat16m1x2_t test_vlseg2e16ff_v_bf16m1x2_tumu(vbool16_t vm, vbfloat16m1x2_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff_v_bf16m1x2_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16m2x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP2]], 0 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } poison, [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP2]], 1 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , } [[TMP4]], [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , i64 } [[TMP2]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP6]] +// +vbfloat16m2x2_t test_vlseg2e16ff_v_bf16m2x2_tumu(vbool8_t vm, vbfloat16m2x2_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff_v_bf16m2x2_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16m4x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.mask.nxv16bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP2]], 0 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } poison, [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP2]], 1 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , } [[TMP4]], [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , i64 } [[TMP2]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP6]] +// +vbfloat16m4x2_t test_vlseg2e16ff_v_bf16m4x2_tumu(vbool4_t vm, vbfloat16m4x2_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff_v_bf16m4x2_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16mf4x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP2]], 0 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } poison, [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP2]], 1 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , } [[TMP4]], [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , i64 } [[TMP2]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP6]] +// +vbfloat16mf4x2_t test_vlseg2e16ff_v_bf16mf4x2_mu(vbool64_t vm, vbfloat16mf4x2_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff_v_bf16mf4x2_mu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16mf2x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP2]], 0 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } poison, [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP2]], 1 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , } [[TMP4]], [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , i64 } [[TMP2]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP6]] +// +vbfloat16mf2x2_t test_vlseg2e16ff_v_bf16mf2x2_mu(vbool32_t vm, vbfloat16mf2x2_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff_v_bf16mf2x2_mu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16m1x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP2]], 0 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } poison, [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP2]], 1 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , } [[TMP4]], [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , i64 } [[TMP2]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP6]] +// +vbfloat16m1x2_t test_vlseg2e16ff_v_bf16m1x2_mu(vbool16_t vm, vbfloat16m1x2_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff_v_bf16m1x2_mu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16m2x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP2]], 0 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } poison, [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP2]], 1 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , } [[TMP4]], [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , i64 } [[TMP2]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP6]] +// +vbfloat16m2x2_t test_vlseg2e16ff_v_bf16m2x2_mu(vbool8_t vm, vbfloat16m2x2_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff_v_bf16m2x2_mu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16m4x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.mask.nxv16bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP2]], 0 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } poison, [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP2]], 1 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , } [[TMP4]], [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , i64 } [[TMP2]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP6]] +// +vbfloat16m4x2_t test_vlseg2e16ff_v_bf16m4x2_mu(vbool4_t vm, vbfloat16m4x2_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff_v_bf16m4x2_mu(vm, vd, rs1, new_vl, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlseg3e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlseg3e16.c new file mode 100644 index 0000000000000000000000000000000000000000..10ec33ec6fecd3502976e34cb9037268aa8ff61e --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlseg3e16.c @@ -0,0 +1,217 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16_v_bf16mf4x3_tu( +// CHECK-RV64-SAME: { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlseg3.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf4x3_t test_vlseg3e16_v_bf16mf4x3_tu(vbfloat16mf4x3_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg3e16_v_bf16mf4x3_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16_v_bf16mf2x3_tu( +// CHECK-RV64-SAME: { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlseg3.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf2x3_t test_vlseg3e16_v_bf16mf2x3_tu(vbfloat16mf2x3_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg3e16_v_bf16mf2x3_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16_v_bf16m1x3_tu( +// CHECK-RV64-SAME: { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlseg3.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m1x3_t test_vlseg3e16_v_bf16m1x3_tu(vbfloat16m1x3_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg3e16_v_bf16m1x3_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16_v_bf16m2x3_tu( +// CHECK-RV64-SAME: { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlseg3.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m2x3_t test_vlseg3e16_v_bf16m2x3_tu(vbfloat16m2x3_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg3e16_v_bf16m2x3_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16_v_bf16mf4x3_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlseg3.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf4x3_t test_vlseg3e16_v_bf16mf4x3_tum(vbool64_t vm, vbfloat16mf4x3_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg3e16_v_bf16mf4x3_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16_v_bf16mf2x3_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlseg3.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf2x3_t test_vlseg3e16_v_bf16mf2x3_tum(vbool32_t vm, vbfloat16mf2x3_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg3e16_v_bf16mf2x3_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16_v_bf16m1x3_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlseg3.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m1x3_t test_vlseg3e16_v_bf16m1x3_tum(vbool16_t vm, vbfloat16m1x3_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg3e16_v_bf16m1x3_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16_v_bf16m2x3_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlseg3.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m2x3_t test_vlseg3e16_v_bf16m2x3_tum(vbool8_t vm, vbfloat16m2x3_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg3e16_v_bf16m2x3_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16_v_bf16mf4x3_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlseg3.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf4x3_t test_vlseg3e16_v_bf16mf4x3_tumu(vbool64_t vm, vbfloat16mf4x3_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg3e16_v_bf16mf4x3_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16_v_bf16mf2x3_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlseg3.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf2x3_t test_vlseg3e16_v_bf16mf2x3_tumu(vbool32_t vm, vbfloat16mf2x3_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg3e16_v_bf16mf2x3_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16_v_bf16m1x3_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlseg3.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m1x3_t test_vlseg3e16_v_bf16m1x3_tumu(vbool16_t vm, vbfloat16m1x3_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg3e16_v_bf16m1x3_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16_v_bf16m2x3_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlseg3.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m2x3_t test_vlseg3e16_v_bf16m2x3_tumu(vbool8_t vm, vbfloat16m2x3_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg3e16_v_bf16m2x3_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16_v_bf16mf4x3_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlseg3.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf4x3_t test_vlseg3e16_v_bf16mf4x3_mu(vbool64_t vm, vbfloat16mf4x3_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg3e16_v_bf16mf4x3_mu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16_v_bf16mf2x3_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlseg3.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf2x3_t test_vlseg3e16_v_bf16mf2x3_mu(vbool32_t vm, vbfloat16mf2x3_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg3e16_v_bf16mf2x3_mu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16_v_bf16m1x3_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlseg3.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m1x3_t test_vlseg3e16_v_bf16m1x3_mu(vbool16_t vm, vbfloat16m1x3_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg3e16_v_bf16m1x3_mu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16_v_bf16m2x3_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlseg3.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m2x3_t test_vlseg3e16_v_bf16m2x3_mu(vbool8_t vm, vbfloat16m2x3_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg3e16_v_bf16m2x3_mu(vm, vd, rs1, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlseg3e16ff.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlseg3e16ff.c new file mode 100644 index 0000000000000000000000000000000000000000..03cef3d745a7b39db13be8f24d72e699ef3ffc19 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlseg3e16ff.c @@ -0,0 +1,345 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16ff_v_bf16mf4x3_tu( +// CHECK-RV64-SAME: { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , , i64 } @llvm.riscv.vlseg3ff.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , i64 } [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = insertvalue { , , } poison, [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , i64 } [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , } [[TMP5]], [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , i64 } [[TMP3]], 2 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , } [[TMP7]], [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , i64 } [[TMP3]], 3 +// CHECK-RV64-NEXT: store i64 [[TMP10]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , } [[TMP9]] +// +vbfloat16mf4x3_t test_vlseg3e16ff_v_bf16mf4x3_tu(vbfloat16mf4x3_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg3e16ff_v_bf16mf4x3_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16ff_v_bf16mf2x3_tu( +// CHECK-RV64-SAME: { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , , i64 } @llvm.riscv.vlseg3ff.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , i64 } [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = insertvalue { , , } poison, [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , i64 } [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , } [[TMP5]], [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , i64 } [[TMP3]], 2 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , } [[TMP7]], [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , i64 } [[TMP3]], 3 +// CHECK-RV64-NEXT: store i64 [[TMP10]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , } [[TMP9]] +// +vbfloat16mf2x3_t test_vlseg3e16ff_v_bf16mf2x3_tu(vbfloat16mf2x3_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg3e16ff_v_bf16mf2x3_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16ff_v_bf16m1x3_tu( +// CHECK-RV64-SAME: { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , , i64 } @llvm.riscv.vlseg3ff.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , i64 } [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = insertvalue { , , } poison, [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , i64 } [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , } [[TMP5]], [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , i64 } [[TMP3]], 2 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , } [[TMP7]], [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , i64 } [[TMP3]], 3 +// CHECK-RV64-NEXT: store i64 [[TMP10]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , } [[TMP9]] +// +vbfloat16m1x3_t test_vlseg3e16ff_v_bf16m1x3_tu(vbfloat16m1x3_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg3e16ff_v_bf16m1x3_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16ff_v_bf16m2x3_tu( +// CHECK-RV64-SAME: { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , , i64 } @llvm.riscv.vlseg3ff.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , i64 } [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = insertvalue { , , } poison, [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , i64 } [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , } [[TMP5]], [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , i64 } [[TMP3]], 2 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , } [[TMP7]], [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , i64 } [[TMP3]], 3 +// CHECK-RV64-NEXT: store i64 [[TMP10]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , } [[TMP9]] +// +vbfloat16m2x3_t test_vlseg3e16ff_v_bf16m2x3_tu(vbfloat16m2x3_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg3e16ff_v_bf16m2x3_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16ff_v_bf16mf4x3_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , , i64 } @llvm.riscv.vlseg3ff.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , i64 } [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = insertvalue { , , } poison, [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , i64 } [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , } [[TMP5]], [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , i64 } [[TMP3]], 2 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , } [[TMP7]], [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , i64 } [[TMP3]], 3 +// CHECK-RV64-NEXT: store i64 [[TMP10]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , } [[TMP9]] +// +vbfloat16mf4x3_t test_vlseg3e16ff_v_bf16mf4x3_tum(vbool64_t vm, vbfloat16mf4x3_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg3e16ff_v_bf16mf4x3_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16ff_v_bf16mf2x3_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , , i64 } @llvm.riscv.vlseg3ff.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , i64 } [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = insertvalue { , , } poison, [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , i64 } [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , } [[TMP5]], [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , i64 } [[TMP3]], 2 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , } [[TMP7]], [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , i64 } [[TMP3]], 3 +// CHECK-RV64-NEXT: store i64 [[TMP10]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , } [[TMP9]] +// +vbfloat16mf2x3_t test_vlseg3e16ff_v_bf16mf2x3_tum(vbool32_t vm, vbfloat16mf2x3_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg3e16ff_v_bf16mf2x3_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16ff_v_bf16m1x3_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , , i64 } @llvm.riscv.vlseg3ff.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , i64 } [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = insertvalue { , , } poison, [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , i64 } [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , } [[TMP5]], [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , i64 } [[TMP3]], 2 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , } [[TMP7]], [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , i64 } [[TMP3]], 3 +// CHECK-RV64-NEXT: store i64 [[TMP10]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , } [[TMP9]] +// +vbfloat16m1x3_t test_vlseg3e16ff_v_bf16m1x3_tum(vbool16_t vm, vbfloat16m1x3_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg3e16ff_v_bf16m1x3_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16ff_v_bf16m2x3_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , , i64 } @llvm.riscv.vlseg3ff.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , i64 } [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = insertvalue { , , } poison, [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , i64 } [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , } [[TMP5]], [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , i64 } [[TMP3]], 2 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , } [[TMP7]], [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , i64 } [[TMP3]], 3 +// CHECK-RV64-NEXT: store i64 [[TMP10]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , } [[TMP9]] +// +vbfloat16m2x3_t test_vlseg3e16ff_v_bf16m2x3_tum(vbool8_t vm, vbfloat16m2x3_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg3e16ff_v_bf16m2x3_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16ff_v_bf16mf4x3_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , , i64 } @llvm.riscv.vlseg3ff.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , i64 } [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = insertvalue { , , } poison, [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , i64 } [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , } [[TMP5]], [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , i64 } [[TMP3]], 2 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , } [[TMP7]], [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , i64 } [[TMP3]], 3 +// CHECK-RV64-NEXT: store i64 [[TMP10]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , } [[TMP9]] +// +vbfloat16mf4x3_t test_vlseg3e16ff_v_bf16mf4x3_tumu(vbool64_t vm, vbfloat16mf4x3_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg3e16ff_v_bf16mf4x3_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16ff_v_bf16mf2x3_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , , i64 } @llvm.riscv.vlseg3ff.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , i64 } [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = insertvalue { , , } poison, [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , i64 } [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , } [[TMP5]], [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , i64 } [[TMP3]], 2 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , } [[TMP7]], [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , i64 } [[TMP3]], 3 +// CHECK-RV64-NEXT: store i64 [[TMP10]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , } [[TMP9]] +// +vbfloat16mf2x3_t test_vlseg3e16ff_v_bf16mf2x3_tumu(vbool32_t vm, vbfloat16mf2x3_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg3e16ff_v_bf16mf2x3_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16ff_v_bf16m1x3_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , , i64 } @llvm.riscv.vlseg3ff.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , i64 } [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = insertvalue { , , } poison, [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , i64 } [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , } [[TMP5]], [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , i64 } [[TMP3]], 2 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , } [[TMP7]], [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , i64 } [[TMP3]], 3 +// CHECK-RV64-NEXT: store i64 [[TMP10]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , } [[TMP9]] +// +vbfloat16m1x3_t test_vlseg3e16ff_v_bf16m1x3_tumu(vbool16_t vm, vbfloat16m1x3_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg3e16ff_v_bf16m1x3_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16ff_v_bf16m2x3_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , , i64 } @llvm.riscv.vlseg3ff.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , i64 } [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = insertvalue { , , } poison, [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , i64 } [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , } [[TMP5]], [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , i64 } [[TMP3]], 2 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , } [[TMP7]], [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , i64 } [[TMP3]], 3 +// CHECK-RV64-NEXT: store i64 [[TMP10]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , } [[TMP9]] +// +vbfloat16m2x3_t test_vlseg3e16ff_v_bf16m2x3_tumu(vbool8_t vm, vbfloat16m2x3_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg3e16ff_v_bf16m2x3_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16ff_v_bf16mf4x3_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , , i64 } @llvm.riscv.vlseg3ff.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , i64 } [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = insertvalue { , , } poison, [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , i64 } [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , } [[TMP5]], [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , i64 } [[TMP3]], 2 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , } [[TMP7]], [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , i64 } [[TMP3]], 3 +// CHECK-RV64-NEXT: store i64 [[TMP10]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , } [[TMP9]] +// +vbfloat16mf4x3_t test_vlseg3e16ff_v_bf16mf4x3_mu(vbool64_t vm, vbfloat16mf4x3_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg3e16ff_v_bf16mf4x3_mu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16ff_v_bf16mf2x3_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , , i64 } @llvm.riscv.vlseg3ff.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , i64 } [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = insertvalue { , , } poison, [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , i64 } [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , } [[TMP5]], [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , i64 } [[TMP3]], 2 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , } [[TMP7]], [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , i64 } [[TMP3]], 3 +// CHECK-RV64-NEXT: store i64 [[TMP10]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , } [[TMP9]] +// +vbfloat16mf2x3_t test_vlseg3e16ff_v_bf16mf2x3_mu(vbool32_t vm, vbfloat16mf2x3_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg3e16ff_v_bf16mf2x3_mu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16ff_v_bf16m1x3_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , , i64 } @llvm.riscv.vlseg3ff.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , i64 } [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = insertvalue { , , } poison, [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , i64 } [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , } [[TMP5]], [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , i64 } [[TMP3]], 2 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , } [[TMP7]], [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , i64 } [[TMP3]], 3 +// CHECK-RV64-NEXT: store i64 [[TMP10]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , } [[TMP9]] +// +vbfloat16m1x3_t test_vlseg3e16ff_v_bf16m1x3_mu(vbool16_t vm, vbfloat16m1x3_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg3e16ff_v_bf16m1x3_mu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16ff_v_bf16m2x3_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , , i64 } @llvm.riscv.vlseg3ff.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , i64 } [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = insertvalue { , , } poison, [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , i64 } [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , } [[TMP5]], [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , i64 } [[TMP3]], 2 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , } [[TMP7]], [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , i64 } [[TMP3]], 3 +// CHECK-RV64-NEXT: store i64 [[TMP10]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , } [[TMP9]] +// +vbfloat16m2x3_t test_vlseg3e16ff_v_bf16m2x3_mu(vbool8_t vm, vbfloat16m2x3_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg3e16ff_v_bf16m2x3_mu(vm, vd, rs1, new_vl, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlseg4e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlseg4e16.c new file mode 100644 index 0000000000000000000000000000000000000000..770458e69ecfe99070cc1de88f23be635583b96b --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlseg4e16.c @@ -0,0 +1,233 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16_v_bf16mf4x4_tu( +// CHECK-RV64-SAME: { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlseg4.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf4x4_t test_vlseg4e16_v_bf16mf4x4_tu(vbfloat16mf4x4_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg4e16_v_bf16mf4x4_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16_v_bf16mf2x4_tu( +// CHECK-RV64-SAME: { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlseg4.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf2x4_t test_vlseg4e16_v_bf16mf2x4_tu(vbfloat16mf2x4_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg4e16_v_bf16mf2x4_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16_v_bf16m1x4_tu( +// CHECK-RV64-SAME: { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlseg4.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m1x4_t test_vlseg4e16_v_bf16m1x4_tu(vbfloat16m1x4_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg4e16_v_bf16m1x4_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16_v_bf16m2x4_tu( +// CHECK-RV64-SAME: { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlseg4.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m2x4_t test_vlseg4e16_v_bf16m2x4_tu(vbfloat16m2x4_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg4e16_v_bf16m2x4_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16_v_bf16mf4x4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlseg4.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf4x4_t test_vlseg4e16_v_bf16mf4x4_tum(vbool64_t vm, vbfloat16mf4x4_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg4e16_v_bf16mf4x4_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16_v_bf16mf2x4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlseg4.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf2x4_t test_vlseg4e16_v_bf16mf2x4_tum(vbool32_t vm, vbfloat16mf2x4_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg4e16_v_bf16mf2x4_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16_v_bf16m1x4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlseg4.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m1x4_t test_vlseg4e16_v_bf16m1x4_tum(vbool16_t vm, vbfloat16m1x4_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg4e16_v_bf16m1x4_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16_v_bf16m2x4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlseg4.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m2x4_t test_vlseg4e16_v_bf16m2x4_tum(vbool8_t vm, vbfloat16m2x4_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg4e16_v_bf16m2x4_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16_v_bf16mf4x4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlseg4.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf4x4_t test_vlseg4e16_v_bf16mf4x4_tumu(vbool64_t vm, vbfloat16mf4x4_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg4e16_v_bf16mf4x4_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16_v_bf16mf2x4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlseg4.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf2x4_t test_vlseg4e16_v_bf16mf2x4_tumu(vbool32_t vm, vbfloat16mf2x4_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg4e16_v_bf16mf2x4_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16_v_bf16m1x4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlseg4.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m1x4_t test_vlseg4e16_v_bf16m1x4_tumu(vbool16_t vm, vbfloat16m1x4_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg4e16_v_bf16m1x4_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16_v_bf16m2x4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlseg4.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m2x4_t test_vlseg4e16_v_bf16m2x4_tumu(vbool8_t vm, vbfloat16m2x4_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg4e16_v_bf16m2x4_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16_v_bf16mf4x4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlseg4.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf4x4_t test_vlseg4e16_v_bf16mf4x4_mu(vbool64_t vm, vbfloat16mf4x4_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg4e16_v_bf16mf4x4_mu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16_v_bf16mf2x4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlseg4.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf2x4_t test_vlseg4e16_v_bf16mf2x4_mu(vbool32_t vm, vbfloat16mf2x4_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg4e16_v_bf16mf2x4_mu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16_v_bf16m1x4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlseg4.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m1x4_t test_vlseg4e16_v_bf16m1x4_mu(vbool16_t vm, vbfloat16m1x4_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg4e16_v_bf16m1x4_mu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16_v_bf16m2x4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlseg4.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m2x4_t test_vlseg4e16_v_bf16m2x4_mu(vbool8_t vm, vbfloat16m2x4_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg4e16_v_bf16m2x4_mu(vm, vd, rs1, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlseg4e16ff.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlseg4e16ff.c new file mode 100644 index 0000000000000000000000000000000000000000..6be407d665675e8036d332acb10bd2fe6d234d77 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlseg4e16ff.c @@ -0,0 +1,393 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16ff_v_bf16mf4x4_tu( +// CHECK-RV64-SAME: { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , , i64 } @llvm.riscv.vlseg4ff.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , } poison, [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , } [[TMP6]], [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , } [[TMP8]], [[TMP9]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 3 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , } [[TMP10]], [[TMP11]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 4 +// CHECK-RV64-NEXT: store i64 [[TMP13]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , } [[TMP12]] +// +vbfloat16mf4x4_t test_vlseg4e16ff_v_bf16mf4x4_tu(vbfloat16mf4x4_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg4e16ff_v_bf16mf4x4_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16ff_v_bf16mf2x4_tu( +// CHECK-RV64-SAME: { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , , i64 } @llvm.riscv.vlseg4ff.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , } poison, [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , } [[TMP6]], [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , } [[TMP8]], [[TMP9]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 3 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , } [[TMP10]], [[TMP11]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 4 +// CHECK-RV64-NEXT: store i64 [[TMP13]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , } [[TMP12]] +// +vbfloat16mf2x4_t test_vlseg4e16ff_v_bf16mf2x4_tu(vbfloat16mf2x4_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg4e16ff_v_bf16mf2x4_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16ff_v_bf16m1x4_tu( +// CHECK-RV64-SAME: { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , , i64 } @llvm.riscv.vlseg4ff.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , } poison, [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , } [[TMP6]], [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , } [[TMP8]], [[TMP9]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 3 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , } [[TMP10]], [[TMP11]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 4 +// CHECK-RV64-NEXT: store i64 [[TMP13]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , } [[TMP12]] +// +vbfloat16m1x4_t test_vlseg4e16ff_v_bf16m1x4_tu(vbfloat16m1x4_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg4e16ff_v_bf16m1x4_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16ff_v_bf16m2x4_tu( +// CHECK-RV64-SAME: { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , , i64 } @llvm.riscv.vlseg4ff.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , } poison, [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , } [[TMP6]], [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , } [[TMP8]], [[TMP9]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 3 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , } [[TMP10]], [[TMP11]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 4 +// CHECK-RV64-NEXT: store i64 [[TMP13]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , } [[TMP12]] +// +vbfloat16m2x4_t test_vlseg4e16ff_v_bf16m2x4_tu(vbfloat16m2x4_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg4e16ff_v_bf16m2x4_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16ff_v_bf16mf4x4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , , i64 } @llvm.riscv.vlseg4ff.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , } poison, [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , } [[TMP6]], [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , } [[TMP8]], [[TMP9]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 3 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , } [[TMP10]], [[TMP11]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 4 +// CHECK-RV64-NEXT: store i64 [[TMP13]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , } [[TMP12]] +// +vbfloat16mf4x4_t test_vlseg4e16ff_v_bf16mf4x4_tum(vbool64_t vm, vbfloat16mf4x4_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg4e16ff_v_bf16mf4x4_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16ff_v_bf16mf2x4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , , i64 } @llvm.riscv.vlseg4ff.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , } poison, [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , } [[TMP6]], [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , } [[TMP8]], [[TMP9]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 3 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , } [[TMP10]], [[TMP11]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 4 +// CHECK-RV64-NEXT: store i64 [[TMP13]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , } [[TMP12]] +// +vbfloat16mf2x4_t test_vlseg4e16ff_v_bf16mf2x4_tum(vbool32_t vm, vbfloat16mf2x4_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg4e16ff_v_bf16mf2x4_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16ff_v_bf16m1x4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , , i64 } @llvm.riscv.vlseg4ff.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , } poison, [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , } [[TMP6]], [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , } [[TMP8]], [[TMP9]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 3 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , } [[TMP10]], [[TMP11]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 4 +// CHECK-RV64-NEXT: store i64 [[TMP13]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , } [[TMP12]] +// +vbfloat16m1x4_t test_vlseg4e16ff_v_bf16m1x4_tum(vbool16_t vm, vbfloat16m1x4_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg4e16ff_v_bf16m1x4_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16ff_v_bf16m2x4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , , i64 } @llvm.riscv.vlseg4ff.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , } poison, [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , } [[TMP6]], [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , } [[TMP8]], [[TMP9]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 3 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , } [[TMP10]], [[TMP11]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 4 +// CHECK-RV64-NEXT: store i64 [[TMP13]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , } [[TMP12]] +// +vbfloat16m2x4_t test_vlseg4e16ff_v_bf16m2x4_tum(vbool8_t vm, vbfloat16m2x4_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg4e16ff_v_bf16m2x4_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16ff_v_bf16mf4x4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , , i64 } @llvm.riscv.vlseg4ff.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , } poison, [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , } [[TMP6]], [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , } [[TMP8]], [[TMP9]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 3 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , } [[TMP10]], [[TMP11]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 4 +// CHECK-RV64-NEXT: store i64 [[TMP13]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , } [[TMP12]] +// +vbfloat16mf4x4_t test_vlseg4e16ff_v_bf16mf4x4_tumu(vbool64_t vm, vbfloat16mf4x4_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg4e16ff_v_bf16mf4x4_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16ff_v_bf16mf2x4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , , i64 } @llvm.riscv.vlseg4ff.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , } poison, [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , } [[TMP6]], [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , } [[TMP8]], [[TMP9]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 3 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , } [[TMP10]], [[TMP11]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 4 +// CHECK-RV64-NEXT: store i64 [[TMP13]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , } [[TMP12]] +// +vbfloat16mf2x4_t test_vlseg4e16ff_v_bf16mf2x4_tumu(vbool32_t vm, vbfloat16mf2x4_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg4e16ff_v_bf16mf2x4_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16ff_v_bf16m1x4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , , i64 } @llvm.riscv.vlseg4ff.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , } poison, [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , } [[TMP6]], [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , } [[TMP8]], [[TMP9]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 3 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , } [[TMP10]], [[TMP11]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 4 +// CHECK-RV64-NEXT: store i64 [[TMP13]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , } [[TMP12]] +// +vbfloat16m1x4_t test_vlseg4e16ff_v_bf16m1x4_tumu(vbool16_t vm, vbfloat16m1x4_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg4e16ff_v_bf16m1x4_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16ff_v_bf16m2x4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , , i64 } @llvm.riscv.vlseg4ff.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , } poison, [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , } [[TMP6]], [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , } [[TMP8]], [[TMP9]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 3 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , } [[TMP10]], [[TMP11]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 4 +// CHECK-RV64-NEXT: store i64 [[TMP13]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , } [[TMP12]] +// +vbfloat16m2x4_t test_vlseg4e16ff_v_bf16m2x4_tumu(vbool8_t vm, vbfloat16m2x4_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg4e16ff_v_bf16m2x4_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16ff_v_bf16mf4x4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , , i64 } @llvm.riscv.vlseg4ff.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , } poison, [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , } [[TMP6]], [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , } [[TMP8]], [[TMP9]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 3 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , } [[TMP10]], [[TMP11]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 4 +// CHECK-RV64-NEXT: store i64 [[TMP13]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , } [[TMP12]] +// +vbfloat16mf4x4_t test_vlseg4e16ff_v_bf16mf4x4_mu(vbool64_t vm, vbfloat16mf4x4_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg4e16ff_v_bf16mf4x4_mu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16ff_v_bf16mf2x4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , , i64 } @llvm.riscv.vlseg4ff.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , } poison, [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , } [[TMP6]], [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , } [[TMP8]], [[TMP9]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 3 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , } [[TMP10]], [[TMP11]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 4 +// CHECK-RV64-NEXT: store i64 [[TMP13]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , } [[TMP12]] +// +vbfloat16mf2x4_t test_vlseg4e16ff_v_bf16mf2x4_mu(vbool32_t vm, vbfloat16mf2x4_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg4e16ff_v_bf16mf2x4_mu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16ff_v_bf16m1x4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , , i64 } @llvm.riscv.vlseg4ff.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , } poison, [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , } [[TMP6]], [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , } [[TMP8]], [[TMP9]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 3 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , } [[TMP10]], [[TMP11]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 4 +// CHECK-RV64-NEXT: store i64 [[TMP13]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , } [[TMP12]] +// +vbfloat16m1x4_t test_vlseg4e16ff_v_bf16m1x4_mu(vbool16_t vm, vbfloat16m1x4_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg4e16ff_v_bf16m1x4_mu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16ff_v_bf16m2x4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , , i64 } @llvm.riscv.vlseg4ff.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , } poison, [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , } [[TMP6]], [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , } [[TMP8]], [[TMP9]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 3 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , } [[TMP10]], [[TMP11]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 4 +// CHECK-RV64-NEXT: store i64 [[TMP13]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , } [[TMP12]] +// +vbfloat16m2x4_t test_vlseg4e16ff_v_bf16m2x4_mu(vbool8_t vm, vbfloat16m2x4_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg4e16ff_v_bf16m2x4_mu(vm, vd, rs1, new_vl, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlseg5e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlseg5e16.c new file mode 100644 index 0000000000000000000000000000000000000000..7ce59eb05effa474689ed5c2fb79a6d53b682e37 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlseg5e16.c @@ -0,0 +1,189 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16_v_bf16mf4x5_tu( +// CHECK-RV64-SAME: { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vlseg5.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf4x5_t test_vlseg5e16_v_bf16mf4x5_tu(vbfloat16mf4x5_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg5e16_v_bf16mf4x5_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16_v_bf16mf2x5_tu( +// CHECK-RV64-SAME: { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vlseg5.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf2x5_t test_vlseg5e16_v_bf16mf2x5_tu(vbfloat16mf2x5_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg5e16_v_bf16mf2x5_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16_v_bf16m1x5_tu( +// CHECK-RV64-SAME: { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vlseg5.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16m1x5_t test_vlseg5e16_v_bf16m1x5_tu(vbfloat16m1x5_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg5e16_v_bf16m1x5_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16_v_bf16mf4x5_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vlseg5.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf4x5_t test_vlseg5e16_v_bf16mf4x5_tum(vbool64_t vm, vbfloat16mf4x5_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg5e16_v_bf16mf4x5_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16_v_bf16mf2x5_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vlseg5.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf2x5_t test_vlseg5e16_v_bf16mf2x5_tum(vbool32_t vm, vbfloat16mf2x5_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg5e16_v_bf16mf2x5_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16_v_bf16m1x5_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vlseg5.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16m1x5_t test_vlseg5e16_v_bf16m1x5_tum(vbool16_t vm, vbfloat16m1x5_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg5e16_v_bf16m1x5_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16_v_bf16mf4x5_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vlseg5.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf4x5_t test_vlseg5e16_v_bf16mf4x5_tumu(vbool64_t vm, vbfloat16mf4x5_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg5e16_v_bf16mf4x5_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16_v_bf16mf2x5_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vlseg5.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf2x5_t test_vlseg5e16_v_bf16mf2x5_tumu(vbool32_t vm, vbfloat16mf2x5_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg5e16_v_bf16mf2x5_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16_v_bf16m1x5_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vlseg5.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16m1x5_t test_vlseg5e16_v_bf16m1x5_tumu(vbool16_t vm, vbfloat16m1x5_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg5e16_v_bf16m1x5_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16_v_bf16mf4x5_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vlseg5.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf4x5_t test_vlseg5e16_v_bf16mf4x5_mu(vbool64_t vm, vbfloat16mf4x5_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg5e16_v_bf16mf4x5_mu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16_v_bf16mf2x5_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vlseg5.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf2x5_t test_vlseg5e16_v_bf16mf2x5_mu(vbool32_t vm, vbfloat16mf2x5_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg5e16_v_bf16mf2x5_mu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16_v_bf16m1x5_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vlseg5.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16m1x5_t test_vlseg5e16_v_bf16m1x5_mu(vbool16_t vm, vbfloat16m1x5_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg5e16_v_bf16m1x5_mu(vm, vd, rs1, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlseg5e16ff.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlseg5e16ff.c new file mode 100644 index 0000000000000000000000000000000000000000..08b00d68fb96f81aa1747fdd249b98050dd85388 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlseg5e16ff.c @@ -0,0 +1,333 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16ff_v_bf16mf4x5_tu( +// CHECK-RV64-SAME: { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , , i64 } @llvm.riscv.vlseg5ff.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , , , } poison, [[TMP6]], 0 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , , , } [[TMP7]], [[TMP8]], 1 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = insertvalue { , , , , } [[TMP9]], [[TMP10]], 2 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = insertvalue { , , , , } [[TMP11]], [[TMP12]], 3 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 4 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = insertvalue { , , , , } [[TMP13]], [[TMP14]], 4 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 5 +// CHECK-RV64-NEXT: store i64 [[TMP16]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , } [[TMP15]] +// +vbfloat16mf4x5_t test_vlseg5e16ff_v_bf16mf4x5_tu(vbfloat16mf4x5_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg5e16ff_v_bf16mf4x5_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16ff_v_bf16mf2x5_tu( +// CHECK-RV64-SAME: { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , , i64 } @llvm.riscv.vlseg5ff.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , , , } poison, [[TMP6]], 0 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , , , } [[TMP7]], [[TMP8]], 1 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = insertvalue { , , , , } [[TMP9]], [[TMP10]], 2 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = insertvalue { , , , , } [[TMP11]], [[TMP12]], 3 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 4 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = insertvalue { , , , , } [[TMP13]], [[TMP14]], 4 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 5 +// CHECK-RV64-NEXT: store i64 [[TMP16]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , } [[TMP15]] +// +vbfloat16mf2x5_t test_vlseg5e16ff_v_bf16mf2x5_tu(vbfloat16mf2x5_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg5e16ff_v_bf16mf2x5_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16ff_v_bf16m1x5_tu( +// CHECK-RV64-SAME: { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , , i64 } @llvm.riscv.vlseg5ff.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , , , } poison, [[TMP6]], 0 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , , , } [[TMP7]], [[TMP8]], 1 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = insertvalue { , , , , } [[TMP9]], [[TMP10]], 2 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = insertvalue { , , , , } [[TMP11]], [[TMP12]], 3 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 4 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = insertvalue { , , , , } [[TMP13]], [[TMP14]], 4 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 5 +// CHECK-RV64-NEXT: store i64 [[TMP16]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , } [[TMP15]] +// +vbfloat16m1x5_t test_vlseg5e16ff_v_bf16m1x5_tu(vbfloat16m1x5_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg5e16ff_v_bf16m1x5_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16ff_v_bf16mf4x5_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , , i64 } @llvm.riscv.vlseg5ff.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , , , } poison, [[TMP6]], 0 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , , , } [[TMP7]], [[TMP8]], 1 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = insertvalue { , , , , } [[TMP9]], [[TMP10]], 2 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = insertvalue { , , , , } [[TMP11]], [[TMP12]], 3 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 4 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = insertvalue { , , , , } [[TMP13]], [[TMP14]], 4 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 5 +// CHECK-RV64-NEXT: store i64 [[TMP16]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , } [[TMP15]] +// +vbfloat16mf4x5_t test_vlseg5e16ff_v_bf16mf4x5_tum(vbool64_t vm, vbfloat16mf4x5_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg5e16ff_v_bf16mf4x5_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16ff_v_bf16mf2x5_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , , i64 } @llvm.riscv.vlseg5ff.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , , , } poison, [[TMP6]], 0 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , , , } [[TMP7]], [[TMP8]], 1 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = insertvalue { , , , , } [[TMP9]], [[TMP10]], 2 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = insertvalue { , , , , } [[TMP11]], [[TMP12]], 3 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 4 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = insertvalue { , , , , } [[TMP13]], [[TMP14]], 4 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 5 +// CHECK-RV64-NEXT: store i64 [[TMP16]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , } [[TMP15]] +// +vbfloat16mf2x5_t test_vlseg5e16ff_v_bf16mf2x5_tum(vbool32_t vm, vbfloat16mf2x5_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg5e16ff_v_bf16mf2x5_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16ff_v_bf16m1x5_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , , i64 } @llvm.riscv.vlseg5ff.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , , , } poison, [[TMP6]], 0 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , , , } [[TMP7]], [[TMP8]], 1 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = insertvalue { , , , , } [[TMP9]], [[TMP10]], 2 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = insertvalue { , , , , } [[TMP11]], [[TMP12]], 3 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 4 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = insertvalue { , , , , } [[TMP13]], [[TMP14]], 4 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 5 +// CHECK-RV64-NEXT: store i64 [[TMP16]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , } [[TMP15]] +// +vbfloat16m1x5_t test_vlseg5e16ff_v_bf16m1x5_tum(vbool16_t vm, vbfloat16m1x5_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg5e16ff_v_bf16m1x5_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16ff_v_bf16mf4x5_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , , i64 } @llvm.riscv.vlseg5ff.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , , , } poison, [[TMP6]], 0 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , , , } [[TMP7]], [[TMP8]], 1 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = insertvalue { , , , , } [[TMP9]], [[TMP10]], 2 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = insertvalue { , , , , } [[TMP11]], [[TMP12]], 3 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 4 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = insertvalue { , , , , } [[TMP13]], [[TMP14]], 4 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 5 +// CHECK-RV64-NEXT: store i64 [[TMP16]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , } [[TMP15]] +// +vbfloat16mf4x5_t test_vlseg5e16ff_v_bf16mf4x5_tumu(vbool64_t vm, vbfloat16mf4x5_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg5e16ff_v_bf16mf4x5_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16ff_v_bf16mf2x5_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , , i64 } @llvm.riscv.vlseg5ff.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , , , } poison, [[TMP6]], 0 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , , , } [[TMP7]], [[TMP8]], 1 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = insertvalue { , , , , } [[TMP9]], [[TMP10]], 2 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = insertvalue { , , , , } [[TMP11]], [[TMP12]], 3 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 4 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = insertvalue { , , , , } [[TMP13]], [[TMP14]], 4 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 5 +// CHECK-RV64-NEXT: store i64 [[TMP16]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , } [[TMP15]] +// +vbfloat16mf2x5_t test_vlseg5e16ff_v_bf16mf2x5_tumu(vbool32_t vm, vbfloat16mf2x5_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg5e16ff_v_bf16mf2x5_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16ff_v_bf16m1x5_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , , i64 } @llvm.riscv.vlseg5ff.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , , , } poison, [[TMP6]], 0 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , , , } [[TMP7]], [[TMP8]], 1 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = insertvalue { , , , , } [[TMP9]], [[TMP10]], 2 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = insertvalue { , , , , } [[TMP11]], [[TMP12]], 3 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 4 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = insertvalue { , , , , } [[TMP13]], [[TMP14]], 4 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 5 +// CHECK-RV64-NEXT: store i64 [[TMP16]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , } [[TMP15]] +// +vbfloat16m1x5_t test_vlseg5e16ff_v_bf16m1x5_tumu(vbool16_t vm, vbfloat16m1x5_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg5e16ff_v_bf16m1x5_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16ff_v_bf16mf4x5_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , , i64 } @llvm.riscv.vlseg5ff.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , , , } poison, [[TMP6]], 0 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , , , } [[TMP7]], [[TMP8]], 1 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = insertvalue { , , , , } [[TMP9]], [[TMP10]], 2 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = insertvalue { , , , , } [[TMP11]], [[TMP12]], 3 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 4 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = insertvalue { , , , , } [[TMP13]], [[TMP14]], 4 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 5 +// CHECK-RV64-NEXT: store i64 [[TMP16]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , } [[TMP15]] +// +vbfloat16mf4x5_t test_vlseg5e16ff_v_bf16mf4x5_mu(vbool64_t vm, vbfloat16mf4x5_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg5e16ff_v_bf16mf4x5_mu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16ff_v_bf16mf2x5_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , , i64 } @llvm.riscv.vlseg5ff.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , , , } poison, [[TMP6]], 0 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , , , } [[TMP7]], [[TMP8]], 1 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = insertvalue { , , , , } [[TMP9]], [[TMP10]], 2 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = insertvalue { , , , , } [[TMP11]], [[TMP12]], 3 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 4 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = insertvalue { , , , , } [[TMP13]], [[TMP14]], 4 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 5 +// CHECK-RV64-NEXT: store i64 [[TMP16]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , } [[TMP15]] +// +vbfloat16mf2x5_t test_vlseg5e16ff_v_bf16mf2x5_mu(vbool32_t vm, vbfloat16mf2x5_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg5e16ff_v_bf16mf2x5_mu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16ff_v_bf16m1x5_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , , i64 } @llvm.riscv.vlseg5ff.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , , , } poison, [[TMP6]], 0 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , , , } [[TMP7]], [[TMP8]], 1 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = insertvalue { , , , , } [[TMP9]], [[TMP10]], 2 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = insertvalue { , , , , } [[TMP11]], [[TMP12]], 3 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 4 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = insertvalue { , , , , } [[TMP13]], [[TMP14]], 4 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 5 +// CHECK-RV64-NEXT: store i64 [[TMP16]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , } [[TMP15]] +// +vbfloat16m1x5_t test_vlseg5e16ff_v_bf16m1x5_mu(vbool16_t vm, vbfloat16m1x5_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg5e16ff_v_bf16m1x5_mu(vm, vd, rs1, new_vl, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlseg6e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlseg6e16.c new file mode 100644 index 0000000000000000000000000000000000000000..1bcf360b86fe322458c53f3dd940a45a4b5f54f8 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlseg6e16.c @@ -0,0 +1,201 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16_v_bf16mf4x6_tu( +// CHECK-RV64-SAME: { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vlseg6.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf4x6_t test_vlseg6e16_v_bf16mf4x6_tu(vbfloat16mf4x6_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg6e16_v_bf16mf4x6_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16_v_bf16mf2x6_tu( +// CHECK-RV64-SAME: { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vlseg6.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf2x6_t test_vlseg6e16_v_bf16mf2x6_tu(vbfloat16mf2x6_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg6e16_v_bf16mf2x6_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16_v_bf16m1x6_tu( +// CHECK-RV64-SAME: { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vlseg6.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16m1x6_t test_vlseg6e16_v_bf16m1x6_tu(vbfloat16m1x6_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg6e16_v_bf16m1x6_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16_v_bf16mf4x6_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vlseg6.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf4x6_t test_vlseg6e16_v_bf16mf4x6_tum(vbool64_t vm, vbfloat16mf4x6_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg6e16_v_bf16mf4x6_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16_v_bf16mf2x6_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vlseg6.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf2x6_t test_vlseg6e16_v_bf16mf2x6_tum(vbool32_t vm, vbfloat16mf2x6_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg6e16_v_bf16mf2x6_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16_v_bf16m1x6_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vlseg6.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16m1x6_t test_vlseg6e16_v_bf16m1x6_tum(vbool16_t vm, vbfloat16m1x6_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg6e16_v_bf16m1x6_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16_v_bf16mf4x6_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vlseg6.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf4x6_t test_vlseg6e16_v_bf16mf4x6_tumu(vbool64_t vm, vbfloat16mf4x6_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg6e16_v_bf16mf4x6_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16_v_bf16mf2x6_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vlseg6.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf2x6_t test_vlseg6e16_v_bf16mf2x6_tumu(vbool32_t vm, vbfloat16mf2x6_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg6e16_v_bf16mf2x6_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16_v_bf16m1x6_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vlseg6.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16m1x6_t test_vlseg6e16_v_bf16m1x6_tumu(vbool16_t vm, vbfloat16m1x6_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg6e16_v_bf16m1x6_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16_v_bf16mf4x6_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vlseg6.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf4x6_t test_vlseg6e16_v_bf16mf4x6_mu(vbool64_t vm, vbfloat16mf4x6_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg6e16_v_bf16mf4x6_mu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16_v_bf16mf2x6_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vlseg6.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf2x6_t test_vlseg6e16_v_bf16mf2x6_mu(vbool32_t vm, vbfloat16mf2x6_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg6e16_v_bf16mf2x6_mu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16_v_bf16m1x6_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vlseg6.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16m1x6_t test_vlseg6e16_v_bf16m1x6_mu(vbool16_t vm, vbfloat16m1x6_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg6e16_v_bf16m1x6_mu(vm, vd, rs1, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlseg6e16ff.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlseg6e16ff.c new file mode 100644 index 0000000000000000000000000000000000000000..ab2a169cf2a0aa56076b6860f7725a94e6b54ce6 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlseg6e16ff.c @@ -0,0 +1,369 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16ff_v_bf16mf4x6_tu( +// CHECK-RV64-SAME: { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , , i64 } @llvm.riscv.vlseg6ff.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 0 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , } poison, [[TMP7]], 0 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , } [[TMP8]], [[TMP9]], 1 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 2 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , } [[TMP10]], [[TMP11]], 2 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 3 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , } [[TMP12]], [[TMP13]], 3 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 4 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , } [[TMP14]], [[TMP15]], 4 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 5 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = insertvalue { , , , , , } [[TMP16]], [[TMP17]], 5 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 6 +// CHECK-RV64-NEXT: store i64 [[TMP19]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP18]] +// +vbfloat16mf4x6_t test_vlseg6e16ff_v_bf16mf4x6_tu(vbfloat16mf4x6_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg6e16ff_v_bf16mf4x6_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16ff_v_bf16mf2x6_tu( +// CHECK-RV64-SAME: { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , , i64 } @llvm.riscv.vlseg6ff.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 0 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , } poison, [[TMP7]], 0 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , } [[TMP8]], [[TMP9]], 1 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 2 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , } [[TMP10]], [[TMP11]], 2 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 3 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , } [[TMP12]], [[TMP13]], 3 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 4 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , } [[TMP14]], [[TMP15]], 4 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 5 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = insertvalue { , , , , , } [[TMP16]], [[TMP17]], 5 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 6 +// CHECK-RV64-NEXT: store i64 [[TMP19]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP18]] +// +vbfloat16mf2x6_t test_vlseg6e16ff_v_bf16mf2x6_tu(vbfloat16mf2x6_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg6e16ff_v_bf16mf2x6_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16ff_v_bf16m1x6_tu( +// CHECK-RV64-SAME: { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , , i64 } @llvm.riscv.vlseg6ff.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 0 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , } poison, [[TMP7]], 0 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , } [[TMP8]], [[TMP9]], 1 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 2 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , } [[TMP10]], [[TMP11]], 2 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 3 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , } [[TMP12]], [[TMP13]], 3 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 4 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , } [[TMP14]], [[TMP15]], 4 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 5 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = insertvalue { , , , , , } [[TMP16]], [[TMP17]], 5 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 6 +// CHECK-RV64-NEXT: store i64 [[TMP19]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP18]] +// +vbfloat16m1x6_t test_vlseg6e16ff_v_bf16m1x6_tu(vbfloat16m1x6_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg6e16ff_v_bf16m1x6_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16ff_v_bf16mf4x6_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , , i64 } @llvm.riscv.vlseg6ff.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 0 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , } poison, [[TMP7]], 0 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , } [[TMP8]], [[TMP9]], 1 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 2 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , } [[TMP10]], [[TMP11]], 2 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 3 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , } [[TMP12]], [[TMP13]], 3 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 4 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , } [[TMP14]], [[TMP15]], 4 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 5 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = insertvalue { , , , , , } [[TMP16]], [[TMP17]], 5 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 6 +// CHECK-RV64-NEXT: store i64 [[TMP19]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP18]] +// +vbfloat16mf4x6_t test_vlseg6e16ff_v_bf16mf4x6_tum(vbool64_t vm, vbfloat16mf4x6_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg6e16ff_v_bf16mf4x6_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16ff_v_bf16mf2x6_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , , i64 } @llvm.riscv.vlseg6ff.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 0 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , } poison, [[TMP7]], 0 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , } [[TMP8]], [[TMP9]], 1 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 2 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , } [[TMP10]], [[TMP11]], 2 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 3 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , } [[TMP12]], [[TMP13]], 3 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 4 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , } [[TMP14]], [[TMP15]], 4 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 5 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = insertvalue { , , , , , } [[TMP16]], [[TMP17]], 5 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 6 +// CHECK-RV64-NEXT: store i64 [[TMP19]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP18]] +// +vbfloat16mf2x6_t test_vlseg6e16ff_v_bf16mf2x6_tum(vbool32_t vm, vbfloat16mf2x6_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg6e16ff_v_bf16mf2x6_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16ff_v_bf16m1x6_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , , i64 } @llvm.riscv.vlseg6ff.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 0 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , } poison, [[TMP7]], 0 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , } [[TMP8]], [[TMP9]], 1 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 2 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , } [[TMP10]], [[TMP11]], 2 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 3 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , } [[TMP12]], [[TMP13]], 3 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 4 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , } [[TMP14]], [[TMP15]], 4 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 5 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = insertvalue { , , , , , } [[TMP16]], [[TMP17]], 5 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 6 +// CHECK-RV64-NEXT: store i64 [[TMP19]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP18]] +// +vbfloat16m1x6_t test_vlseg6e16ff_v_bf16m1x6_tum(vbool16_t vm, vbfloat16m1x6_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg6e16ff_v_bf16m1x6_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16ff_v_bf16mf4x6_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , , i64 } @llvm.riscv.vlseg6ff.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 0 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , } poison, [[TMP7]], 0 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , } [[TMP8]], [[TMP9]], 1 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 2 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , } [[TMP10]], [[TMP11]], 2 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 3 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , } [[TMP12]], [[TMP13]], 3 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 4 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , } [[TMP14]], [[TMP15]], 4 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 5 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = insertvalue { , , , , , } [[TMP16]], [[TMP17]], 5 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 6 +// CHECK-RV64-NEXT: store i64 [[TMP19]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP18]] +// +vbfloat16mf4x6_t test_vlseg6e16ff_v_bf16mf4x6_tumu(vbool64_t vm, vbfloat16mf4x6_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg6e16ff_v_bf16mf4x6_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16ff_v_bf16mf2x6_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , , i64 } @llvm.riscv.vlseg6ff.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 0 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , } poison, [[TMP7]], 0 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , } [[TMP8]], [[TMP9]], 1 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 2 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , } [[TMP10]], [[TMP11]], 2 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 3 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , } [[TMP12]], [[TMP13]], 3 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 4 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , } [[TMP14]], [[TMP15]], 4 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 5 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = insertvalue { , , , , , } [[TMP16]], [[TMP17]], 5 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 6 +// CHECK-RV64-NEXT: store i64 [[TMP19]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP18]] +// +vbfloat16mf2x6_t test_vlseg6e16ff_v_bf16mf2x6_tumu(vbool32_t vm, vbfloat16mf2x6_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg6e16ff_v_bf16mf2x6_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16ff_v_bf16m1x6_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , , i64 } @llvm.riscv.vlseg6ff.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 0 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , } poison, [[TMP7]], 0 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , } [[TMP8]], [[TMP9]], 1 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 2 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , } [[TMP10]], [[TMP11]], 2 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 3 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , } [[TMP12]], [[TMP13]], 3 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 4 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , } [[TMP14]], [[TMP15]], 4 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 5 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = insertvalue { , , , , , } [[TMP16]], [[TMP17]], 5 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 6 +// CHECK-RV64-NEXT: store i64 [[TMP19]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP18]] +// +vbfloat16m1x6_t test_vlseg6e16ff_v_bf16m1x6_tumu(vbool16_t vm, vbfloat16m1x6_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg6e16ff_v_bf16m1x6_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16ff_v_bf16mf4x6_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , , i64 } @llvm.riscv.vlseg6ff.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 0 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , } poison, [[TMP7]], 0 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , } [[TMP8]], [[TMP9]], 1 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 2 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , } [[TMP10]], [[TMP11]], 2 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 3 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , } [[TMP12]], [[TMP13]], 3 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 4 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , } [[TMP14]], [[TMP15]], 4 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 5 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = insertvalue { , , , , , } [[TMP16]], [[TMP17]], 5 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 6 +// CHECK-RV64-NEXT: store i64 [[TMP19]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP18]] +// +vbfloat16mf4x6_t test_vlseg6e16ff_v_bf16mf4x6_mu(vbool64_t vm, vbfloat16mf4x6_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg6e16ff_v_bf16mf4x6_mu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16ff_v_bf16mf2x6_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , , i64 } @llvm.riscv.vlseg6ff.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 0 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , } poison, [[TMP7]], 0 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , } [[TMP8]], [[TMP9]], 1 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 2 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , } [[TMP10]], [[TMP11]], 2 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 3 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , } [[TMP12]], [[TMP13]], 3 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 4 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , } [[TMP14]], [[TMP15]], 4 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 5 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = insertvalue { , , , , , } [[TMP16]], [[TMP17]], 5 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 6 +// CHECK-RV64-NEXT: store i64 [[TMP19]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP18]] +// +vbfloat16mf2x6_t test_vlseg6e16ff_v_bf16mf2x6_mu(vbool32_t vm, vbfloat16mf2x6_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg6e16ff_v_bf16mf2x6_mu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16ff_v_bf16m1x6_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , , i64 } @llvm.riscv.vlseg6ff.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 0 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , } poison, [[TMP7]], 0 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , } [[TMP8]], [[TMP9]], 1 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 2 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , } [[TMP10]], [[TMP11]], 2 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 3 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , } [[TMP12]], [[TMP13]], 3 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 4 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , } [[TMP14]], [[TMP15]], 4 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 5 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = insertvalue { , , , , , } [[TMP16]], [[TMP17]], 5 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 6 +// CHECK-RV64-NEXT: store i64 [[TMP19]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP18]] +// +vbfloat16m1x6_t test_vlseg6e16ff_v_bf16m1x6_mu(vbool16_t vm, vbfloat16m1x6_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg6e16ff_v_bf16m1x6_mu(vm, vd, rs1, new_vl, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlseg7e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlseg7e16.c new file mode 100644 index 0000000000000000000000000000000000000000..0147a14abcd3661d2c1f2dd53b2cc223fd9ee5ca --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlseg7e16.c @@ -0,0 +1,213 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16_v_bf16mf4x7_tu( +// CHECK-RV64-SAME: { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vlseg7.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf4x7_t test_vlseg7e16_v_bf16mf4x7_tu(vbfloat16mf4x7_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg7e16_v_bf16mf4x7_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16_v_bf16mf2x7_tu( +// CHECK-RV64-SAME: { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vlseg7.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf2x7_t test_vlseg7e16_v_bf16mf2x7_tu(vbfloat16mf2x7_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg7e16_v_bf16mf2x7_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16_v_bf16m1x7_tu( +// CHECK-RV64-SAME: { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vlseg7.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16m1x7_t test_vlseg7e16_v_bf16m1x7_tu(vbfloat16m1x7_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg7e16_v_bf16m1x7_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16_v_bf16mf4x7_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vlseg7.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf4x7_t test_vlseg7e16_v_bf16mf4x7_tum(vbool64_t vm, vbfloat16mf4x7_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg7e16_v_bf16mf4x7_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16_v_bf16mf2x7_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vlseg7.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf2x7_t test_vlseg7e16_v_bf16mf2x7_tum(vbool32_t vm, vbfloat16mf2x7_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg7e16_v_bf16mf2x7_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16_v_bf16m1x7_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vlseg7.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16m1x7_t test_vlseg7e16_v_bf16m1x7_tum(vbool16_t vm, vbfloat16m1x7_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg7e16_v_bf16m1x7_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16_v_bf16mf4x7_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vlseg7.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf4x7_t test_vlseg7e16_v_bf16mf4x7_tumu(vbool64_t vm, vbfloat16mf4x7_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg7e16_v_bf16mf4x7_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16_v_bf16mf2x7_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vlseg7.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf2x7_t test_vlseg7e16_v_bf16mf2x7_tumu(vbool32_t vm, vbfloat16mf2x7_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg7e16_v_bf16mf2x7_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16_v_bf16m1x7_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vlseg7.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16m1x7_t test_vlseg7e16_v_bf16m1x7_tumu(vbool16_t vm, vbfloat16m1x7_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg7e16_v_bf16m1x7_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16_v_bf16mf4x7_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vlseg7.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf4x7_t test_vlseg7e16_v_bf16mf4x7_mu(vbool64_t vm, vbfloat16mf4x7_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg7e16_v_bf16mf4x7_mu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16_v_bf16mf2x7_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vlseg7.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf2x7_t test_vlseg7e16_v_bf16mf2x7_mu(vbool32_t vm, vbfloat16mf2x7_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg7e16_v_bf16mf2x7_mu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16_v_bf16m1x7_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vlseg7.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16m1x7_t test_vlseg7e16_v_bf16m1x7_mu(vbool16_t vm, vbfloat16m1x7_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg7e16_v_bf16m1x7_mu(vm, vd, rs1, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlseg7e16ff.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlseg7e16ff.c new file mode 100644 index 0000000000000000000000000000000000000000..1eee11324dba3ddc8b83aa480756d3abc1af96bb --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlseg7e16ff.c @@ -0,0 +1,405 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16ff_v_bf16mf4x7_tu( +// CHECK-RV64-SAME: { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , , i64 } @llvm.riscv.vlseg7ff.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 0 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , , , , , } poison, [[TMP8]], 0 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = insertvalue { , , , , , , } [[TMP9]], [[TMP10]], 1 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 2 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = insertvalue { , , , , , , } [[TMP11]], [[TMP12]], 2 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = insertvalue { , , , , , , } [[TMP13]], [[TMP14]], 3 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 4 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = insertvalue { , , , , , , } [[TMP15]], [[TMP16]], 4 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 5 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = insertvalue { , , , , , , } [[TMP17]], [[TMP18]], 5 +// CHECK-RV64-NEXT: [[TMP20:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 6 +// CHECK-RV64-NEXT: [[TMP21:%.*]] = insertvalue { , , , , , , } [[TMP19]], [[TMP20]], 6 +// CHECK-RV64-NEXT: [[TMP22:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 7 +// CHECK-RV64-NEXT: store i64 [[TMP22]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP21]] +// +vbfloat16mf4x7_t test_vlseg7e16ff_v_bf16mf4x7_tu(vbfloat16mf4x7_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg7e16ff_v_bf16mf4x7_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16ff_v_bf16mf2x7_tu( +// CHECK-RV64-SAME: { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , , i64 } @llvm.riscv.vlseg7ff.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 0 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , , , , , } poison, [[TMP8]], 0 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = insertvalue { , , , , , , } [[TMP9]], [[TMP10]], 1 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 2 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = insertvalue { , , , , , , } [[TMP11]], [[TMP12]], 2 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = insertvalue { , , , , , , } [[TMP13]], [[TMP14]], 3 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 4 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = insertvalue { , , , , , , } [[TMP15]], [[TMP16]], 4 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 5 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = insertvalue { , , , , , , } [[TMP17]], [[TMP18]], 5 +// CHECK-RV64-NEXT: [[TMP20:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 6 +// CHECK-RV64-NEXT: [[TMP21:%.*]] = insertvalue { , , , , , , } [[TMP19]], [[TMP20]], 6 +// CHECK-RV64-NEXT: [[TMP22:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 7 +// CHECK-RV64-NEXT: store i64 [[TMP22]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP21]] +// +vbfloat16mf2x7_t test_vlseg7e16ff_v_bf16mf2x7_tu(vbfloat16mf2x7_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg7e16ff_v_bf16mf2x7_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16ff_v_bf16m1x7_tu( +// CHECK-RV64-SAME: { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , , i64 } @llvm.riscv.vlseg7ff.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 0 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , , , , , } poison, [[TMP8]], 0 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = insertvalue { , , , , , , } [[TMP9]], [[TMP10]], 1 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 2 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = insertvalue { , , , , , , } [[TMP11]], [[TMP12]], 2 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = insertvalue { , , , , , , } [[TMP13]], [[TMP14]], 3 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 4 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = insertvalue { , , , , , , } [[TMP15]], [[TMP16]], 4 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 5 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = insertvalue { , , , , , , } [[TMP17]], [[TMP18]], 5 +// CHECK-RV64-NEXT: [[TMP20:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 6 +// CHECK-RV64-NEXT: [[TMP21:%.*]] = insertvalue { , , , , , , } [[TMP19]], [[TMP20]], 6 +// CHECK-RV64-NEXT: [[TMP22:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 7 +// CHECK-RV64-NEXT: store i64 [[TMP22]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP21]] +// +vbfloat16m1x7_t test_vlseg7e16ff_v_bf16m1x7_tu(vbfloat16m1x7_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg7e16ff_v_bf16m1x7_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16ff_v_bf16mf4x7_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , , i64 } @llvm.riscv.vlseg7ff.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 0 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , , , , , } poison, [[TMP8]], 0 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = insertvalue { , , , , , , } [[TMP9]], [[TMP10]], 1 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 2 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = insertvalue { , , , , , , } [[TMP11]], [[TMP12]], 2 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = insertvalue { , , , , , , } [[TMP13]], [[TMP14]], 3 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 4 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = insertvalue { , , , , , , } [[TMP15]], [[TMP16]], 4 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 5 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = insertvalue { , , , , , , } [[TMP17]], [[TMP18]], 5 +// CHECK-RV64-NEXT: [[TMP20:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 6 +// CHECK-RV64-NEXT: [[TMP21:%.*]] = insertvalue { , , , , , , } [[TMP19]], [[TMP20]], 6 +// CHECK-RV64-NEXT: [[TMP22:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 7 +// CHECK-RV64-NEXT: store i64 [[TMP22]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP21]] +// +vbfloat16mf4x7_t test_vlseg7e16ff_v_bf16mf4x7_tum(vbool64_t vm, vbfloat16mf4x7_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg7e16ff_v_bf16mf4x7_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16ff_v_bf16mf2x7_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , , i64 } @llvm.riscv.vlseg7ff.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 0 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , , , , , } poison, [[TMP8]], 0 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = insertvalue { , , , , , , } [[TMP9]], [[TMP10]], 1 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 2 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = insertvalue { , , , , , , } [[TMP11]], [[TMP12]], 2 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = insertvalue { , , , , , , } [[TMP13]], [[TMP14]], 3 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 4 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = insertvalue { , , , , , , } [[TMP15]], [[TMP16]], 4 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 5 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = insertvalue { , , , , , , } [[TMP17]], [[TMP18]], 5 +// CHECK-RV64-NEXT: [[TMP20:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 6 +// CHECK-RV64-NEXT: [[TMP21:%.*]] = insertvalue { , , , , , , } [[TMP19]], [[TMP20]], 6 +// CHECK-RV64-NEXT: [[TMP22:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 7 +// CHECK-RV64-NEXT: store i64 [[TMP22]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP21]] +// +vbfloat16mf2x7_t test_vlseg7e16ff_v_bf16mf2x7_tum(vbool32_t vm, vbfloat16mf2x7_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg7e16ff_v_bf16mf2x7_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16ff_v_bf16m1x7_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , , i64 } @llvm.riscv.vlseg7ff.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 0 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , , , , , } poison, [[TMP8]], 0 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = insertvalue { , , , , , , } [[TMP9]], [[TMP10]], 1 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 2 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = insertvalue { , , , , , , } [[TMP11]], [[TMP12]], 2 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = insertvalue { , , , , , , } [[TMP13]], [[TMP14]], 3 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 4 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = insertvalue { , , , , , , } [[TMP15]], [[TMP16]], 4 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 5 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = insertvalue { , , , , , , } [[TMP17]], [[TMP18]], 5 +// CHECK-RV64-NEXT: [[TMP20:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 6 +// CHECK-RV64-NEXT: [[TMP21:%.*]] = insertvalue { , , , , , , } [[TMP19]], [[TMP20]], 6 +// CHECK-RV64-NEXT: [[TMP22:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 7 +// CHECK-RV64-NEXT: store i64 [[TMP22]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP21]] +// +vbfloat16m1x7_t test_vlseg7e16ff_v_bf16m1x7_tum(vbool16_t vm, vbfloat16m1x7_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg7e16ff_v_bf16m1x7_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16ff_v_bf16mf4x7_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , , i64 } @llvm.riscv.vlseg7ff.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 0 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , , , , , } poison, [[TMP8]], 0 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = insertvalue { , , , , , , } [[TMP9]], [[TMP10]], 1 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 2 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = insertvalue { , , , , , , } [[TMP11]], [[TMP12]], 2 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = insertvalue { , , , , , , } [[TMP13]], [[TMP14]], 3 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 4 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = insertvalue { , , , , , , } [[TMP15]], [[TMP16]], 4 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 5 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = insertvalue { , , , , , , } [[TMP17]], [[TMP18]], 5 +// CHECK-RV64-NEXT: [[TMP20:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 6 +// CHECK-RV64-NEXT: [[TMP21:%.*]] = insertvalue { , , , , , , } [[TMP19]], [[TMP20]], 6 +// CHECK-RV64-NEXT: [[TMP22:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 7 +// CHECK-RV64-NEXT: store i64 [[TMP22]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP21]] +// +vbfloat16mf4x7_t test_vlseg7e16ff_v_bf16mf4x7_tumu(vbool64_t vm, vbfloat16mf4x7_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg7e16ff_v_bf16mf4x7_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16ff_v_bf16mf2x7_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , , i64 } @llvm.riscv.vlseg7ff.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 0 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , , , , , } poison, [[TMP8]], 0 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = insertvalue { , , , , , , } [[TMP9]], [[TMP10]], 1 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 2 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = insertvalue { , , , , , , } [[TMP11]], [[TMP12]], 2 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = insertvalue { , , , , , , } [[TMP13]], [[TMP14]], 3 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 4 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = insertvalue { , , , , , , } [[TMP15]], [[TMP16]], 4 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 5 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = insertvalue { , , , , , , } [[TMP17]], [[TMP18]], 5 +// CHECK-RV64-NEXT: [[TMP20:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 6 +// CHECK-RV64-NEXT: [[TMP21:%.*]] = insertvalue { , , , , , , } [[TMP19]], [[TMP20]], 6 +// CHECK-RV64-NEXT: [[TMP22:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 7 +// CHECK-RV64-NEXT: store i64 [[TMP22]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP21]] +// +vbfloat16mf2x7_t test_vlseg7e16ff_v_bf16mf2x7_tumu(vbool32_t vm, vbfloat16mf2x7_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg7e16ff_v_bf16mf2x7_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16ff_v_bf16m1x7_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , , i64 } @llvm.riscv.vlseg7ff.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 0 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , , , , , } poison, [[TMP8]], 0 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = insertvalue { , , , , , , } [[TMP9]], [[TMP10]], 1 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 2 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = insertvalue { , , , , , , } [[TMP11]], [[TMP12]], 2 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = insertvalue { , , , , , , } [[TMP13]], [[TMP14]], 3 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 4 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = insertvalue { , , , , , , } [[TMP15]], [[TMP16]], 4 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 5 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = insertvalue { , , , , , , } [[TMP17]], [[TMP18]], 5 +// CHECK-RV64-NEXT: [[TMP20:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 6 +// CHECK-RV64-NEXT: [[TMP21:%.*]] = insertvalue { , , , , , , } [[TMP19]], [[TMP20]], 6 +// CHECK-RV64-NEXT: [[TMP22:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 7 +// CHECK-RV64-NEXT: store i64 [[TMP22]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP21]] +// +vbfloat16m1x7_t test_vlseg7e16ff_v_bf16m1x7_tumu(vbool16_t vm, vbfloat16m1x7_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg7e16ff_v_bf16m1x7_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16ff_v_bf16mf4x7_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , , i64 } @llvm.riscv.vlseg7ff.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 0 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , , , , , } poison, [[TMP8]], 0 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = insertvalue { , , , , , , } [[TMP9]], [[TMP10]], 1 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 2 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = insertvalue { , , , , , , } [[TMP11]], [[TMP12]], 2 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = insertvalue { , , , , , , } [[TMP13]], [[TMP14]], 3 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 4 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = insertvalue { , , , , , , } [[TMP15]], [[TMP16]], 4 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 5 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = insertvalue { , , , , , , } [[TMP17]], [[TMP18]], 5 +// CHECK-RV64-NEXT: [[TMP20:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 6 +// CHECK-RV64-NEXT: [[TMP21:%.*]] = insertvalue { , , , , , , } [[TMP19]], [[TMP20]], 6 +// CHECK-RV64-NEXT: [[TMP22:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 7 +// CHECK-RV64-NEXT: store i64 [[TMP22]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP21]] +// +vbfloat16mf4x7_t test_vlseg7e16ff_v_bf16mf4x7_mu(vbool64_t vm, vbfloat16mf4x7_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg7e16ff_v_bf16mf4x7_mu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16ff_v_bf16mf2x7_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , , i64 } @llvm.riscv.vlseg7ff.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 0 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , , , , , } poison, [[TMP8]], 0 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = insertvalue { , , , , , , } [[TMP9]], [[TMP10]], 1 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 2 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = insertvalue { , , , , , , } [[TMP11]], [[TMP12]], 2 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = insertvalue { , , , , , , } [[TMP13]], [[TMP14]], 3 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 4 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = insertvalue { , , , , , , } [[TMP15]], [[TMP16]], 4 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 5 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = insertvalue { , , , , , , } [[TMP17]], [[TMP18]], 5 +// CHECK-RV64-NEXT: [[TMP20:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 6 +// CHECK-RV64-NEXT: [[TMP21:%.*]] = insertvalue { , , , , , , } [[TMP19]], [[TMP20]], 6 +// CHECK-RV64-NEXT: [[TMP22:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 7 +// CHECK-RV64-NEXT: store i64 [[TMP22]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP21]] +// +vbfloat16mf2x7_t test_vlseg7e16ff_v_bf16mf2x7_mu(vbool32_t vm, vbfloat16mf2x7_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg7e16ff_v_bf16mf2x7_mu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16ff_v_bf16m1x7_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , , i64 } @llvm.riscv.vlseg7ff.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 0 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , , , , , } poison, [[TMP8]], 0 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = insertvalue { , , , , , , } [[TMP9]], [[TMP10]], 1 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 2 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = insertvalue { , , , , , , } [[TMP11]], [[TMP12]], 2 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = insertvalue { , , , , , , } [[TMP13]], [[TMP14]], 3 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 4 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = insertvalue { , , , , , , } [[TMP15]], [[TMP16]], 4 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 5 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = insertvalue { , , , , , , } [[TMP17]], [[TMP18]], 5 +// CHECK-RV64-NEXT: [[TMP20:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 6 +// CHECK-RV64-NEXT: [[TMP21:%.*]] = insertvalue { , , , , , , } [[TMP19]], [[TMP20]], 6 +// CHECK-RV64-NEXT: [[TMP22:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 7 +// CHECK-RV64-NEXT: store i64 [[TMP22]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP21]] +// +vbfloat16m1x7_t test_vlseg7e16ff_v_bf16m1x7_mu(vbool16_t vm, vbfloat16m1x7_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg7e16ff_v_bf16m1x7_mu(vm, vd, rs1, new_vl, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlseg8e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlseg8e16.c new file mode 100644 index 0000000000000000000000000000000000000000..b11f79f4e6a4e9b424d1317c5ac6477079ee7a52 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlseg8e16.c @@ -0,0 +1,225 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16_v_bf16mf4x8_tu( +// CHECK-RV64-SAME: { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vlseg8.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf4x8_t test_vlseg8e16_v_bf16mf4x8_tu(vbfloat16mf4x8_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg8e16_v_bf16mf4x8_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16_v_bf16mf2x8_tu( +// CHECK-RV64-SAME: { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vlseg8.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf2x8_t test_vlseg8e16_v_bf16mf2x8_tu(vbfloat16mf2x8_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg8e16_v_bf16mf2x8_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16_v_bf16m1x8_tu( +// CHECK-RV64-SAME: { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vlseg8.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16m1x8_t test_vlseg8e16_v_bf16m1x8_tu(vbfloat16m1x8_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg8e16_v_bf16m1x8_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16_v_bf16mf4x8_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vlseg8.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf4x8_t test_vlseg8e16_v_bf16mf4x8_tum(vbool64_t vm, vbfloat16mf4x8_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg8e16_v_bf16mf4x8_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16_v_bf16mf2x8_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vlseg8.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf2x8_t test_vlseg8e16_v_bf16mf2x8_tum(vbool32_t vm, vbfloat16mf2x8_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg8e16_v_bf16mf2x8_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16_v_bf16m1x8_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vlseg8.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16m1x8_t test_vlseg8e16_v_bf16m1x8_tum(vbool16_t vm, vbfloat16m1x8_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg8e16_v_bf16m1x8_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16_v_bf16mf4x8_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vlseg8.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf4x8_t test_vlseg8e16_v_bf16mf4x8_tumu(vbool64_t vm, vbfloat16mf4x8_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg8e16_v_bf16mf4x8_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16_v_bf16mf2x8_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vlseg8.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf2x8_t test_vlseg8e16_v_bf16mf2x8_tumu(vbool32_t vm, vbfloat16mf2x8_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg8e16_v_bf16mf2x8_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16_v_bf16m1x8_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vlseg8.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16m1x8_t test_vlseg8e16_v_bf16m1x8_tumu(vbool16_t vm, vbfloat16m1x8_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg8e16_v_bf16m1x8_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16_v_bf16mf4x8_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vlseg8.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf4x8_t test_vlseg8e16_v_bf16mf4x8_mu(vbool64_t vm, vbfloat16mf4x8_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg8e16_v_bf16mf4x8_mu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16_v_bf16mf2x8_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vlseg8.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf2x8_t test_vlseg8e16_v_bf16mf2x8_mu(vbool32_t vm, vbfloat16mf2x8_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg8e16_v_bf16mf2x8_mu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16_v_bf16m1x8_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vlseg8.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16m1x8_t test_vlseg8e16_v_bf16m1x8_mu(vbool16_t vm, vbfloat16m1x8_t vd, const __bf16 *rs1, size_t vl) { + return __riscv_vlseg8e16_v_bf16m1x8_mu(vm, vd, rs1, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlseg8e16ff.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlseg8e16ff.c new file mode 100644 index 0000000000000000000000000000000000000000..4f5e3868f78cd675e48512f1f120770fb704fe80 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlseg8e16ff.c @@ -0,0 +1,441 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16ff_v_bf16mf4x8_tu( +// CHECK-RV64-SAME: { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , , i64 } @llvm.riscv.vlseg8ff.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 0 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , , , } poison, [[TMP9]], 0 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 1 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , , , } [[TMP10]], [[TMP11]], 1 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , , , } [[TMP12]], [[TMP13]], 2 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 3 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , , , } [[TMP14]], [[TMP15]], 3 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 4 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = insertvalue { , , , , , , , } [[TMP16]], [[TMP17]], 4 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 5 +// CHECK-RV64-NEXT: [[TMP20:%.*]] = insertvalue { , , , , , , , } [[TMP18]], [[TMP19]], 5 +// CHECK-RV64-NEXT: [[TMP21:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 6 +// CHECK-RV64-NEXT: [[TMP22:%.*]] = insertvalue { , , , , , , , } [[TMP20]], [[TMP21]], 6 +// CHECK-RV64-NEXT: [[TMP23:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 7 +// CHECK-RV64-NEXT: [[TMP24:%.*]] = insertvalue { , , , , , , , } [[TMP22]], [[TMP23]], 7 +// CHECK-RV64-NEXT: [[TMP25:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 8 +// CHECK-RV64-NEXT: store i64 [[TMP25]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP24]] +// +vbfloat16mf4x8_t test_vlseg8e16ff_v_bf16mf4x8_tu(vbfloat16mf4x8_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg8e16ff_v_bf16mf4x8_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16ff_v_bf16mf2x8_tu( +// CHECK-RV64-SAME: { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , , i64 } @llvm.riscv.vlseg8ff.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 0 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , , , } poison, [[TMP9]], 0 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 1 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , , , } [[TMP10]], [[TMP11]], 1 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , , , } [[TMP12]], [[TMP13]], 2 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 3 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , , , } [[TMP14]], [[TMP15]], 3 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 4 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = insertvalue { , , , , , , , } [[TMP16]], [[TMP17]], 4 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 5 +// CHECK-RV64-NEXT: [[TMP20:%.*]] = insertvalue { , , , , , , , } [[TMP18]], [[TMP19]], 5 +// CHECK-RV64-NEXT: [[TMP21:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 6 +// CHECK-RV64-NEXT: [[TMP22:%.*]] = insertvalue { , , , , , , , } [[TMP20]], [[TMP21]], 6 +// CHECK-RV64-NEXT: [[TMP23:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 7 +// CHECK-RV64-NEXT: [[TMP24:%.*]] = insertvalue { , , , , , , , } [[TMP22]], [[TMP23]], 7 +// CHECK-RV64-NEXT: [[TMP25:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 8 +// CHECK-RV64-NEXT: store i64 [[TMP25]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP24]] +// +vbfloat16mf2x8_t test_vlseg8e16ff_v_bf16mf2x8_tu(vbfloat16mf2x8_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg8e16ff_v_bf16mf2x8_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16ff_v_bf16m1x8_tu( +// CHECK-RV64-SAME: { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , , i64 } @llvm.riscv.vlseg8ff.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 0 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , , , } poison, [[TMP9]], 0 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 1 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , , , } [[TMP10]], [[TMP11]], 1 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , , , } [[TMP12]], [[TMP13]], 2 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 3 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , , , } [[TMP14]], [[TMP15]], 3 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 4 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = insertvalue { , , , , , , , } [[TMP16]], [[TMP17]], 4 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 5 +// CHECK-RV64-NEXT: [[TMP20:%.*]] = insertvalue { , , , , , , , } [[TMP18]], [[TMP19]], 5 +// CHECK-RV64-NEXT: [[TMP21:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 6 +// CHECK-RV64-NEXT: [[TMP22:%.*]] = insertvalue { , , , , , , , } [[TMP20]], [[TMP21]], 6 +// CHECK-RV64-NEXT: [[TMP23:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 7 +// CHECK-RV64-NEXT: [[TMP24:%.*]] = insertvalue { , , , , , , , } [[TMP22]], [[TMP23]], 7 +// CHECK-RV64-NEXT: [[TMP25:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 8 +// CHECK-RV64-NEXT: store i64 [[TMP25]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP24]] +// +vbfloat16m1x8_t test_vlseg8e16ff_v_bf16m1x8_tu(vbfloat16m1x8_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg8e16ff_v_bf16m1x8_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16ff_v_bf16mf4x8_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , , i64 } @llvm.riscv.vlseg8ff.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 0 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , , , } poison, [[TMP9]], 0 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 1 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , , , } [[TMP10]], [[TMP11]], 1 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , , , } [[TMP12]], [[TMP13]], 2 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 3 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , , , } [[TMP14]], [[TMP15]], 3 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 4 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = insertvalue { , , , , , , , } [[TMP16]], [[TMP17]], 4 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 5 +// CHECK-RV64-NEXT: [[TMP20:%.*]] = insertvalue { , , , , , , , } [[TMP18]], [[TMP19]], 5 +// CHECK-RV64-NEXT: [[TMP21:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 6 +// CHECK-RV64-NEXT: [[TMP22:%.*]] = insertvalue { , , , , , , , } [[TMP20]], [[TMP21]], 6 +// CHECK-RV64-NEXT: [[TMP23:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 7 +// CHECK-RV64-NEXT: [[TMP24:%.*]] = insertvalue { , , , , , , , } [[TMP22]], [[TMP23]], 7 +// CHECK-RV64-NEXT: [[TMP25:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 8 +// CHECK-RV64-NEXT: store i64 [[TMP25]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP24]] +// +vbfloat16mf4x8_t test_vlseg8e16ff_v_bf16mf4x8_tum(vbool64_t vm, vbfloat16mf4x8_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg8e16ff_v_bf16mf4x8_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16ff_v_bf16mf2x8_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , , i64 } @llvm.riscv.vlseg8ff.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 0 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , , , } poison, [[TMP9]], 0 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 1 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , , , } [[TMP10]], [[TMP11]], 1 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , , , } [[TMP12]], [[TMP13]], 2 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 3 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , , , } [[TMP14]], [[TMP15]], 3 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 4 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = insertvalue { , , , , , , , } [[TMP16]], [[TMP17]], 4 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 5 +// CHECK-RV64-NEXT: [[TMP20:%.*]] = insertvalue { , , , , , , , } [[TMP18]], [[TMP19]], 5 +// CHECK-RV64-NEXT: [[TMP21:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 6 +// CHECK-RV64-NEXT: [[TMP22:%.*]] = insertvalue { , , , , , , , } [[TMP20]], [[TMP21]], 6 +// CHECK-RV64-NEXT: [[TMP23:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 7 +// CHECK-RV64-NEXT: [[TMP24:%.*]] = insertvalue { , , , , , , , } [[TMP22]], [[TMP23]], 7 +// CHECK-RV64-NEXT: [[TMP25:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 8 +// CHECK-RV64-NEXT: store i64 [[TMP25]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP24]] +// +vbfloat16mf2x8_t test_vlseg8e16ff_v_bf16mf2x8_tum(vbool32_t vm, vbfloat16mf2x8_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg8e16ff_v_bf16mf2x8_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16ff_v_bf16m1x8_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , , i64 } @llvm.riscv.vlseg8ff.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 0 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , , , } poison, [[TMP9]], 0 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 1 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , , , } [[TMP10]], [[TMP11]], 1 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , , , } [[TMP12]], [[TMP13]], 2 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 3 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , , , } [[TMP14]], [[TMP15]], 3 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 4 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = insertvalue { , , , , , , , } [[TMP16]], [[TMP17]], 4 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 5 +// CHECK-RV64-NEXT: [[TMP20:%.*]] = insertvalue { , , , , , , , } [[TMP18]], [[TMP19]], 5 +// CHECK-RV64-NEXT: [[TMP21:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 6 +// CHECK-RV64-NEXT: [[TMP22:%.*]] = insertvalue { , , , , , , , } [[TMP20]], [[TMP21]], 6 +// CHECK-RV64-NEXT: [[TMP23:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 7 +// CHECK-RV64-NEXT: [[TMP24:%.*]] = insertvalue { , , , , , , , } [[TMP22]], [[TMP23]], 7 +// CHECK-RV64-NEXT: [[TMP25:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 8 +// CHECK-RV64-NEXT: store i64 [[TMP25]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP24]] +// +vbfloat16m1x8_t test_vlseg8e16ff_v_bf16m1x8_tum(vbool16_t vm, vbfloat16m1x8_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg8e16ff_v_bf16m1x8_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16ff_v_bf16mf4x8_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , , i64 } @llvm.riscv.vlseg8ff.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 0 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , , , } poison, [[TMP9]], 0 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 1 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , , , } [[TMP10]], [[TMP11]], 1 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , , , } [[TMP12]], [[TMP13]], 2 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 3 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , , , } [[TMP14]], [[TMP15]], 3 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 4 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = insertvalue { , , , , , , , } [[TMP16]], [[TMP17]], 4 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 5 +// CHECK-RV64-NEXT: [[TMP20:%.*]] = insertvalue { , , , , , , , } [[TMP18]], [[TMP19]], 5 +// CHECK-RV64-NEXT: [[TMP21:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 6 +// CHECK-RV64-NEXT: [[TMP22:%.*]] = insertvalue { , , , , , , , } [[TMP20]], [[TMP21]], 6 +// CHECK-RV64-NEXT: [[TMP23:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 7 +// CHECK-RV64-NEXT: [[TMP24:%.*]] = insertvalue { , , , , , , , } [[TMP22]], [[TMP23]], 7 +// CHECK-RV64-NEXT: [[TMP25:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 8 +// CHECK-RV64-NEXT: store i64 [[TMP25]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP24]] +// +vbfloat16mf4x8_t test_vlseg8e16ff_v_bf16mf4x8_tumu(vbool64_t vm, vbfloat16mf4x8_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg8e16ff_v_bf16mf4x8_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16ff_v_bf16mf2x8_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , , i64 } @llvm.riscv.vlseg8ff.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 0 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , , , } poison, [[TMP9]], 0 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 1 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , , , } [[TMP10]], [[TMP11]], 1 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , , , } [[TMP12]], [[TMP13]], 2 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 3 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , , , } [[TMP14]], [[TMP15]], 3 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 4 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = insertvalue { , , , , , , , } [[TMP16]], [[TMP17]], 4 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 5 +// CHECK-RV64-NEXT: [[TMP20:%.*]] = insertvalue { , , , , , , , } [[TMP18]], [[TMP19]], 5 +// CHECK-RV64-NEXT: [[TMP21:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 6 +// CHECK-RV64-NEXT: [[TMP22:%.*]] = insertvalue { , , , , , , , } [[TMP20]], [[TMP21]], 6 +// CHECK-RV64-NEXT: [[TMP23:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 7 +// CHECK-RV64-NEXT: [[TMP24:%.*]] = insertvalue { , , , , , , , } [[TMP22]], [[TMP23]], 7 +// CHECK-RV64-NEXT: [[TMP25:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 8 +// CHECK-RV64-NEXT: store i64 [[TMP25]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP24]] +// +vbfloat16mf2x8_t test_vlseg8e16ff_v_bf16mf2x8_tumu(vbool32_t vm, vbfloat16mf2x8_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg8e16ff_v_bf16mf2x8_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16ff_v_bf16m1x8_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , , i64 } @llvm.riscv.vlseg8ff.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 0 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , , , } poison, [[TMP9]], 0 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 1 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , , , } [[TMP10]], [[TMP11]], 1 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , , , } [[TMP12]], [[TMP13]], 2 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 3 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , , , } [[TMP14]], [[TMP15]], 3 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 4 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = insertvalue { , , , , , , , } [[TMP16]], [[TMP17]], 4 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 5 +// CHECK-RV64-NEXT: [[TMP20:%.*]] = insertvalue { , , , , , , , } [[TMP18]], [[TMP19]], 5 +// CHECK-RV64-NEXT: [[TMP21:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 6 +// CHECK-RV64-NEXT: [[TMP22:%.*]] = insertvalue { , , , , , , , } [[TMP20]], [[TMP21]], 6 +// CHECK-RV64-NEXT: [[TMP23:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 7 +// CHECK-RV64-NEXT: [[TMP24:%.*]] = insertvalue { , , , , , , , } [[TMP22]], [[TMP23]], 7 +// CHECK-RV64-NEXT: [[TMP25:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 8 +// CHECK-RV64-NEXT: store i64 [[TMP25]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP24]] +// +vbfloat16m1x8_t test_vlseg8e16ff_v_bf16m1x8_tumu(vbool16_t vm, vbfloat16m1x8_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg8e16ff_v_bf16m1x8_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16ff_v_bf16mf4x8_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , , i64 } @llvm.riscv.vlseg8ff.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 0 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , , , } poison, [[TMP9]], 0 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 1 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , , , } [[TMP10]], [[TMP11]], 1 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , , , } [[TMP12]], [[TMP13]], 2 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 3 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , , , } [[TMP14]], [[TMP15]], 3 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 4 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = insertvalue { , , , , , , , } [[TMP16]], [[TMP17]], 4 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 5 +// CHECK-RV64-NEXT: [[TMP20:%.*]] = insertvalue { , , , , , , , } [[TMP18]], [[TMP19]], 5 +// CHECK-RV64-NEXT: [[TMP21:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 6 +// CHECK-RV64-NEXT: [[TMP22:%.*]] = insertvalue { , , , , , , , } [[TMP20]], [[TMP21]], 6 +// CHECK-RV64-NEXT: [[TMP23:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 7 +// CHECK-RV64-NEXT: [[TMP24:%.*]] = insertvalue { , , , , , , , } [[TMP22]], [[TMP23]], 7 +// CHECK-RV64-NEXT: [[TMP25:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 8 +// CHECK-RV64-NEXT: store i64 [[TMP25]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP24]] +// +vbfloat16mf4x8_t test_vlseg8e16ff_v_bf16mf4x8_mu(vbool64_t vm, vbfloat16mf4x8_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg8e16ff_v_bf16mf4x8_mu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16ff_v_bf16mf2x8_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , , i64 } @llvm.riscv.vlseg8ff.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 0 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , , , } poison, [[TMP9]], 0 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 1 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , , , } [[TMP10]], [[TMP11]], 1 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , , , } [[TMP12]], [[TMP13]], 2 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 3 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , , , } [[TMP14]], [[TMP15]], 3 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 4 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = insertvalue { , , , , , , , } [[TMP16]], [[TMP17]], 4 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 5 +// CHECK-RV64-NEXT: [[TMP20:%.*]] = insertvalue { , , , , , , , } [[TMP18]], [[TMP19]], 5 +// CHECK-RV64-NEXT: [[TMP21:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 6 +// CHECK-RV64-NEXT: [[TMP22:%.*]] = insertvalue { , , , , , , , } [[TMP20]], [[TMP21]], 6 +// CHECK-RV64-NEXT: [[TMP23:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 7 +// CHECK-RV64-NEXT: [[TMP24:%.*]] = insertvalue { , , , , , , , } [[TMP22]], [[TMP23]], 7 +// CHECK-RV64-NEXT: [[TMP25:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 8 +// CHECK-RV64-NEXT: store i64 [[TMP25]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP24]] +// +vbfloat16mf2x8_t test_vlseg8e16ff_v_bf16mf2x8_mu(vbool32_t vm, vbfloat16mf2x8_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg8e16ff_v_bf16mf2x8_mu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16ff_v_bf16m1x8_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , , i64 } @llvm.riscv.vlseg8ff.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 0 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , , , } poison, [[TMP9]], 0 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 1 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , , , } [[TMP10]], [[TMP11]], 1 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , , , } [[TMP12]], [[TMP13]], 2 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 3 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , , , } [[TMP14]], [[TMP15]], 3 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 4 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = insertvalue { , , , , , , , } [[TMP16]], [[TMP17]], 4 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 5 +// CHECK-RV64-NEXT: [[TMP20:%.*]] = insertvalue { , , , , , , , } [[TMP18]], [[TMP19]], 5 +// CHECK-RV64-NEXT: [[TMP21:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 6 +// CHECK-RV64-NEXT: [[TMP22:%.*]] = insertvalue { , , , , , , , } [[TMP20]], [[TMP21]], 6 +// CHECK-RV64-NEXT: [[TMP23:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 7 +// CHECK-RV64-NEXT: [[TMP24:%.*]] = insertvalue { , , , , , , , } [[TMP22]], [[TMP23]], 7 +// CHECK-RV64-NEXT: [[TMP25:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 8 +// CHECK-RV64-NEXT: store i64 [[TMP25]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP24]] +// +vbfloat16m1x8_t test_vlseg8e16ff_v_bf16m1x8_mu(vbool16_t vm, vbfloat16m1x8_t vd, const __bf16 *rs1, size_t *new_vl, size_t vl) { + return __riscv_vlseg8e16ff_v_bf16m1x8_mu(vm, vd, rs1, new_vl, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlsseg2e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlsseg2e16.c new file mode 100644 index 0000000000000000000000000000000000000000..9ab83506e3a4b5b25e937c3a3696ae57cd5c93ba --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlsseg2e16.c @@ -0,0 +1,249 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16mf4x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlsseg2.nxv1bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf4x2_t test_vlsseg2e16_v_bf16mf4x2_tu(vbfloat16mf4x2_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg2e16_v_bf16mf4x2_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16mf2x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlsseg2.nxv2bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf2x2_t test_vlsseg2e16_v_bf16mf2x2_tu(vbfloat16mf2x2_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg2e16_v_bf16mf2x2_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16m1x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlsseg2.nxv4bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m1x2_t test_vlsseg2e16_v_bf16m1x2_tu(vbfloat16m1x2_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg2e16_v_bf16m1x2_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16m2x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlsseg2.nxv8bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m2x2_t test_vlsseg2e16_v_bf16m2x2_tu(vbfloat16m2x2_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg2e16_v_bf16m2x2_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16m4x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlsseg2.nxv16bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m4x2_t test_vlsseg2e16_v_bf16m4x2_tu(vbfloat16m4x2_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg2e16_v_bf16m4x2_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16mf4x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlsseg2.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf4x2_t test_vlsseg2e16_v_bf16mf4x2_tum(vbool64_t vm, vbfloat16mf4x2_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg2e16_v_bf16mf4x2_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16mf2x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlsseg2.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf2x2_t test_vlsseg2e16_v_bf16mf2x2_tum(vbool32_t vm, vbfloat16mf2x2_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg2e16_v_bf16mf2x2_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16m1x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlsseg2.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m1x2_t test_vlsseg2e16_v_bf16m1x2_tum(vbool16_t vm, vbfloat16m1x2_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg2e16_v_bf16m1x2_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16m2x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlsseg2.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m2x2_t test_vlsseg2e16_v_bf16m2x2_tum(vbool8_t vm, vbfloat16m2x2_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg2e16_v_bf16m2x2_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16m4x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlsseg2.mask.nxv16bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m4x2_t test_vlsseg2e16_v_bf16m4x2_tum(vbool4_t vm, vbfloat16m4x2_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg2e16_v_bf16m4x2_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16mf4x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlsseg2.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf4x2_t test_vlsseg2e16_v_bf16mf4x2_tumu(vbool64_t vm, vbfloat16mf4x2_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg2e16_v_bf16mf4x2_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16mf2x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlsseg2.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf2x2_t test_vlsseg2e16_v_bf16mf2x2_tumu(vbool32_t vm, vbfloat16mf2x2_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg2e16_v_bf16mf2x2_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16m1x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlsseg2.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m1x2_t test_vlsseg2e16_v_bf16m1x2_tumu(vbool16_t vm, vbfloat16m1x2_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg2e16_v_bf16m1x2_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16m2x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlsseg2.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m2x2_t test_vlsseg2e16_v_bf16m2x2_tumu(vbool8_t vm, vbfloat16m2x2_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg2e16_v_bf16m2x2_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16m4x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlsseg2.mask.nxv16bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m4x2_t test_vlsseg2e16_v_bf16m4x2_tumu(vbool4_t vm, vbfloat16m4x2_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg2e16_v_bf16m4x2_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16mf4x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlsseg2.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf4x2_t test_vlsseg2e16_v_bf16mf4x2_mu(vbool64_t vm, vbfloat16mf4x2_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg2e16_v_bf16mf4x2_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16mf2x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlsseg2.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf2x2_t test_vlsseg2e16_v_bf16mf2x2_mu(vbool32_t vm, vbfloat16mf2x2_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg2e16_v_bf16mf2x2_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16m1x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlsseg2.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m1x2_t test_vlsseg2e16_v_bf16m1x2_mu(vbool16_t vm, vbfloat16m1x2_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg2e16_v_bf16m1x2_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16m2x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlsseg2.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m2x2_t test_vlsseg2e16_v_bf16m2x2_mu(vbool8_t vm, vbfloat16m2x2_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg2e16_v_bf16m2x2_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16m4x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlsseg2.mask.nxv16bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m4x2_t test_vlsseg2e16_v_bf16m4x2_mu(vbool4_t vm, vbfloat16m4x2_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg2e16_v_bf16m4x2_mu(vm, vd, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlsseg3e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlsseg3e16.c new file mode 100644 index 0000000000000000000000000000000000000000..8e02291afd1cee8054e21737f1de010f011eda60 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlsseg3e16.c @@ -0,0 +1,217 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlsseg3e16_v_bf16mf4x3_tu( +// CHECK-RV64-SAME: { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlsseg3.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf4x3_t test_vlsseg3e16_v_bf16mf4x3_tu(vbfloat16mf4x3_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg3e16_v_bf16mf4x3_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlsseg3e16_v_bf16mf2x3_tu( +// CHECK-RV64-SAME: { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlsseg3.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf2x3_t test_vlsseg3e16_v_bf16mf2x3_tu(vbfloat16mf2x3_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg3e16_v_bf16mf2x3_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlsseg3e16_v_bf16m1x3_tu( +// CHECK-RV64-SAME: { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlsseg3.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m1x3_t test_vlsseg3e16_v_bf16m1x3_tu(vbfloat16m1x3_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg3e16_v_bf16m1x3_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlsseg3e16_v_bf16m2x3_tu( +// CHECK-RV64-SAME: { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlsseg3.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m2x3_t test_vlsseg3e16_v_bf16m2x3_tu(vbfloat16m2x3_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg3e16_v_bf16m2x3_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlsseg3e16_v_bf16mf4x3_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlsseg3.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf4x3_t test_vlsseg3e16_v_bf16mf4x3_tum(vbool64_t vm, vbfloat16mf4x3_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg3e16_v_bf16mf4x3_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlsseg3e16_v_bf16mf2x3_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlsseg3.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf2x3_t test_vlsseg3e16_v_bf16mf2x3_tum(vbool32_t vm, vbfloat16mf2x3_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg3e16_v_bf16mf2x3_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlsseg3e16_v_bf16m1x3_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlsseg3.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m1x3_t test_vlsseg3e16_v_bf16m1x3_tum(vbool16_t vm, vbfloat16m1x3_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg3e16_v_bf16m1x3_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlsseg3e16_v_bf16m2x3_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlsseg3.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m2x3_t test_vlsseg3e16_v_bf16m2x3_tum(vbool8_t vm, vbfloat16m2x3_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg3e16_v_bf16m2x3_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlsseg3e16_v_bf16mf4x3_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlsseg3.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf4x3_t test_vlsseg3e16_v_bf16mf4x3_tumu(vbool64_t vm, vbfloat16mf4x3_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg3e16_v_bf16mf4x3_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlsseg3e16_v_bf16mf2x3_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlsseg3.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf2x3_t test_vlsseg3e16_v_bf16mf2x3_tumu(vbool32_t vm, vbfloat16mf2x3_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg3e16_v_bf16mf2x3_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlsseg3e16_v_bf16m1x3_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlsseg3.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m1x3_t test_vlsseg3e16_v_bf16m1x3_tumu(vbool16_t vm, vbfloat16m1x3_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg3e16_v_bf16m1x3_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlsseg3e16_v_bf16m2x3_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlsseg3.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m2x3_t test_vlsseg3e16_v_bf16m2x3_tumu(vbool8_t vm, vbfloat16m2x3_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg3e16_v_bf16m2x3_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlsseg3e16_v_bf16mf4x3_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlsseg3.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf4x3_t test_vlsseg3e16_v_bf16mf4x3_mu(vbool64_t vm, vbfloat16mf4x3_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg3e16_v_bf16mf4x3_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlsseg3e16_v_bf16mf2x3_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlsseg3.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf2x3_t test_vlsseg3e16_v_bf16mf2x3_mu(vbool32_t vm, vbfloat16mf2x3_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg3e16_v_bf16mf2x3_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlsseg3e16_v_bf16m1x3_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlsseg3.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m1x3_t test_vlsseg3e16_v_bf16m1x3_mu(vbool16_t vm, vbfloat16m1x3_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg3e16_v_bf16m1x3_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlsseg3e16_v_bf16m2x3_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlsseg3.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m2x3_t test_vlsseg3e16_v_bf16m2x3_mu(vbool8_t vm, vbfloat16m2x3_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg3e16_v_bf16m2x3_mu(vm, vd, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlsseg4e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlsseg4e16.c new file mode 100644 index 0000000000000000000000000000000000000000..c9c57d5156e2ec43fe6fc3588aa866b10dbc85c3 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlsseg4e16.c @@ -0,0 +1,233 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlsseg4e16_v_bf16mf4x4_tu( +// CHECK-RV64-SAME: { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlsseg4.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf4x4_t test_vlsseg4e16_v_bf16mf4x4_tu(vbfloat16mf4x4_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg4e16_v_bf16mf4x4_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlsseg4e16_v_bf16mf2x4_tu( +// CHECK-RV64-SAME: { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlsseg4.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf2x4_t test_vlsseg4e16_v_bf16mf2x4_tu(vbfloat16mf2x4_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg4e16_v_bf16mf2x4_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlsseg4e16_v_bf16m1x4_tu( +// CHECK-RV64-SAME: { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlsseg4.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m1x4_t test_vlsseg4e16_v_bf16m1x4_tu(vbfloat16m1x4_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg4e16_v_bf16m1x4_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlsseg4e16_v_bf16m2x4_tu( +// CHECK-RV64-SAME: { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlsseg4.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m2x4_t test_vlsseg4e16_v_bf16m2x4_tu(vbfloat16m2x4_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg4e16_v_bf16m2x4_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlsseg4e16_v_bf16mf4x4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlsseg4.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf4x4_t test_vlsseg4e16_v_bf16mf4x4_tum(vbool64_t vm, vbfloat16mf4x4_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg4e16_v_bf16mf4x4_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlsseg4e16_v_bf16mf2x4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlsseg4.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf2x4_t test_vlsseg4e16_v_bf16mf2x4_tum(vbool32_t vm, vbfloat16mf2x4_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg4e16_v_bf16mf2x4_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlsseg4e16_v_bf16m1x4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlsseg4.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m1x4_t test_vlsseg4e16_v_bf16m1x4_tum(vbool16_t vm, vbfloat16m1x4_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg4e16_v_bf16m1x4_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlsseg4e16_v_bf16m2x4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlsseg4.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m2x4_t test_vlsseg4e16_v_bf16m2x4_tum(vbool8_t vm, vbfloat16m2x4_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg4e16_v_bf16m2x4_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlsseg4e16_v_bf16mf4x4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlsseg4.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf4x4_t test_vlsseg4e16_v_bf16mf4x4_tumu(vbool64_t vm, vbfloat16mf4x4_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg4e16_v_bf16mf4x4_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlsseg4e16_v_bf16mf2x4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlsseg4.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf2x4_t test_vlsseg4e16_v_bf16mf2x4_tumu(vbool32_t vm, vbfloat16mf2x4_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg4e16_v_bf16mf2x4_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlsseg4e16_v_bf16m1x4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlsseg4.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m1x4_t test_vlsseg4e16_v_bf16m1x4_tumu(vbool16_t vm, vbfloat16m1x4_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg4e16_v_bf16m1x4_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlsseg4e16_v_bf16m2x4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlsseg4.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m2x4_t test_vlsseg4e16_v_bf16m2x4_tumu(vbool8_t vm, vbfloat16m2x4_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg4e16_v_bf16m2x4_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlsseg4e16_v_bf16mf4x4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlsseg4.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf4x4_t test_vlsseg4e16_v_bf16mf4x4_mu(vbool64_t vm, vbfloat16mf4x4_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg4e16_v_bf16mf4x4_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlsseg4e16_v_bf16mf2x4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlsseg4.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf2x4_t test_vlsseg4e16_v_bf16mf2x4_mu(vbool32_t vm, vbfloat16mf2x4_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg4e16_v_bf16mf2x4_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlsseg4e16_v_bf16m1x4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlsseg4.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m1x4_t test_vlsseg4e16_v_bf16m1x4_mu(vbool16_t vm, vbfloat16m1x4_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg4e16_v_bf16m1x4_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlsseg4e16_v_bf16m2x4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlsseg4.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m2x4_t test_vlsseg4e16_v_bf16m2x4_mu(vbool8_t vm, vbfloat16m2x4_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg4e16_v_bf16m2x4_mu(vm, vd, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlsseg5e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlsseg5e16.c new file mode 100644 index 0000000000000000000000000000000000000000..2f4f7e6f0f79af78db962df00a60e29223c738b2 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlsseg5e16.c @@ -0,0 +1,189 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlsseg5e16_v_bf16mf4x5_tu( +// CHECK-RV64-SAME: { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vlsseg5.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf4x5_t test_vlsseg5e16_v_bf16mf4x5_tu(vbfloat16mf4x5_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg5e16_v_bf16mf4x5_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlsseg5e16_v_bf16mf2x5_tu( +// CHECK-RV64-SAME: { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vlsseg5.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf2x5_t test_vlsseg5e16_v_bf16mf2x5_tu(vbfloat16mf2x5_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg5e16_v_bf16mf2x5_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlsseg5e16_v_bf16m1x5_tu( +// CHECK-RV64-SAME: { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vlsseg5.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16m1x5_t test_vlsseg5e16_v_bf16m1x5_tu(vbfloat16m1x5_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg5e16_v_bf16m1x5_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlsseg5e16_v_bf16mf4x5_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vlsseg5.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf4x5_t test_vlsseg5e16_v_bf16mf4x5_tum(vbool64_t vm, vbfloat16mf4x5_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg5e16_v_bf16mf4x5_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlsseg5e16_v_bf16mf2x5_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vlsseg5.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf2x5_t test_vlsseg5e16_v_bf16mf2x5_tum(vbool32_t vm, vbfloat16mf2x5_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg5e16_v_bf16mf2x5_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlsseg5e16_v_bf16m1x5_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vlsseg5.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16m1x5_t test_vlsseg5e16_v_bf16m1x5_tum(vbool16_t vm, vbfloat16m1x5_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg5e16_v_bf16m1x5_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlsseg5e16_v_bf16mf4x5_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vlsseg5.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf4x5_t test_vlsseg5e16_v_bf16mf4x5_tumu(vbool64_t vm, vbfloat16mf4x5_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg5e16_v_bf16mf4x5_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlsseg5e16_v_bf16mf2x5_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vlsseg5.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf2x5_t test_vlsseg5e16_v_bf16mf2x5_tumu(vbool32_t vm, vbfloat16mf2x5_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg5e16_v_bf16mf2x5_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlsseg5e16_v_bf16m1x5_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vlsseg5.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16m1x5_t test_vlsseg5e16_v_bf16m1x5_tumu(vbool16_t vm, vbfloat16m1x5_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg5e16_v_bf16m1x5_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlsseg5e16_v_bf16mf4x5_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vlsseg5.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf4x5_t test_vlsseg5e16_v_bf16mf4x5_mu(vbool64_t vm, vbfloat16mf4x5_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg5e16_v_bf16mf4x5_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlsseg5e16_v_bf16mf2x5_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vlsseg5.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf2x5_t test_vlsseg5e16_v_bf16mf2x5_mu(vbool32_t vm, vbfloat16mf2x5_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg5e16_v_bf16mf2x5_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlsseg5e16_v_bf16m1x5_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vlsseg5.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16m1x5_t test_vlsseg5e16_v_bf16m1x5_mu(vbool16_t vm, vbfloat16m1x5_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg5e16_v_bf16m1x5_mu(vm, vd, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlsseg6e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlsseg6e16.c new file mode 100644 index 0000000000000000000000000000000000000000..5dd8adc57c690fa2b6afbb10388902954a922ff1 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlsseg6e16.c @@ -0,0 +1,201 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlsseg6e16_v_bf16mf4x6_tu( +// CHECK-RV64-SAME: { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vlsseg6.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf4x6_t test_vlsseg6e16_v_bf16mf4x6_tu(vbfloat16mf4x6_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg6e16_v_bf16mf4x6_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlsseg6e16_v_bf16mf2x6_tu( +// CHECK-RV64-SAME: { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vlsseg6.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf2x6_t test_vlsseg6e16_v_bf16mf2x6_tu(vbfloat16mf2x6_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg6e16_v_bf16mf2x6_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlsseg6e16_v_bf16m1x6_tu( +// CHECK-RV64-SAME: { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vlsseg6.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16m1x6_t test_vlsseg6e16_v_bf16m1x6_tu(vbfloat16m1x6_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg6e16_v_bf16m1x6_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlsseg6e16_v_bf16mf4x6_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vlsseg6.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf4x6_t test_vlsseg6e16_v_bf16mf4x6_tum(vbool64_t vm, vbfloat16mf4x6_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg6e16_v_bf16mf4x6_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlsseg6e16_v_bf16mf2x6_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vlsseg6.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf2x6_t test_vlsseg6e16_v_bf16mf2x6_tum(vbool32_t vm, vbfloat16mf2x6_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg6e16_v_bf16mf2x6_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlsseg6e16_v_bf16m1x6_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vlsseg6.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16m1x6_t test_vlsseg6e16_v_bf16m1x6_tum(vbool16_t vm, vbfloat16m1x6_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg6e16_v_bf16m1x6_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlsseg6e16_v_bf16mf4x6_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vlsseg6.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf4x6_t test_vlsseg6e16_v_bf16mf4x6_tumu(vbool64_t vm, vbfloat16mf4x6_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg6e16_v_bf16mf4x6_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlsseg6e16_v_bf16mf2x6_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vlsseg6.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf2x6_t test_vlsseg6e16_v_bf16mf2x6_tumu(vbool32_t vm, vbfloat16mf2x6_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg6e16_v_bf16mf2x6_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlsseg6e16_v_bf16m1x6_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vlsseg6.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16m1x6_t test_vlsseg6e16_v_bf16m1x6_tumu(vbool16_t vm, vbfloat16m1x6_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg6e16_v_bf16m1x6_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlsseg6e16_v_bf16mf4x6_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vlsseg6.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf4x6_t test_vlsseg6e16_v_bf16mf4x6_mu(vbool64_t vm, vbfloat16mf4x6_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg6e16_v_bf16mf4x6_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlsseg6e16_v_bf16mf2x6_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vlsseg6.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf2x6_t test_vlsseg6e16_v_bf16mf2x6_mu(vbool32_t vm, vbfloat16mf2x6_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg6e16_v_bf16mf2x6_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlsseg6e16_v_bf16m1x6_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vlsseg6.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16m1x6_t test_vlsseg6e16_v_bf16m1x6_mu(vbool16_t vm, vbfloat16m1x6_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg6e16_v_bf16m1x6_mu(vm, vd, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlsseg7e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlsseg7e16.c new file mode 100644 index 0000000000000000000000000000000000000000..dd6acd4906cbe5cd51bc9a8e55f6f893804acdb1 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlsseg7e16.c @@ -0,0 +1,213 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlsseg7e16_v_bf16mf4x7_tu( +// CHECK-RV64-SAME: { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vlsseg7.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf4x7_t test_vlsseg7e16_v_bf16mf4x7_tu(vbfloat16mf4x7_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg7e16_v_bf16mf4x7_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlsseg7e16_v_bf16mf2x7_tu( +// CHECK-RV64-SAME: { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vlsseg7.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf2x7_t test_vlsseg7e16_v_bf16mf2x7_tu(vbfloat16mf2x7_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg7e16_v_bf16mf2x7_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlsseg7e16_v_bf16m1x7_tu( +// CHECK-RV64-SAME: { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vlsseg7.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16m1x7_t test_vlsseg7e16_v_bf16m1x7_tu(vbfloat16m1x7_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg7e16_v_bf16m1x7_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlsseg7e16_v_bf16mf4x7_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vlsseg7.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf4x7_t test_vlsseg7e16_v_bf16mf4x7_tum(vbool64_t vm, vbfloat16mf4x7_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg7e16_v_bf16mf4x7_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlsseg7e16_v_bf16mf2x7_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vlsseg7.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf2x7_t test_vlsseg7e16_v_bf16mf2x7_tum(vbool32_t vm, vbfloat16mf2x7_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg7e16_v_bf16mf2x7_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlsseg7e16_v_bf16m1x7_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vlsseg7.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16m1x7_t test_vlsseg7e16_v_bf16m1x7_tum(vbool16_t vm, vbfloat16m1x7_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg7e16_v_bf16m1x7_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlsseg7e16_v_bf16mf4x7_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vlsseg7.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf4x7_t test_vlsseg7e16_v_bf16mf4x7_tumu(vbool64_t vm, vbfloat16mf4x7_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg7e16_v_bf16mf4x7_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlsseg7e16_v_bf16mf2x7_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vlsseg7.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf2x7_t test_vlsseg7e16_v_bf16mf2x7_tumu(vbool32_t vm, vbfloat16mf2x7_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg7e16_v_bf16mf2x7_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlsseg7e16_v_bf16m1x7_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vlsseg7.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16m1x7_t test_vlsseg7e16_v_bf16m1x7_tumu(vbool16_t vm, vbfloat16m1x7_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg7e16_v_bf16m1x7_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlsseg7e16_v_bf16mf4x7_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vlsseg7.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf4x7_t test_vlsseg7e16_v_bf16mf4x7_mu(vbool64_t vm, vbfloat16mf4x7_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg7e16_v_bf16mf4x7_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlsseg7e16_v_bf16mf2x7_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vlsseg7.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf2x7_t test_vlsseg7e16_v_bf16mf2x7_mu(vbool32_t vm, vbfloat16mf2x7_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg7e16_v_bf16mf2x7_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlsseg7e16_v_bf16m1x7_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vlsseg7.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16m1x7_t test_vlsseg7e16_v_bf16m1x7_mu(vbool16_t vm, vbfloat16m1x7_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg7e16_v_bf16m1x7_mu(vm, vd, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlsseg8e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlsseg8e16.c new file mode 100644 index 0000000000000000000000000000000000000000..9973765dc6544940e8bb830256d1a76a8ae11271 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vlsseg8e16.c @@ -0,0 +1,225 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlsseg8e16_v_bf16mf4x8_tu( +// CHECK-RV64-SAME: { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vlsseg8.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf4x8_t test_vlsseg8e16_v_bf16mf4x8_tu(vbfloat16mf4x8_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg8e16_v_bf16mf4x8_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlsseg8e16_v_bf16mf2x8_tu( +// CHECK-RV64-SAME: { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vlsseg8.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf2x8_t test_vlsseg8e16_v_bf16mf2x8_tu(vbfloat16mf2x8_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg8e16_v_bf16mf2x8_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlsseg8e16_v_bf16m1x8_tu( +// CHECK-RV64-SAME: { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vlsseg8.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16m1x8_t test_vlsseg8e16_v_bf16m1x8_tu(vbfloat16m1x8_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg8e16_v_bf16m1x8_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlsseg8e16_v_bf16mf4x8_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vlsseg8.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf4x8_t test_vlsseg8e16_v_bf16mf4x8_tum(vbool64_t vm, vbfloat16mf4x8_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg8e16_v_bf16mf4x8_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlsseg8e16_v_bf16mf2x8_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vlsseg8.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf2x8_t test_vlsseg8e16_v_bf16mf2x8_tum(vbool32_t vm, vbfloat16mf2x8_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg8e16_v_bf16mf2x8_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlsseg8e16_v_bf16m1x8_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vlsseg8.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16m1x8_t test_vlsseg8e16_v_bf16m1x8_tum(vbool16_t vm, vbfloat16m1x8_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg8e16_v_bf16m1x8_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlsseg8e16_v_bf16mf4x8_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vlsseg8.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf4x8_t test_vlsseg8e16_v_bf16mf4x8_tumu(vbool64_t vm, vbfloat16mf4x8_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg8e16_v_bf16mf4x8_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlsseg8e16_v_bf16mf2x8_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vlsseg8.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf2x8_t test_vlsseg8e16_v_bf16mf2x8_tumu(vbool32_t vm, vbfloat16mf2x8_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg8e16_v_bf16mf2x8_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlsseg8e16_v_bf16m1x8_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vlsseg8.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16m1x8_t test_vlsseg8e16_v_bf16m1x8_tumu(vbool16_t vm, vbfloat16m1x8_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg8e16_v_bf16m1x8_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlsseg8e16_v_bf16mf4x8_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vlsseg8.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf4x8_t test_vlsseg8e16_v_bf16mf4x8_mu(vbool64_t vm, vbfloat16mf4x8_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg8e16_v_bf16mf4x8_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlsseg8e16_v_bf16mf2x8_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vlsseg8.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf2x8_t test_vlsseg8e16_v_bf16mf2x8_mu(vbool32_t vm, vbfloat16mf2x8_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg8e16_v_bf16mf2x8_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlsseg8e16_v_bf16m1x8_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vlsseg8.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16m1x8_t test_vlsseg8e16_v_bf16m1x8_mu(vbool16_t vm, vbfloat16m1x8_t vd, const __bf16 *rs1, ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg8e16_v_bf16m1x8_mu(vm, vd, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vluxei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vluxei16.c new file mode 100644 index 0000000000000000000000000000000000000000..490f594671e5e6a0e510a9b720e4cef824a61660 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vluxei16.c @@ -0,0 +1,249 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16mf4_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.nxv1bf16.nxv1i16.i64( [[VD]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vluxei16_v_bf16mf4_tu(vbfloat16mf4_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxei16_v_bf16mf4_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16mf2_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.nxv2bf16.nxv2i16.i64( [[VD]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vluxei16_v_bf16mf2_tu(vbfloat16mf2_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxei16_v_bf16mf2_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16m1_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.nxv4bf16.nxv4i16.i64( [[VD]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vluxei16_v_bf16m1_tu(vbfloat16m1_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vluxei16_v_bf16m1_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16m2_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.nxv8bf16.nxv8i16.i64( [[VD]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vluxei16_v_bf16m2_tu(vbfloat16m2_t vd, const __bf16 *rs1, vuint16m2_t rs2, size_t vl) { + return __riscv_vluxei16_v_bf16m2_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16m4_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.nxv16bf16.nxv16i16.i64( [[VD]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vluxei16_v_bf16m4_tu(vbfloat16m4_t vd, const __bf16 *rs1, vuint16m4_t rs2, size_t vl) { + return __riscv_vluxei16_v_bf16m4_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16m8_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.nxv32bf16.nxv32i16.i64( [[VD]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vluxei16_v_bf16m8_tu(vbfloat16m8_t vd, const __bf16 *rs1, vuint16m8_t rs2, size_t vl) { + return __riscv_vluxei16_v_bf16m8_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16mf4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.mask.nxv1bf16.nxv1i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vluxei16_v_bf16mf4_tum(vbool64_t vm, vbfloat16mf4_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxei16_v_bf16mf4_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16mf2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.mask.nxv2bf16.nxv2i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vluxei16_v_bf16mf2_tum(vbool32_t vm, vbfloat16mf2_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxei16_v_bf16mf2_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16m1_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.mask.nxv4bf16.nxv4i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vluxei16_v_bf16m1_tum(vbool16_t vm, vbfloat16m1_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vluxei16_v_bf16m1_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16m2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.mask.nxv8bf16.nxv8i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vluxei16_v_bf16m2_tum(vbool8_t vm, vbfloat16m2_t vd, const __bf16 *rs1, vuint16m2_t rs2, size_t vl) { + return __riscv_vluxei16_v_bf16m2_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16m4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.mask.nxv16bf16.nxv16i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vluxei16_v_bf16m4_tum(vbool4_t vm, vbfloat16m4_t vd, const __bf16 *rs1, vuint16m4_t rs2, size_t vl) { + return __riscv_vluxei16_v_bf16m4_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16m8_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.mask.nxv32bf16.nxv32i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vluxei16_v_bf16m8_tum(vbool2_t vm, vbfloat16m8_t vd, const __bf16 *rs1, vuint16m8_t rs2, size_t vl) { + return __riscv_vluxei16_v_bf16m8_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16mf4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.mask.nxv1bf16.nxv1i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vluxei16_v_bf16mf4_tumu(vbool64_t vm, vbfloat16mf4_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxei16_v_bf16mf4_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16mf2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.mask.nxv2bf16.nxv2i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vluxei16_v_bf16mf2_tumu(vbool32_t vm, vbfloat16mf2_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxei16_v_bf16mf2_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16m1_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.mask.nxv4bf16.nxv4i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vluxei16_v_bf16m1_tumu(vbool16_t vm, vbfloat16m1_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vluxei16_v_bf16m1_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16m2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.mask.nxv8bf16.nxv8i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vluxei16_v_bf16m2_tumu(vbool8_t vm, vbfloat16m2_t vd, const __bf16 *rs1, vuint16m2_t rs2, size_t vl) { + return __riscv_vluxei16_v_bf16m2_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16m4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.mask.nxv16bf16.nxv16i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vluxei16_v_bf16m4_tumu(vbool4_t vm, vbfloat16m4_t vd, const __bf16 *rs1, vuint16m4_t rs2, size_t vl) { + return __riscv_vluxei16_v_bf16m4_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16m8_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.mask.nxv32bf16.nxv32i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vluxei16_v_bf16m8_tumu(vbool2_t vm, vbfloat16m8_t vd, const __bf16 *rs1, vuint16m8_t rs2, size_t vl) { + return __riscv_vluxei16_v_bf16m8_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16mf4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.mask.nxv1bf16.nxv1i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vluxei16_v_bf16mf4_mu(vbool64_t vm, vbfloat16mf4_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxei16_v_bf16mf4_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16mf2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.mask.nxv2bf16.nxv2i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vluxei16_v_bf16mf2_mu(vbool32_t vm, vbfloat16mf2_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxei16_v_bf16mf2_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16m1_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.mask.nxv4bf16.nxv4i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vluxei16_v_bf16m1_mu(vbool16_t vm, vbfloat16m1_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vluxei16_v_bf16m1_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16m2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.mask.nxv8bf16.nxv8i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vluxei16_v_bf16m2_mu(vbool8_t vm, vbfloat16m2_t vd, const __bf16 *rs1, vuint16m2_t rs2, size_t vl) { + return __riscv_vluxei16_v_bf16m2_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16m4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.mask.nxv16bf16.nxv16i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vluxei16_v_bf16m4_mu(vbool4_t vm, vbfloat16m4_t vd, const __bf16 *rs1, vuint16m4_t rs2, size_t vl) { + return __riscv_vluxei16_v_bf16m4_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16m8_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.mask.nxv32bf16.nxv32i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vluxei16_v_bf16m8_mu(vbool2_t vm, vbfloat16m8_t vd, const __bf16 *rs1, vuint16m8_t rs2, size_t vl) { + return __riscv_vluxei16_v_bf16m8_mu(vm, vd, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vluxseg2ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vluxseg2ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..c363102b8c2b2f3a9cd3ca7997417ca1fa4c13cf --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vluxseg2ei16.c @@ -0,0 +1,249 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16mf4x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vluxseg2.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf4x2_t test_vluxseg2ei16_v_bf16mf4x2_tu(vbfloat16mf4x2_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg2ei16_v_bf16mf4x2_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16mf2x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vluxseg2.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf2x2_t test_vluxseg2ei16_v_bf16mf2x2_tu(vbfloat16mf2x2_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg2ei16_v_bf16mf2x2_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16m1x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vluxseg2.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m1x2_t test_vluxseg2ei16_v_bf16m1x2_tu(vbfloat16m1x2_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg2ei16_v_bf16m1x2_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16m2x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vluxseg2.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m2x2_t test_vluxseg2ei16_v_bf16m2x2_tu(vbfloat16m2x2_t vd, const __bf16 *rs1, vuint16m2_t rs2, size_t vl) { + return __riscv_vluxseg2ei16_v_bf16m2x2_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16m4x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vluxseg2.nxv16bf16.nxv16i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m4x2_t test_vluxseg2ei16_v_bf16m4x2_tu(vbfloat16m4x2_t vd, const __bf16 *rs1, vuint16m4_t rs2, size_t vl) { + return __riscv_vluxseg2ei16_v_bf16m4x2_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16mf4x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vluxseg2.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf4x2_t test_vluxseg2ei16_v_bf16mf4x2_tum(vbool64_t vm, vbfloat16mf4x2_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg2ei16_v_bf16mf4x2_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16mf2x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vluxseg2.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf2x2_t test_vluxseg2ei16_v_bf16mf2x2_tum(vbool32_t vm, vbfloat16mf2x2_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg2ei16_v_bf16mf2x2_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16m1x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vluxseg2.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m1x2_t test_vluxseg2ei16_v_bf16m1x2_tum(vbool16_t vm, vbfloat16m1x2_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg2ei16_v_bf16m1x2_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16m2x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vluxseg2.mask.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m2x2_t test_vluxseg2ei16_v_bf16m2x2_tum(vbool8_t vm, vbfloat16m2x2_t vd, const __bf16 *rs1, vuint16m2_t rs2, size_t vl) { + return __riscv_vluxseg2ei16_v_bf16m2x2_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16m4x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vluxseg2.mask.nxv16bf16.nxv16i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m4x2_t test_vluxseg2ei16_v_bf16m4x2_tum(vbool4_t vm, vbfloat16m4x2_t vd, const __bf16 *rs1, vuint16m4_t rs2, size_t vl) { + return __riscv_vluxseg2ei16_v_bf16m4x2_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16mf4x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vluxseg2.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf4x2_t test_vluxseg2ei16_v_bf16mf4x2_tumu(vbool64_t vm, vbfloat16mf4x2_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg2ei16_v_bf16mf4x2_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16mf2x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vluxseg2.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf2x2_t test_vluxseg2ei16_v_bf16mf2x2_tumu(vbool32_t vm, vbfloat16mf2x2_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg2ei16_v_bf16mf2x2_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16m1x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vluxseg2.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m1x2_t test_vluxseg2ei16_v_bf16m1x2_tumu(vbool16_t vm, vbfloat16m1x2_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg2ei16_v_bf16m1x2_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16m2x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vluxseg2.mask.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m2x2_t test_vluxseg2ei16_v_bf16m2x2_tumu(vbool8_t vm, vbfloat16m2x2_t vd, const __bf16 *rs1, vuint16m2_t rs2, size_t vl) { + return __riscv_vluxseg2ei16_v_bf16m2x2_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16m4x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vluxseg2.mask.nxv16bf16.nxv16i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m4x2_t test_vluxseg2ei16_v_bf16m4x2_tumu(vbool4_t vm, vbfloat16m4x2_t vd, const __bf16 *rs1, vuint16m4_t rs2, size_t vl) { + return __riscv_vluxseg2ei16_v_bf16m4x2_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16mf4x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vluxseg2.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf4x2_t test_vluxseg2ei16_v_bf16mf4x2_mu(vbool64_t vm, vbfloat16mf4x2_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg2ei16_v_bf16mf4x2_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16mf2x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vluxseg2.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf2x2_t test_vluxseg2ei16_v_bf16mf2x2_mu(vbool32_t vm, vbfloat16mf2x2_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg2ei16_v_bf16mf2x2_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16m1x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vluxseg2.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m1x2_t test_vluxseg2ei16_v_bf16m1x2_mu(vbool16_t vm, vbfloat16m1x2_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg2ei16_v_bf16m1x2_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16m2x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vluxseg2.mask.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m2x2_t test_vluxseg2ei16_v_bf16m2x2_mu(vbool8_t vm, vbfloat16m2x2_t vd, const __bf16 *rs1, vuint16m2_t rs2, size_t vl) { + return __riscv_vluxseg2ei16_v_bf16m2x2_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16m4x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vluxseg2.mask.nxv16bf16.nxv16i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m4x2_t test_vluxseg2ei16_v_bf16m4x2_mu(vbool4_t vm, vbfloat16m4x2_t vd, const __bf16 *rs1, vuint16m4_t rs2, size_t vl) { + return __riscv_vluxseg2ei16_v_bf16m4x2_mu(vm, vd, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vluxseg3ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vluxseg3ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..b93fd2b5afd487e79fc7b77c420dab2d91b47fda --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vluxseg3ei16.c @@ -0,0 +1,217 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vluxseg3ei16_v_bf16mf4x3_tu( +// CHECK-RV64-SAME: { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vluxseg3.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf4x3_t test_vluxseg3ei16_v_bf16mf4x3_tu(vbfloat16mf4x3_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg3ei16_v_bf16mf4x3_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vluxseg3ei16_v_bf16mf2x3_tu( +// CHECK-RV64-SAME: { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vluxseg3.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf2x3_t test_vluxseg3ei16_v_bf16mf2x3_tu(vbfloat16mf2x3_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg3ei16_v_bf16mf2x3_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vluxseg3ei16_v_bf16m1x3_tu( +// CHECK-RV64-SAME: { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vluxseg3.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m1x3_t test_vluxseg3ei16_v_bf16m1x3_tu(vbfloat16m1x3_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg3ei16_v_bf16m1x3_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vluxseg3ei16_v_bf16m2x3_tu( +// CHECK-RV64-SAME: { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vluxseg3.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m2x3_t test_vluxseg3ei16_v_bf16m2x3_tu(vbfloat16m2x3_t vd, const __bf16 *rs1, vuint16m2_t rs2, size_t vl) { + return __riscv_vluxseg3ei16_v_bf16m2x3_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vluxseg3ei16_v_bf16mf4x3_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vluxseg3.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf4x3_t test_vluxseg3ei16_v_bf16mf4x3_tum(vbool64_t vm, vbfloat16mf4x3_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg3ei16_v_bf16mf4x3_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vluxseg3ei16_v_bf16mf2x3_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vluxseg3.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf2x3_t test_vluxseg3ei16_v_bf16mf2x3_tum(vbool32_t vm, vbfloat16mf2x3_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg3ei16_v_bf16mf2x3_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vluxseg3ei16_v_bf16m1x3_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vluxseg3.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m1x3_t test_vluxseg3ei16_v_bf16m1x3_tum(vbool16_t vm, vbfloat16m1x3_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg3ei16_v_bf16m1x3_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vluxseg3ei16_v_bf16m2x3_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vluxseg3.mask.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m2x3_t test_vluxseg3ei16_v_bf16m2x3_tum(vbool8_t vm, vbfloat16m2x3_t vd, const __bf16 *rs1, vuint16m2_t rs2, size_t vl) { + return __riscv_vluxseg3ei16_v_bf16m2x3_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vluxseg3ei16_v_bf16mf4x3_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vluxseg3.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf4x3_t test_vluxseg3ei16_v_bf16mf4x3_tumu(vbool64_t vm, vbfloat16mf4x3_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg3ei16_v_bf16mf4x3_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vluxseg3ei16_v_bf16mf2x3_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vluxseg3.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf2x3_t test_vluxseg3ei16_v_bf16mf2x3_tumu(vbool32_t vm, vbfloat16mf2x3_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg3ei16_v_bf16mf2x3_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vluxseg3ei16_v_bf16m1x3_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vluxseg3.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m1x3_t test_vluxseg3ei16_v_bf16m1x3_tumu(vbool16_t vm, vbfloat16m1x3_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg3ei16_v_bf16m1x3_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vluxseg3ei16_v_bf16m2x3_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vluxseg3.mask.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m2x3_t test_vluxseg3ei16_v_bf16m2x3_tumu(vbool8_t vm, vbfloat16m2x3_t vd, const __bf16 *rs1, vuint16m2_t rs2, size_t vl) { + return __riscv_vluxseg3ei16_v_bf16m2x3_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vluxseg3ei16_v_bf16mf4x3_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vluxseg3.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf4x3_t test_vluxseg3ei16_v_bf16mf4x3_mu(vbool64_t vm, vbfloat16mf4x3_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg3ei16_v_bf16mf4x3_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vluxseg3ei16_v_bf16mf2x3_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vluxseg3.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf2x3_t test_vluxseg3ei16_v_bf16mf2x3_mu(vbool32_t vm, vbfloat16mf2x3_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg3ei16_v_bf16mf2x3_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vluxseg3ei16_v_bf16m1x3_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vluxseg3.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m1x3_t test_vluxseg3ei16_v_bf16m1x3_mu(vbool16_t vm, vbfloat16m1x3_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg3ei16_v_bf16m1x3_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vluxseg3ei16_v_bf16m2x3_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vluxseg3.mask.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m2x3_t test_vluxseg3ei16_v_bf16m2x3_mu(vbool8_t vm, vbfloat16m2x3_t vd, const __bf16 *rs1, vuint16m2_t rs2, size_t vl) { + return __riscv_vluxseg3ei16_v_bf16m2x3_mu(vm, vd, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vluxseg4ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vluxseg4ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..ba48a9e1d5f5820ffd9b074ba40dacba306b4479 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vluxseg4ei16.c @@ -0,0 +1,233 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vluxseg4ei16_v_bf16mf4x4_tu( +// CHECK-RV64-SAME: { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vluxseg4.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf4x4_t test_vluxseg4ei16_v_bf16mf4x4_tu(vbfloat16mf4x4_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg4ei16_v_bf16mf4x4_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vluxseg4ei16_v_bf16mf2x4_tu( +// CHECK-RV64-SAME: { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vluxseg4.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf2x4_t test_vluxseg4ei16_v_bf16mf2x4_tu(vbfloat16mf2x4_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg4ei16_v_bf16mf2x4_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vluxseg4ei16_v_bf16m1x4_tu( +// CHECK-RV64-SAME: { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vluxseg4.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m1x4_t test_vluxseg4ei16_v_bf16m1x4_tu(vbfloat16m1x4_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg4ei16_v_bf16m1x4_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vluxseg4ei16_v_bf16m2x4_tu( +// CHECK-RV64-SAME: { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vluxseg4.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m2x4_t test_vluxseg4ei16_v_bf16m2x4_tu(vbfloat16m2x4_t vd, const __bf16 *rs1, vuint16m2_t rs2, size_t vl) { + return __riscv_vluxseg4ei16_v_bf16m2x4_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vluxseg4ei16_v_bf16mf4x4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vluxseg4.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf4x4_t test_vluxseg4ei16_v_bf16mf4x4_tum(vbool64_t vm, vbfloat16mf4x4_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg4ei16_v_bf16mf4x4_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vluxseg4ei16_v_bf16mf2x4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vluxseg4.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf2x4_t test_vluxseg4ei16_v_bf16mf2x4_tum(vbool32_t vm, vbfloat16mf2x4_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg4ei16_v_bf16mf2x4_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vluxseg4ei16_v_bf16m1x4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vluxseg4.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m1x4_t test_vluxseg4ei16_v_bf16m1x4_tum(vbool16_t vm, vbfloat16m1x4_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg4ei16_v_bf16m1x4_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vluxseg4ei16_v_bf16m2x4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vluxseg4.mask.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m2x4_t test_vluxseg4ei16_v_bf16m2x4_tum(vbool8_t vm, vbfloat16m2x4_t vd, const __bf16 *rs1, vuint16m2_t rs2, size_t vl) { + return __riscv_vluxseg4ei16_v_bf16m2x4_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vluxseg4ei16_v_bf16mf4x4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vluxseg4.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf4x4_t test_vluxseg4ei16_v_bf16mf4x4_tumu(vbool64_t vm, vbfloat16mf4x4_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg4ei16_v_bf16mf4x4_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vluxseg4ei16_v_bf16mf2x4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vluxseg4.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf2x4_t test_vluxseg4ei16_v_bf16mf2x4_tumu(vbool32_t vm, vbfloat16mf2x4_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg4ei16_v_bf16mf2x4_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vluxseg4ei16_v_bf16m1x4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vluxseg4.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m1x4_t test_vluxseg4ei16_v_bf16m1x4_tumu(vbool16_t vm, vbfloat16m1x4_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg4ei16_v_bf16m1x4_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vluxseg4ei16_v_bf16m2x4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vluxseg4.mask.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m2x4_t test_vluxseg4ei16_v_bf16m2x4_tumu(vbool8_t vm, vbfloat16m2x4_t vd, const __bf16 *rs1, vuint16m2_t rs2, size_t vl) { + return __riscv_vluxseg4ei16_v_bf16m2x4_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vluxseg4ei16_v_bf16mf4x4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vluxseg4.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf4x4_t test_vluxseg4ei16_v_bf16mf4x4_mu(vbool64_t vm, vbfloat16mf4x4_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg4ei16_v_bf16mf4x4_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vluxseg4ei16_v_bf16mf2x4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vluxseg4.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf2x4_t test_vluxseg4ei16_v_bf16mf2x4_mu(vbool32_t vm, vbfloat16mf2x4_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg4ei16_v_bf16mf2x4_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vluxseg4ei16_v_bf16m1x4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vluxseg4.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m1x4_t test_vluxseg4ei16_v_bf16m1x4_mu(vbool16_t vm, vbfloat16m1x4_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg4ei16_v_bf16m1x4_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vluxseg4ei16_v_bf16m2x4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vluxseg4.mask.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m2x4_t test_vluxseg4ei16_v_bf16m2x4_mu(vbool8_t vm, vbfloat16m2x4_t vd, const __bf16 *rs1, vuint16m2_t rs2, size_t vl) { + return __riscv_vluxseg4ei16_v_bf16m2x4_mu(vm, vd, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vluxseg5ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vluxseg5ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..9e8443b135a63542fd9855ccca13d9293df42609 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vluxseg5ei16.c @@ -0,0 +1,189 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vluxseg5ei16_v_bf16mf4x5_tu( +// CHECK-RV64-SAME: { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vluxseg5.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf4x5_t test_vluxseg5ei16_v_bf16mf4x5_tu(vbfloat16mf4x5_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg5ei16_v_bf16mf4x5_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vluxseg5ei16_v_bf16mf2x5_tu( +// CHECK-RV64-SAME: { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vluxseg5.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf2x5_t test_vluxseg5ei16_v_bf16mf2x5_tu(vbfloat16mf2x5_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg5ei16_v_bf16mf2x5_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vluxseg5ei16_v_bf16m1x5_tu( +// CHECK-RV64-SAME: { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vluxseg5.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16m1x5_t test_vluxseg5ei16_v_bf16m1x5_tu(vbfloat16m1x5_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg5ei16_v_bf16m1x5_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vluxseg5ei16_v_bf16mf4x5_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vluxseg5.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf4x5_t test_vluxseg5ei16_v_bf16mf4x5_tum(vbool64_t vm, vbfloat16mf4x5_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg5ei16_v_bf16mf4x5_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vluxseg5ei16_v_bf16mf2x5_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vluxseg5.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf2x5_t test_vluxseg5ei16_v_bf16mf2x5_tum(vbool32_t vm, vbfloat16mf2x5_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg5ei16_v_bf16mf2x5_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vluxseg5ei16_v_bf16m1x5_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vluxseg5.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16m1x5_t test_vluxseg5ei16_v_bf16m1x5_tum(vbool16_t vm, vbfloat16m1x5_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg5ei16_v_bf16m1x5_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vluxseg5ei16_v_bf16mf4x5_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vluxseg5.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf4x5_t test_vluxseg5ei16_v_bf16mf4x5_tumu(vbool64_t vm, vbfloat16mf4x5_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg5ei16_v_bf16mf4x5_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vluxseg5ei16_v_bf16mf2x5_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vluxseg5.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf2x5_t test_vluxseg5ei16_v_bf16mf2x5_tumu(vbool32_t vm, vbfloat16mf2x5_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg5ei16_v_bf16mf2x5_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vluxseg5ei16_v_bf16m1x5_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vluxseg5.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16m1x5_t test_vluxseg5ei16_v_bf16m1x5_tumu(vbool16_t vm, vbfloat16m1x5_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg5ei16_v_bf16m1x5_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vluxseg5ei16_v_bf16mf4x5_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vluxseg5.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf4x5_t test_vluxseg5ei16_v_bf16mf4x5_mu(vbool64_t vm, vbfloat16mf4x5_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg5ei16_v_bf16mf4x5_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vluxseg5ei16_v_bf16mf2x5_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vluxseg5.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf2x5_t test_vluxseg5ei16_v_bf16mf2x5_mu(vbool32_t vm, vbfloat16mf2x5_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg5ei16_v_bf16mf2x5_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vluxseg5ei16_v_bf16m1x5_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vluxseg5.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16m1x5_t test_vluxseg5ei16_v_bf16m1x5_mu(vbool16_t vm, vbfloat16m1x5_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg5ei16_v_bf16m1x5_mu(vm, vd, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vluxseg6ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vluxseg6ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..635baa5378ba7f26d068a56f75649ba4b7d6dcdf --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vluxseg6ei16.c @@ -0,0 +1,201 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vluxseg6ei16_v_bf16mf4x6_tu( +// CHECK-RV64-SAME: { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vluxseg6.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf4x6_t test_vluxseg6ei16_v_bf16mf4x6_tu(vbfloat16mf4x6_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg6ei16_v_bf16mf4x6_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vluxseg6ei16_v_bf16mf2x6_tu( +// CHECK-RV64-SAME: { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vluxseg6.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf2x6_t test_vluxseg6ei16_v_bf16mf2x6_tu(vbfloat16mf2x6_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg6ei16_v_bf16mf2x6_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vluxseg6ei16_v_bf16m1x6_tu( +// CHECK-RV64-SAME: { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vluxseg6.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16m1x6_t test_vluxseg6ei16_v_bf16m1x6_tu(vbfloat16m1x6_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg6ei16_v_bf16m1x6_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vluxseg6ei16_v_bf16mf4x6_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vluxseg6.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf4x6_t test_vluxseg6ei16_v_bf16mf4x6_tum(vbool64_t vm, vbfloat16mf4x6_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg6ei16_v_bf16mf4x6_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vluxseg6ei16_v_bf16mf2x6_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vluxseg6.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf2x6_t test_vluxseg6ei16_v_bf16mf2x6_tum(vbool32_t vm, vbfloat16mf2x6_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg6ei16_v_bf16mf2x6_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vluxseg6ei16_v_bf16m1x6_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vluxseg6.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16m1x6_t test_vluxseg6ei16_v_bf16m1x6_tum(vbool16_t vm, vbfloat16m1x6_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg6ei16_v_bf16m1x6_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vluxseg6ei16_v_bf16mf4x6_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vluxseg6.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf4x6_t test_vluxseg6ei16_v_bf16mf4x6_tumu(vbool64_t vm, vbfloat16mf4x6_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg6ei16_v_bf16mf4x6_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vluxseg6ei16_v_bf16mf2x6_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vluxseg6.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf2x6_t test_vluxseg6ei16_v_bf16mf2x6_tumu(vbool32_t vm, vbfloat16mf2x6_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg6ei16_v_bf16mf2x6_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vluxseg6ei16_v_bf16m1x6_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vluxseg6.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16m1x6_t test_vluxseg6ei16_v_bf16m1x6_tumu(vbool16_t vm, vbfloat16m1x6_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg6ei16_v_bf16m1x6_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vluxseg6ei16_v_bf16mf4x6_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vluxseg6.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf4x6_t test_vluxseg6ei16_v_bf16mf4x6_mu(vbool64_t vm, vbfloat16mf4x6_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg6ei16_v_bf16mf4x6_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vluxseg6ei16_v_bf16mf2x6_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vluxseg6.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf2x6_t test_vluxseg6ei16_v_bf16mf2x6_mu(vbool32_t vm, vbfloat16mf2x6_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg6ei16_v_bf16mf2x6_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vluxseg6ei16_v_bf16m1x6_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vluxseg6.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16m1x6_t test_vluxseg6ei16_v_bf16m1x6_mu(vbool16_t vm, vbfloat16m1x6_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg6ei16_v_bf16m1x6_mu(vm, vd, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vluxseg7ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vluxseg7ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..69045bc79853d65ac5dde187f181a24b18776e60 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vluxseg7ei16.c @@ -0,0 +1,213 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vluxseg7ei16_v_bf16mf4x7_tu( +// CHECK-RV64-SAME: { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vluxseg7.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf4x7_t test_vluxseg7ei16_v_bf16mf4x7_tu(vbfloat16mf4x7_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg7ei16_v_bf16mf4x7_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vluxseg7ei16_v_bf16mf2x7_tu( +// CHECK-RV64-SAME: { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vluxseg7.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf2x7_t test_vluxseg7ei16_v_bf16mf2x7_tu(vbfloat16mf2x7_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg7ei16_v_bf16mf2x7_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vluxseg7ei16_v_bf16m1x7_tu( +// CHECK-RV64-SAME: { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vluxseg7.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16m1x7_t test_vluxseg7ei16_v_bf16m1x7_tu(vbfloat16m1x7_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg7ei16_v_bf16m1x7_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vluxseg7ei16_v_bf16mf4x7_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vluxseg7.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf4x7_t test_vluxseg7ei16_v_bf16mf4x7_tum(vbool64_t vm, vbfloat16mf4x7_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg7ei16_v_bf16mf4x7_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vluxseg7ei16_v_bf16mf2x7_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vluxseg7.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf2x7_t test_vluxseg7ei16_v_bf16mf2x7_tum(vbool32_t vm, vbfloat16mf2x7_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg7ei16_v_bf16mf2x7_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vluxseg7ei16_v_bf16m1x7_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vluxseg7.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16m1x7_t test_vluxseg7ei16_v_bf16m1x7_tum(vbool16_t vm, vbfloat16m1x7_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg7ei16_v_bf16m1x7_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vluxseg7ei16_v_bf16mf4x7_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vluxseg7.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf4x7_t test_vluxseg7ei16_v_bf16mf4x7_tumu(vbool64_t vm, vbfloat16mf4x7_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg7ei16_v_bf16mf4x7_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vluxseg7ei16_v_bf16mf2x7_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vluxseg7.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf2x7_t test_vluxseg7ei16_v_bf16mf2x7_tumu(vbool32_t vm, vbfloat16mf2x7_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg7ei16_v_bf16mf2x7_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vluxseg7ei16_v_bf16m1x7_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vluxseg7.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16m1x7_t test_vluxseg7ei16_v_bf16m1x7_tumu(vbool16_t vm, vbfloat16m1x7_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg7ei16_v_bf16m1x7_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vluxseg7ei16_v_bf16mf4x7_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vluxseg7.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf4x7_t test_vluxseg7ei16_v_bf16mf4x7_mu(vbool64_t vm, vbfloat16mf4x7_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg7ei16_v_bf16mf4x7_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vluxseg7ei16_v_bf16mf2x7_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vluxseg7.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf2x7_t test_vluxseg7ei16_v_bf16mf2x7_mu(vbool32_t vm, vbfloat16mf2x7_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg7ei16_v_bf16mf2x7_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vluxseg7ei16_v_bf16m1x7_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vluxseg7.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16m1x7_t test_vluxseg7ei16_v_bf16m1x7_mu(vbool16_t vm, vbfloat16m1x7_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg7ei16_v_bf16m1x7_mu(vm, vd, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vluxseg8ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vluxseg8ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..17cb9dd26a75558d7e9a1bc73e02bac8bf24043f --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/bfloat16/vluxseg8ei16.c @@ -0,0 +1,225 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vluxseg8ei16_v_bf16mf4x8_tu( +// CHECK-RV64-SAME: { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vluxseg8.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf4x8_t test_vluxseg8ei16_v_bf16mf4x8_tu(vbfloat16mf4x8_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg8ei16_v_bf16mf4x8_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vluxseg8ei16_v_bf16mf2x8_tu( +// CHECK-RV64-SAME: { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vluxseg8.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf2x8_t test_vluxseg8ei16_v_bf16mf2x8_tu(vbfloat16mf2x8_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg8ei16_v_bf16mf2x8_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vluxseg8ei16_v_bf16m1x8_tu( +// CHECK-RV64-SAME: { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vluxseg8.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16m1x8_t test_vluxseg8ei16_v_bf16m1x8_tu(vbfloat16m1x8_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg8ei16_v_bf16m1x8_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vluxseg8ei16_v_bf16mf4x8_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vluxseg8.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf4x8_t test_vluxseg8ei16_v_bf16mf4x8_tum(vbool64_t vm, vbfloat16mf4x8_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg8ei16_v_bf16mf4x8_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vluxseg8ei16_v_bf16mf2x8_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vluxseg8.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf2x8_t test_vluxseg8ei16_v_bf16mf2x8_tum(vbool32_t vm, vbfloat16mf2x8_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg8ei16_v_bf16mf2x8_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vluxseg8ei16_v_bf16m1x8_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vluxseg8.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16m1x8_t test_vluxseg8ei16_v_bf16m1x8_tum(vbool16_t vm, vbfloat16m1x8_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg8ei16_v_bf16m1x8_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vluxseg8ei16_v_bf16mf4x8_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vluxseg8.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf4x8_t test_vluxseg8ei16_v_bf16mf4x8_tumu(vbool64_t vm, vbfloat16mf4x8_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg8ei16_v_bf16mf4x8_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vluxseg8ei16_v_bf16mf2x8_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vluxseg8.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf2x8_t test_vluxseg8ei16_v_bf16mf2x8_tumu(vbool32_t vm, vbfloat16mf2x8_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg8ei16_v_bf16mf2x8_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vluxseg8ei16_v_bf16m1x8_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vluxseg8.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16m1x8_t test_vluxseg8ei16_v_bf16m1x8_tumu(vbool16_t vm, vbfloat16m1x8_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg8ei16_v_bf16m1x8_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vluxseg8ei16_v_bf16mf4x8_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vluxseg8.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf4x8_t test_vluxseg8ei16_v_bf16mf4x8_mu(vbool64_t vm, vbfloat16mf4x8_t vd, const __bf16 *rs1, vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg8ei16_v_bf16mf4x8_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vluxseg8ei16_v_bf16mf2x8_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vluxseg8.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf2x8_t test_vluxseg8ei16_v_bf16mf2x8_mu(vbool32_t vm, vbfloat16mf2x8_t vd, const __bf16 *rs1, vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg8ei16_v_bf16mf2x8_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vluxseg8ei16_v_bf16m1x8_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vluxseg8.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16m1x8_t test_vluxseg8ei16_v_bf16m1x8_mu(vbool16_t vm, vbfloat16m1x8_t vd, const __bf16 *rs1, vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg8ei16_v_bf16m1x8_mu(vm, vd, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/vaesdf.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/vaesdf.c index 8c18e323f7ceca225f58a82e504c64bd327c3675..27457c8f3af9b9643c54e616b67d14bf8112dc11 100644 --- a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/vaesdf.c +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/vaesdf.c @@ -206,13 +206,3 @@ vuint32m8_t test_vaesdf_vv_u32m8_tu(vuint32m8_t vd, vuint32m8_t vs2, size_t vl) return __riscv_vaesdf_vv_u32m8_tu(vd, vs2, vl); } -// CHECK-RV64-LABEL: define dso_local @test_vaesdf_vs_u32m8_u32m8_tu -// CHECK-RV64-SAME: ( [[VD:%.*]], [[VS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { -// CHECK-RV64-NEXT: entry: -// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vaesdf.vs.nxv16i32.nxv16i32.i64( [[VD]], [[VS2]], i64 [[VL]], i64 2) -// CHECK-RV64-NEXT: ret [[TMP0]] -// -vuint32m8_t test_vaesdf_vs_u32m8_u32m8_tu(vuint32m8_t vd, vuint32m8_t vs2, size_t vl) { - return __riscv_vaesdf_vs_u32m8_u32m8_tu(vd, vs2, vl); -} - diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/vaesdm.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/vaesdm.c index 7566be80e9d93df4098541d3187a954ce8eb5e89..e23194eac3dcbb3b430b6c858e550c88bb008811 100644 --- a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/vaesdm.c +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/vaesdm.c @@ -206,13 +206,3 @@ vuint32m8_t test_vaesdm_vv_u32m8_tu(vuint32m8_t vd, vuint32m8_t vs2, size_t vl) return __riscv_vaesdm_vv_u32m8_tu(vd, vs2, vl); } -// CHECK-RV64-LABEL: define dso_local @test_vaesdm_vs_u32m8_u32m8_tu -// CHECK-RV64-SAME: ( [[VD:%.*]], [[VS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { -// CHECK-RV64-NEXT: entry: -// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vaesdm.vs.nxv16i32.nxv16i32.i64( [[VD]], [[VS2]], i64 [[VL]], i64 2) -// CHECK-RV64-NEXT: ret [[TMP0]] -// -vuint32m8_t test_vaesdm_vs_u32m8_u32m8_tu(vuint32m8_t vd, vuint32m8_t vs2, size_t vl) { - return __riscv_vaesdm_vs_u32m8_u32m8_tu(vd, vs2, vl); -} - diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/vaesef.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/vaesef.c index ddeed6e78be1327e746e1229fd51d782cb097a5e..4e99777b57fbcf93acec1ee568bc11184f4a8e7f 100644 --- a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/vaesef.c +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/vaesef.c @@ -206,13 +206,3 @@ vuint32m8_t test_vaesef_vv_u32m8_tu(vuint32m8_t vd, vuint32m8_t vs2, size_t vl) return __riscv_vaesef_vv_u32m8_tu(vd, vs2, vl); } -// CHECK-RV64-LABEL: define dso_local @test_vaesef_vs_u32m8_u32m8_tu -// CHECK-RV64-SAME: ( [[VD:%.*]], [[VS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { -// CHECK-RV64-NEXT: entry: -// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vaesef.vs.nxv16i32.nxv16i32.i64( [[VD]], [[VS2]], i64 [[VL]], i64 2) -// CHECK-RV64-NEXT: ret [[TMP0]] -// -vuint32m8_t test_vaesef_vs_u32m8_u32m8_tu(vuint32m8_t vd, vuint32m8_t vs2, size_t vl) { - return __riscv_vaesef_vs_u32m8_u32m8_tu(vd, vs2, vl); -} - diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/vaesem.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/vaesem.c index 2bd6350798f64348d0a1c96d409643602287a54d..7488792effd4297fbc6a8c8675b91ac604aa99a6 100644 --- a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/vaesem.c +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/vaesem.c @@ -206,13 +206,3 @@ vuint32m8_t test_vaesem_vv_u32m8_tu(vuint32m8_t vd, vuint32m8_t vs2, size_t vl) return __riscv_vaesem_vv_u32m8_tu(vd, vs2, vl); } -// CHECK-RV64-LABEL: define dso_local @test_vaesem_vs_u32m8_u32m8_tu -// CHECK-RV64-SAME: ( [[VD:%.*]], [[VS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { -// CHECK-RV64-NEXT: entry: -// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vaesem.vs.nxv16i32.nxv16i32.i64( [[VD]], [[VS2]], i64 [[VL]], i64 2) -// CHECK-RV64-NEXT: ret [[TMP0]] -// -vuint32m8_t test_vaesem_vs_u32m8_u32m8_tu(vuint32m8_t vd, vuint32m8_t vs2, size_t vl) { - return __riscv_vaesem_vs_u32m8_u32m8_tu(vd, vs2, vl); -} - diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/vaesz.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/vaesz.c index 101efd751f86e3f6310854536f38026fa903892a..08291a2cbca6be16f2265c970560c09967b03ef2 100644 --- a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/vaesz.c +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/vaesz.c @@ -156,13 +156,3 @@ vuint32m8_t test_vaesz_vs_u32m4_u32m8_tu(vuint32m8_t vd, vuint32m4_t vs2, size_t return __riscv_vaesz_vs_u32m4_u32m8_tu(vd, vs2, vl); } -// CHECK-RV64-LABEL: define dso_local @test_vaesz_vs_u32m8_u32m8_tu -// CHECK-RV64-SAME: ( [[VD:%.*]], [[VS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { -// CHECK-RV64-NEXT: entry: -// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vaesz.vs.nxv16i32.nxv16i32.i64( [[VD]], [[VS2]], i64 [[VL]], i64 2) -// CHECK-RV64-NEXT: ret [[TMP0]] -// -vuint32m8_t test_vaesz_vs_u32m8_u32m8_tu(vuint32m8_t vd, vuint32m8_t vs2, size_t vl) { - return __riscv_vaesz_vs_u32m8_u32m8_tu(vd, vs2, vl); -} - diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/vsm4r.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/vsm4r.c index c58f8d22d4601de639e882ca476b13d52cbf29a8..11faf7f36d23ef971d622b5e0efcd52a5908397c 100644 --- a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/vsm4r.c +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/non-overloaded/vsm4r.c @@ -206,13 +206,3 @@ vuint32m8_t test_vsm4r_vv_u32m8_tu(vuint32m8_t vd, vuint32m8_t vs2, size_t vl) { return __riscv_vsm4r_vv_u32m8_tu(vd, vs2, vl); } -// CHECK-RV64-LABEL: define dso_local @test_vsm4r_vs_u32m8_u32m8_tu -// CHECK-RV64-SAME: ( [[VD:%.*]], [[VS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { -// CHECK-RV64-NEXT: entry: -// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vsm4r.vs.nxv16i32.nxv16i32.i64( [[VD]], [[VS2]], i64 [[VL]], i64 2) -// CHECK-RV64-NEXT: ret [[TMP0]] -// -vuint32m8_t test_vsm4r_vs_u32m8_u32m8_tu(vuint32m8_t vd, vuint32m8_t vs2, size_t vl) { - return __riscv_vsm4r_vs_u32m8_u32m8_tu(vd, vs2, vl); -} - diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vle16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vle16.c new file mode 100644 index 0000000000000000000000000000000000000000..bc7996306cc3be3803778dc46b4e0f21991b1134 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vle16.c @@ -0,0 +1,273 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16mf4_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.nxv1bf16.i64( [[VD]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vle16_v_bf16mf4_tu(vbfloat16mf4_t vd, const __bf16 *rs1, + size_t vl) { + return __riscv_vle16_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16mf2_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.nxv2bf16.i64( [[VD]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vle16_v_bf16mf2_tu(vbfloat16mf2_t vd, const __bf16 *rs1, + size_t vl) { + return __riscv_vle16_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16m1_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.nxv4bf16.i64( [[VD]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vle16_v_bf16m1_tu(vbfloat16m1_t vd, const __bf16 *rs1, + size_t vl) { + return __riscv_vle16_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16m2_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.nxv8bf16.i64( [[VD]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vle16_v_bf16m2_tu(vbfloat16m2_t vd, const __bf16 *rs1, + size_t vl) { + return __riscv_vle16_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16m4_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.nxv16bf16.i64( [[VD]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vle16_v_bf16m4_tu(vbfloat16m4_t vd, const __bf16 *rs1, + size_t vl) { + return __riscv_vle16_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16m8_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.nxv32bf16.i64( [[VD]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vle16_v_bf16m8_tu(vbfloat16m8_t vd, const __bf16 *rs1, + size_t vl) { + return __riscv_vle16_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16mf4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.mask.nxv1bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vle16_v_bf16mf4_tum(vbool64_t vm, vbfloat16mf4_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vle16_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16mf2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.mask.nxv2bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vle16_v_bf16mf2_tum(vbool32_t vm, vbfloat16mf2_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vle16_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16m1_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.mask.nxv4bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vle16_v_bf16m1_tum(vbool16_t vm, vbfloat16m1_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vle16_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16m2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.mask.nxv8bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vle16_v_bf16m2_tum(vbool8_t vm, vbfloat16m2_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vle16_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16m4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.mask.nxv16bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vle16_v_bf16m4_tum(vbool4_t vm, vbfloat16m4_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vle16_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16m8_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.mask.nxv32bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vle16_v_bf16m8_tum(vbool2_t vm, vbfloat16m8_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vle16_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16mf4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.mask.nxv1bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vle16_v_bf16mf4_tumu(vbool64_t vm, vbfloat16mf4_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vle16_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16mf2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.mask.nxv2bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vle16_v_bf16mf2_tumu(vbool32_t vm, vbfloat16mf2_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vle16_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16m1_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.mask.nxv4bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vle16_v_bf16m1_tumu(vbool16_t vm, vbfloat16m1_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vle16_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16m2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.mask.nxv8bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vle16_v_bf16m2_tumu(vbool8_t vm, vbfloat16m2_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vle16_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16m4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.mask.nxv16bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vle16_v_bf16m4_tumu(vbool4_t vm, vbfloat16m4_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vle16_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16m8_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.mask.nxv32bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vle16_v_bf16m8_tumu(vbool2_t vm, vbfloat16m8_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vle16_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16mf4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.mask.nxv1bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vle16_v_bf16mf4_mu(vbool64_t vm, vbfloat16mf4_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vle16_mu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16mf2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.mask.nxv2bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vle16_v_bf16mf2_mu(vbool32_t vm, vbfloat16mf2_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vle16_mu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16m1_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.mask.nxv4bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vle16_v_bf16m1_mu(vbool16_t vm, vbfloat16m1_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vle16_mu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16m2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.mask.nxv8bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vle16_v_bf16m2_mu(vbool8_t vm, vbfloat16m2_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vle16_mu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16m4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.mask.nxv16bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vle16_v_bf16m4_mu(vbool4_t vm, vbfloat16m4_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vle16_mu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16_v_bf16m8_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vle.mask.nxv32bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vle16_v_bf16m8_mu(vbool2_t vm, vbfloat16m8_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vle16_mu(vm, vd, rs1, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vle16ff.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vle16ff.c new file mode 100644 index 0000000000000000000000000000000000000000..75ad618e426284d72a7f16dca17399f9e540ae95 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vle16ff.c @@ -0,0 +1,363 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16mf4_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.nxv1bf16.i64( [[VD]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 2 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16mf4_t test_vle16ff_v_bf16mf4_tu(vbfloat16mf4_t vd, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vle16ff_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16mf2_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.nxv2bf16.i64( [[VD]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 2 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16mf2_t test_vle16ff_v_bf16mf2_tu(vbfloat16mf2_t vd, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vle16ff_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16m1_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.nxv4bf16.i64( [[VD]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 2 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16m1_t test_vle16ff_v_bf16m1_tu(vbfloat16m1_t vd, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vle16ff_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16m2_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.nxv8bf16.i64( [[VD]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 2 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16m2_t test_vle16ff_v_bf16m2_tu(vbfloat16m2_t vd, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vle16ff_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16m4_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.nxv16bf16.i64( [[VD]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 2 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16m4_t test_vle16ff_v_bf16m4_tu(vbfloat16m4_t vd, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vle16ff_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16m8_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.nxv32bf16.i64( [[VD]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 2 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16m8_t test_vle16ff_v_bf16m8_tu(vbfloat16m8_t vd, const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vle16ff_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16mf4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.mask.nxv1bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16mf4_t test_vle16ff_v_bf16mf4_tum(vbool64_t vm, vbfloat16mf4_t vd, + const __bf16 *rs1, size_t *new_vl, + size_t vl) { + return __riscv_vle16ff_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16mf2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.mask.nxv2bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16mf2_t test_vle16ff_v_bf16mf2_tum(vbool32_t vm, vbfloat16mf2_t vd, + const __bf16 *rs1, size_t *new_vl, + size_t vl) { + return __riscv_vle16ff_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16m1_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.mask.nxv4bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16m1_t test_vle16ff_v_bf16m1_tum(vbool16_t vm, vbfloat16m1_t vd, + const __bf16 *rs1, size_t *new_vl, + size_t vl) { + return __riscv_vle16ff_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16m2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.mask.nxv8bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16m2_t test_vle16ff_v_bf16m2_tum(vbool8_t vm, vbfloat16m2_t vd, + const __bf16 *rs1, size_t *new_vl, + size_t vl) { + return __riscv_vle16ff_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16m4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.mask.nxv16bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16m4_t test_vle16ff_v_bf16m4_tum(vbool4_t vm, vbfloat16m4_t vd, + const __bf16 *rs1, size_t *new_vl, + size_t vl) { + return __riscv_vle16ff_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16m8_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.mask.nxv32bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16m8_t test_vle16ff_v_bf16m8_tum(vbool2_t vm, vbfloat16m8_t vd, + const __bf16 *rs1, size_t *new_vl, + size_t vl) { + return __riscv_vle16ff_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16mf4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.mask.nxv1bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16mf4_t test_vle16ff_v_bf16mf4_tumu(vbool64_t vm, vbfloat16mf4_t vd, + const __bf16 *rs1, size_t *new_vl, + size_t vl) { + return __riscv_vle16ff_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16mf2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.mask.nxv2bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16mf2_t test_vle16ff_v_bf16mf2_tumu(vbool32_t vm, vbfloat16mf2_t vd, + const __bf16 *rs1, size_t *new_vl, + size_t vl) { + return __riscv_vle16ff_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16m1_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.mask.nxv4bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16m1_t test_vle16ff_v_bf16m1_tumu(vbool16_t vm, vbfloat16m1_t vd, + const __bf16 *rs1, size_t *new_vl, + size_t vl) { + return __riscv_vle16ff_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16m2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.mask.nxv8bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16m2_t test_vle16ff_v_bf16m2_tumu(vbool8_t vm, vbfloat16m2_t vd, + const __bf16 *rs1, size_t *new_vl, + size_t vl) { + return __riscv_vle16ff_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16m4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.mask.nxv16bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16m4_t test_vle16ff_v_bf16m4_tumu(vbool4_t vm, vbfloat16m4_t vd, + const __bf16 *rs1, size_t *new_vl, + size_t vl) { + return __riscv_vle16ff_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16m8_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.mask.nxv32bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16m8_t test_vle16ff_v_bf16m8_tumu(vbool2_t vm, vbfloat16m8_t vd, + const __bf16 *rs1, size_t *new_vl, + size_t vl) { + return __riscv_vle16ff_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16mf4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.mask.nxv1bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16mf4_t test_vle16ff_v_bf16mf4_mu(vbool64_t vm, vbfloat16mf4_t vd, + const __bf16 *rs1, size_t *new_vl, + size_t vl) { + return __riscv_vle16ff_mu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16mf2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.mask.nxv2bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16mf2_t test_vle16ff_v_bf16mf2_mu(vbool32_t vm, vbfloat16mf2_t vd, + const __bf16 *rs1, size_t *new_vl, + size_t vl) { + return __riscv_vle16ff_mu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16m1_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.mask.nxv4bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16m1_t test_vle16ff_v_bf16m1_mu(vbool16_t vm, vbfloat16m1_t vd, + const __bf16 *rs1, size_t *new_vl, + size_t vl) { + return __riscv_vle16ff_mu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16m2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.mask.nxv8bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16m2_t test_vle16ff_v_bf16m2_mu(vbool8_t vm, vbfloat16m2_t vd, + const __bf16 *rs1, size_t *new_vl, + size_t vl) { + return __riscv_vle16ff_mu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16m4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.mask.nxv16bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16m4_t test_vle16ff_v_bf16m4_mu(vbool4_t vm, vbfloat16m4_t vd, + const __bf16 *rs1, size_t *new_vl, + size_t vl) { + return __riscv_vle16ff_mu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vle16ff_v_bf16m8_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call { , i64 } @llvm.riscv.vleff.mask.nxv32bf16.i64( [[VD]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , i64 } [[TMP0]], 0 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , i64 } [[TMP0]], 1 +// CHECK-RV64-NEXT: store i64 [[TMP2]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret [[TMP1]] +// +vbfloat16m8_t test_vle16ff_v_bf16m8_mu(vbool2_t vm, vbfloat16m8_t vd, + const __bf16 *rs1, size_t *new_vl, + size_t vl) { + return __riscv_vle16ff_mu(vm, vd, rs1, new_vl, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vloxei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vloxei16.c new file mode 100644 index 0000000000000000000000000000000000000000..389031e75c7401fc1c028c0d0d81cec050a66830 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vloxei16.c @@ -0,0 +1,291 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16mf4_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.nxv1bf16.nxv1i16.i64( [[VD]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vloxei16_v_bf16mf4_tu(vbfloat16mf4_t vd, const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16mf2_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.nxv2bf16.nxv2i16.i64( [[VD]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vloxei16_v_bf16mf2_tu(vbfloat16mf2_t vd, const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16m1_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.nxv4bf16.nxv4i16.i64( [[VD]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vloxei16_v_bf16m1_tu(vbfloat16m1_t vd, const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vloxei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16m2_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.nxv8bf16.nxv8i16.i64( [[VD]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vloxei16_v_bf16m2_tu(vbfloat16m2_t vd, const __bf16 *rs1, + vuint16m2_t rs2, size_t vl) { + return __riscv_vloxei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16m4_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.nxv16bf16.nxv16i16.i64( [[VD]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vloxei16_v_bf16m4_tu(vbfloat16m4_t vd, const __bf16 *rs1, + vuint16m4_t rs2, size_t vl) { + return __riscv_vloxei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16m8_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.nxv32bf16.nxv32i16.i64( [[VD]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vloxei16_v_bf16m8_tu(vbfloat16m8_t vd, const __bf16 *rs1, + vuint16m8_t rs2, size_t vl) { + return __riscv_vloxei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16mf4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.mask.nxv1bf16.nxv1i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vloxei16_v_bf16mf4_tum(vbool64_t vm, vbfloat16mf4_t vd, + const __bf16 *rs1, vuint16mf4_t rs2, + size_t vl) { + return __riscv_vloxei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16mf2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.mask.nxv2bf16.nxv2i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vloxei16_v_bf16mf2_tum(vbool32_t vm, vbfloat16mf2_t vd, + const __bf16 *rs1, vuint16mf2_t rs2, + size_t vl) { + return __riscv_vloxei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16m1_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.mask.nxv4bf16.nxv4i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vloxei16_v_bf16m1_tum(vbool16_t vm, vbfloat16m1_t vd, + const __bf16 *rs1, vuint16m1_t rs2, + size_t vl) { + return __riscv_vloxei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16m2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.mask.nxv8bf16.nxv8i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vloxei16_v_bf16m2_tum(vbool8_t vm, vbfloat16m2_t vd, + const __bf16 *rs1, vuint16m2_t rs2, + size_t vl) { + return __riscv_vloxei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16m4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.mask.nxv16bf16.nxv16i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vloxei16_v_bf16m4_tum(vbool4_t vm, vbfloat16m4_t vd, + const __bf16 *rs1, vuint16m4_t rs2, + size_t vl) { + return __riscv_vloxei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16m8_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.mask.nxv32bf16.nxv32i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vloxei16_v_bf16m8_tum(vbool2_t vm, vbfloat16m8_t vd, + const __bf16 *rs1, vuint16m8_t rs2, + size_t vl) { + return __riscv_vloxei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16mf4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.mask.nxv1bf16.nxv1i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vloxei16_v_bf16mf4_tumu(vbool64_t vm, vbfloat16mf4_t vd, + const __bf16 *rs1, vuint16mf4_t rs2, + size_t vl) { + return __riscv_vloxei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16mf2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.mask.nxv2bf16.nxv2i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vloxei16_v_bf16mf2_tumu(vbool32_t vm, vbfloat16mf2_t vd, + const __bf16 *rs1, vuint16mf2_t rs2, + size_t vl) { + return __riscv_vloxei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16m1_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.mask.nxv4bf16.nxv4i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vloxei16_v_bf16m1_tumu(vbool16_t vm, vbfloat16m1_t vd, + const __bf16 *rs1, vuint16m1_t rs2, + size_t vl) { + return __riscv_vloxei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16m2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.mask.nxv8bf16.nxv8i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vloxei16_v_bf16m2_tumu(vbool8_t vm, vbfloat16m2_t vd, + const __bf16 *rs1, vuint16m2_t rs2, + size_t vl) { + return __riscv_vloxei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16m4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.mask.nxv16bf16.nxv16i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vloxei16_v_bf16m4_tumu(vbool4_t vm, vbfloat16m4_t vd, + const __bf16 *rs1, vuint16m4_t rs2, + size_t vl) { + return __riscv_vloxei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16m8_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.mask.nxv32bf16.nxv32i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vloxei16_v_bf16m8_tumu(vbool2_t vm, vbfloat16m8_t vd, + const __bf16 *rs1, vuint16m8_t rs2, + size_t vl) { + return __riscv_vloxei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16mf4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.mask.nxv1bf16.nxv1i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vloxei16_v_bf16mf4_mu(vbool64_t vm, vbfloat16mf4_t vd, + const __bf16 *rs1, vuint16mf4_t rs2, + size_t vl) { + return __riscv_vloxei16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16mf2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.mask.nxv2bf16.nxv2i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vloxei16_v_bf16mf2_mu(vbool32_t vm, vbfloat16mf2_t vd, + const __bf16 *rs1, vuint16mf2_t rs2, + size_t vl) { + return __riscv_vloxei16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16m1_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.mask.nxv4bf16.nxv4i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vloxei16_v_bf16m1_mu(vbool16_t vm, vbfloat16m1_t vd, + const __bf16 *rs1, vuint16m1_t rs2, + size_t vl) { + return __riscv_vloxei16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16m2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.mask.nxv8bf16.nxv8i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vloxei16_v_bf16m2_mu(vbool8_t vm, vbfloat16m2_t vd, + const __bf16 *rs1, vuint16m2_t rs2, + size_t vl) { + return __riscv_vloxei16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16m4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.mask.nxv16bf16.nxv16i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vloxei16_v_bf16m4_mu(vbool4_t vm, vbfloat16m4_t vd, + const __bf16 *rs1, vuint16m4_t rs2, + size_t vl) { + return __riscv_vloxei16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vloxei16_v_bf16m8_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vloxei.mask.nxv32bf16.nxv32i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vloxei16_v_bf16m8_mu(vbool2_t vm, vbfloat16m8_t vd, + const __bf16 *rs1, vuint16m8_t rs2, + size_t vl) { + return __riscv_vloxei16_mu(vm, vd, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vloxseg2ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vloxseg2ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..eab9cb4d632eca15a500d7903bce7d3b0a849971 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vloxseg2ei16.c @@ -0,0 +1,306 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16mf4x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vloxseg2.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf4x2_t test_vloxseg2ei16_v_bf16mf4x2_tu(vbfloat16mf4x2_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg2ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16mf2x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vloxseg2.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf2x2_t test_vloxseg2ei16_v_bf16mf2x2_tu(vbfloat16mf2x2_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg2ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16m1x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vloxseg2.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m1x2_t test_vloxseg2ei16_v_bf16m1x2_tu(vbfloat16m1x2_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg2ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16m2x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vloxseg2.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m2x2_t test_vloxseg2ei16_v_bf16m2x2_tu(vbfloat16m2x2_t vd, + const __bf16 *rs1, + vuint16m2_t rs2, size_t vl) { + return __riscv_vloxseg2ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16m4x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vloxseg2.nxv16bf16.nxv16i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m4x2_t test_vloxseg2ei16_v_bf16m4x2_tu(vbfloat16m4x2_t vd, + const __bf16 *rs1, + vuint16m4_t rs2, size_t vl) { + return __riscv_vloxseg2ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16mf4x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vloxseg2.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf4x2_t test_vloxseg2ei16_v_bf16mf4x2_tum(vbool64_t vm, + vbfloat16mf4x2_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, + size_t vl) { + return __riscv_vloxseg2ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16mf2x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vloxseg2.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf2x2_t test_vloxseg2ei16_v_bf16mf2x2_tum(vbool32_t vm, + vbfloat16mf2x2_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, + size_t vl) { + return __riscv_vloxseg2ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16m1x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vloxseg2.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m1x2_t test_vloxseg2ei16_v_bf16m1x2_tum(vbool16_t vm, + vbfloat16m1x2_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg2ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16m2x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vloxseg2.mask.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m2x2_t test_vloxseg2ei16_v_bf16m2x2_tum(vbool8_t vm, + vbfloat16m2x2_t vd, + const __bf16 *rs1, + vuint16m2_t rs2, size_t vl) { + return __riscv_vloxseg2ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16m4x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vloxseg2.mask.nxv16bf16.nxv16i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m4x2_t test_vloxseg2ei16_v_bf16m4x2_tum(vbool4_t vm, + vbfloat16m4x2_t vd, + const __bf16 *rs1, + vuint16m4_t rs2, size_t vl) { + return __riscv_vloxseg2ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16mf4x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vloxseg2.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf4x2_t test_vloxseg2ei16_v_bf16mf4x2_tumu(vbool64_t vm, + vbfloat16mf4x2_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, + size_t vl) { + return __riscv_vloxseg2ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16mf2x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vloxseg2.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf2x2_t test_vloxseg2ei16_v_bf16mf2x2_tumu(vbool32_t vm, + vbfloat16mf2x2_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, + size_t vl) { + return __riscv_vloxseg2ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16m1x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vloxseg2.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m1x2_t test_vloxseg2ei16_v_bf16m1x2_tumu(vbool16_t vm, + vbfloat16m1x2_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg2ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16m2x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vloxseg2.mask.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m2x2_t test_vloxseg2ei16_v_bf16m2x2_tumu(vbool8_t vm, + vbfloat16m2x2_t vd, + const __bf16 *rs1, + vuint16m2_t rs2, size_t vl) { + return __riscv_vloxseg2ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16m4x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vloxseg2.mask.nxv16bf16.nxv16i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m4x2_t test_vloxseg2ei16_v_bf16m4x2_tumu(vbool4_t vm, + vbfloat16m4x2_t vd, + const __bf16 *rs1, + vuint16m4_t rs2, size_t vl) { + return __riscv_vloxseg2ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16mf4x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vloxseg2.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf4x2_t test_vloxseg2ei16_v_bf16mf4x2_mu(vbool64_t vm, + vbfloat16mf4x2_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg2ei16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16mf2x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vloxseg2.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf2x2_t test_vloxseg2ei16_v_bf16mf2x2_mu(vbool32_t vm, + vbfloat16mf2x2_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg2ei16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16m1x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vloxseg2.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m1x2_t test_vloxseg2ei16_v_bf16m1x2_mu(vbool16_t vm, + vbfloat16m1x2_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg2ei16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16m2x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vloxseg2.mask.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m2x2_t test_vloxseg2ei16_v_bf16m2x2_mu(vbool8_t vm, vbfloat16m2x2_t vd, + const __bf16 *rs1, + vuint16m2_t rs2, size_t vl) { + return __riscv_vloxseg2ei16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vloxseg2ei16_v_bf16m4x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vloxseg2.mask.nxv16bf16.nxv16i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m4x2_t test_vloxseg2ei16_v_bf16m4x2_mu(vbool4_t vm, vbfloat16m4x2_t vd, + const __bf16 *rs1, + vuint16m4_t rs2, size_t vl) { + return __riscv_vloxseg2ei16_mu(vm, vd, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vloxseg3ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vloxseg3ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..ba5294df12542d6b0d2bf94aa3709389fef001e8 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vloxseg3ei16.c @@ -0,0 +1,264 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vloxseg3ei16_v_bf16mf4x3_tu( +// CHECK-RV64-SAME: { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vloxseg3.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf4x3_t test_vloxseg3ei16_v_bf16mf4x3_tu(vbfloat16mf4x3_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg3ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vloxseg3ei16_v_bf16mf2x3_tu( +// CHECK-RV64-SAME: { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vloxseg3.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf2x3_t test_vloxseg3ei16_v_bf16mf2x3_tu(vbfloat16mf2x3_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg3ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vloxseg3ei16_v_bf16m1x3_tu( +// CHECK-RV64-SAME: { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vloxseg3.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m1x3_t test_vloxseg3ei16_v_bf16m1x3_tu(vbfloat16m1x3_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg3ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vloxseg3ei16_v_bf16m2x3_tu( +// CHECK-RV64-SAME: { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vloxseg3.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m2x3_t test_vloxseg3ei16_v_bf16m2x3_tu(vbfloat16m2x3_t vd, + const __bf16 *rs1, + vuint16m2_t rs2, size_t vl) { + return __riscv_vloxseg3ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vloxseg3ei16_v_bf16mf4x3_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vloxseg3.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf4x3_t test_vloxseg3ei16_v_bf16mf4x3_tum(vbool64_t vm, + vbfloat16mf4x3_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, + size_t vl) { + return __riscv_vloxseg3ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vloxseg3ei16_v_bf16mf2x3_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vloxseg3.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf2x3_t test_vloxseg3ei16_v_bf16mf2x3_tum(vbool32_t vm, + vbfloat16mf2x3_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, + size_t vl) { + return __riscv_vloxseg3ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vloxseg3ei16_v_bf16m1x3_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vloxseg3.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m1x3_t test_vloxseg3ei16_v_bf16m1x3_tum(vbool16_t vm, + vbfloat16m1x3_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg3ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vloxseg3ei16_v_bf16m2x3_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vloxseg3.mask.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m2x3_t test_vloxseg3ei16_v_bf16m2x3_tum(vbool8_t vm, + vbfloat16m2x3_t vd, + const __bf16 *rs1, + vuint16m2_t rs2, size_t vl) { + return __riscv_vloxseg3ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vloxseg3ei16_v_bf16mf4x3_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vloxseg3.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf4x3_t test_vloxseg3ei16_v_bf16mf4x3_tumu(vbool64_t vm, + vbfloat16mf4x3_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, + size_t vl) { + return __riscv_vloxseg3ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vloxseg3ei16_v_bf16mf2x3_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vloxseg3.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf2x3_t test_vloxseg3ei16_v_bf16mf2x3_tumu(vbool32_t vm, + vbfloat16mf2x3_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, + size_t vl) { + return __riscv_vloxseg3ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vloxseg3ei16_v_bf16m1x3_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vloxseg3.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m1x3_t test_vloxseg3ei16_v_bf16m1x3_tumu(vbool16_t vm, + vbfloat16m1x3_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg3ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vloxseg3ei16_v_bf16m2x3_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vloxseg3.mask.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m2x3_t test_vloxseg3ei16_v_bf16m2x3_tumu(vbool8_t vm, + vbfloat16m2x3_t vd, + const __bf16 *rs1, + vuint16m2_t rs2, size_t vl) { + return __riscv_vloxseg3ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vloxseg3ei16_v_bf16mf4x3_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vloxseg3.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf4x3_t test_vloxseg3ei16_v_bf16mf4x3_mu(vbool64_t vm, + vbfloat16mf4x3_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg3ei16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vloxseg3ei16_v_bf16mf2x3_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vloxseg3.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf2x3_t test_vloxseg3ei16_v_bf16mf2x3_mu(vbool32_t vm, + vbfloat16mf2x3_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg3ei16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vloxseg3ei16_v_bf16m1x3_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vloxseg3.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m1x3_t test_vloxseg3ei16_v_bf16m1x3_mu(vbool16_t vm, + vbfloat16m1x3_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg3ei16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vloxseg3ei16_v_bf16m2x3_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vloxseg3.mask.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m2x3_t test_vloxseg3ei16_v_bf16m2x3_mu(vbool8_t vm, vbfloat16m2x3_t vd, + const __bf16 *rs1, + vuint16m2_t rs2, size_t vl) { + return __riscv_vloxseg3ei16_mu(vm, vd, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vloxseg4ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vloxseg4ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..94e96b9875a1b7ae2cec7e3312f667dcf21d8848 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vloxseg4ei16.c @@ -0,0 +1,280 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vloxseg4ei16_v_bf16mf4x4_tu( +// CHECK-RV64-SAME: { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vloxseg4.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf4x4_t test_vloxseg4ei16_v_bf16mf4x4_tu(vbfloat16mf4x4_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg4ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vloxseg4ei16_v_bf16mf2x4_tu( +// CHECK-RV64-SAME: { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vloxseg4.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf2x4_t test_vloxseg4ei16_v_bf16mf2x4_tu(vbfloat16mf2x4_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg4ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vloxseg4ei16_v_bf16m1x4_tu( +// CHECK-RV64-SAME: { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vloxseg4.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m1x4_t test_vloxseg4ei16_v_bf16m1x4_tu(vbfloat16m1x4_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg4ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vloxseg4ei16_v_bf16m2x4_tu( +// CHECK-RV64-SAME: { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vloxseg4.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m2x4_t test_vloxseg4ei16_v_bf16m2x4_tu(vbfloat16m2x4_t vd, + const __bf16 *rs1, + vuint16m2_t rs2, size_t vl) { + return __riscv_vloxseg4ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vloxseg4ei16_v_bf16mf4x4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vloxseg4.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf4x4_t test_vloxseg4ei16_v_bf16mf4x4_tum(vbool64_t vm, + vbfloat16mf4x4_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, + size_t vl) { + return __riscv_vloxseg4ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vloxseg4ei16_v_bf16mf2x4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vloxseg4.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf2x4_t test_vloxseg4ei16_v_bf16mf2x4_tum(vbool32_t vm, + vbfloat16mf2x4_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, + size_t vl) { + return __riscv_vloxseg4ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vloxseg4ei16_v_bf16m1x4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vloxseg4.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m1x4_t test_vloxseg4ei16_v_bf16m1x4_tum(vbool16_t vm, + vbfloat16m1x4_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg4ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vloxseg4ei16_v_bf16m2x4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vloxseg4.mask.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m2x4_t test_vloxseg4ei16_v_bf16m2x4_tum(vbool8_t vm, + vbfloat16m2x4_t vd, + const __bf16 *rs1, + vuint16m2_t rs2, size_t vl) { + return __riscv_vloxseg4ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vloxseg4ei16_v_bf16mf4x4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vloxseg4.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf4x4_t test_vloxseg4ei16_v_bf16mf4x4_tumu(vbool64_t vm, + vbfloat16mf4x4_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, + size_t vl) { + return __riscv_vloxseg4ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vloxseg4ei16_v_bf16mf2x4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vloxseg4.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf2x4_t test_vloxseg4ei16_v_bf16mf2x4_tumu(vbool32_t vm, + vbfloat16mf2x4_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, + size_t vl) { + return __riscv_vloxseg4ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vloxseg4ei16_v_bf16m1x4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vloxseg4.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m1x4_t test_vloxseg4ei16_v_bf16m1x4_tumu(vbool16_t vm, + vbfloat16m1x4_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg4ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vloxseg4ei16_v_bf16m2x4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vloxseg4.mask.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m2x4_t test_vloxseg4ei16_v_bf16m2x4_tumu(vbool8_t vm, + vbfloat16m2x4_t vd, + const __bf16 *rs1, + vuint16m2_t rs2, size_t vl) { + return __riscv_vloxseg4ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vloxseg4ei16_v_bf16mf4x4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vloxseg4.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf4x4_t test_vloxseg4ei16_v_bf16mf4x4_mu(vbool64_t vm, + vbfloat16mf4x4_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg4ei16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vloxseg4ei16_v_bf16mf2x4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vloxseg4.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf2x4_t test_vloxseg4ei16_v_bf16mf2x4_mu(vbool32_t vm, + vbfloat16mf2x4_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg4ei16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vloxseg4ei16_v_bf16m1x4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vloxseg4.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m1x4_t test_vloxseg4ei16_v_bf16m1x4_mu(vbool16_t vm, + vbfloat16m1x4_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg4ei16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vloxseg4ei16_v_bf16m2x4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vloxseg4.mask.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m2x4_t test_vloxseg4ei16_v_bf16m2x4_mu(vbool8_t vm, vbfloat16m2x4_t vd, + const __bf16 *rs1, + vuint16m2_t rs2, size_t vl) { + return __riscv_vloxseg4ei16_mu(vm, vd, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vloxseg5ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vloxseg5ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..54f1a6626d4895d3c18aa992e570e6ce1507b8c5 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vloxseg5ei16.c @@ -0,0 +1,226 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vloxseg5ei16_v_bf16mf4x5_tu( +// CHECK-RV64-SAME: { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vloxseg5.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf4x5_t test_vloxseg5ei16_v_bf16mf4x5_tu(vbfloat16mf4x5_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg5ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vloxseg5ei16_v_bf16mf2x5_tu( +// CHECK-RV64-SAME: { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vloxseg5.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf2x5_t test_vloxseg5ei16_v_bf16mf2x5_tu(vbfloat16mf2x5_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg5ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vloxseg5ei16_v_bf16m1x5_tu( +// CHECK-RV64-SAME: { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vloxseg5.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16m1x5_t test_vloxseg5ei16_v_bf16m1x5_tu(vbfloat16m1x5_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg5ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vloxseg5ei16_v_bf16mf4x5_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vloxseg5.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf4x5_t test_vloxseg5ei16_v_bf16mf4x5_tum(vbool64_t vm, + vbfloat16mf4x5_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, + size_t vl) { + return __riscv_vloxseg5ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vloxseg5ei16_v_bf16mf2x5_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vloxseg5.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf2x5_t test_vloxseg5ei16_v_bf16mf2x5_tum(vbool32_t vm, + vbfloat16mf2x5_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, + size_t vl) { + return __riscv_vloxseg5ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vloxseg5ei16_v_bf16m1x5_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vloxseg5.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16m1x5_t test_vloxseg5ei16_v_bf16m1x5_tum(vbool16_t vm, + vbfloat16m1x5_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg5ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vloxseg5ei16_v_bf16mf4x5_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vloxseg5.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf4x5_t test_vloxseg5ei16_v_bf16mf4x5_tumu(vbool64_t vm, + vbfloat16mf4x5_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, + size_t vl) { + return __riscv_vloxseg5ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vloxseg5ei16_v_bf16mf2x5_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vloxseg5.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf2x5_t test_vloxseg5ei16_v_bf16mf2x5_tumu(vbool32_t vm, + vbfloat16mf2x5_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, + size_t vl) { + return __riscv_vloxseg5ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vloxseg5ei16_v_bf16m1x5_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vloxseg5.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16m1x5_t test_vloxseg5ei16_v_bf16m1x5_tumu(vbool16_t vm, + vbfloat16m1x5_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg5ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vloxseg5ei16_v_bf16mf4x5_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vloxseg5.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf4x5_t test_vloxseg5ei16_v_bf16mf4x5_mu(vbool64_t vm, + vbfloat16mf4x5_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg5ei16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vloxseg5ei16_v_bf16mf2x5_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vloxseg5.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf2x5_t test_vloxseg5ei16_v_bf16mf2x5_mu(vbool32_t vm, + vbfloat16mf2x5_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg5ei16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vloxseg5ei16_v_bf16m1x5_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vloxseg5.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16m1x5_t test_vloxseg5ei16_v_bf16m1x5_mu(vbool16_t vm, + vbfloat16m1x5_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg5ei16_mu(vm, vd, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vloxseg6ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vloxseg6ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..a1ee2af0de3d8a00cd6115126748a5912fd967d2 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vloxseg6ei16.c @@ -0,0 +1,238 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vloxseg6ei16_v_bf16mf4x6_tu( +// CHECK-RV64-SAME: { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vloxseg6.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf4x6_t test_vloxseg6ei16_v_bf16mf4x6_tu(vbfloat16mf4x6_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg6ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vloxseg6ei16_v_bf16mf2x6_tu( +// CHECK-RV64-SAME: { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vloxseg6.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf2x6_t test_vloxseg6ei16_v_bf16mf2x6_tu(vbfloat16mf2x6_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg6ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vloxseg6ei16_v_bf16m1x6_tu( +// CHECK-RV64-SAME: { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vloxseg6.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16m1x6_t test_vloxseg6ei16_v_bf16m1x6_tu(vbfloat16m1x6_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg6ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vloxseg6ei16_v_bf16mf4x6_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vloxseg6.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf4x6_t test_vloxseg6ei16_v_bf16mf4x6_tum(vbool64_t vm, + vbfloat16mf4x6_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, + size_t vl) { + return __riscv_vloxseg6ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vloxseg6ei16_v_bf16mf2x6_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vloxseg6.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf2x6_t test_vloxseg6ei16_v_bf16mf2x6_tum(vbool32_t vm, + vbfloat16mf2x6_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, + size_t vl) { + return __riscv_vloxseg6ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vloxseg6ei16_v_bf16m1x6_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vloxseg6.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16m1x6_t test_vloxseg6ei16_v_bf16m1x6_tum(vbool16_t vm, + vbfloat16m1x6_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg6ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vloxseg6ei16_v_bf16mf4x6_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vloxseg6.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf4x6_t test_vloxseg6ei16_v_bf16mf4x6_tumu(vbool64_t vm, + vbfloat16mf4x6_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, + size_t vl) { + return __riscv_vloxseg6ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vloxseg6ei16_v_bf16mf2x6_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vloxseg6.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf2x6_t test_vloxseg6ei16_v_bf16mf2x6_tumu(vbool32_t vm, + vbfloat16mf2x6_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, + size_t vl) { + return __riscv_vloxseg6ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vloxseg6ei16_v_bf16m1x6_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vloxseg6.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16m1x6_t test_vloxseg6ei16_v_bf16m1x6_tumu(vbool16_t vm, + vbfloat16m1x6_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg6ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vloxseg6ei16_v_bf16mf4x6_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vloxseg6.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf4x6_t test_vloxseg6ei16_v_bf16mf4x6_mu(vbool64_t vm, + vbfloat16mf4x6_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg6ei16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vloxseg6ei16_v_bf16mf2x6_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vloxseg6.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf2x6_t test_vloxseg6ei16_v_bf16mf2x6_mu(vbool32_t vm, + vbfloat16mf2x6_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg6ei16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vloxseg6ei16_v_bf16m1x6_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vloxseg6.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16m1x6_t test_vloxseg6ei16_v_bf16m1x6_mu(vbool16_t vm, + vbfloat16m1x6_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg6ei16_mu(vm, vd, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vloxseg7ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vloxseg7ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..6b9cd5cf05267d78d420636940e0d0fa964cb786 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vloxseg7ei16.c @@ -0,0 +1,250 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vloxseg7ei16_v_bf16mf4x7_tu( +// CHECK-RV64-SAME: { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vloxseg7.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf4x7_t test_vloxseg7ei16_v_bf16mf4x7_tu(vbfloat16mf4x7_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg7ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vloxseg7ei16_v_bf16mf2x7_tu( +// CHECK-RV64-SAME: { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vloxseg7.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf2x7_t test_vloxseg7ei16_v_bf16mf2x7_tu(vbfloat16mf2x7_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg7ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vloxseg7ei16_v_bf16m1x7_tu( +// CHECK-RV64-SAME: { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vloxseg7.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16m1x7_t test_vloxseg7ei16_v_bf16m1x7_tu(vbfloat16m1x7_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg7ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vloxseg7ei16_v_bf16mf4x7_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vloxseg7.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf4x7_t test_vloxseg7ei16_v_bf16mf4x7_tum(vbool64_t vm, + vbfloat16mf4x7_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, + size_t vl) { + return __riscv_vloxseg7ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vloxseg7ei16_v_bf16mf2x7_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vloxseg7.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf2x7_t test_vloxseg7ei16_v_bf16mf2x7_tum(vbool32_t vm, + vbfloat16mf2x7_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, + size_t vl) { + return __riscv_vloxseg7ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vloxseg7ei16_v_bf16m1x7_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vloxseg7.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16m1x7_t test_vloxseg7ei16_v_bf16m1x7_tum(vbool16_t vm, + vbfloat16m1x7_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg7ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vloxseg7ei16_v_bf16mf4x7_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vloxseg7.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf4x7_t test_vloxseg7ei16_v_bf16mf4x7_tumu(vbool64_t vm, + vbfloat16mf4x7_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, + size_t vl) { + return __riscv_vloxseg7ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vloxseg7ei16_v_bf16mf2x7_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vloxseg7.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf2x7_t test_vloxseg7ei16_v_bf16mf2x7_tumu(vbool32_t vm, + vbfloat16mf2x7_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, + size_t vl) { + return __riscv_vloxseg7ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vloxseg7ei16_v_bf16m1x7_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vloxseg7.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16m1x7_t test_vloxseg7ei16_v_bf16m1x7_tumu(vbool16_t vm, + vbfloat16m1x7_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg7ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vloxseg7ei16_v_bf16mf4x7_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vloxseg7.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf4x7_t test_vloxseg7ei16_v_bf16mf4x7_mu(vbool64_t vm, + vbfloat16mf4x7_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg7ei16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vloxseg7ei16_v_bf16mf2x7_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vloxseg7.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf2x7_t test_vloxseg7ei16_v_bf16mf2x7_mu(vbool32_t vm, + vbfloat16mf2x7_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg7ei16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vloxseg7ei16_v_bf16m1x7_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vloxseg7.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16m1x7_t test_vloxseg7ei16_v_bf16m1x7_mu(vbool16_t vm, + vbfloat16m1x7_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg7ei16_mu(vm, vd, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vloxseg8ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vloxseg8ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..f743b83d83c0fb02438b145e4515493f4cff14ca --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vloxseg8ei16.c @@ -0,0 +1,262 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vloxseg8ei16_v_bf16mf4x8_tu( +// CHECK-RV64-SAME: { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vloxseg8.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf4x8_t test_vloxseg8ei16_v_bf16mf4x8_tu(vbfloat16mf4x8_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg8ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vloxseg8ei16_v_bf16mf2x8_tu( +// CHECK-RV64-SAME: { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vloxseg8.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf2x8_t test_vloxseg8ei16_v_bf16mf2x8_tu(vbfloat16mf2x8_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg8ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vloxseg8ei16_v_bf16m1x8_tu( +// CHECK-RV64-SAME: { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vloxseg8.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16m1x8_t test_vloxseg8ei16_v_bf16m1x8_tu(vbfloat16m1x8_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg8ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vloxseg8ei16_v_bf16mf4x8_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vloxseg8.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf4x8_t test_vloxseg8ei16_v_bf16mf4x8_tum(vbool64_t vm, + vbfloat16mf4x8_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, + size_t vl) { + return __riscv_vloxseg8ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vloxseg8ei16_v_bf16mf2x8_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vloxseg8.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf2x8_t test_vloxseg8ei16_v_bf16mf2x8_tum(vbool32_t vm, + vbfloat16mf2x8_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, + size_t vl) { + return __riscv_vloxseg8ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vloxseg8ei16_v_bf16m1x8_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vloxseg8.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16m1x8_t test_vloxseg8ei16_v_bf16m1x8_tum(vbool16_t vm, + vbfloat16m1x8_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg8ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vloxseg8ei16_v_bf16mf4x8_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vloxseg8.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf4x8_t test_vloxseg8ei16_v_bf16mf4x8_tumu(vbool64_t vm, + vbfloat16mf4x8_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, + size_t vl) { + return __riscv_vloxseg8ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vloxseg8ei16_v_bf16mf2x8_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vloxseg8.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf2x8_t test_vloxseg8ei16_v_bf16mf2x8_tumu(vbool32_t vm, + vbfloat16mf2x8_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, + size_t vl) { + return __riscv_vloxseg8ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vloxseg8ei16_v_bf16m1x8_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vloxseg8.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16m1x8_t test_vloxseg8ei16_v_bf16m1x8_tumu(vbool16_t vm, + vbfloat16m1x8_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg8ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vloxseg8ei16_v_bf16mf4x8_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vloxseg8.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf4x8_t test_vloxseg8ei16_v_bf16mf4x8_mu(vbool64_t vm, + vbfloat16mf4x8_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vloxseg8ei16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vloxseg8ei16_v_bf16mf2x8_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vloxseg8.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf2x8_t test_vloxseg8ei16_v_bf16mf2x8_mu(vbool32_t vm, + vbfloat16mf2x8_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vloxseg8ei16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vloxseg8ei16_v_bf16m1x8_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vloxseg8.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16m1x8_t test_vloxseg8ei16_v_bf16m1x8_mu(vbool16_t vm, + vbfloat16m1x8_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vloxseg8ei16_mu(vm, vd, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlse16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlse16.c new file mode 100644 index 0000000000000000000000000000000000000000..95652db60be027b7e497e9d7756ec90706a0a950 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlse16.c @@ -0,0 +1,291 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16mf4_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.nxv1bf16.i64( [[VD]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vlse16_v_bf16mf4_tu(vbfloat16mf4_t vd, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlse16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16mf2_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.nxv2bf16.i64( [[VD]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vlse16_v_bf16mf2_tu(vbfloat16mf2_t vd, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlse16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16m1_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.nxv4bf16.i64( [[VD]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vlse16_v_bf16m1_tu(vbfloat16m1_t vd, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlse16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16m2_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.nxv8bf16.i64( [[VD]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vlse16_v_bf16m2_tu(vbfloat16m2_t vd, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlse16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16m4_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.nxv16bf16.i64( [[VD]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vlse16_v_bf16m4_tu(vbfloat16m4_t vd, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlse16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16m8_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.nxv32bf16.i64( [[VD]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vlse16_v_bf16m8_tu(vbfloat16m8_t vd, const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlse16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16mf4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.mask.nxv1bf16.i64( [[VD]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vlse16_v_bf16mf4_tum(vbool64_t vm, vbfloat16mf4_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlse16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16mf2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.mask.nxv2bf16.i64( [[VD]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vlse16_v_bf16mf2_tum(vbool32_t vm, vbfloat16mf2_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlse16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16m1_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.mask.nxv4bf16.i64( [[VD]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vlse16_v_bf16m1_tum(vbool16_t vm, vbfloat16m1_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlse16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16m2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.mask.nxv8bf16.i64( [[VD]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vlse16_v_bf16m2_tum(vbool8_t vm, vbfloat16m2_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlse16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16m4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.mask.nxv16bf16.i64( [[VD]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vlse16_v_bf16m4_tum(vbool4_t vm, vbfloat16m4_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlse16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16m8_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.mask.nxv32bf16.i64( [[VD]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vlse16_v_bf16m8_tum(vbool2_t vm, vbfloat16m8_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlse16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16mf4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.mask.nxv1bf16.i64( [[VD]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vlse16_v_bf16mf4_tumu(vbool64_t vm, vbfloat16mf4_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlse16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16mf2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.mask.nxv2bf16.i64( [[VD]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vlse16_v_bf16mf2_tumu(vbool32_t vm, vbfloat16mf2_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlse16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16m1_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.mask.nxv4bf16.i64( [[VD]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vlse16_v_bf16m1_tumu(vbool16_t vm, vbfloat16m1_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlse16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16m2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.mask.nxv8bf16.i64( [[VD]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vlse16_v_bf16m2_tumu(vbool8_t vm, vbfloat16m2_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlse16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16m4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.mask.nxv16bf16.i64( [[VD]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vlse16_v_bf16m4_tumu(vbool4_t vm, vbfloat16m4_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlse16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16m8_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.mask.nxv32bf16.i64( [[VD]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vlse16_v_bf16m8_tumu(vbool2_t vm, vbfloat16m8_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlse16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16mf4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.mask.nxv1bf16.i64( [[VD]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vlse16_v_bf16mf4_mu(vbool64_t vm, vbfloat16mf4_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlse16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16mf2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.mask.nxv2bf16.i64( [[VD]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vlse16_v_bf16mf2_mu(vbool32_t vm, vbfloat16mf2_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlse16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16m1_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.mask.nxv4bf16.i64( [[VD]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vlse16_v_bf16m1_mu(vbool16_t vm, vbfloat16m1_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlse16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16m2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.mask.nxv8bf16.i64( [[VD]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vlse16_v_bf16m2_mu(vbool8_t vm, vbfloat16m2_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlse16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16m4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.mask.nxv16bf16.i64( [[VD]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vlse16_v_bf16m4_mu(vbool4_t vm, vbfloat16m4_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlse16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vlse16_v_bf16m8_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vlse.mask.nxv32bf16.i64( [[VD]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vlse16_v_bf16m8_mu(vbool2_t vm, vbfloat16m8_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlse16_mu(vm, vd, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlseg2e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlseg2e16.c new file mode 100644 index 0000000000000000000000000000000000000000..2d15ad7713e01ac03f00a6930abcc7c71b48816a --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlseg2e16.c @@ -0,0 +1,275 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16mf4x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlseg2.nxv1bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf4x2_t test_vlseg2e16_v_bf16mf4x2_tu(vbfloat16mf4x2_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg2e16_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16mf2x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlseg2.nxv2bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf2x2_t test_vlseg2e16_v_bf16mf2x2_tu(vbfloat16mf2x2_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg2e16_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16m1x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlseg2.nxv4bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m1x2_t test_vlseg2e16_v_bf16m1x2_tu(vbfloat16m1x2_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg2e16_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16m2x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlseg2.nxv8bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m2x2_t test_vlseg2e16_v_bf16m2x2_tu(vbfloat16m2x2_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg2e16_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16m4x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlseg2.nxv16bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m4x2_t test_vlseg2e16_v_bf16m4x2_tu(vbfloat16m4x2_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg2e16_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16mf4x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlseg2.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf4x2_t test_vlseg2e16_v_bf16mf4x2_tum(vbool64_t vm, + vbfloat16mf4x2_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg2e16_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16mf2x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlseg2.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf2x2_t test_vlseg2e16_v_bf16mf2x2_tum(vbool32_t vm, + vbfloat16mf2x2_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg2e16_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16m1x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlseg2.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m1x2_t test_vlseg2e16_v_bf16m1x2_tum(vbool16_t vm, vbfloat16m1x2_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg2e16_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16m2x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlseg2.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m2x2_t test_vlseg2e16_v_bf16m2x2_tum(vbool8_t vm, vbfloat16m2x2_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg2e16_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16m4x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlseg2.mask.nxv16bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m4x2_t test_vlseg2e16_v_bf16m4x2_tum(vbool4_t vm, vbfloat16m4x2_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg2e16_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16mf4x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlseg2.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf4x2_t test_vlseg2e16_v_bf16mf4x2_tumu(vbool64_t vm, + vbfloat16mf4x2_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg2e16_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16mf2x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlseg2.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf2x2_t test_vlseg2e16_v_bf16mf2x2_tumu(vbool32_t vm, + vbfloat16mf2x2_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg2e16_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16m1x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlseg2.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m1x2_t test_vlseg2e16_v_bf16m1x2_tumu(vbool16_t vm, vbfloat16m1x2_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg2e16_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16m2x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlseg2.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m2x2_t test_vlseg2e16_v_bf16m2x2_tumu(vbool8_t vm, vbfloat16m2x2_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg2e16_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16m4x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlseg2.mask.nxv16bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m4x2_t test_vlseg2e16_v_bf16m4x2_tumu(vbool4_t vm, vbfloat16m4x2_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg2e16_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16mf4x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlseg2.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf4x2_t test_vlseg2e16_v_bf16mf4x2_mu(vbool64_t vm, + vbfloat16mf4x2_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg2e16_mu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16mf2x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlseg2.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf2x2_t test_vlseg2e16_v_bf16mf2x2_mu(vbool32_t vm, + vbfloat16mf2x2_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg2e16_mu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16m1x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlseg2.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m1x2_t test_vlseg2e16_v_bf16m1x2_mu(vbool16_t vm, vbfloat16m1x2_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg2e16_mu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16m2x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlseg2.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m2x2_t test_vlseg2e16_v_bf16m2x2_mu(vbool8_t vm, vbfloat16m2x2_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg2e16_mu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16_v_bf16m4x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlseg2.mask.nxv16bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m4x2_t test_vlseg2e16_v_bf16m4x2_mu(vbool4_t vm, vbfloat16m4x2_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg2e16_mu(vm, vd, rs1, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlseg2e16ff.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlseg2e16ff.c new file mode 100644 index 0000000000000000000000000000000000000000..d08cb9254e1ee19211bb58a7227e210cea596754 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlseg2e16ff.c @@ -0,0 +1,419 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16mf4x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.nxv1bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP2]], 0 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } poison, [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP2]], 1 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , } [[TMP4]], [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , i64 } [[TMP2]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP6]] +// +vbfloat16mf4x2_t test_vlseg2e16ff_v_bf16mf4x2_tu(vbfloat16mf4x2_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16mf2x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.nxv2bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP2]], 0 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } poison, [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP2]], 1 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , } [[TMP4]], [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , i64 } [[TMP2]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP6]] +// +vbfloat16mf2x2_t test_vlseg2e16ff_v_bf16mf2x2_tu(vbfloat16mf2x2_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16m1x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.nxv4bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP2]], 0 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } poison, [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP2]], 1 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , } [[TMP4]], [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , i64 } [[TMP2]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP6]] +// +vbfloat16m1x2_t test_vlseg2e16ff_v_bf16m1x2_tu(vbfloat16m1x2_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16m2x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.nxv8bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP2]], 0 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } poison, [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP2]], 1 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , } [[TMP4]], [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , i64 } [[TMP2]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP6]] +// +vbfloat16m2x2_t test_vlseg2e16ff_v_bf16m2x2_tu(vbfloat16m2x2_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16m4x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.nxv16bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP2]], 0 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } poison, [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP2]], 1 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , } [[TMP4]], [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , i64 } [[TMP2]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP6]] +// +vbfloat16m4x2_t test_vlseg2e16ff_v_bf16m4x2_tu(vbfloat16m4x2_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16mf4x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP2]], 0 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } poison, [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP2]], 1 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , } [[TMP4]], [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , i64 } [[TMP2]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP6]] +// +vbfloat16mf4x2_t test_vlseg2e16ff_v_bf16mf4x2_tum(vbool64_t vm, + vbfloat16mf4x2_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16mf2x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP2]], 0 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } poison, [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP2]], 1 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , } [[TMP4]], [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , i64 } [[TMP2]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP6]] +// +vbfloat16mf2x2_t test_vlseg2e16ff_v_bf16mf2x2_tum(vbool32_t vm, + vbfloat16mf2x2_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16m1x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP2]], 0 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } poison, [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP2]], 1 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , } [[TMP4]], [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , i64 } [[TMP2]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP6]] +// +vbfloat16m1x2_t test_vlseg2e16ff_v_bf16m1x2_tum(vbool16_t vm, + vbfloat16m1x2_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16m2x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP2]], 0 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } poison, [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP2]], 1 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , } [[TMP4]], [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , i64 } [[TMP2]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP6]] +// +vbfloat16m2x2_t test_vlseg2e16ff_v_bf16m2x2_tum(vbool8_t vm, vbfloat16m2x2_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16m4x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.mask.nxv16bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP2]], 0 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } poison, [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP2]], 1 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , } [[TMP4]], [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , i64 } [[TMP2]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP6]] +// +vbfloat16m4x2_t test_vlseg2e16ff_v_bf16m4x2_tum(vbool4_t vm, vbfloat16m4x2_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16mf4x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP2]], 0 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } poison, [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP2]], 1 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , } [[TMP4]], [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , i64 } [[TMP2]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP6]] +// +vbfloat16mf4x2_t test_vlseg2e16ff_v_bf16mf4x2_tumu(vbool64_t vm, + vbfloat16mf4x2_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16mf2x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP2]], 0 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } poison, [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP2]], 1 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , } [[TMP4]], [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , i64 } [[TMP2]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP6]] +// +vbfloat16mf2x2_t test_vlseg2e16ff_v_bf16mf2x2_tumu(vbool32_t vm, + vbfloat16mf2x2_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16m1x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP2]], 0 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } poison, [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP2]], 1 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , } [[TMP4]], [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , i64 } [[TMP2]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP6]] +// +vbfloat16m1x2_t test_vlseg2e16ff_v_bf16m1x2_tumu(vbool16_t vm, + vbfloat16m1x2_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16m2x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP2]], 0 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } poison, [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP2]], 1 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , } [[TMP4]], [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , i64 } [[TMP2]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP6]] +// +vbfloat16m2x2_t test_vlseg2e16ff_v_bf16m2x2_tumu(vbool8_t vm, + vbfloat16m2x2_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16m4x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.mask.nxv16bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP2]], 0 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } poison, [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP2]], 1 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , } [[TMP4]], [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , i64 } [[TMP2]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP6]] +// +vbfloat16m4x2_t test_vlseg2e16ff_v_bf16m4x2_tumu(vbool4_t vm, + vbfloat16m4x2_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16mf4x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP2]], 0 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } poison, [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP2]], 1 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , } [[TMP4]], [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , i64 } [[TMP2]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP6]] +// +vbfloat16mf4x2_t test_vlseg2e16ff_v_bf16mf4x2_mu(vbool64_t vm, + vbfloat16mf4x2_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff_mu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16mf2x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP2]], 0 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } poison, [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP2]], 1 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , } [[TMP4]], [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , i64 } [[TMP2]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP6]] +// +vbfloat16mf2x2_t test_vlseg2e16ff_v_bf16mf2x2_mu(vbool32_t vm, + vbfloat16mf2x2_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff_mu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16m1x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP2]], 0 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } poison, [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP2]], 1 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , } [[TMP4]], [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , i64 } [[TMP2]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP6]] +// +vbfloat16m1x2_t test_vlseg2e16ff_v_bf16m1x2_mu(vbool16_t vm, vbfloat16m1x2_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff_mu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16m2x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP2]], 0 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } poison, [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP2]], 1 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , } [[TMP4]], [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , i64 } [[TMP2]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP6]] +// +vbfloat16m2x2_t test_vlseg2e16ff_v_bf16m2x2_mu(vbool8_t vm, vbfloat16m2x2_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff_mu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlseg2e16ff_v_bf16m4x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , , i64 } @llvm.riscv.vlseg2ff.mask.nxv16bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , i64 } [[TMP2]], 0 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = insertvalue { , } poison, [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , i64 } [[TMP2]], 1 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , } [[TMP4]], [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , i64 } [[TMP2]], 2 +// CHECK-RV64-NEXT: store i64 [[TMP7]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , } [[TMP6]] +// +vbfloat16m4x2_t test_vlseg2e16ff_v_bf16m4x2_mu(vbool4_t vm, vbfloat16m4x2_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg2e16ff_mu(vm, vd, rs1, new_vl, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlseg3e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlseg3e16.c new file mode 100644 index 0000000000000000000000000000000000000000..336e8d0b898389dfe0d4dba433fcd529b3bb1c52 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlseg3e16.c @@ -0,0 +1,239 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16_v_bf16mf4x3_tu( +// CHECK-RV64-SAME: { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlseg3.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf4x3_t test_vlseg3e16_v_bf16mf4x3_tu(vbfloat16mf4x3_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg3e16_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16_v_bf16mf2x3_tu( +// CHECK-RV64-SAME: { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlseg3.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf2x3_t test_vlseg3e16_v_bf16mf2x3_tu(vbfloat16mf2x3_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg3e16_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16_v_bf16m1x3_tu( +// CHECK-RV64-SAME: { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlseg3.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m1x3_t test_vlseg3e16_v_bf16m1x3_tu(vbfloat16m1x3_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg3e16_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16_v_bf16m2x3_tu( +// CHECK-RV64-SAME: { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlseg3.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m2x3_t test_vlseg3e16_v_bf16m2x3_tu(vbfloat16m2x3_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg3e16_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16_v_bf16mf4x3_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlseg3.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf4x3_t test_vlseg3e16_v_bf16mf4x3_tum(vbool64_t vm, + vbfloat16mf4x3_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg3e16_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16_v_bf16mf2x3_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlseg3.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf2x3_t test_vlseg3e16_v_bf16mf2x3_tum(vbool32_t vm, + vbfloat16mf2x3_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg3e16_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16_v_bf16m1x3_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlseg3.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m1x3_t test_vlseg3e16_v_bf16m1x3_tum(vbool16_t vm, vbfloat16m1x3_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg3e16_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16_v_bf16m2x3_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlseg3.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m2x3_t test_vlseg3e16_v_bf16m2x3_tum(vbool8_t vm, vbfloat16m2x3_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg3e16_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16_v_bf16mf4x3_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlseg3.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf4x3_t test_vlseg3e16_v_bf16mf4x3_tumu(vbool64_t vm, + vbfloat16mf4x3_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg3e16_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16_v_bf16mf2x3_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlseg3.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf2x3_t test_vlseg3e16_v_bf16mf2x3_tumu(vbool32_t vm, + vbfloat16mf2x3_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg3e16_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16_v_bf16m1x3_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlseg3.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m1x3_t test_vlseg3e16_v_bf16m1x3_tumu(vbool16_t vm, vbfloat16m1x3_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg3e16_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16_v_bf16m2x3_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlseg3.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m2x3_t test_vlseg3e16_v_bf16m2x3_tumu(vbool8_t vm, vbfloat16m2x3_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg3e16_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16_v_bf16mf4x3_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlseg3.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf4x3_t test_vlseg3e16_v_bf16mf4x3_mu(vbool64_t vm, + vbfloat16mf4x3_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg3e16_mu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16_v_bf16mf2x3_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlseg3.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf2x3_t test_vlseg3e16_v_bf16mf2x3_mu(vbool32_t vm, + vbfloat16mf2x3_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg3e16_mu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16_v_bf16m1x3_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlseg3.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m1x3_t test_vlseg3e16_v_bf16m1x3_mu(vbool16_t vm, vbfloat16m1x3_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg3e16_mu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16_v_bf16m2x3_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlseg3.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m2x3_t test_vlseg3e16_v_bf16m2x3_mu(vbool8_t vm, vbfloat16m2x3_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg3e16_mu(vm, vd, rs1, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlseg3e16ff.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlseg3e16ff.c new file mode 100644 index 0000000000000000000000000000000000000000..7dc19f9199c6972297f8a42cfb2d68dfeb9b9753 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlseg3e16ff.c @@ -0,0 +1,386 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16ff_v_bf16mf4x3_tu( +// CHECK-RV64-SAME: { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , , i64 } @llvm.riscv.vlseg3ff.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , i64 } [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = insertvalue { , , } poison, [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , i64 } [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , } [[TMP5]], [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , i64 } [[TMP3]], 2 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , } [[TMP7]], [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , i64 } [[TMP3]], 3 +// CHECK-RV64-NEXT: store i64 [[TMP10]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , } [[TMP9]] +// +vbfloat16mf4x3_t test_vlseg3e16ff_v_bf16mf4x3_tu(vbfloat16mf4x3_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg3e16ff_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16ff_v_bf16mf2x3_tu( +// CHECK-RV64-SAME: { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , , i64 } @llvm.riscv.vlseg3ff.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , i64 } [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = insertvalue { , , } poison, [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , i64 } [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , } [[TMP5]], [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , i64 } [[TMP3]], 2 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , } [[TMP7]], [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , i64 } [[TMP3]], 3 +// CHECK-RV64-NEXT: store i64 [[TMP10]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , } [[TMP9]] +// +vbfloat16mf2x3_t test_vlseg3e16ff_v_bf16mf2x3_tu(vbfloat16mf2x3_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg3e16ff_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16ff_v_bf16m1x3_tu( +// CHECK-RV64-SAME: { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , , i64 } @llvm.riscv.vlseg3ff.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , i64 } [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = insertvalue { , , } poison, [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , i64 } [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , } [[TMP5]], [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , i64 } [[TMP3]], 2 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , } [[TMP7]], [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , i64 } [[TMP3]], 3 +// CHECK-RV64-NEXT: store i64 [[TMP10]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , } [[TMP9]] +// +vbfloat16m1x3_t test_vlseg3e16ff_v_bf16m1x3_tu(vbfloat16m1x3_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg3e16ff_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16ff_v_bf16m2x3_tu( +// CHECK-RV64-SAME: { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , , i64 } @llvm.riscv.vlseg3ff.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , i64 } [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = insertvalue { , , } poison, [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , i64 } [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , } [[TMP5]], [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , i64 } [[TMP3]], 2 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , } [[TMP7]], [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , i64 } [[TMP3]], 3 +// CHECK-RV64-NEXT: store i64 [[TMP10]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , } [[TMP9]] +// +vbfloat16m2x3_t test_vlseg3e16ff_v_bf16m2x3_tu(vbfloat16m2x3_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg3e16ff_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16ff_v_bf16mf4x3_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , , i64 } @llvm.riscv.vlseg3ff.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , i64 } [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = insertvalue { , , } poison, [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , i64 } [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , } [[TMP5]], [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , i64 } [[TMP3]], 2 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , } [[TMP7]], [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , i64 } [[TMP3]], 3 +// CHECK-RV64-NEXT: store i64 [[TMP10]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , } [[TMP9]] +// +vbfloat16mf4x3_t test_vlseg3e16ff_v_bf16mf4x3_tum(vbool64_t vm, + vbfloat16mf4x3_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg3e16ff_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16ff_v_bf16mf2x3_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , , i64 } @llvm.riscv.vlseg3ff.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , i64 } [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = insertvalue { , , } poison, [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , i64 } [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , } [[TMP5]], [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , i64 } [[TMP3]], 2 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , } [[TMP7]], [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , i64 } [[TMP3]], 3 +// CHECK-RV64-NEXT: store i64 [[TMP10]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , } [[TMP9]] +// +vbfloat16mf2x3_t test_vlseg3e16ff_v_bf16mf2x3_tum(vbool32_t vm, + vbfloat16mf2x3_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg3e16ff_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16ff_v_bf16m1x3_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , , i64 } @llvm.riscv.vlseg3ff.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , i64 } [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = insertvalue { , , } poison, [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , i64 } [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , } [[TMP5]], [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , i64 } [[TMP3]], 2 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , } [[TMP7]], [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , i64 } [[TMP3]], 3 +// CHECK-RV64-NEXT: store i64 [[TMP10]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , } [[TMP9]] +// +vbfloat16m1x3_t test_vlseg3e16ff_v_bf16m1x3_tum(vbool16_t vm, + vbfloat16m1x3_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg3e16ff_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16ff_v_bf16m2x3_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , , i64 } @llvm.riscv.vlseg3ff.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , i64 } [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = insertvalue { , , } poison, [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , i64 } [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , } [[TMP5]], [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , i64 } [[TMP3]], 2 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , } [[TMP7]], [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , i64 } [[TMP3]], 3 +// CHECK-RV64-NEXT: store i64 [[TMP10]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , } [[TMP9]] +// +vbfloat16m2x3_t test_vlseg3e16ff_v_bf16m2x3_tum(vbool8_t vm, vbfloat16m2x3_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg3e16ff_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16ff_v_bf16mf4x3_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , , i64 } @llvm.riscv.vlseg3ff.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , i64 } [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = insertvalue { , , } poison, [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , i64 } [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , } [[TMP5]], [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , i64 } [[TMP3]], 2 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , } [[TMP7]], [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , i64 } [[TMP3]], 3 +// CHECK-RV64-NEXT: store i64 [[TMP10]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , } [[TMP9]] +// +vbfloat16mf4x3_t test_vlseg3e16ff_v_bf16mf4x3_tumu(vbool64_t vm, + vbfloat16mf4x3_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg3e16ff_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16ff_v_bf16mf2x3_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , , i64 } @llvm.riscv.vlseg3ff.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , i64 } [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = insertvalue { , , } poison, [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , i64 } [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , } [[TMP5]], [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , i64 } [[TMP3]], 2 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , } [[TMP7]], [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , i64 } [[TMP3]], 3 +// CHECK-RV64-NEXT: store i64 [[TMP10]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , } [[TMP9]] +// +vbfloat16mf2x3_t test_vlseg3e16ff_v_bf16mf2x3_tumu(vbool32_t vm, + vbfloat16mf2x3_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg3e16ff_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16ff_v_bf16m1x3_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , , i64 } @llvm.riscv.vlseg3ff.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , i64 } [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = insertvalue { , , } poison, [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , i64 } [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , } [[TMP5]], [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , i64 } [[TMP3]], 2 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , } [[TMP7]], [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , i64 } [[TMP3]], 3 +// CHECK-RV64-NEXT: store i64 [[TMP10]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , } [[TMP9]] +// +vbfloat16m1x3_t test_vlseg3e16ff_v_bf16m1x3_tumu(vbool16_t vm, + vbfloat16m1x3_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg3e16ff_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16ff_v_bf16m2x3_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , , i64 } @llvm.riscv.vlseg3ff.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , i64 } [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = insertvalue { , , } poison, [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , i64 } [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , } [[TMP5]], [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , i64 } [[TMP3]], 2 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , } [[TMP7]], [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , i64 } [[TMP3]], 3 +// CHECK-RV64-NEXT: store i64 [[TMP10]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , } [[TMP9]] +// +vbfloat16m2x3_t test_vlseg3e16ff_v_bf16m2x3_tumu(vbool8_t vm, + vbfloat16m2x3_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg3e16ff_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16ff_v_bf16mf4x3_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , , i64 } @llvm.riscv.vlseg3ff.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , i64 } [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = insertvalue { , , } poison, [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , i64 } [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , } [[TMP5]], [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , i64 } [[TMP3]], 2 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , } [[TMP7]], [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , i64 } [[TMP3]], 3 +// CHECK-RV64-NEXT: store i64 [[TMP10]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , } [[TMP9]] +// +vbfloat16mf4x3_t test_vlseg3e16ff_v_bf16mf4x3_mu(vbool64_t vm, + vbfloat16mf4x3_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg3e16ff_mu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16ff_v_bf16mf2x3_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , , i64 } @llvm.riscv.vlseg3ff.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , i64 } [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = insertvalue { , , } poison, [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , i64 } [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , } [[TMP5]], [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , i64 } [[TMP3]], 2 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , } [[TMP7]], [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , i64 } [[TMP3]], 3 +// CHECK-RV64-NEXT: store i64 [[TMP10]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , } [[TMP9]] +// +vbfloat16mf2x3_t test_vlseg3e16ff_v_bf16mf2x3_mu(vbool32_t vm, + vbfloat16mf2x3_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg3e16ff_mu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16ff_v_bf16m1x3_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , , i64 } @llvm.riscv.vlseg3ff.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , i64 } [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = insertvalue { , , } poison, [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , i64 } [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , } [[TMP5]], [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , i64 } [[TMP3]], 2 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , } [[TMP7]], [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , i64 } [[TMP3]], 3 +// CHECK-RV64-NEXT: store i64 [[TMP10]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , } [[TMP9]] +// +vbfloat16m1x3_t test_vlseg3e16ff_v_bf16m1x3_mu(vbool16_t vm, vbfloat16m1x3_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg3e16ff_mu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlseg3e16ff_v_bf16m2x3_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , , i64 } @llvm.riscv.vlseg3ff.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , i64 } [[TMP3]], 0 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = insertvalue { , , } poison, [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , i64 } [[TMP3]], 1 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , } [[TMP5]], [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , i64 } [[TMP3]], 2 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , } [[TMP7]], [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , i64 } [[TMP3]], 3 +// CHECK-RV64-NEXT: store i64 [[TMP10]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , } [[TMP9]] +// +vbfloat16m2x3_t test_vlseg3e16ff_v_bf16m2x3_mu(vbool8_t vm, vbfloat16m2x3_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg3e16ff_mu(vm, vd, rs1, new_vl, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlseg4e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlseg4e16.c new file mode 100644 index 0000000000000000000000000000000000000000..ddb335cc242e6d82d215d5d66f954cb4928c11ee --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlseg4e16.c @@ -0,0 +1,255 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16_v_bf16mf4x4_tu( +// CHECK-RV64-SAME: { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlseg4.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf4x4_t test_vlseg4e16_v_bf16mf4x4_tu(vbfloat16mf4x4_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg4e16_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16_v_bf16mf2x4_tu( +// CHECK-RV64-SAME: { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlseg4.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf2x4_t test_vlseg4e16_v_bf16mf2x4_tu(vbfloat16mf2x4_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg4e16_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16_v_bf16m1x4_tu( +// CHECK-RV64-SAME: { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlseg4.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m1x4_t test_vlseg4e16_v_bf16m1x4_tu(vbfloat16m1x4_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg4e16_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16_v_bf16m2x4_tu( +// CHECK-RV64-SAME: { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlseg4.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m2x4_t test_vlseg4e16_v_bf16m2x4_tu(vbfloat16m2x4_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg4e16_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16_v_bf16mf4x4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlseg4.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf4x4_t test_vlseg4e16_v_bf16mf4x4_tum(vbool64_t vm, + vbfloat16mf4x4_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg4e16_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16_v_bf16mf2x4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlseg4.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf2x4_t test_vlseg4e16_v_bf16mf2x4_tum(vbool32_t vm, + vbfloat16mf2x4_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg4e16_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16_v_bf16m1x4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlseg4.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m1x4_t test_vlseg4e16_v_bf16m1x4_tum(vbool16_t vm, vbfloat16m1x4_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg4e16_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16_v_bf16m2x4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlseg4.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m2x4_t test_vlseg4e16_v_bf16m2x4_tum(vbool8_t vm, vbfloat16m2x4_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg4e16_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16_v_bf16mf4x4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlseg4.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf4x4_t test_vlseg4e16_v_bf16mf4x4_tumu(vbool64_t vm, + vbfloat16mf4x4_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg4e16_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16_v_bf16mf2x4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlseg4.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf2x4_t test_vlseg4e16_v_bf16mf2x4_tumu(vbool32_t vm, + vbfloat16mf2x4_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg4e16_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16_v_bf16m1x4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlseg4.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m1x4_t test_vlseg4e16_v_bf16m1x4_tumu(vbool16_t vm, vbfloat16m1x4_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg4e16_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16_v_bf16m2x4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlseg4.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m2x4_t test_vlseg4e16_v_bf16m2x4_tumu(vbool8_t vm, vbfloat16m2x4_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg4e16_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16_v_bf16mf4x4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlseg4.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf4x4_t test_vlseg4e16_v_bf16mf4x4_mu(vbool64_t vm, + vbfloat16mf4x4_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg4e16_mu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16_v_bf16mf2x4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlseg4.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf2x4_t test_vlseg4e16_v_bf16mf2x4_mu(vbool32_t vm, + vbfloat16mf2x4_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg4e16_mu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16_v_bf16m1x4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlseg4.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m1x4_t test_vlseg4e16_v_bf16m1x4_mu(vbool16_t vm, vbfloat16m1x4_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg4e16_mu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16_v_bf16m2x4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlseg4.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m2x4_t test_vlseg4e16_v_bf16m2x4_mu(vbool8_t vm, vbfloat16m2x4_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg4e16_mu(vm, vd, rs1, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlseg4e16ff.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlseg4e16ff.c new file mode 100644 index 0000000000000000000000000000000000000000..b16766c184d16c42549ce3eb0de774deb2c518e6 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlseg4e16ff.c @@ -0,0 +1,434 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16ff_v_bf16mf4x4_tu( +// CHECK-RV64-SAME: { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , , i64 } @llvm.riscv.vlseg4ff.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , } poison, [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , } [[TMP6]], [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , } [[TMP8]], [[TMP9]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 3 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , } [[TMP10]], [[TMP11]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 4 +// CHECK-RV64-NEXT: store i64 [[TMP13]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , } [[TMP12]] +// +vbfloat16mf4x4_t test_vlseg4e16ff_v_bf16mf4x4_tu(vbfloat16mf4x4_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg4e16ff_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16ff_v_bf16mf2x4_tu( +// CHECK-RV64-SAME: { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , , i64 } @llvm.riscv.vlseg4ff.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , } poison, [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , } [[TMP6]], [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , } [[TMP8]], [[TMP9]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 3 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , } [[TMP10]], [[TMP11]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 4 +// CHECK-RV64-NEXT: store i64 [[TMP13]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , } [[TMP12]] +// +vbfloat16mf2x4_t test_vlseg4e16ff_v_bf16mf2x4_tu(vbfloat16mf2x4_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg4e16ff_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16ff_v_bf16m1x4_tu( +// CHECK-RV64-SAME: { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , , i64 } @llvm.riscv.vlseg4ff.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , } poison, [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , } [[TMP6]], [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , } [[TMP8]], [[TMP9]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 3 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , } [[TMP10]], [[TMP11]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 4 +// CHECK-RV64-NEXT: store i64 [[TMP13]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , } [[TMP12]] +// +vbfloat16m1x4_t test_vlseg4e16ff_v_bf16m1x4_tu(vbfloat16m1x4_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg4e16ff_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16ff_v_bf16m2x4_tu( +// CHECK-RV64-SAME: { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , , i64 } @llvm.riscv.vlseg4ff.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , } poison, [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , } [[TMP6]], [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , } [[TMP8]], [[TMP9]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 3 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , } [[TMP10]], [[TMP11]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 4 +// CHECK-RV64-NEXT: store i64 [[TMP13]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , } [[TMP12]] +// +vbfloat16m2x4_t test_vlseg4e16ff_v_bf16m2x4_tu(vbfloat16m2x4_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg4e16ff_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16ff_v_bf16mf4x4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , , i64 } @llvm.riscv.vlseg4ff.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , } poison, [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , } [[TMP6]], [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , } [[TMP8]], [[TMP9]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 3 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , } [[TMP10]], [[TMP11]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 4 +// CHECK-RV64-NEXT: store i64 [[TMP13]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , } [[TMP12]] +// +vbfloat16mf4x4_t test_vlseg4e16ff_v_bf16mf4x4_tum(vbool64_t vm, + vbfloat16mf4x4_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg4e16ff_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16ff_v_bf16mf2x4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , , i64 } @llvm.riscv.vlseg4ff.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , } poison, [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , } [[TMP6]], [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , } [[TMP8]], [[TMP9]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 3 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , } [[TMP10]], [[TMP11]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 4 +// CHECK-RV64-NEXT: store i64 [[TMP13]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , } [[TMP12]] +// +vbfloat16mf2x4_t test_vlseg4e16ff_v_bf16mf2x4_tum(vbool32_t vm, + vbfloat16mf2x4_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg4e16ff_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16ff_v_bf16m1x4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , , i64 } @llvm.riscv.vlseg4ff.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , } poison, [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , } [[TMP6]], [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , } [[TMP8]], [[TMP9]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 3 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , } [[TMP10]], [[TMP11]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 4 +// CHECK-RV64-NEXT: store i64 [[TMP13]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , } [[TMP12]] +// +vbfloat16m1x4_t test_vlseg4e16ff_v_bf16m1x4_tum(vbool16_t vm, + vbfloat16m1x4_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg4e16ff_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16ff_v_bf16m2x4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , , i64 } @llvm.riscv.vlseg4ff.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , } poison, [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , } [[TMP6]], [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , } [[TMP8]], [[TMP9]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 3 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , } [[TMP10]], [[TMP11]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 4 +// CHECK-RV64-NEXT: store i64 [[TMP13]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , } [[TMP12]] +// +vbfloat16m2x4_t test_vlseg4e16ff_v_bf16m2x4_tum(vbool8_t vm, vbfloat16m2x4_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg4e16ff_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16ff_v_bf16mf4x4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , , i64 } @llvm.riscv.vlseg4ff.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , } poison, [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , } [[TMP6]], [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , } [[TMP8]], [[TMP9]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 3 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , } [[TMP10]], [[TMP11]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 4 +// CHECK-RV64-NEXT: store i64 [[TMP13]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , } [[TMP12]] +// +vbfloat16mf4x4_t test_vlseg4e16ff_v_bf16mf4x4_tumu(vbool64_t vm, + vbfloat16mf4x4_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg4e16ff_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16ff_v_bf16mf2x4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , , i64 } @llvm.riscv.vlseg4ff.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , } poison, [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , } [[TMP6]], [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , } [[TMP8]], [[TMP9]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 3 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , } [[TMP10]], [[TMP11]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 4 +// CHECK-RV64-NEXT: store i64 [[TMP13]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , } [[TMP12]] +// +vbfloat16mf2x4_t test_vlseg4e16ff_v_bf16mf2x4_tumu(vbool32_t vm, + vbfloat16mf2x4_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg4e16ff_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16ff_v_bf16m1x4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , , i64 } @llvm.riscv.vlseg4ff.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , } poison, [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , } [[TMP6]], [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , } [[TMP8]], [[TMP9]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 3 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , } [[TMP10]], [[TMP11]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 4 +// CHECK-RV64-NEXT: store i64 [[TMP13]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , } [[TMP12]] +// +vbfloat16m1x4_t test_vlseg4e16ff_v_bf16m1x4_tumu(vbool16_t vm, + vbfloat16m1x4_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg4e16ff_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16ff_v_bf16m2x4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , , i64 } @llvm.riscv.vlseg4ff.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , } poison, [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , } [[TMP6]], [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , } [[TMP8]], [[TMP9]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 3 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , } [[TMP10]], [[TMP11]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 4 +// CHECK-RV64-NEXT: store i64 [[TMP13]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , } [[TMP12]] +// +vbfloat16m2x4_t test_vlseg4e16ff_v_bf16m2x4_tumu(vbool8_t vm, + vbfloat16m2x4_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg4e16ff_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16ff_v_bf16mf4x4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , , i64 } @llvm.riscv.vlseg4ff.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , } poison, [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , } [[TMP6]], [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , } [[TMP8]], [[TMP9]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 3 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , } [[TMP10]], [[TMP11]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 4 +// CHECK-RV64-NEXT: store i64 [[TMP13]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , } [[TMP12]] +// +vbfloat16mf4x4_t test_vlseg4e16ff_v_bf16mf4x4_mu(vbool64_t vm, + vbfloat16mf4x4_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg4e16ff_mu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16ff_v_bf16mf2x4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , , i64 } @llvm.riscv.vlseg4ff.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , } poison, [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , } [[TMP6]], [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , } [[TMP8]], [[TMP9]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 3 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , } [[TMP10]], [[TMP11]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 4 +// CHECK-RV64-NEXT: store i64 [[TMP13]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , } [[TMP12]] +// +vbfloat16mf2x4_t test_vlseg4e16ff_v_bf16mf2x4_mu(vbool32_t vm, + vbfloat16mf2x4_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg4e16ff_mu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16ff_v_bf16m1x4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , , i64 } @llvm.riscv.vlseg4ff.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , } poison, [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , } [[TMP6]], [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , } [[TMP8]], [[TMP9]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 3 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , } [[TMP10]], [[TMP11]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 4 +// CHECK-RV64-NEXT: store i64 [[TMP13]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , } [[TMP12]] +// +vbfloat16m1x4_t test_vlseg4e16ff_v_bf16m1x4_mu(vbool16_t vm, vbfloat16m1x4_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg4e16ff_mu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlseg4e16ff_v_bf16m2x4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , , i64 } @llvm.riscv.vlseg4ff.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 0 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = insertvalue { , , , } poison, [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 1 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , } [[TMP6]], [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 2 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , } [[TMP8]], [[TMP9]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 3 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , } [[TMP10]], [[TMP11]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , i64 } [[TMP4]], 4 +// CHECK-RV64-NEXT: store i64 [[TMP13]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , } [[TMP12]] +// +vbfloat16m2x4_t test_vlseg4e16ff_v_bf16m2x4_mu(vbool8_t vm, vbfloat16m2x4_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg4e16ff_mu(vm, vd, rs1, new_vl, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlseg5e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlseg5e16.c new file mode 100644 index 0000000000000000000000000000000000000000..8b8fb4457de2b282f9bc54a4d7b802fcdf580e7b --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlseg5e16.c @@ -0,0 +1,207 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16_v_bf16mf4x5_tu( +// CHECK-RV64-SAME: { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vlseg5.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf4x5_t test_vlseg5e16_v_bf16mf4x5_tu(vbfloat16mf4x5_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg5e16_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16_v_bf16mf2x5_tu( +// CHECK-RV64-SAME: { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vlseg5.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf2x5_t test_vlseg5e16_v_bf16mf2x5_tu(vbfloat16mf2x5_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg5e16_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16_v_bf16m1x5_tu( +// CHECK-RV64-SAME: { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vlseg5.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16m1x5_t test_vlseg5e16_v_bf16m1x5_tu(vbfloat16m1x5_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg5e16_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16_v_bf16mf4x5_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vlseg5.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf4x5_t test_vlseg5e16_v_bf16mf4x5_tum(vbool64_t vm, + vbfloat16mf4x5_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg5e16_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16_v_bf16mf2x5_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vlseg5.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf2x5_t test_vlseg5e16_v_bf16mf2x5_tum(vbool32_t vm, + vbfloat16mf2x5_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg5e16_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16_v_bf16m1x5_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vlseg5.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16m1x5_t test_vlseg5e16_v_bf16m1x5_tum(vbool16_t vm, vbfloat16m1x5_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg5e16_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16_v_bf16mf4x5_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vlseg5.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf4x5_t test_vlseg5e16_v_bf16mf4x5_tumu(vbool64_t vm, + vbfloat16mf4x5_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg5e16_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16_v_bf16mf2x5_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vlseg5.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf2x5_t test_vlseg5e16_v_bf16mf2x5_tumu(vbool32_t vm, + vbfloat16mf2x5_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg5e16_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16_v_bf16m1x5_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vlseg5.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16m1x5_t test_vlseg5e16_v_bf16m1x5_tumu(vbool16_t vm, vbfloat16m1x5_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg5e16_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16_v_bf16mf4x5_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vlseg5.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf4x5_t test_vlseg5e16_v_bf16mf4x5_mu(vbool64_t vm, + vbfloat16mf4x5_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg5e16_mu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16_v_bf16mf2x5_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vlseg5.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf2x5_t test_vlseg5e16_v_bf16mf2x5_mu(vbool32_t vm, + vbfloat16mf2x5_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg5e16_mu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16_v_bf16m1x5_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vlseg5.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16m1x5_t test_vlseg5e16_v_bf16m1x5_mu(vbool16_t vm, vbfloat16m1x5_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg5e16_mu(vm, vd, rs1, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlseg5e16ff.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlseg5e16ff.c new file mode 100644 index 0000000000000000000000000000000000000000..7aab7e9e205da96594bf0decf59ec3f3ef71b0ae --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlseg5e16ff.c @@ -0,0 +1,365 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16ff_v_bf16mf4x5_tu( +// CHECK-RV64-SAME: { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , , i64 } @llvm.riscv.vlseg5ff.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , , , } poison, [[TMP6]], 0 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , , , } [[TMP7]], [[TMP8]], 1 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = insertvalue { , , , , } [[TMP9]], [[TMP10]], 2 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = insertvalue { , , , , } [[TMP11]], [[TMP12]], 3 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 4 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = insertvalue { , , , , } [[TMP13]], [[TMP14]], 4 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 5 +// CHECK-RV64-NEXT: store i64 [[TMP16]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , } [[TMP15]] +// +vbfloat16mf4x5_t test_vlseg5e16ff_v_bf16mf4x5_tu(vbfloat16mf4x5_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg5e16ff_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16ff_v_bf16mf2x5_tu( +// CHECK-RV64-SAME: { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , , i64 } @llvm.riscv.vlseg5ff.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , , , } poison, [[TMP6]], 0 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , , , } [[TMP7]], [[TMP8]], 1 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = insertvalue { , , , , } [[TMP9]], [[TMP10]], 2 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = insertvalue { , , , , } [[TMP11]], [[TMP12]], 3 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 4 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = insertvalue { , , , , } [[TMP13]], [[TMP14]], 4 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 5 +// CHECK-RV64-NEXT: store i64 [[TMP16]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , } [[TMP15]] +// +vbfloat16mf2x5_t test_vlseg5e16ff_v_bf16mf2x5_tu(vbfloat16mf2x5_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg5e16ff_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16ff_v_bf16m1x5_tu( +// CHECK-RV64-SAME: { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , , i64 } @llvm.riscv.vlseg5ff.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , , , } poison, [[TMP6]], 0 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , , , } [[TMP7]], [[TMP8]], 1 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = insertvalue { , , , , } [[TMP9]], [[TMP10]], 2 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = insertvalue { , , , , } [[TMP11]], [[TMP12]], 3 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 4 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = insertvalue { , , , , } [[TMP13]], [[TMP14]], 4 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 5 +// CHECK-RV64-NEXT: store i64 [[TMP16]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , } [[TMP15]] +// +vbfloat16m1x5_t test_vlseg5e16ff_v_bf16m1x5_tu(vbfloat16m1x5_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg5e16ff_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16ff_v_bf16mf4x5_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , , i64 } @llvm.riscv.vlseg5ff.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , , , } poison, [[TMP6]], 0 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , , , } [[TMP7]], [[TMP8]], 1 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = insertvalue { , , , , } [[TMP9]], [[TMP10]], 2 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = insertvalue { , , , , } [[TMP11]], [[TMP12]], 3 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 4 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = insertvalue { , , , , } [[TMP13]], [[TMP14]], 4 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 5 +// CHECK-RV64-NEXT: store i64 [[TMP16]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , } [[TMP15]] +// +vbfloat16mf4x5_t test_vlseg5e16ff_v_bf16mf4x5_tum(vbool64_t vm, + vbfloat16mf4x5_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg5e16ff_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16ff_v_bf16mf2x5_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , , i64 } @llvm.riscv.vlseg5ff.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , , , } poison, [[TMP6]], 0 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , , , } [[TMP7]], [[TMP8]], 1 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = insertvalue { , , , , } [[TMP9]], [[TMP10]], 2 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = insertvalue { , , , , } [[TMP11]], [[TMP12]], 3 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 4 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = insertvalue { , , , , } [[TMP13]], [[TMP14]], 4 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 5 +// CHECK-RV64-NEXT: store i64 [[TMP16]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , } [[TMP15]] +// +vbfloat16mf2x5_t test_vlseg5e16ff_v_bf16mf2x5_tum(vbool32_t vm, + vbfloat16mf2x5_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg5e16ff_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16ff_v_bf16m1x5_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , , i64 } @llvm.riscv.vlseg5ff.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , , , } poison, [[TMP6]], 0 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , , , } [[TMP7]], [[TMP8]], 1 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = insertvalue { , , , , } [[TMP9]], [[TMP10]], 2 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = insertvalue { , , , , } [[TMP11]], [[TMP12]], 3 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 4 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = insertvalue { , , , , } [[TMP13]], [[TMP14]], 4 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 5 +// CHECK-RV64-NEXT: store i64 [[TMP16]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , } [[TMP15]] +// +vbfloat16m1x5_t test_vlseg5e16ff_v_bf16m1x5_tum(vbool16_t vm, + vbfloat16m1x5_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg5e16ff_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16ff_v_bf16mf4x5_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , , i64 } @llvm.riscv.vlseg5ff.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , , , } poison, [[TMP6]], 0 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , , , } [[TMP7]], [[TMP8]], 1 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = insertvalue { , , , , } [[TMP9]], [[TMP10]], 2 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = insertvalue { , , , , } [[TMP11]], [[TMP12]], 3 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 4 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = insertvalue { , , , , } [[TMP13]], [[TMP14]], 4 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 5 +// CHECK-RV64-NEXT: store i64 [[TMP16]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , } [[TMP15]] +// +vbfloat16mf4x5_t test_vlseg5e16ff_v_bf16mf4x5_tumu(vbool64_t vm, + vbfloat16mf4x5_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg5e16ff_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16ff_v_bf16mf2x5_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , , i64 } @llvm.riscv.vlseg5ff.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , , , } poison, [[TMP6]], 0 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , , , } [[TMP7]], [[TMP8]], 1 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = insertvalue { , , , , } [[TMP9]], [[TMP10]], 2 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = insertvalue { , , , , } [[TMP11]], [[TMP12]], 3 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 4 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = insertvalue { , , , , } [[TMP13]], [[TMP14]], 4 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 5 +// CHECK-RV64-NEXT: store i64 [[TMP16]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , } [[TMP15]] +// +vbfloat16mf2x5_t test_vlseg5e16ff_v_bf16mf2x5_tumu(vbool32_t vm, + vbfloat16mf2x5_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg5e16ff_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16ff_v_bf16m1x5_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , , i64 } @llvm.riscv.vlseg5ff.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , , , } poison, [[TMP6]], 0 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , , , } [[TMP7]], [[TMP8]], 1 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = insertvalue { , , , , } [[TMP9]], [[TMP10]], 2 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = insertvalue { , , , , } [[TMP11]], [[TMP12]], 3 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 4 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = insertvalue { , , , , } [[TMP13]], [[TMP14]], 4 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 5 +// CHECK-RV64-NEXT: store i64 [[TMP16]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , } [[TMP15]] +// +vbfloat16m1x5_t test_vlseg5e16ff_v_bf16m1x5_tumu(vbool16_t vm, + vbfloat16m1x5_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg5e16ff_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16ff_v_bf16mf4x5_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , , i64 } @llvm.riscv.vlseg5ff.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , , , } poison, [[TMP6]], 0 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , , , } [[TMP7]], [[TMP8]], 1 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = insertvalue { , , , , } [[TMP9]], [[TMP10]], 2 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = insertvalue { , , , , } [[TMP11]], [[TMP12]], 3 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 4 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = insertvalue { , , , , } [[TMP13]], [[TMP14]], 4 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 5 +// CHECK-RV64-NEXT: store i64 [[TMP16]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , } [[TMP15]] +// +vbfloat16mf4x5_t test_vlseg5e16ff_v_bf16mf4x5_mu(vbool64_t vm, + vbfloat16mf4x5_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg5e16ff_mu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16ff_v_bf16mf2x5_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , , i64 } @llvm.riscv.vlseg5ff.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , , , } poison, [[TMP6]], 0 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , , , } [[TMP7]], [[TMP8]], 1 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = insertvalue { , , , , } [[TMP9]], [[TMP10]], 2 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = insertvalue { , , , , } [[TMP11]], [[TMP12]], 3 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 4 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = insertvalue { , , , , } [[TMP13]], [[TMP14]], 4 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 5 +// CHECK-RV64-NEXT: store i64 [[TMP16]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , } [[TMP15]] +// +vbfloat16mf2x5_t test_vlseg5e16ff_v_bf16mf2x5_mu(vbool32_t vm, + vbfloat16mf2x5_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg5e16ff_mu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlseg5e16ff_v_bf16m1x5_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , , i64 } @llvm.riscv.vlseg5ff.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 0 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = insertvalue { , , , , } poison, [[TMP6]], 0 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 1 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , , , } [[TMP7]], [[TMP8]], 1 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 2 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = insertvalue { , , , , } [[TMP9]], [[TMP10]], 2 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 3 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = insertvalue { , , , , } [[TMP11]], [[TMP12]], 3 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 4 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = insertvalue { , , , , } [[TMP13]], [[TMP14]], 4 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = extractvalue { , , , , , i64 } [[TMP5]], 5 +// CHECK-RV64-NEXT: store i64 [[TMP16]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , } [[TMP15]] +// +vbfloat16m1x5_t test_vlseg5e16ff_v_bf16m1x5_mu(vbool16_t vm, vbfloat16m1x5_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg5e16ff_mu(vm, vd, rs1, new_vl, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlseg6e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlseg6e16.c new file mode 100644 index 0000000000000000000000000000000000000000..916997df7eb2dd1f1624e8e03b2ab25cd336cbe7 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlseg6e16.c @@ -0,0 +1,219 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16_v_bf16mf4x6_tu( +// CHECK-RV64-SAME: { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vlseg6.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf4x6_t test_vlseg6e16_v_bf16mf4x6_tu(vbfloat16mf4x6_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg6e16_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16_v_bf16mf2x6_tu( +// CHECK-RV64-SAME: { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vlseg6.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf2x6_t test_vlseg6e16_v_bf16mf2x6_tu(vbfloat16mf2x6_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg6e16_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16_v_bf16m1x6_tu( +// CHECK-RV64-SAME: { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vlseg6.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16m1x6_t test_vlseg6e16_v_bf16m1x6_tu(vbfloat16m1x6_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg6e16_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16_v_bf16mf4x6_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vlseg6.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf4x6_t test_vlseg6e16_v_bf16mf4x6_tum(vbool64_t vm, + vbfloat16mf4x6_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg6e16_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16_v_bf16mf2x6_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vlseg6.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf2x6_t test_vlseg6e16_v_bf16mf2x6_tum(vbool32_t vm, + vbfloat16mf2x6_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg6e16_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16_v_bf16m1x6_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vlseg6.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16m1x6_t test_vlseg6e16_v_bf16m1x6_tum(vbool16_t vm, vbfloat16m1x6_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg6e16_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16_v_bf16mf4x6_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vlseg6.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf4x6_t test_vlseg6e16_v_bf16mf4x6_tumu(vbool64_t vm, + vbfloat16mf4x6_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg6e16_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16_v_bf16mf2x6_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vlseg6.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf2x6_t test_vlseg6e16_v_bf16mf2x6_tumu(vbool32_t vm, + vbfloat16mf2x6_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg6e16_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16_v_bf16m1x6_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vlseg6.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16m1x6_t test_vlseg6e16_v_bf16m1x6_tumu(vbool16_t vm, vbfloat16m1x6_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg6e16_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16_v_bf16mf4x6_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vlseg6.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf4x6_t test_vlseg6e16_v_bf16mf4x6_mu(vbool64_t vm, + vbfloat16mf4x6_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg6e16_mu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16_v_bf16mf2x6_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vlseg6.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf2x6_t test_vlseg6e16_v_bf16mf2x6_mu(vbool32_t vm, + vbfloat16mf2x6_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg6e16_mu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16_v_bf16m1x6_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vlseg6.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16m1x6_t test_vlseg6e16_v_bf16m1x6_mu(vbool16_t vm, vbfloat16m1x6_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg6e16_mu(vm, vd, rs1, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlseg6e16ff.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlseg6e16ff.c new file mode 100644 index 0000000000000000000000000000000000000000..7d269acd4a1adf956cfb93732e6d7e85f74ad133 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlseg6e16ff.c @@ -0,0 +1,401 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16ff_v_bf16mf4x6_tu( +// CHECK-RV64-SAME: { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , , i64 } @llvm.riscv.vlseg6ff.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 0 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , } poison, [[TMP7]], 0 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , } [[TMP8]], [[TMP9]], 1 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 2 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , } [[TMP10]], [[TMP11]], 2 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 3 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , } [[TMP12]], [[TMP13]], 3 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 4 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , } [[TMP14]], [[TMP15]], 4 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 5 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = insertvalue { , , , , , } [[TMP16]], [[TMP17]], 5 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 6 +// CHECK-RV64-NEXT: store i64 [[TMP19]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP18]] +// +vbfloat16mf4x6_t test_vlseg6e16ff_v_bf16mf4x6_tu(vbfloat16mf4x6_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg6e16ff_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16ff_v_bf16mf2x6_tu( +// CHECK-RV64-SAME: { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , , i64 } @llvm.riscv.vlseg6ff.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 0 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , } poison, [[TMP7]], 0 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , } [[TMP8]], [[TMP9]], 1 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 2 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , } [[TMP10]], [[TMP11]], 2 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 3 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , } [[TMP12]], [[TMP13]], 3 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 4 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , } [[TMP14]], [[TMP15]], 4 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 5 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = insertvalue { , , , , , } [[TMP16]], [[TMP17]], 5 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 6 +// CHECK-RV64-NEXT: store i64 [[TMP19]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP18]] +// +vbfloat16mf2x6_t test_vlseg6e16ff_v_bf16mf2x6_tu(vbfloat16mf2x6_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg6e16ff_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16ff_v_bf16m1x6_tu( +// CHECK-RV64-SAME: { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , , i64 } @llvm.riscv.vlseg6ff.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 0 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , } poison, [[TMP7]], 0 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , } [[TMP8]], [[TMP9]], 1 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 2 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , } [[TMP10]], [[TMP11]], 2 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 3 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , } [[TMP12]], [[TMP13]], 3 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 4 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , } [[TMP14]], [[TMP15]], 4 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 5 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = insertvalue { , , , , , } [[TMP16]], [[TMP17]], 5 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 6 +// CHECK-RV64-NEXT: store i64 [[TMP19]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP18]] +// +vbfloat16m1x6_t test_vlseg6e16ff_v_bf16m1x6_tu(vbfloat16m1x6_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg6e16ff_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16ff_v_bf16mf4x6_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , , i64 } @llvm.riscv.vlseg6ff.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 0 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , } poison, [[TMP7]], 0 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , } [[TMP8]], [[TMP9]], 1 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 2 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , } [[TMP10]], [[TMP11]], 2 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 3 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , } [[TMP12]], [[TMP13]], 3 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 4 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , } [[TMP14]], [[TMP15]], 4 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 5 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = insertvalue { , , , , , } [[TMP16]], [[TMP17]], 5 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 6 +// CHECK-RV64-NEXT: store i64 [[TMP19]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP18]] +// +vbfloat16mf4x6_t test_vlseg6e16ff_v_bf16mf4x6_tum(vbool64_t vm, + vbfloat16mf4x6_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg6e16ff_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16ff_v_bf16mf2x6_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , , i64 } @llvm.riscv.vlseg6ff.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 0 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , } poison, [[TMP7]], 0 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , } [[TMP8]], [[TMP9]], 1 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 2 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , } [[TMP10]], [[TMP11]], 2 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 3 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , } [[TMP12]], [[TMP13]], 3 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 4 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , } [[TMP14]], [[TMP15]], 4 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 5 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = insertvalue { , , , , , } [[TMP16]], [[TMP17]], 5 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 6 +// CHECK-RV64-NEXT: store i64 [[TMP19]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP18]] +// +vbfloat16mf2x6_t test_vlseg6e16ff_v_bf16mf2x6_tum(vbool32_t vm, + vbfloat16mf2x6_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg6e16ff_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16ff_v_bf16m1x6_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , , i64 } @llvm.riscv.vlseg6ff.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 0 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , } poison, [[TMP7]], 0 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , } [[TMP8]], [[TMP9]], 1 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 2 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , } [[TMP10]], [[TMP11]], 2 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 3 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , } [[TMP12]], [[TMP13]], 3 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 4 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , } [[TMP14]], [[TMP15]], 4 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 5 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = insertvalue { , , , , , } [[TMP16]], [[TMP17]], 5 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 6 +// CHECK-RV64-NEXT: store i64 [[TMP19]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP18]] +// +vbfloat16m1x6_t test_vlseg6e16ff_v_bf16m1x6_tum(vbool16_t vm, + vbfloat16m1x6_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg6e16ff_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16ff_v_bf16mf4x6_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , , i64 } @llvm.riscv.vlseg6ff.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 0 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , } poison, [[TMP7]], 0 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , } [[TMP8]], [[TMP9]], 1 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 2 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , } [[TMP10]], [[TMP11]], 2 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 3 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , } [[TMP12]], [[TMP13]], 3 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 4 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , } [[TMP14]], [[TMP15]], 4 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 5 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = insertvalue { , , , , , } [[TMP16]], [[TMP17]], 5 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 6 +// CHECK-RV64-NEXT: store i64 [[TMP19]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP18]] +// +vbfloat16mf4x6_t test_vlseg6e16ff_v_bf16mf4x6_tumu(vbool64_t vm, + vbfloat16mf4x6_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg6e16ff_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16ff_v_bf16mf2x6_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , , i64 } @llvm.riscv.vlseg6ff.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 0 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , } poison, [[TMP7]], 0 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , } [[TMP8]], [[TMP9]], 1 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 2 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , } [[TMP10]], [[TMP11]], 2 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 3 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , } [[TMP12]], [[TMP13]], 3 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 4 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , } [[TMP14]], [[TMP15]], 4 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 5 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = insertvalue { , , , , , } [[TMP16]], [[TMP17]], 5 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 6 +// CHECK-RV64-NEXT: store i64 [[TMP19]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP18]] +// +vbfloat16mf2x6_t test_vlseg6e16ff_v_bf16mf2x6_tumu(vbool32_t vm, + vbfloat16mf2x6_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg6e16ff_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16ff_v_bf16m1x6_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , , i64 } @llvm.riscv.vlseg6ff.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 0 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , } poison, [[TMP7]], 0 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , } [[TMP8]], [[TMP9]], 1 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 2 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , } [[TMP10]], [[TMP11]], 2 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 3 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , } [[TMP12]], [[TMP13]], 3 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 4 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , } [[TMP14]], [[TMP15]], 4 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 5 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = insertvalue { , , , , , } [[TMP16]], [[TMP17]], 5 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 6 +// CHECK-RV64-NEXT: store i64 [[TMP19]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP18]] +// +vbfloat16m1x6_t test_vlseg6e16ff_v_bf16m1x6_tumu(vbool16_t vm, + vbfloat16m1x6_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg6e16ff_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16ff_v_bf16mf4x6_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , , i64 } @llvm.riscv.vlseg6ff.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 0 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , } poison, [[TMP7]], 0 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , } [[TMP8]], [[TMP9]], 1 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 2 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , } [[TMP10]], [[TMP11]], 2 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 3 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , } [[TMP12]], [[TMP13]], 3 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 4 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , } [[TMP14]], [[TMP15]], 4 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 5 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = insertvalue { , , , , , } [[TMP16]], [[TMP17]], 5 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 6 +// CHECK-RV64-NEXT: store i64 [[TMP19]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP18]] +// +vbfloat16mf4x6_t test_vlseg6e16ff_v_bf16mf4x6_mu(vbool64_t vm, + vbfloat16mf4x6_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg6e16ff_mu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16ff_v_bf16mf2x6_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , , i64 } @llvm.riscv.vlseg6ff.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 0 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , } poison, [[TMP7]], 0 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , } [[TMP8]], [[TMP9]], 1 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 2 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , } [[TMP10]], [[TMP11]], 2 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 3 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , } [[TMP12]], [[TMP13]], 3 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 4 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , } [[TMP14]], [[TMP15]], 4 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 5 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = insertvalue { , , , , , } [[TMP16]], [[TMP17]], 5 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 6 +// CHECK-RV64-NEXT: store i64 [[TMP19]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP18]] +// +vbfloat16mf2x6_t test_vlseg6e16ff_v_bf16mf2x6_mu(vbool32_t vm, + vbfloat16mf2x6_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg6e16ff_mu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlseg6e16ff_v_bf16m1x6_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , , i64 } @llvm.riscv.vlseg6ff.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 0 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = insertvalue { , , , , , } poison, [[TMP7]], 0 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 1 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , } [[TMP8]], [[TMP9]], 1 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 2 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , } [[TMP10]], [[TMP11]], 2 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 3 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , } [[TMP12]], [[TMP13]], 3 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 4 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , } [[TMP14]], [[TMP15]], 4 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 5 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = insertvalue { , , , , , } [[TMP16]], [[TMP17]], 5 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = extractvalue { , , , , , , i64 } [[TMP6]], 6 +// CHECK-RV64-NEXT: store i64 [[TMP19]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP18]] +// +vbfloat16m1x6_t test_vlseg6e16ff_v_bf16m1x6_mu(vbool16_t vm, vbfloat16m1x6_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg6e16ff_mu(vm, vd, rs1, new_vl, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlseg7e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlseg7e16.c new file mode 100644 index 0000000000000000000000000000000000000000..d664f6c24e4b156d2297dad73b3d244985c419fb --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlseg7e16.c @@ -0,0 +1,231 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16_v_bf16mf4x7_tu( +// CHECK-RV64-SAME: { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vlseg7.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf4x7_t test_vlseg7e16_v_bf16mf4x7_tu(vbfloat16mf4x7_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg7e16_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16_v_bf16mf2x7_tu( +// CHECK-RV64-SAME: { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vlseg7.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf2x7_t test_vlseg7e16_v_bf16mf2x7_tu(vbfloat16mf2x7_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg7e16_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16_v_bf16m1x7_tu( +// CHECK-RV64-SAME: { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vlseg7.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16m1x7_t test_vlseg7e16_v_bf16m1x7_tu(vbfloat16m1x7_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg7e16_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16_v_bf16mf4x7_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vlseg7.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf4x7_t test_vlseg7e16_v_bf16mf4x7_tum(vbool64_t vm, + vbfloat16mf4x7_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg7e16_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16_v_bf16mf2x7_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vlseg7.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf2x7_t test_vlseg7e16_v_bf16mf2x7_tum(vbool32_t vm, + vbfloat16mf2x7_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg7e16_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16_v_bf16m1x7_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vlseg7.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16m1x7_t test_vlseg7e16_v_bf16m1x7_tum(vbool16_t vm, vbfloat16m1x7_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg7e16_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16_v_bf16mf4x7_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vlseg7.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf4x7_t test_vlseg7e16_v_bf16mf4x7_tumu(vbool64_t vm, + vbfloat16mf4x7_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg7e16_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16_v_bf16mf2x7_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vlseg7.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf2x7_t test_vlseg7e16_v_bf16mf2x7_tumu(vbool32_t vm, + vbfloat16mf2x7_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg7e16_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16_v_bf16m1x7_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vlseg7.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16m1x7_t test_vlseg7e16_v_bf16m1x7_tumu(vbool16_t vm, vbfloat16m1x7_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg7e16_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16_v_bf16mf4x7_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vlseg7.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf4x7_t test_vlseg7e16_v_bf16mf4x7_mu(vbool64_t vm, + vbfloat16mf4x7_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg7e16_mu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16_v_bf16mf2x7_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vlseg7.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf2x7_t test_vlseg7e16_v_bf16mf2x7_mu(vbool32_t vm, + vbfloat16mf2x7_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg7e16_mu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16_v_bf16m1x7_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vlseg7.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16m1x7_t test_vlseg7e16_v_bf16m1x7_mu(vbool16_t vm, vbfloat16m1x7_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg7e16_mu(vm, vd, rs1, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlseg7e16ff.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlseg7e16ff.c new file mode 100644 index 0000000000000000000000000000000000000000..bf7920a7f613a031d9d981f83c48fafb4050e4a9 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlseg7e16ff.c @@ -0,0 +1,437 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16ff_v_bf16mf4x7_tu( +// CHECK-RV64-SAME: { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , , i64 } @llvm.riscv.vlseg7ff.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 0 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , , , , , } poison, [[TMP8]], 0 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = insertvalue { , , , , , , } [[TMP9]], [[TMP10]], 1 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 2 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = insertvalue { , , , , , , } [[TMP11]], [[TMP12]], 2 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = insertvalue { , , , , , , } [[TMP13]], [[TMP14]], 3 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 4 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = insertvalue { , , , , , , } [[TMP15]], [[TMP16]], 4 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 5 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = insertvalue { , , , , , , } [[TMP17]], [[TMP18]], 5 +// CHECK-RV64-NEXT: [[TMP20:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 6 +// CHECK-RV64-NEXT: [[TMP21:%.*]] = insertvalue { , , , , , , } [[TMP19]], [[TMP20]], 6 +// CHECK-RV64-NEXT: [[TMP22:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 7 +// CHECK-RV64-NEXT: store i64 [[TMP22]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP21]] +// +vbfloat16mf4x7_t test_vlseg7e16ff_v_bf16mf4x7_tu(vbfloat16mf4x7_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg7e16ff_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16ff_v_bf16mf2x7_tu( +// CHECK-RV64-SAME: { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , , i64 } @llvm.riscv.vlseg7ff.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 0 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , , , , , } poison, [[TMP8]], 0 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = insertvalue { , , , , , , } [[TMP9]], [[TMP10]], 1 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 2 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = insertvalue { , , , , , , } [[TMP11]], [[TMP12]], 2 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = insertvalue { , , , , , , } [[TMP13]], [[TMP14]], 3 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 4 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = insertvalue { , , , , , , } [[TMP15]], [[TMP16]], 4 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 5 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = insertvalue { , , , , , , } [[TMP17]], [[TMP18]], 5 +// CHECK-RV64-NEXT: [[TMP20:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 6 +// CHECK-RV64-NEXT: [[TMP21:%.*]] = insertvalue { , , , , , , } [[TMP19]], [[TMP20]], 6 +// CHECK-RV64-NEXT: [[TMP22:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 7 +// CHECK-RV64-NEXT: store i64 [[TMP22]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP21]] +// +vbfloat16mf2x7_t test_vlseg7e16ff_v_bf16mf2x7_tu(vbfloat16mf2x7_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg7e16ff_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16ff_v_bf16m1x7_tu( +// CHECK-RV64-SAME: { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , , i64 } @llvm.riscv.vlseg7ff.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 0 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , , , , , } poison, [[TMP8]], 0 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = insertvalue { , , , , , , } [[TMP9]], [[TMP10]], 1 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 2 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = insertvalue { , , , , , , } [[TMP11]], [[TMP12]], 2 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = insertvalue { , , , , , , } [[TMP13]], [[TMP14]], 3 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 4 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = insertvalue { , , , , , , } [[TMP15]], [[TMP16]], 4 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 5 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = insertvalue { , , , , , , } [[TMP17]], [[TMP18]], 5 +// CHECK-RV64-NEXT: [[TMP20:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 6 +// CHECK-RV64-NEXT: [[TMP21:%.*]] = insertvalue { , , , , , , } [[TMP19]], [[TMP20]], 6 +// CHECK-RV64-NEXT: [[TMP22:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 7 +// CHECK-RV64-NEXT: store i64 [[TMP22]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP21]] +// +vbfloat16m1x7_t test_vlseg7e16ff_v_bf16m1x7_tu(vbfloat16m1x7_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg7e16ff_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16ff_v_bf16mf4x7_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , , i64 } @llvm.riscv.vlseg7ff.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 0 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , , , , , } poison, [[TMP8]], 0 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = insertvalue { , , , , , , } [[TMP9]], [[TMP10]], 1 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 2 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = insertvalue { , , , , , , } [[TMP11]], [[TMP12]], 2 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = insertvalue { , , , , , , } [[TMP13]], [[TMP14]], 3 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 4 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = insertvalue { , , , , , , } [[TMP15]], [[TMP16]], 4 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 5 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = insertvalue { , , , , , , } [[TMP17]], [[TMP18]], 5 +// CHECK-RV64-NEXT: [[TMP20:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 6 +// CHECK-RV64-NEXT: [[TMP21:%.*]] = insertvalue { , , , , , , } [[TMP19]], [[TMP20]], 6 +// CHECK-RV64-NEXT: [[TMP22:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 7 +// CHECK-RV64-NEXT: store i64 [[TMP22]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP21]] +// +vbfloat16mf4x7_t test_vlseg7e16ff_v_bf16mf4x7_tum(vbool64_t vm, + vbfloat16mf4x7_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg7e16ff_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16ff_v_bf16mf2x7_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , , i64 } @llvm.riscv.vlseg7ff.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 0 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , , , , , } poison, [[TMP8]], 0 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = insertvalue { , , , , , , } [[TMP9]], [[TMP10]], 1 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 2 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = insertvalue { , , , , , , } [[TMP11]], [[TMP12]], 2 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = insertvalue { , , , , , , } [[TMP13]], [[TMP14]], 3 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 4 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = insertvalue { , , , , , , } [[TMP15]], [[TMP16]], 4 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 5 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = insertvalue { , , , , , , } [[TMP17]], [[TMP18]], 5 +// CHECK-RV64-NEXT: [[TMP20:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 6 +// CHECK-RV64-NEXT: [[TMP21:%.*]] = insertvalue { , , , , , , } [[TMP19]], [[TMP20]], 6 +// CHECK-RV64-NEXT: [[TMP22:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 7 +// CHECK-RV64-NEXT: store i64 [[TMP22]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP21]] +// +vbfloat16mf2x7_t test_vlseg7e16ff_v_bf16mf2x7_tum(vbool32_t vm, + vbfloat16mf2x7_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg7e16ff_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16ff_v_bf16m1x7_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , , i64 } @llvm.riscv.vlseg7ff.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 0 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , , , , , } poison, [[TMP8]], 0 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = insertvalue { , , , , , , } [[TMP9]], [[TMP10]], 1 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 2 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = insertvalue { , , , , , , } [[TMP11]], [[TMP12]], 2 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = insertvalue { , , , , , , } [[TMP13]], [[TMP14]], 3 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 4 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = insertvalue { , , , , , , } [[TMP15]], [[TMP16]], 4 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 5 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = insertvalue { , , , , , , } [[TMP17]], [[TMP18]], 5 +// CHECK-RV64-NEXT: [[TMP20:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 6 +// CHECK-RV64-NEXT: [[TMP21:%.*]] = insertvalue { , , , , , , } [[TMP19]], [[TMP20]], 6 +// CHECK-RV64-NEXT: [[TMP22:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 7 +// CHECK-RV64-NEXT: store i64 [[TMP22]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP21]] +// +vbfloat16m1x7_t test_vlseg7e16ff_v_bf16m1x7_tum(vbool16_t vm, + vbfloat16m1x7_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg7e16ff_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16ff_v_bf16mf4x7_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , , i64 } @llvm.riscv.vlseg7ff.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 0 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , , , , , } poison, [[TMP8]], 0 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = insertvalue { , , , , , , } [[TMP9]], [[TMP10]], 1 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 2 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = insertvalue { , , , , , , } [[TMP11]], [[TMP12]], 2 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = insertvalue { , , , , , , } [[TMP13]], [[TMP14]], 3 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 4 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = insertvalue { , , , , , , } [[TMP15]], [[TMP16]], 4 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 5 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = insertvalue { , , , , , , } [[TMP17]], [[TMP18]], 5 +// CHECK-RV64-NEXT: [[TMP20:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 6 +// CHECK-RV64-NEXT: [[TMP21:%.*]] = insertvalue { , , , , , , } [[TMP19]], [[TMP20]], 6 +// CHECK-RV64-NEXT: [[TMP22:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 7 +// CHECK-RV64-NEXT: store i64 [[TMP22]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP21]] +// +vbfloat16mf4x7_t test_vlseg7e16ff_v_bf16mf4x7_tumu(vbool64_t vm, + vbfloat16mf4x7_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg7e16ff_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16ff_v_bf16mf2x7_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , , i64 } @llvm.riscv.vlseg7ff.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 0 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , , , , , } poison, [[TMP8]], 0 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = insertvalue { , , , , , , } [[TMP9]], [[TMP10]], 1 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 2 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = insertvalue { , , , , , , } [[TMP11]], [[TMP12]], 2 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = insertvalue { , , , , , , } [[TMP13]], [[TMP14]], 3 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 4 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = insertvalue { , , , , , , } [[TMP15]], [[TMP16]], 4 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 5 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = insertvalue { , , , , , , } [[TMP17]], [[TMP18]], 5 +// CHECK-RV64-NEXT: [[TMP20:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 6 +// CHECK-RV64-NEXT: [[TMP21:%.*]] = insertvalue { , , , , , , } [[TMP19]], [[TMP20]], 6 +// CHECK-RV64-NEXT: [[TMP22:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 7 +// CHECK-RV64-NEXT: store i64 [[TMP22]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP21]] +// +vbfloat16mf2x7_t test_vlseg7e16ff_v_bf16mf2x7_tumu(vbool32_t vm, + vbfloat16mf2x7_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg7e16ff_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16ff_v_bf16m1x7_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , , i64 } @llvm.riscv.vlseg7ff.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 0 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , , , , , } poison, [[TMP8]], 0 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = insertvalue { , , , , , , } [[TMP9]], [[TMP10]], 1 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 2 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = insertvalue { , , , , , , } [[TMP11]], [[TMP12]], 2 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = insertvalue { , , , , , , } [[TMP13]], [[TMP14]], 3 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 4 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = insertvalue { , , , , , , } [[TMP15]], [[TMP16]], 4 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 5 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = insertvalue { , , , , , , } [[TMP17]], [[TMP18]], 5 +// CHECK-RV64-NEXT: [[TMP20:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 6 +// CHECK-RV64-NEXT: [[TMP21:%.*]] = insertvalue { , , , , , , } [[TMP19]], [[TMP20]], 6 +// CHECK-RV64-NEXT: [[TMP22:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 7 +// CHECK-RV64-NEXT: store i64 [[TMP22]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP21]] +// +vbfloat16m1x7_t test_vlseg7e16ff_v_bf16m1x7_tumu(vbool16_t vm, + vbfloat16m1x7_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg7e16ff_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16ff_v_bf16mf4x7_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , , i64 } @llvm.riscv.vlseg7ff.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 0 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , , , , , } poison, [[TMP8]], 0 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = insertvalue { , , , , , , } [[TMP9]], [[TMP10]], 1 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 2 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = insertvalue { , , , , , , } [[TMP11]], [[TMP12]], 2 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = insertvalue { , , , , , , } [[TMP13]], [[TMP14]], 3 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 4 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = insertvalue { , , , , , , } [[TMP15]], [[TMP16]], 4 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 5 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = insertvalue { , , , , , , } [[TMP17]], [[TMP18]], 5 +// CHECK-RV64-NEXT: [[TMP20:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 6 +// CHECK-RV64-NEXT: [[TMP21:%.*]] = insertvalue { , , , , , , } [[TMP19]], [[TMP20]], 6 +// CHECK-RV64-NEXT: [[TMP22:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 7 +// CHECK-RV64-NEXT: store i64 [[TMP22]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP21]] +// +vbfloat16mf4x7_t test_vlseg7e16ff_v_bf16mf4x7_mu(vbool64_t vm, + vbfloat16mf4x7_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg7e16ff_mu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16ff_v_bf16mf2x7_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , , i64 } @llvm.riscv.vlseg7ff.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 0 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , , , , , } poison, [[TMP8]], 0 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = insertvalue { , , , , , , } [[TMP9]], [[TMP10]], 1 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 2 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = insertvalue { , , , , , , } [[TMP11]], [[TMP12]], 2 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = insertvalue { , , , , , , } [[TMP13]], [[TMP14]], 3 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 4 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = insertvalue { , , , , , , } [[TMP15]], [[TMP16]], 4 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 5 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = insertvalue { , , , , , , } [[TMP17]], [[TMP18]], 5 +// CHECK-RV64-NEXT: [[TMP20:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 6 +// CHECK-RV64-NEXT: [[TMP21:%.*]] = insertvalue { , , , , , , } [[TMP19]], [[TMP20]], 6 +// CHECK-RV64-NEXT: [[TMP22:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 7 +// CHECK-RV64-NEXT: store i64 [[TMP22]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP21]] +// +vbfloat16mf2x7_t test_vlseg7e16ff_v_bf16mf2x7_mu(vbool32_t vm, + vbfloat16mf2x7_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg7e16ff_mu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlseg7e16ff_v_bf16m1x7_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , , i64 } @llvm.riscv.vlseg7ff.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP8:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 0 +// CHECK-RV64-NEXT: [[TMP9:%.*]] = insertvalue { , , , , , , } poison, [[TMP8]], 0 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 1 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = insertvalue { , , , , , , } [[TMP9]], [[TMP10]], 1 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 2 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = insertvalue { , , , , , , } [[TMP11]], [[TMP12]], 2 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 3 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = insertvalue { , , , , , , } [[TMP13]], [[TMP14]], 3 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 4 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = insertvalue { , , , , , , } [[TMP15]], [[TMP16]], 4 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 5 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = insertvalue { , , , , , , } [[TMP17]], [[TMP18]], 5 +// CHECK-RV64-NEXT: [[TMP20:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 6 +// CHECK-RV64-NEXT: [[TMP21:%.*]] = insertvalue { , , , , , , } [[TMP19]], [[TMP20]], 6 +// CHECK-RV64-NEXT: [[TMP22:%.*]] = extractvalue { , , , , , , , i64 } [[TMP7]], 7 +// CHECK-RV64-NEXT: store i64 [[TMP22]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP21]] +// +vbfloat16m1x7_t test_vlseg7e16ff_v_bf16m1x7_mu(vbool16_t vm, vbfloat16m1x7_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg7e16ff_mu(vm, vd, rs1, new_vl, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlseg8e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlseg8e16.c new file mode 100644 index 0000000000000000000000000000000000000000..66d7b64611f9a17c61d1a10bae26f56414dde176 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlseg8e16.c @@ -0,0 +1,243 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16_v_bf16mf4x8_tu( +// CHECK-RV64-SAME: { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vlseg8.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf4x8_t test_vlseg8e16_v_bf16mf4x8_tu(vbfloat16mf4x8_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg8e16_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16_v_bf16mf2x8_tu( +// CHECK-RV64-SAME: { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vlseg8.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf2x8_t test_vlseg8e16_v_bf16mf2x8_tu(vbfloat16mf2x8_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg8e16_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16_v_bf16m1x8_tu( +// CHECK-RV64-SAME: { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vlseg8.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16m1x8_t test_vlseg8e16_v_bf16m1x8_tu(vbfloat16m1x8_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg8e16_tu(vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16_v_bf16mf4x8_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vlseg8.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf4x8_t test_vlseg8e16_v_bf16mf4x8_tum(vbool64_t vm, + vbfloat16mf4x8_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg8e16_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16_v_bf16mf2x8_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vlseg8.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf2x8_t test_vlseg8e16_v_bf16mf2x8_tum(vbool32_t vm, + vbfloat16mf2x8_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg8e16_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16_v_bf16m1x8_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vlseg8.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16m1x8_t test_vlseg8e16_v_bf16m1x8_tum(vbool16_t vm, vbfloat16m1x8_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg8e16_tum(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16_v_bf16mf4x8_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vlseg8.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf4x8_t test_vlseg8e16_v_bf16mf4x8_tumu(vbool64_t vm, + vbfloat16mf4x8_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg8e16_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16_v_bf16mf2x8_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vlseg8.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf2x8_t test_vlseg8e16_v_bf16mf2x8_tumu(vbool32_t vm, + vbfloat16mf2x8_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg8e16_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16_v_bf16m1x8_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vlseg8.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16m1x8_t test_vlseg8e16_v_bf16m1x8_tumu(vbool16_t vm, vbfloat16m1x8_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg8e16_tumu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16_v_bf16mf4x8_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vlseg8.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf4x8_t test_vlseg8e16_v_bf16mf4x8_mu(vbool64_t vm, + vbfloat16mf4x8_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg8e16_mu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16_v_bf16mf2x8_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vlseg8.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf2x8_t test_vlseg8e16_v_bf16mf2x8_mu(vbool32_t vm, + vbfloat16mf2x8_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg8e16_mu(vm, vd, rs1, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16_v_bf16m1x8_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vlseg8.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16m1x8_t test_vlseg8e16_v_bf16m1x8_mu(vbool16_t vm, vbfloat16m1x8_t vd, + const __bf16 *rs1, size_t vl) { + return __riscv_vlseg8e16_mu(vm, vd, rs1, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlseg8e16ff.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlseg8e16ff.c new file mode 100644 index 0000000000000000000000000000000000000000..049984355afee70f4bc9f12461690d22af64d6a7 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlseg8e16ff.c @@ -0,0 +1,473 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16ff_v_bf16mf4x8_tu( +// CHECK-RV64-SAME: { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , , i64 } @llvm.riscv.vlseg8ff.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 0 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , , , } poison, [[TMP9]], 0 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 1 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , , , } [[TMP10]], [[TMP11]], 1 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , , , } [[TMP12]], [[TMP13]], 2 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 3 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , , , } [[TMP14]], [[TMP15]], 3 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 4 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = insertvalue { , , , , , , , } [[TMP16]], [[TMP17]], 4 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 5 +// CHECK-RV64-NEXT: [[TMP20:%.*]] = insertvalue { , , , , , , , } [[TMP18]], [[TMP19]], 5 +// CHECK-RV64-NEXT: [[TMP21:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 6 +// CHECK-RV64-NEXT: [[TMP22:%.*]] = insertvalue { , , , , , , , } [[TMP20]], [[TMP21]], 6 +// CHECK-RV64-NEXT: [[TMP23:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 7 +// CHECK-RV64-NEXT: [[TMP24:%.*]] = insertvalue { , , , , , , , } [[TMP22]], [[TMP23]], 7 +// CHECK-RV64-NEXT: [[TMP25:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 8 +// CHECK-RV64-NEXT: store i64 [[TMP25]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP24]] +// +vbfloat16mf4x8_t test_vlseg8e16ff_v_bf16mf4x8_tu(vbfloat16mf4x8_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg8e16ff_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16ff_v_bf16mf2x8_tu( +// CHECK-RV64-SAME: { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , , i64 } @llvm.riscv.vlseg8ff.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 0 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , , , } poison, [[TMP9]], 0 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 1 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , , , } [[TMP10]], [[TMP11]], 1 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , , , } [[TMP12]], [[TMP13]], 2 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 3 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , , , } [[TMP14]], [[TMP15]], 3 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 4 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = insertvalue { , , , , , , , } [[TMP16]], [[TMP17]], 4 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 5 +// CHECK-RV64-NEXT: [[TMP20:%.*]] = insertvalue { , , , , , , , } [[TMP18]], [[TMP19]], 5 +// CHECK-RV64-NEXT: [[TMP21:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 6 +// CHECK-RV64-NEXT: [[TMP22:%.*]] = insertvalue { , , , , , , , } [[TMP20]], [[TMP21]], 6 +// CHECK-RV64-NEXT: [[TMP23:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 7 +// CHECK-RV64-NEXT: [[TMP24:%.*]] = insertvalue { , , , , , , , } [[TMP22]], [[TMP23]], 7 +// CHECK-RV64-NEXT: [[TMP25:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 8 +// CHECK-RV64-NEXT: store i64 [[TMP25]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP24]] +// +vbfloat16mf2x8_t test_vlseg8e16ff_v_bf16mf2x8_tu(vbfloat16mf2x8_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg8e16ff_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16ff_v_bf16m1x8_tu( +// CHECK-RV64-SAME: { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , , i64 } @llvm.riscv.vlseg8ff.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[VL]]) +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 0 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , , , } poison, [[TMP9]], 0 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 1 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , , , } [[TMP10]], [[TMP11]], 1 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , , , } [[TMP12]], [[TMP13]], 2 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 3 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , , , } [[TMP14]], [[TMP15]], 3 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 4 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = insertvalue { , , , , , , , } [[TMP16]], [[TMP17]], 4 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 5 +// CHECK-RV64-NEXT: [[TMP20:%.*]] = insertvalue { , , , , , , , } [[TMP18]], [[TMP19]], 5 +// CHECK-RV64-NEXT: [[TMP21:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 6 +// CHECK-RV64-NEXT: [[TMP22:%.*]] = insertvalue { , , , , , , , } [[TMP20]], [[TMP21]], 6 +// CHECK-RV64-NEXT: [[TMP23:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 7 +// CHECK-RV64-NEXT: [[TMP24:%.*]] = insertvalue { , , , , , , , } [[TMP22]], [[TMP23]], 7 +// CHECK-RV64-NEXT: [[TMP25:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 8 +// CHECK-RV64-NEXT: store i64 [[TMP25]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP24]] +// +vbfloat16m1x8_t test_vlseg8e16ff_v_bf16m1x8_tu(vbfloat16m1x8_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg8e16ff_tu(vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16ff_v_bf16mf4x8_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , , i64 } @llvm.riscv.vlseg8ff.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 0 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , , , } poison, [[TMP9]], 0 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 1 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , , , } [[TMP10]], [[TMP11]], 1 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , , , } [[TMP12]], [[TMP13]], 2 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 3 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , , , } [[TMP14]], [[TMP15]], 3 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 4 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = insertvalue { , , , , , , , } [[TMP16]], [[TMP17]], 4 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 5 +// CHECK-RV64-NEXT: [[TMP20:%.*]] = insertvalue { , , , , , , , } [[TMP18]], [[TMP19]], 5 +// CHECK-RV64-NEXT: [[TMP21:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 6 +// CHECK-RV64-NEXT: [[TMP22:%.*]] = insertvalue { , , , , , , , } [[TMP20]], [[TMP21]], 6 +// CHECK-RV64-NEXT: [[TMP23:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 7 +// CHECK-RV64-NEXT: [[TMP24:%.*]] = insertvalue { , , , , , , , } [[TMP22]], [[TMP23]], 7 +// CHECK-RV64-NEXT: [[TMP25:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 8 +// CHECK-RV64-NEXT: store i64 [[TMP25]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP24]] +// +vbfloat16mf4x8_t test_vlseg8e16ff_v_bf16mf4x8_tum(vbool64_t vm, + vbfloat16mf4x8_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg8e16ff_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16ff_v_bf16mf2x8_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , , i64 } @llvm.riscv.vlseg8ff.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 0 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , , , } poison, [[TMP9]], 0 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 1 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , , , } [[TMP10]], [[TMP11]], 1 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , , , } [[TMP12]], [[TMP13]], 2 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 3 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , , , } [[TMP14]], [[TMP15]], 3 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 4 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = insertvalue { , , , , , , , } [[TMP16]], [[TMP17]], 4 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 5 +// CHECK-RV64-NEXT: [[TMP20:%.*]] = insertvalue { , , , , , , , } [[TMP18]], [[TMP19]], 5 +// CHECK-RV64-NEXT: [[TMP21:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 6 +// CHECK-RV64-NEXT: [[TMP22:%.*]] = insertvalue { , , , , , , , } [[TMP20]], [[TMP21]], 6 +// CHECK-RV64-NEXT: [[TMP23:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 7 +// CHECK-RV64-NEXT: [[TMP24:%.*]] = insertvalue { , , , , , , , } [[TMP22]], [[TMP23]], 7 +// CHECK-RV64-NEXT: [[TMP25:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 8 +// CHECK-RV64-NEXT: store i64 [[TMP25]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP24]] +// +vbfloat16mf2x8_t test_vlseg8e16ff_v_bf16mf2x8_tum(vbool32_t vm, + vbfloat16mf2x8_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg8e16ff_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16ff_v_bf16m1x8_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , , i64 } @llvm.riscv.vlseg8ff.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 0 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , , , } poison, [[TMP9]], 0 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 1 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , , , } [[TMP10]], [[TMP11]], 1 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , , , } [[TMP12]], [[TMP13]], 2 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 3 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , , , } [[TMP14]], [[TMP15]], 3 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 4 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = insertvalue { , , , , , , , } [[TMP16]], [[TMP17]], 4 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 5 +// CHECK-RV64-NEXT: [[TMP20:%.*]] = insertvalue { , , , , , , , } [[TMP18]], [[TMP19]], 5 +// CHECK-RV64-NEXT: [[TMP21:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 6 +// CHECK-RV64-NEXT: [[TMP22:%.*]] = insertvalue { , , , , , , , } [[TMP20]], [[TMP21]], 6 +// CHECK-RV64-NEXT: [[TMP23:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 7 +// CHECK-RV64-NEXT: [[TMP24:%.*]] = insertvalue { , , , , , , , } [[TMP22]], [[TMP23]], 7 +// CHECK-RV64-NEXT: [[TMP25:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 8 +// CHECK-RV64-NEXT: store i64 [[TMP25]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP24]] +// +vbfloat16m1x8_t test_vlseg8e16ff_v_bf16m1x8_tum(vbool16_t vm, + vbfloat16m1x8_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg8e16ff_tum(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16ff_v_bf16mf4x8_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , , i64 } @llvm.riscv.vlseg8ff.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 0 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , , , } poison, [[TMP9]], 0 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 1 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , , , } [[TMP10]], [[TMP11]], 1 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , , , } [[TMP12]], [[TMP13]], 2 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 3 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , , , } [[TMP14]], [[TMP15]], 3 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 4 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = insertvalue { , , , , , , , } [[TMP16]], [[TMP17]], 4 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 5 +// CHECK-RV64-NEXT: [[TMP20:%.*]] = insertvalue { , , , , , , , } [[TMP18]], [[TMP19]], 5 +// CHECK-RV64-NEXT: [[TMP21:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 6 +// CHECK-RV64-NEXT: [[TMP22:%.*]] = insertvalue { , , , , , , , } [[TMP20]], [[TMP21]], 6 +// CHECK-RV64-NEXT: [[TMP23:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 7 +// CHECK-RV64-NEXT: [[TMP24:%.*]] = insertvalue { , , , , , , , } [[TMP22]], [[TMP23]], 7 +// CHECK-RV64-NEXT: [[TMP25:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 8 +// CHECK-RV64-NEXT: store i64 [[TMP25]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP24]] +// +vbfloat16mf4x8_t test_vlseg8e16ff_v_bf16mf4x8_tumu(vbool64_t vm, + vbfloat16mf4x8_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg8e16ff_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16ff_v_bf16mf2x8_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , , i64 } @llvm.riscv.vlseg8ff.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 0 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , , , } poison, [[TMP9]], 0 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 1 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , , , } [[TMP10]], [[TMP11]], 1 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , , , } [[TMP12]], [[TMP13]], 2 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 3 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , , , } [[TMP14]], [[TMP15]], 3 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 4 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = insertvalue { , , , , , , , } [[TMP16]], [[TMP17]], 4 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 5 +// CHECK-RV64-NEXT: [[TMP20:%.*]] = insertvalue { , , , , , , , } [[TMP18]], [[TMP19]], 5 +// CHECK-RV64-NEXT: [[TMP21:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 6 +// CHECK-RV64-NEXT: [[TMP22:%.*]] = insertvalue { , , , , , , , } [[TMP20]], [[TMP21]], 6 +// CHECK-RV64-NEXT: [[TMP23:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 7 +// CHECK-RV64-NEXT: [[TMP24:%.*]] = insertvalue { , , , , , , , } [[TMP22]], [[TMP23]], 7 +// CHECK-RV64-NEXT: [[TMP25:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 8 +// CHECK-RV64-NEXT: store i64 [[TMP25]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP24]] +// +vbfloat16mf2x8_t test_vlseg8e16ff_v_bf16mf2x8_tumu(vbool32_t vm, + vbfloat16mf2x8_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg8e16ff_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16ff_v_bf16m1x8_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , , i64 } @llvm.riscv.vlseg8ff.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 0 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , , , } poison, [[TMP9]], 0 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 1 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , , , } [[TMP10]], [[TMP11]], 1 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , , , } [[TMP12]], [[TMP13]], 2 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 3 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , , , } [[TMP14]], [[TMP15]], 3 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 4 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = insertvalue { , , , , , , , } [[TMP16]], [[TMP17]], 4 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 5 +// CHECK-RV64-NEXT: [[TMP20:%.*]] = insertvalue { , , , , , , , } [[TMP18]], [[TMP19]], 5 +// CHECK-RV64-NEXT: [[TMP21:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 6 +// CHECK-RV64-NEXT: [[TMP22:%.*]] = insertvalue { , , , , , , , } [[TMP20]], [[TMP21]], 6 +// CHECK-RV64-NEXT: [[TMP23:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 7 +// CHECK-RV64-NEXT: [[TMP24:%.*]] = insertvalue { , , , , , , , } [[TMP22]], [[TMP23]], 7 +// CHECK-RV64-NEXT: [[TMP25:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 8 +// CHECK-RV64-NEXT: store i64 [[TMP25]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP24]] +// +vbfloat16m1x8_t test_vlseg8e16ff_v_bf16m1x8_tumu(vbool16_t vm, + vbfloat16m1x8_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg8e16ff_tumu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16ff_v_bf16mf4x8_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , , i64 } @llvm.riscv.vlseg8ff.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 0 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , , , } poison, [[TMP9]], 0 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 1 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , , , } [[TMP10]], [[TMP11]], 1 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , , , } [[TMP12]], [[TMP13]], 2 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 3 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , , , } [[TMP14]], [[TMP15]], 3 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 4 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = insertvalue { , , , , , , , } [[TMP16]], [[TMP17]], 4 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 5 +// CHECK-RV64-NEXT: [[TMP20:%.*]] = insertvalue { , , , , , , , } [[TMP18]], [[TMP19]], 5 +// CHECK-RV64-NEXT: [[TMP21:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 6 +// CHECK-RV64-NEXT: [[TMP22:%.*]] = insertvalue { , , , , , , , } [[TMP20]], [[TMP21]], 6 +// CHECK-RV64-NEXT: [[TMP23:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 7 +// CHECK-RV64-NEXT: [[TMP24:%.*]] = insertvalue { , , , , , , , } [[TMP22]], [[TMP23]], 7 +// CHECK-RV64-NEXT: [[TMP25:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 8 +// CHECK-RV64-NEXT: store i64 [[TMP25]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP24]] +// +vbfloat16mf4x8_t test_vlseg8e16ff_v_bf16mf4x8_mu(vbool64_t vm, + vbfloat16mf4x8_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg8e16ff_mu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16ff_v_bf16mf2x8_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , , i64 } @llvm.riscv.vlseg8ff.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 0 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , , , } poison, [[TMP9]], 0 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 1 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , , , } [[TMP10]], [[TMP11]], 1 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , , , } [[TMP12]], [[TMP13]], 2 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 3 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , , , } [[TMP14]], [[TMP15]], 3 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 4 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = insertvalue { , , , , , , , } [[TMP16]], [[TMP17]], 4 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 5 +// CHECK-RV64-NEXT: [[TMP20:%.*]] = insertvalue { , , , , , , , } [[TMP18]], [[TMP19]], 5 +// CHECK-RV64-NEXT: [[TMP21:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 6 +// CHECK-RV64-NEXT: [[TMP22:%.*]] = insertvalue { , , , , , , , } [[TMP20]], [[TMP21]], 6 +// CHECK-RV64-NEXT: [[TMP23:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 7 +// CHECK-RV64-NEXT: [[TMP24:%.*]] = insertvalue { , , , , , , , } [[TMP22]], [[TMP23]], 7 +// CHECK-RV64-NEXT: [[TMP25:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 8 +// CHECK-RV64-NEXT: store i64 [[TMP25]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP24]] +// +vbfloat16mf2x8_t test_vlseg8e16ff_v_bf16mf2x8_mu(vbool32_t vm, + vbfloat16mf2x8_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg8e16ff_mu(vm, vd, rs1, new_vl, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlseg8e16ff_v_bf16m1x8_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], ptr noundef [[NEW_VL:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , , i64 } @llvm.riscv.vlseg8ff.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: [[TMP9:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 0 +// CHECK-RV64-NEXT: [[TMP10:%.*]] = insertvalue { , , , , , , , } poison, [[TMP9]], 0 +// CHECK-RV64-NEXT: [[TMP11:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 1 +// CHECK-RV64-NEXT: [[TMP12:%.*]] = insertvalue { , , , , , , , } [[TMP10]], [[TMP11]], 1 +// CHECK-RV64-NEXT: [[TMP13:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 2 +// CHECK-RV64-NEXT: [[TMP14:%.*]] = insertvalue { , , , , , , , } [[TMP12]], [[TMP13]], 2 +// CHECK-RV64-NEXT: [[TMP15:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 3 +// CHECK-RV64-NEXT: [[TMP16:%.*]] = insertvalue { , , , , , , , } [[TMP14]], [[TMP15]], 3 +// CHECK-RV64-NEXT: [[TMP17:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 4 +// CHECK-RV64-NEXT: [[TMP18:%.*]] = insertvalue { , , , , , , , } [[TMP16]], [[TMP17]], 4 +// CHECK-RV64-NEXT: [[TMP19:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 5 +// CHECK-RV64-NEXT: [[TMP20:%.*]] = insertvalue { , , , , , , , } [[TMP18]], [[TMP19]], 5 +// CHECK-RV64-NEXT: [[TMP21:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 6 +// CHECK-RV64-NEXT: [[TMP22:%.*]] = insertvalue { , , , , , , , } [[TMP20]], [[TMP21]], 6 +// CHECK-RV64-NEXT: [[TMP23:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 7 +// CHECK-RV64-NEXT: [[TMP24:%.*]] = insertvalue { , , , , , , , } [[TMP22]], [[TMP23]], 7 +// CHECK-RV64-NEXT: [[TMP25:%.*]] = extractvalue { , , , , , , , , i64 } [[TMP8]], 8 +// CHECK-RV64-NEXT: store i64 [[TMP25]], ptr [[NEW_VL]], align 8 +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP24]] +// +vbfloat16m1x8_t test_vlseg8e16ff_v_bf16m1x8_mu(vbool16_t vm, vbfloat16m1x8_t vd, + const __bf16 *rs1, + size_t *new_vl, size_t vl) { + return __riscv_vlseg8e16ff_mu(vm, vd, rs1, new_vl, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlsseg2e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlsseg2e16.c new file mode 100644 index 0000000000000000000000000000000000000000..ad0cc42d2304c44f3a534c8212d02adf2ab0ed37 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlsseg2e16.c @@ -0,0 +1,296 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16mf4x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlsseg2.nxv1bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf4x2_t test_vlsseg2e16_v_bf16mf4x2_tu(vbfloat16mf4x2_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg2e16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16mf2x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlsseg2.nxv2bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf2x2_t test_vlsseg2e16_v_bf16mf2x2_tu(vbfloat16mf2x2_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg2e16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16m1x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlsseg2.nxv4bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m1x2_t test_vlsseg2e16_v_bf16m1x2_tu(vbfloat16m1x2_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg2e16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16m2x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlsseg2.nxv8bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m2x2_t test_vlsseg2e16_v_bf16m2x2_tu(vbfloat16m2x2_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg2e16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16m4x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlsseg2.nxv16bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m4x2_t test_vlsseg2e16_v_bf16m4x2_tu(vbfloat16m4x2_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg2e16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16mf4x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlsseg2.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf4x2_t test_vlsseg2e16_v_bf16mf4x2_tum(vbool64_t vm, + vbfloat16mf4x2_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg2e16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16mf2x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlsseg2.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf2x2_t test_vlsseg2e16_v_bf16mf2x2_tum(vbool32_t vm, + vbfloat16mf2x2_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg2e16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16m1x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlsseg2.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m1x2_t test_vlsseg2e16_v_bf16m1x2_tum(vbool16_t vm, vbfloat16m1x2_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg2e16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16m2x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlsseg2.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m2x2_t test_vlsseg2e16_v_bf16m2x2_tum(vbool8_t vm, vbfloat16m2x2_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg2e16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16m4x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlsseg2.mask.nxv16bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m4x2_t test_vlsseg2e16_v_bf16m4x2_tum(vbool4_t vm, vbfloat16m4x2_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg2e16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16mf4x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlsseg2.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf4x2_t test_vlsseg2e16_v_bf16mf4x2_tumu(vbool64_t vm, + vbfloat16mf4x2_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg2e16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16mf2x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlsseg2.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf2x2_t test_vlsseg2e16_v_bf16mf2x2_tumu(vbool32_t vm, + vbfloat16mf2x2_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg2e16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16m1x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlsseg2.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m1x2_t test_vlsseg2e16_v_bf16m1x2_tumu(vbool16_t vm, + vbfloat16m1x2_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg2e16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16m2x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlsseg2.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m2x2_t test_vlsseg2e16_v_bf16m2x2_tumu(vbool8_t vm, vbfloat16m2x2_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg2e16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16m4x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlsseg2.mask.nxv16bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m4x2_t test_vlsseg2e16_v_bf16m4x2_tumu(vbool4_t vm, vbfloat16m4x2_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg2e16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16mf4x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlsseg2.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf4x2_t test_vlsseg2e16_v_bf16mf4x2_mu(vbool64_t vm, + vbfloat16mf4x2_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg2e16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16mf2x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlsseg2.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf2x2_t test_vlsseg2e16_v_bf16mf2x2_mu(vbool32_t vm, + vbfloat16mf2x2_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg2e16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16m1x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlsseg2.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m1x2_t test_vlsseg2e16_v_bf16m1x2_mu(vbool16_t vm, vbfloat16m1x2_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg2e16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16m2x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlsseg2.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m2x2_t test_vlsseg2e16_v_bf16m2x2_mu(vbool8_t vm, vbfloat16m2x2_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg2e16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vlsseg2e16_v_bf16m4x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vlsseg2.mask.nxv16bf16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m4x2_t test_vlsseg2e16_v_bf16m4x2_mu(vbool4_t vm, vbfloat16m4x2_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg2e16_mu(vm, vd, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlsseg3e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlsseg3e16.c new file mode 100644 index 0000000000000000000000000000000000000000..d9866c24dcdd047cd0e4b972e6534d8fb1e10a87 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlsseg3e16.c @@ -0,0 +1,256 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlsseg3e16_v_bf16mf4x3_tu( +// CHECK-RV64-SAME: { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlsseg3.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf4x3_t test_vlsseg3e16_v_bf16mf4x3_tu(vbfloat16mf4x3_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg3e16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlsseg3e16_v_bf16mf2x3_tu( +// CHECK-RV64-SAME: { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlsseg3.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf2x3_t test_vlsseg3e16_v_bf16mf2x3_tu(vbfloat16mf2x3_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg3e16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlsseg3e16_v_bf16m1x3_tu( +// CHECK-RV64-SAME: { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlsseg3.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m1x3_t test_vlsseg3e16_v_bf16m1x3_tu(vbfloat16m1x3_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg3e16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlsseg3e16_v_bf16m2x3_tu( +// CHECK-RV64-SAME: { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlsseg3.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m2x3_t test_vlsseg3e16_v_bf16m2x3_tu(vbfloat16m2x3_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg3e16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlsseg3e16_v_bf16mf4x3_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlsseg3.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf4x3_t test_vlsseg3e16_v_bf16mf4x3_tum(vbool64_t vm, + vbfloat16mf4x3_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg3e16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlsseg3e16_v_bf16mf2x3_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlsseg3.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf2x3_t test_vlsseg3e16_v_bf16mf2x3_tum(vbool32_t vm, + vbfloat16mf2x3_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg3e16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlsseg3e16_v_bf16m1x3_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlsseg3.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m1x3_t test_vlsseg3e16_v_bf16m1x3_tum(vbool16_t vm, vbfloat16m1x3_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg3e16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlsseg3e16_v_bf16m2x3_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlsseg3.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m2x3_t test_vlsseg3e16_v_bf16m2x3_tum(vbool8_t vm, vbfloat16m2x3_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg3e16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlsseg3e16_v_bf16mf4x3_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlsseg3.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf4x3_t test_vlsseg3e16_v_bf16mf4x3_tumu(vbool64_t vm, + vbfloat16mf4x3_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg3e16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlsseg3e16_v_bf16mf2x3_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlsseg3.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf2x3_t test_vlsseg3e16_v_bf16mf2x3_tumu(vbool32_t vm, + vbfloat16mf2x3_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg3e16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlsseg3e16_v_bf16m1x3_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlsseg3.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m1x3_t test_vlsseg3e16_v_bf16m1x3_tumu(vbool16_t vm, + vbfloat16m1x3_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg3e16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlsseg3e16_v_bf16m2x3_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlsseg3.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m2x3_t test_vlsseg3e16_v_bf16m2x3_tumu(vbool8_t vm, vbfloat16m2x3_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg3e16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlsseg3e16_v_bf16mf4x3_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlsseg3.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf4x3_t test_vlsseg3e16_v_bf16mf4x3_mu(vbool64_t vm, + vbfloat16mf4x3_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg3e16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlsseg3e16_v_bf16mf2x3_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlsseg3.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf2x3_t test_vlsseg3e16_v_bf16mf2x3_mu(vbool32_t vm, + vbfloat16mf2x3_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg3e16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlsseg3e16_v_bf16m1x3_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlsseg3.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m1x3_t test_vlsseg3e16_v_bf16m1x3_mu(vbool16_t vm, vbfloat16m1x3_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg3e16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vlsseg3e16_v_bf16m2x3_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vlsseg3.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m2x3_t test_vlsseg3e16_v_bf16m2x3_mu(vbool8_t vm, vbfloat16m2x3_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg3e16_mu(vm, vd, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlsseg4e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlsseg4e16.c new file mode 100644 index 0000000000000000000000000000000000000000..ceb8e7412d06fae552b487538f50e23520d9fa8a --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlsseg4e16.c @@ -0,0 +1,272 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlsseg4e16_v_bf16mf4x4_tu( +// CHECK-RV64-SAME: { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlsseg4.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf4x4_t test_vlsseg4e16_v_bf16mf4x4_tu(vbfloat16mf4x4_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg4e16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlsseg4e16_v_bf16mf2x4_tu( +// CHECK-RV64-SAME: { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlsseg4.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf2x4_t test_vlsseg4e16_v_bf16mf2x4_tu(vbfloat16mf2x4_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg4e16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlsseg4e16_v_bf16m1x4_tu( +// CHECK-RV64-SAME: { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlsseg4.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m1x4_t test_vlsseg4e16_v_bf16m1x4_tu(vbfloat16m1x4_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg4e16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlsseg4e16_v_bf16m2x4_tu( +// CHECK-RV64-SAME: { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlsseg4.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m2x4_t test_vlsseg4e16_v_bf16m2x4_tu(vbfloat16m2x4_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg4e16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlsseg4e16_v_bf16mf4x4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlsseg4.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf4x4_t test_vlsseg4e16_v_bf16mf4x4_tum(vbool64_t vm, + vbfloat16mf4x4_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg4e16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlsseg4e16_v_bf16mf2x4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlsseg4.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf2x4_t test_vlsseg4e16_v_bf16mf2x4_tum(vbool32_t vm, + vbfloat16mf2x4_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg4e16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlsseg4e16_v_bf16m1x4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlsseg4.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m1x4_t test_vlsseg4e16_v_bf16m1x4_tum(vbool16_t vm, vbfloat16m1x4_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg4e16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlsseg4e16_v_bf16m2x4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlsseg4.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m2x4_t test_vlsseg4e16_v_bf16m2x4_tum(vbool8_t vm, vbfloat16m2x4_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg4e16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlsseg4e16_v_bf16mf4x4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlsseg4.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf4x4_t test_vlsseg4e16_v_bf16mf4x4_tumu(vbool64_t vm, + vbfloat16mf4x4_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg4e16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlsseg4e16_v_bf16mf2x4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlsseg4.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf2x4_t test_vlsseg4e16_v_bf16mf2x4_tumu(vbool32_t vm, + vbfloat16mf2x4_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg4e16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlsseg4e16_v_bf16m1x4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlsseg4.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m1x4_t test_vlsseg4e16_v_bf16m1x4_tumu(vbool16_t vm, + vbfloat16m1x4_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg4e16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlsseg4e16_v_bf16m2x4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlsseg4.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m2x4_t test_vlsseg4e16_v_bf16m2x4_tumu(vbool8_t vm, vbfloat16m2x4_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg4e16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlsseg4e16_v_bf16mf4x4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlsseg4.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf4x4_t test_vlsseg4e16_v_bf16mf4x4_mu(vbool64_t vm, + vbfloat16mf4x4_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg4e16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlsseg4e16_v_bf16mf2x4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlsseg4.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf2x4_t test_vlsseg4e16_v_bf16mf2x4_mu(vbool32_t vm, + vbfloat16mf2x4_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg4e16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlsseg4e16_v_bf16m1x4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlsseg4.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m1x4_t test_vlsseg4e16_v_bf16m1x4_mu(vbool16_t vm, vbfloat16m1x4_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg4e16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vlsseg4e16_v_bf16m2x4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vlsseg4.mask.nxv8bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m2x4_t test_vlsseg4e16_v_bf16m2x4_mu(vbool8_t vm, vbfloat16m2x4_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg4e16_mu(vm, vd, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlsseg5e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlsseg5e16.c new file mode 100644 index 0000000000000000000000000000000000000000..ff43061fc70d2e8e5b028825d392fbb6995fa9db --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlsseg5e16.c @@ -0,0 +1,220 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlsseg5e16_v_bf16mf4x5_tu( +// CHECK-RV64-SAME: { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vlsseg5.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf4x5_t test_vlsseg5e16_v_bf16mf4x5_tu(vbfloat16mf4x5_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg5e16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlsseg5e16_v_bf16mf2x5_tu( +// CHECK-RV64-SAME: { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vlsseg5.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf2x5_t test_vlsseg5e16_v_bf16mf2x5_tu(vbfloat16mf2x5_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg5e16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlsseg5e16_v_bf16m1x5_tu( +// CHECK-RV64-SAME: { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vlsseg5.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16m1x5_t test_vlsseg5e16_v_bf16m1x5_tu(vbfloat16m1x5_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg5e16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlsseg5e16_v_bf16mf4x5_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vlsseg5.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf4x5_t test_vlsseg5e16_v_bf16mf4x5_tum(vbool64_t vm, + vbfloat16mf4x5_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg5e16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlsseg5e16_v_bf16mf2x5_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vlsseg5.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf2x5_t test_vlsseg5e16_v_bf16mf2x5_tum(vbool32_t vm, + vbfloat16mf2x5_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg5e16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlsseg5e16_v_bf16m1x5_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vlsseg5.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16m1x5_t test_vlsseg5e16_v_bf16m1x5_tum(vbool16_t vm, vbfloat16m1x5_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg5e16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlsseg5e16_v_bf16mf4x5_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vlsseg5.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf4x5_t test_vlsseg5e16_v_bf16mf4x5_tumu(vbool64_t vm, + vbfloat16mf4x5_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg5e16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlsseg5e16_v_bf16mf2x5_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vlsseg5.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf2x5_t test_vlsseg5e16_v_bf16mf2x5_tumu(vbool32_t vm, + vbfloat16mf2x5_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg5e16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlsseg5e16_v_bf16m1x5_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vlsseg5.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16m1x5_t test_vlsseg5e16_v_bf16m1x5_tumu(vbool16_t vm, + vbfloat16m1x5_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg5e16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlsseg5e16_v_bf16mf4x5_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vlsseg5.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf4x5_t test_vlsseg5e16_v_bf16mf4x5_mu(vbool64_t vm, + vbfloat16mf4x5_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg5e16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlsseg5e16_v_bf16mf2x5_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vlsseg5.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf2x5_t test_vlsseg5e16_v_bf16mf2x5_mu(vbool32_t vm, + vbfloat16mf2x5_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg5e16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vlsseg5e16_v_bf16m1x5_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vlsseg5.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16m1x5_t test_vlsseg5e16_v_bf16m1x5_mu(vbool16_t vm, vbfloat16m1x5_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg5e16_mu(vm, vd, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlsseg6e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlsseg6e16.c new file mode 100644 index 0000000000000000000000000000000000000000..4220e8e07839191224e43852cc8c1e5204f96191 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlsseg6e16.c @@ -0,0 +1,232 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlsseg6e16_v_bf16mf4x6_tu( +// CHECK-RV64-SAME: { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vlsseg6.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf4x6_t test_vlsseg6e16_v_bf16mf4x6_tu(vbfloat16mf4x6_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg6e16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlsseg6e16_v_bf16mf2x6_tu( +// CHECK-RV64-SAME: { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vlsseg6.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf2x6_t test_vlsseg6e16_v_bf16mf2x6_tu(vbfloat16mf2x6_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg6e16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlsseg6e16_v_bf16m1x6_tu( +// CHECK-RV64-SAME: { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vlsseg6.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16m1x6_t test_vlsseg6e16_v_bf16m1x6_tu(vbfloat16m1x6_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg6e16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlsseg6e16_v_bf16mf4x6_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vlsseg6.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf4x6_t test_vlsseg6e16_v_bf16mf4x6_tum(vbool64_t vm, + vbfloat16mf4x6_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg6e16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlsseg6e16_v_bf16mf2x6_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vlsseg6.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf2x6_t test_vlsseg6e16_v_bf16mf2x6_tum(vbool32_t vm, + vbfloat16mf2x6_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg6e16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlsseg6e16_v_bf16m1x6_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vlsseg6.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16m1x6_t test_vlsseg6e16_v_bf16m1x6_tum(vbool16_t vm, vbfloat16m1x6_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg6e16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlsseg6e16_v_bf16mf4x6_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vlsseg6.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf4x6_t test_vlsseg6e16_v_bf16mf4x6_tumu(vbool64_t vm, + vbfloat16mf4x6_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg6e16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlsseg6e16_v_bf16mf2x6_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vlsseg6.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf2x6_t test_vlsseg6e16_v_bf16mf2x6_tumu(vbool32_t vm, + vbfloat16mf2x6_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg6e16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlsseg6e16_v_bf16m1x6_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vlsseg6.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16m1x6_t test_vlsseg6e16_v_bf16m1x6_tumu(vbool16_t vm, + vbfloat16m1x6_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg6e16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlsseg6e16_v_bf16mf4x6_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vlsseg6.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf4x6_t test_vlsseg6e16_v_bf16mf4x6_mu(vbool64_t vm, + vbfloat16mf4x6_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg6e16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlsseg6e16_v_bf16mf2x6_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vlsseg6.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf2x6_t test_vlsseg6e16_v_bf16mf2x6_mu(vbool32_t vm, + vbfloat16mf2x6_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg6e16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vlsseg6e16_v_bf16m1x6_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vlsseg6.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16m1x6_t test_vlsseg6e16_v_bf16m1x6_mu(vbool16_t vm, vbfloat16m1x6_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg6e16_mu(vm, vd, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlsseg7e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlsseg7e16.c new file mode 100644 index 0000000000000000000000000000000000000000..45705a6dae78ea52fd7e590af0a4fb1385a9843f --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlsseg7e16.c @@ -0,0 +1,244 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlsseg7e16_v_bf16mf4x7_tu( +// CHECK-RV64-SAME: { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vlsseg7.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf4x7_t test_vlsseg7e16_v_bf16mf4x7_tu(vbfloat16mf4x7_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg7e16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlsseg7e16_v_bf16mf2x7_tu( +// CHECK-RV64-SAME: { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vlsseg7.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf2x7_t test_vlsseg7e16_v_bf16mf2x7_tu(vbfloat16mf2x7_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg7e16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlsseg7e16_v_bf16m1x7_tu( +// CHECK-RV64-SAME: { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vlsseg7.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16m1x7_t test_vlsseg7e16_v_bf16m1x7_tu(vbfloat16m1x7_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg7e16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlsseg7e16_v_bf16mf4x7_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vlsseg7.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf4x7_t test_vlsseg7e16_v_bf16mf4x7_tum(vbool64_t vm, + vbfloat16mf4x7_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg7e16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlsseg7e16_v_bf16mf2x7_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vlsseg7.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf2x7_t test_vlsseg7e16_v_bf16mf2x7_tum(vbool32_t vm, + vbfloat16mf2x7_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg7e16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlsseg7e16_v_bf16m1x7_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vlsseg7.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16m1x7_t test_vlsseg7e16_v_bf16m1x7_tum(vbool16_t vm, vbfloat16m1x7_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg7e16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlsseg7e16_v_bf16mf4x7_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vlsseg7.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf4x7_t test_vlsseg7e16_v_bf16mf4x7_tumu(vbool64_t vm, + vbfloat16mf4x7_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg7e16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlsseg7e16_v_bf16mf2x7_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vlsseg7.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf2x7_t test_vlsseg7e16_v_bf16mf2x7_tumu(vbool32_t vm, + vbfloat16mf2x7_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg7e16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlsseg7e16_v_bf16m1x7_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vlsseg7.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16m1x7_t test_vlsseg7e16_v_bf16m1x7_tumu(vbool16_t vm, + vbfloat16m1x7_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg7e16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlsseg7e16_v_bf16mf4x7_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vlsseg7.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf4x7_t test_vlsseg7e16_v_bf16mf4x7_mu(vbool64_t vm, + vbfloat16mf4x7_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg7e16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlsseg7e16_v_bf16mf2x7_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vlsseg7.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf2x7_t test_vlsseg7e16_v_bf16mf2x7_mu(vbool32_t vm, + vbfloat16mf2x7_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg7e16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vlsseg7e16_v_bf16m1x7_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vlsseg7.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16m1x7_t test_vlsseg7e16_v_bf16m1x7_mu(vbool16_t vm, vbfloat16m1x7_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg7e16_mu(vm, vd, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlsseg8e16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlsseg8e16.c new file mode 100644 index 0000000000000000000000000000000000000000..dd3a5fd367345abef770b84e8de8b01296a7cea5 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vlsseg8e16.c @@ -0,0 +1,256 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlsseg8e16_v_bf16mf4x8_tu( +// CHECK-RV64-SAME: { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vlsseg8.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf4x8_t test_vlsseg8e16_v_bf16mf4x8_tu(vbfloat16mf4x8_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg8e16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlsseg8e16_v_bf16mf2x8_tu( +// CHECK-RV64-SAME: { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vlsseg8.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf2x8_t test_vlsseg8e16_v_bf16mf2x8_tu(vbfloat16mf2x8_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg8e16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlsseg8e16_v_bf16m1x8_tu( +// CHECK-RV64-SAME: { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vlsseg8.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16m1x8_t test_vlsseg8e16_v_bf16m1x8_tu(vbfloat16m1x8_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg8e16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlsseg8e16_v_bf16mf4x8_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vlsseg8.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf4x8_t test_vlsseg8e16_v_bf16mf4x8_tum(vbool64_t vm, + vbfloat16mf4x8_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg8e16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlsseg8e16_v_bf16mf2x8_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vlsseg8.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf2x8_t test_vlsseg8e16_v_bf16mf2x8_tum(vbool32_t vm, + vbfloat16mf2x8_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg8e16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlsseg8e16_v_bf16m1x8_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vlsseg8.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16m1x8_t test_vlsseg8e16_v_bf16m1x8_tum(vbool16_t vm, vbfloat16m1x8_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg8e16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlsseg8e16_v_bf16mf4x8_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vlsseg8.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf4x8_t test_vlsseg8e16_v_bf16mf4x8_tumu(vbool64_t vm, + vbfloat16mf4x8_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg8e16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlsseg8e16_v_bf16mf2x8_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vlsseg8.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf2x8_t test_vlsseg8e16_v_bf16mf2x8_tumu(vbool32_t vm, + vbfloat16mf2x8_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg8e16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlsseg8e16_v_bf16m1x8_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vlsseg8.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16m1x8_t test_vlsseg8e16_v_bf16m1x8_tumu(vbool16_t vm, + vbfloat16m1x8_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg8e16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlsseg8e16_v_bf16mf4x8_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vlsseg8.mask.nxv1bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf4x8_t test_vlsseg8e16_v_bf16mf4x8_mu(vbool64_t vm, + vbfloat16mf4x8_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg8e16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlsseg8e16_v_bf16mf2x8_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vlsseg8.mask.nxv2bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf2x8_t test_vlsseg8e16_v_bf16mf2x8_mu(vbool32_t vm, + vbfloat16mf2x8_t vd, + const __bf16 *rs1, + ptrdiff_t rs2, size_t vl) { + return __riscv_vlsseg8e16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vlsseg8e16_v_bf16m1x8_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], i64 noundef [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vlsseg8.mask.nxv4bf16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], i64 [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16m1x8_t test_vlsseg8e16_v_bf16m1x8_mu(vbool16_t vm, vbfloat16m1x8_t vd, + const __bf16 *rs1, ptrdiff_t rs2, + size_t vl) { + return __riscv_vlsseg8e16_mu(vm, vd, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vluxei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vluxei16.c new file mode 100644 index 0000000000000000000000000000000000000000..10e7fb56146198944537a46673d546052fa8c6e2 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vluxei16.c @@ -0,0 +1,291 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16mf4_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.nxv1bf16.nxv1i16.i64( [[VD]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vluxei16_v_bf16mf4_tu(vbfloat16mf4_t vd, const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16mf2_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.nxv2bf16.nxv2i16.i64( [[VD]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vluxei16_v_bf16mf2_tu(vbfloat16mf2_t vd, const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16m1_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.nxv4bf16.nxv4i16.i64( [[VD]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vluxei16_v_bf16m1_tu(vbfloat16m1_t vd, const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vluxei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16m2_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.nxv8bf16.nxv8i16.i64( [[VD]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vluxei16_v_bf16m2_tu(vbfloat16m2_t vd, const __bf16 *rs1, + vuint16m2_t rs2, size_t vl) { + return __riscv_vluxei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16m4_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.nxv16bf16.nxv16i16.i64( [[VD]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vluxei16_v_bf16m4_tu(vbfloat16m4_t vd, const __bf16 *rs1, + vuint16m4_t rs2, size_t vl) { + return __riscv_vluxei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16m8_tu( +// CHECK-RV64-SAME: [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.nxv32bf16.nxv32i16.i64( [[VD]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vluxei16_v_bf16m8_tu(vbfloat16m8_t vd, const __bf16 *rs1, + vuint16m8_t rs2, size_t vl) { + return __riscv_vluxei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16mf4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.mask.nxv1bf16.nxv1i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vluxei16_v_bf16mf4_tum(vbool64_t vm, vbfloat16mf4_t vd, + const __bf16 *rs1, vuint16mf4_t rs2, + size_t vl) { + return __riscv_vluxei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16mf2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.mask.nxv2bf16.nxv2i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vluxei16_v_bf16mf2_tum(vbool32_t vm, vbfloat16mf2_t vd, + const __bf16 *rs1, vuint16mf2_t rs2, + size_t vl) { + return __riscv_vluxei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16m1_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.mask.nxv4bf16.nxv4i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vluxei16_v_bf16m1_tum(vbool16_t vm, vbfloat16m1_t vd, + const __bf16 *rs1, vuint16m1_t rs2, + size_t vl) { + return __riscv_vluxei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16m2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.mask.nxv8bf16.nxv8i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vluxei16_v_bf16m2_tum(vbool8_t vm, vbfloat16m2_t vd, + const __bf16 *rs1, vuint16m2_t rs2, + size_t vl) { + return __riscv_vluxei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16m4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.mask.nxv16bf16.nxv16i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vluxei16_v_bf16m4_tum(vbool4_t vm, vbfloat16m4_t vd, + const __bf16 *rs1, vuint16m4_t rs2, + size_t vl) { + return __riscv_vluxei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16m8_tum( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.mask.nxv32bf16.nxv32i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vluxei16_v_bf16m8_tum(vbool2_t vm, vbfloat16m8_t vd, + const __bf16 *rs1, vuint16m8_t rs2, + size_t vl) { + return __riscv_vluxei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16mf4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.mask.nxv1bf16.nxv1i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vluxei16_v_bf16mf4_tumu(vbool64_t vm, vbfloat16mf4_t vd, + const __bf16 *rs1, vuint16mf4_t rs2, + size_t vl) { + return __riscv_vluxei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16mf2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.mask.nxv2bf16.nxv2i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vluxei16_v_bf16mf2_tumu(vbool32_t vm, vbfloat16mf2_t vd, + const __bf16 *rs1, vuint16mf2_t rs2, + size_t vl) { + return __riscv_vluxei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16m1_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.mask.nxv4bf16.nxv4i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vluxei16_v_bf16m1_tumu(vbool16_t vm, vbfloat16m1_t vd, + const __bf16 *rs1, vuint16m1_t rs2, + size_t vl) { + return __riscv_vluxei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16m2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.mask.nxv8bf16.nxv8i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vluxei16_v_bf16m2_tumu(vbool8_t vm, vbfloat16m2_t vd, + const __bf16 *rs1, vuint16m2_t rs2, + size_t vl) { + return __riscv_vluxei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16m4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.mask.nxv16bf16.nxv16i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vluxei16_v_bf16m4_tumu(vbool4_t vm, vbfloat16m4_t vd, + const __bf16 *rs1, vuint16m4_t rs2, + size_t vl) { + return __riscv_vluxei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16m8_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.mask.nxv32bf16.nxv32i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vluxei16_v_bf16m8_tumu(vbool2_t vm, vbfloat16m8_t vd, + const __bf16 *rs1, vuint16m8_t rs2, + size_t vl) { + return __riscv_vluxei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16mf4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.mask.nxv1bf16.nxv1i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf4_t test_vluxei16_v_bf16mf4_mu(vbool64_t vm, vbfloat16mf4_t vd, + const __bf16 *rs1, vuint16mf4_t rs2, + size_t vl) { + return __riscv_vluxei16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16mf2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.mask.nxv2bf16.nxv2i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16mf2_t test_vluxei16_v_bf16mf2_mu(vbool32_t vm, vbfloat16mf2_t vd, + const __bf16 *rs1, vuint16mf2_t rs2, + size_t vl) { + return __riscv_vluxei16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16m1_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.mask.nxv4bf16.nxv4i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m1_t test_vluxei16_v_bf16m1_mu(vbool16_t vm, vbfloat16m1_t vd, + const __bf16 *rs1, vuint16m1_t rs2, + size_t vl) { + return __riscv_vluxei16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16m2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.mask.nxv8bf16.nxv8i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m2_t test_vluxei16_v_bf16m2_mu(vbool8_t vm, vbfloat16m2_t vd, + const __bf16 *rs1, vuint16m2_t rs2, + size_t vl) { + return __riscv_vluxei16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16m4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.mask.nxv16bf16.nxv16i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m4_t test_vluxei16_v_bf16m4_mu(vbool4_t vm, vbfloat16m4_t vd, + const __bf16 *rs1, vuint16m4_t rs2, + size_t vl) { + return __riscv_vluxei16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local @test_vluxei16_v_bf16m8_mu( +// CHECK-RV64-SAME: [[VM:%.*]], [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vluxei.mask.nxv32bf16.nxv32i16.i64( [[VD]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret [[TMP0]] +// +vbfloat16m8_t test_vluxei16_v_bf16m8_mu(vbool2_t vm, vbfloat16m8_t vd, + const __bf16 *rs1, vuint16m8_t rs2, + size_t vl) { + return __riscv_vluxei16_mu(vm, vd, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vluxseg2ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vluxseg2ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..40b94c5d40767b00249a970c409c708b9c1b7beb --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vluxseg2ei16.c @@ -0,0 +1,306 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16mf4x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vluxseg2.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf4x2_t test_vluxseg2ei16_v_bf16mf4x2_tu(vbfloat16mf4x2_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg2ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16mf2x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vluxseg2.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf2x2_t test_vluxseg2ei16_v_bf16mf2x2_tu(vbfloat16mf2x2_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg2ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16m1x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vluxseg2.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m1x2_t test_vluxseg2ei16_v_bf16m1x2_tu(vbfloat16m1x2_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg2ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16m2x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vluxseg2.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m2x2_t test_vluxseg2ei16_v_bf16m2x2_tu(vbfloat16m2x2_t vd, + const __bf16 *rs1, + vuint16m2_t rs2, size_t vl) { + return __riscv_vluxseg2ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16m4x2_tu( +// CHECK-RV64-SAME: { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vluxseg2.nxv16bf16.nxv16i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m4x2_t test_vluxseg2ei16_v_bf16m4x2_tu(vbfloat16m4x2_t vd, + const __bf16 *rs1, + vuint16m4_t rs2, size_t vl) { + return __riscv_vluxseg2ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16mf4x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vluxseg2.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf4x2_t test_vluxseg2ei16_v_bf16mf4x2_tum(vbool64_t vm, + vbfloat16mf4x2_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, + size_t vl) { + return __riscv_vluxseg2ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16mf2x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vluxseg2.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf2x2_t test_vluxseg2ei16_v_bf16mf2x2_tum(vbool32_t vm, + vbfloat16mf2x2_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, + size_t vl) { + return __riscv_vluxseg2ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16m1x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vluxseg2.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m1x2_t test_vluxseg2ei16_v_bf16m1x2_tum(vbool16_t vm, + vbfloat16m1x2_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg2ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16m2x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vluxseg2.mask.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m2x2_t test_vluxseg2ei16_v_bf16m2x2_tum(vbool8_t vm, + vbfloat16m2x2_t vd, + const __bf16 *rs1, + vuint16m2_t rs2, size_t vl) { + return __riscv_vluxseg2ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16m4x2_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vluxseg2.mask.nxv16bf16.nxv16i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m4x2_t test_vluxseg2ei16_v_bf16m4x2_tum(vbool4_t vm, + vbfloat16m4x2_t vd, + const __bf16 *rs1, + vuint16m4_t rs2, size_t vl) { + return __riscv_vluxseg2ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16mf4x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vluxseg2.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf4x2_t test_vluxseg2ei16_v_bf16mf4x2_tumu(vbool64_t vm, + vbfloat16mf4x2_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, + size_t vl) { + return __riscv_vluxseg2ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16mf2x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vluxseg2.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf2x2_t test_vluxseg2ei16_v_bf16mf2x2_tumu(vbool32_t vm, + vbfloat16mf2x2_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, + size_t vl) { + return __riscv_vluxseg2ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16m1x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vluxseg2.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m1x2_t test_vluxseg2ei16_v_bf16m1x2_tumu(vbool16_t vm, + vbfloat16m1x2_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg2ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16m2x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vluxseg2.mask.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m2x2_t test_vluxseg2ei16_v_bf16m2x2_tumu(vbool8_t vm, + vbfloat16m2x2_t vd, + const __bf16 *rs1, + vuint16m2_t rs2, size_t vl) { + return __riscv_vluxseg2ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16m4x2_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vluxseg2.mask.nxv16bf16.nxv16i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m4x2_t test_vluxseg2ei16_v_bf16m4x2_tumu(vbool4_t vm, + vbfloat16m4x2_t vd, + const __bf16 *rs1, + vuint16m4_t rs2, size_t vl) { + return __riscv_vluxseg2ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16mf4x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vluxseg2.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf4x2_t test_vluxseg2ei16_v_bf16mf4x2_mu(vbool64_t vm, + vbfloat16mf4x2_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg2ei16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16mf2x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vluxseg2.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16mf2x2_t test_vluxseg2ei16_v_bf16mf2x2_mu(vbool32_t vm, + vbfloat16mf2x2_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg2ei16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16m1x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vluxseg2.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m1x2_t test_vluxseg2ei16_v_bf16m1x2_mu(vbool16_t vm, + vbfloat16m1x2_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg2ei16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16m2x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vluxseg2.mask.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m2x2_t test_vluxseg2ei16_v_bf16m2x2_mu(vbool8_t vm, vbfloat16m2x2_t vd, + const __bf16 *rs1, + vuint16m2_t rs2, size_t vl) { + return __riscv_vluxseg2ei16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , } @test_vluxseg2ei16_v_bf16m4x2_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = call { , } @llvm.riscv.vluxseg2.mask.nxv16bf16.nxv16i16.i64( [[TMP0]], [[TMP1]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , } [[TMP2]] +// +vbfloat16m4x2_t test_vluxseg2ei16_v_bf16m4x2_mu(vbool4_t vm, vbfloat16m4x2_t vd, + const __bf16 *rs1, + vuint16m4_t rs2, size_t vl) { + return __riscv_vluxseg2ei16_mu(vm, vd, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vluxseg3ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vluxseg3ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..305e811f197b51eb571ed3a747ee881e8eda91a6 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vluxseg3ei16.c @@ -0,0 +1,264 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vluxseg3ei16_v_bf16mf4x3_tu( +// CHECK-RV64-SAME: { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vluxseg3.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf4x3_t test_vluxseg3ei16_v_bf16mf4x3_tu(vbfloat16mf4x3_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg3ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vluxseg3ei16_v_bf16mf2x3_tu( +// CHECK-RV64-SAME: { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vluxseg3.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf2x3_t test_vluxseg3ei16_v_bf16mf2x3_tu(vbfloat16mf2x3_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg3ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vluxseg3ei16_v_bf16m1x3_tu( +// CHECK-RV64-SAME: { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vluxseg3.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m1x3_t test_vluxseg3ei16_v_bf16m1x3_tu(vbfloat16m1x3_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg3ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vluxseg3ei16_v_bf16m2x3_tu( +// CHECK-RV64-SAME: { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vluxseg3.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m2x3_t test_vluxseg3ei16_v_bf16m2x3_tu(vbfloat16m2x3_t vd, + const __bf16 *rs1, + vuint16m2_t rs2, size_t vl) { + return __riscv_vluxseg3ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vluxseg3ei16_v_bf16mf4x3_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vluxseg3.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf4x3_t test_vluxseg3ei16_v_bf16mf4x3_tum(vbool64_t vm, + vbfloat16mf4x3_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, + size_t vl) { + return __riscv_vluxseg3ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vluxseg3ei16_v_bf16mf2x3_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vluxseg3.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf2x3_t test_vluxseg3ei16_v_bf16mf2x3_tum(vbool32_t vm, + vbfloat16mf2x3_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, + size_t vl) { + return __riscv_vluxseg3ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vluxseg3ei16_v_bf16m1x3_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vluxseg3.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m1x3_t test_vluxseg3ei16_v_bf16m1x3_tum(vbool16_t vm, + vbfloat16m1x3_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg3ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vluxseg3ei16_v_bf16m2x3_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vluxseg3.mask.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m2x3_t test_vluxseg3ei16_v_bf16m2x3_tum(vbool8_t vm, + vbfloat16m2x3_t vd, + const __bf16 *rs1, + vuint16m2_t rs2, size_t vl) { + return __riscv_vluxseg3ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vluxseg3ei16_v_bf16mf4x3_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vluxseg3.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf4x3_t test_vluxseg3ei16_v_bf16mf4x3_tumu(vbool64_t vm, + vbfloat16mf4x3_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, + size_t vl) { + return __riscv_vluxseg3ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vluxseg3ei16_v_bf16mf2x3_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vluxseg3.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf2x3_t test_vluxseg3ei16_v_bf16mf2x3_tumu(vbool32_t vm, + vbfloat16mf2x3_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, + size_t vl) { + return __riscv_vluxseg3ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vluxseg3ei16_v_bf16m1x3_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vluxseg3.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m1x3_t test_vluxseg3ei16_v_bf16m1x3_tumu(vbool16_t vm, + vbfloat16m1x3_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg3ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vluxseg3ei16_v_bf16m2x3_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vluxseg3.mask.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m2x3_t test_vluxseg3ei16_v_bf16m2x3_tumu(vbool8_t vm, + vbfloat16m2x3_t vd, + const __bf16 *rs1, + vuint16m2_t rs2, size_t vl) { + return __riscv_vluxseg3ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vluxseg3ei16_v_bf16mf4x3_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vluxseg3.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf4x3_t test_vluxseg3ei16_v_bf16mf4x3_mu(vbool64_t vm, + vbfloat16mf4x3_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg3ei16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vluxseg3ei16_v_bf16mf2x3_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vluxseg3.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16mf2x3_t test_vluxseg3ei16_v_bf16mf2x3_mu(vbool32_t vm, + vbfloat16mf2x3_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg3ei16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vluxseg3ei16_v_bf16m1x3_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vluxseg3.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m1x3_t test_vluxseg3ei16_v_bf16m1x3_mu(vbool16_t vm, + vbfloat16m1x3_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg3ei16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , } @test_vluxseg3ei16_v_bf16m2x3_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = call { , , } @llvm.riscv.vluxseg3.mask.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , } [[TMP3]] +// +vbfloat16m2x3_t test_vluxseg3ei16_v_bf16m2x3_mu(vbool8_t vm, vbfloat16m2x3_t vd, + const __bf16 *rs1, + vuint16m2_t rs2, size_t vl) { + return __riscv_vluxseg3ei16_mu(vm, vd, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vluxseg4ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vluxseg4ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..eeb7834b44eff0af262d698be2e6ae2c0cf929f4 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vluxseg4ei16.c @@ -0,0 +1,280 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vluxseg4ei16_v_bf16mf4x4_tu( +// CHECK-RV64-SAME: { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vluxseg4.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf4x4_t test_vluxseg4ei16_v_bf16mf4x4_tu(vbfloat16mf4x4_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg4ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vluxseg4ei16_v_bf16mf2x4_tu( +// CHECK-RV64-SAME: { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vluxseg4.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf2x4_t test_vluxseg4ei16_v_bf16mf2x4_tu(vbfloat16mf2x4_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg4ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vluxseg4ei16_v_bf16m1x4_tu( +// CHECK-RV64-SAME: { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vluxseg4.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m1x4_t test_vluxseg4ei16_v_bf16m1x4_tu(vbfloat16m1x4_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg4ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vluxseg4ei16_v_bf16m2x4_tu( +// CHECK-RV64-SAME: { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vluxseg4.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m2x4_t test_vluxseg4ei16_v_bf16m2x4_tu(vbfloat16m2x4_t vd, + const __bf16 *rs1, + vuint16m2_t rs2, size_t vl) { + return __riscv_vluxseg4ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vluxseg4ei16_v_bf16mf4x4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vluxseg4.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf4x4_t test_vluxseg4ei16_v_bf16mf4x4_tum(vbool64_t vm, + vbfloat16mf4x4_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, + size_t vl) { + return __riscv_vluxseg4ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vluxseg4ei16_v_bf16mf2x4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vluxseg4.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf2x4_t test_vluxseg4ei16_v_bf16mf2x4_tum(vbool32_t vm, + vbfloat16mf2x4_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, + size_t vl) { + return __riscv_vluxseg4ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vluxseg4ei16_v_bf16m1x4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vluxseg4.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m1x4_t test_vluxseg4ei16_v_bf16m1x4_tum(vbool16_t vm, + vbfloat16m1x4_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg4ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vluxseg4ei16_v_bf16m2x4_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vluxseg4.mask.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m2x4_t test_vluxseg4ei16_v_bf16m2x4_tum(vbool8_t vm, + vbfloat16m2x4_t vd, + const __bf16 *rs1, + vuint16m2_t rs2, size_t vl) { + return __riscv_vluxseg4ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vluxseg4ei16_v_bf16mf4x4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vluxseg4.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf4x4_t test_vluxseg4ei16_v_bf16mf4x4_tumu(vbool64_t vm, + vbfloat16mf4x4_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, + size_t vl) { + return __riscv_vluxseg4ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vluxseg4ei16_v_bf16mf2x4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vluxseg4.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf2x4_t test_vluxseg4ei16_v_bf16mf2x4_tumu(vbool32_t vm, + vbfloat16mf2x4_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, + size_t vl) { + return __riscv_vluxseg4ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vluxseg4ei16_v_bf16m1x4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vluxseg4.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m1x4_t test_vluxseg4ei16_v_bf16m1x4_tumu(vbool16_t vm, + vbfloat16m1x4_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg4ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vluxseg4ei16_v_bf16m2x4_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vluxseg4.mask.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m2x4_t test_vluxseg4ei16_v_bf16m2x4_tumu(vbool8_t vm, + vbfloat16m2x4_t vd, + const __bf16 *rs1, + vuint16m2_t rs2, size_t vl) { + return __riscv_vluxseg4ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vluxseg4ei16_v_bf16mf4x4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vluxseg4.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf4x4_t test_vluxseg4ei16_v_bf16mf4x4_mu(vbool64_t vm, + vbfloat16mf4x4_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg4ei16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vluxseg4ei16_v_bf16mf2x4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vluxseg4.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16mf2x4_t test_vluxseg4ei16_v_bf16mf2x4_mu(vbool32_t vm, + vbfloat16mf2x4_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg4ei16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vluxseg4ei16_v_bf16m1x4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vluxseg4.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m1x4_t test_vluxseg4ei16_v_bf16m1x4_mu(vbool16_t vm, + vbfloat16m1x4_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg4ei16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , } @test_vluxseg4ei16_v_bf16m2x4_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = call { , , , } @llvm.riscv.vluxseg4.mask.nxv8bf16.nxv8i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , } [[TMP4]] +// +vbfloat16m2x4_t test_vluxseg4ei16_v_bf16m2x4_mu(vbool8_t vm, vbfloat16m2x4_t vd, + const __bf16 *rs1, + vuint16m2_t rs2, size_t vl) { + return __riscv_vluxseg4ei16_mu(vm, vd, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vluxseg5ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vluxseg5ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..0efa49935450a96f9e9a905b683d4214cd92d320 --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vluxseg5ei16.c @@ -0,0 +1,226 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vluxseg5ei16_v_bf16mf4x5_tu( +// CHECK-RV64-SAME: { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vluxseg5.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf4x5_t test_vluxseg5ei16_v_bf16mf4x5_tu(vbfloat16mf4x5_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg5ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vluxseg5ei16_v_bf16mf2x5_tu( +// CHECK-RV64-SAME: { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vluxseg5.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf2x5_t test_vluxseg5ei16_v_bf16mf2x5_tu(vbfloat16mf2x5_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg5ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vluxseg5ei16_v_bf16m1x5_tu( +// CHECK-RV64-SAME: { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vluxseg5.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16m1x5_t test_vluxseg5ei16_v_bf16m1x5_tu(vbfloat16m1x5_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg5ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vluxseg5ei16_v_bf16mf4x5_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vluxseg5.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf4x5_t test_vluxseg5ei16_v_bf16mf4x5_tum(vbool64_t vm, + vbfloat16mf4x5_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, + size_t vl) { + return __riscv_vluxseg5ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vluxseg5ei16_v_bf16mf2x5_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vluxseg5.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf2x5_t test_vluxseg5ei16_v_bf16mf2x5_tum(vbool32_t vm, + vbfloat16mf2x5_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, + size_t vl) { + return __riscv_vluxseg5ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vluxseg5ei16_v_bf16m1x5_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vluxseg5.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16m1x5_t test_vluxseg5ei16_v_bf16m1x5_tum(vbool16_t vm, + vbfloat16m1x5_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg5ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vluxseg5ei16_v_bf16mf4x5_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vluxseg5.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf4x5_t test_vluxseg5ei16_v_bf16mf4x5_tumu(vbool64_t vm, + vbfloat16mf4x5_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, + size_t vl) { + return __riscv_vluxseg5ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vluxseg5ei16_v_bf16mf2x5_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vluxseg5.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf2x5_t test_vluxseg5ei16_v_bf16mf2x5_tumu(vbool32_t vm, + vbfloat16mf2x5_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, + size_t vl) { + return __riscv_vluxseg5ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vluxseg5ei16_v_bf16m1x5_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vluxseg5.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16m1x5_t test_vluxseg5ei16_v_bf16m1x5_tumu(vbool16_t vm, + vbfloat16m1x5_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg5ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vluxseg5ei16_v_bf16mf4x5_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vluxseg5.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf4x5_t test_vluxseg5ei16_v_bf16mf4x5_mu(vbool64_t vm, + vbfloat16mf4x5_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg5ei16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vluxseg5ei16_v_bf16mf2x5_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vluxseg5.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16mf2x5_t test_vluxseg5ei16_v_bf16mf2x5_mu(vbool32_t vm, + vbfloat16mf2x5_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg5ei16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , } @test_vluxseg5ei16_v_bf16m1x5_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = call { , , , , } @llvm.riscv.vluxseg5.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , } [[TMP5]] +// +vbfloat16m1x5_t test_vluxseg5ei16_v_bf16m1x5_mu(vbool16_t vm, + vbfloat16m1x5_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg5ei16_mu(vm, vd, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vluxseg6ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vluxseg6ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..42f09322f7b72dcd649119e3025547025551766d --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vluxseg6ei16.c @@ -0,0 +1,238 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vluxseg6ei16_v_bf16mf4x6_tu( +// CHECK-RV64-SAME: { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vluxseg6.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf4x6_t test_vluxseg6ei16_v_bf16mf4x6_tu(vbfloat16mf4x6_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg6ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vluxseg6ei16_v_bf16mf2x6_tu( +// CHECK-RV64-SAME: { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vluxseg6.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf2x6_t test_vluxseg6ei16_v_bf16mf2x6_tu(vbfloat16mf2x6_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg6ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vluxseg6ei16_v_bf16m1x6_tu( +// CHECK-RV64-SAME: { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vluxseg6.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16m1x6_t test_vluxseg6ei16_v_bf16m1x6_tu(vbfloat16m1x6_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg6ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vluxseg6ei16_v_bf16mf4x6_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vluxseg6.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf4x6_t test_vluxseg6ei16_v_bf16mf4x6_tum(vbool64_t vm, + vbfloat16mf4x6_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, + size_t vl) { + return __riscv_vluxseg6ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vluxseg6ei16_v_bf16mf2x6_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vluxseg6.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf2x6_t test_vluxseg6ei16_v_bf16mf2x6_tum(vbool32_t vm, + vbfloat16mf2x6_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, + size_t vl) { + return __riscv_vluxseg6ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vluxseg6ei16_v_bf16m1x6_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vluxseg6.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16m1x6_t test_vluxseg6ei16_v_bf16m1x6_tum(vbool16_t vm, + vbfloat16m1x6_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg6ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vluxseg6ei16_v_bf16mf4x6_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vluxseg6.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf4x6_t test_vluxseg6ei16_v_bf16mf4x6_tumu(vbool64_t vm, + vbfloat16mf4x6_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, + size_t vl) { + return __riscv_vluxseg6ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vluxseg6ei16_v_bf16mf2x6_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vluxseg6.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf2x6_t test_vluxseg6ei16_v_bf16mf2x6_tumu(vbool32_t vm, + vbfloat16mf2x6_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, + size_t vl) { + return __riscv_vluxseg6ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vluxseg6ei16_v_bf16m1x6_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vluxseg6.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16m1x6_t test_vluxseg6ei16_v_bf16m1x6_tumu(vbool16_t vm, + vbfloat16m1x6_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg6ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vluxseg6ei16_v_bf16mf4x6_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vluxseg6.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf4x6_t test_vluxseg6ei16_v_bf16mf4x6_mu(vbool64_t vm, + vbfloat16mf4x6_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg6ei16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vluxseg6ei16_v_bf16mf2x6_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vluxseg6.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16mf2x6_t test_vluxseg6ei16_v_bf16mf2x6_mu(vbool32_t vm, + vbfloat16mf2x6_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg6ei16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , } @test_vluxseg6ei16_v_bf16m1x6_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = call { , , , , , } @llvm.riscv.vluxseg6.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , } [[TMP6]] +// +vbfloat16m1x6_t test_vluxseg6ei16_v_bf16m1x6_mu(vbool16_t vm, + vbfloat16m1x6_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg6ei16_mu(vm, vd, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vluxseg7ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vluxseg7ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..7a6f6eef4e0b5d22e1b037e0c2f39002a5b1974c --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vluxseg7ei16.c @@ -0,0 +1,250 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vluxseg7ei16_v_bf16mf4x7_tu( +// CHECK-RV64-SAME: { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vluxseg7.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf4x7_t test_vluxseg7ei16_v_bf16mf4x7_tu(vbfloat16mf4x7_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg7ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vluxseg7ei16_v_bf16mf2x7_tu( +// CHECK-RV64-SAME: { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vluxseg7.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf2x7_t test_vluxseg7ei16_v_bf16mf2x7_tu(vbfloat16mf2x7_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg7ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vluxseg7ei16_v_bf16m1x7_tu( +// CHECK-RV64-SAME: { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vluxseg7.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16m1x7_t test_vluxseg7ei16_v_bf16m1x7_tu(vbfloat16m1x7_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg7ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vluxseg7ei16_v_bf16mf4x7_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vluxseg7.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf4x7_t test_vluxseg7ei16_v_bf16mf4x7_tum(vbool64_t vm, + vbfloat16mf4x7_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, + size_t vl) { + return __riscv_vluxseg7ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vluxseg7ei16_v_bf16mf2x7_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vluxseg7.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf2x7_t test_vluxseg7ei16_v_bf16mf2x7_tum(vbool32_t vm, + vbfloat16mf2x7_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, + size_t vl) { + return __riscv_vluxseg7ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vluxseg7ei16_v_bf16m1x7_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vluxseg7.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16m1x7_t test_vluxseg7ei16_v_bf16m1x7_tum(vbool16_t vm, + vbfloat16m1x7_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg7ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vluxseg7ei16_v_bf16mf4x7_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vluxseg7.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf4x7_t test_vluxseg7ei16_v_bf16mf4x7_tumu(vbool64_t vm, + vbfloat16mf4x7_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, + size_t vl) { + return __riscv_vluxseg7ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vluxseg7ei16_v_bf16mf2x7_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vluxseg7.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf2x7_t test_vluxseg7ei16_v_bf16mf2x7_tumu(vbool32_t vm, + vbfloat16mf2x7_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, + size_t vl) { + return __riscv_vluxseg7ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vluxseg7ei16_v_bf16m1x7_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vluxseg7.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16m1x7_t test_vluxseg7ei16_v_bf16m1x7_tumu(vbool16_t vm, + vbfloat16m1x7_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg7ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vluxseg7ei16_v_bf16mf4x7_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vluxseg7.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf4x7_t test_vluxseg7ei16_v_bf16mf4x7_mu(vbool64_t vm, + vbfloat16mf4x7_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg7ei16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vluxseg7ei16_v_bf16mf2x7_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vluxseg7.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16mf2x7_t test_vluxseg7ei16_v_bf16mf2x7_mu(vbool32_t vm, + vbfloat16mf2x7_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg7ei16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , } @test_vluxseg7ei16_v_bf16m1x7_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = call { , , , , , , } @llvm.riscv.vluxseg7.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , , } [[TMP7]] +// +vbfloat16m1x7_t test_vluxseg7ei16_v_bf16m1x7_mu(vbool16_t vm, + vbfloat16m1x7_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg7ei16_mu(vm, vd, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vluxseg8ei16.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vluxseg8ei16.c new file mode 100644 index 0000000000000000000000000000000000000000..57207ccad17ed5b482031d09c2c6127f2d2d6abd --- /dev/null +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/bfloat16/vluxseg8ei16.c @@ -0,0 +1,262 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 4 +// REQUIRES: riscv-registered-target +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfbfmin \ +// RUN: -target-feature +experimental-zvfbfwma -disable-O0-optnone \ +// RUN: -emit-llvm %s -o - | opt -S -passes=mem2reg | \ +// RUN: FileCheck --check-prefix=CHECK-RV64 %s + +#include + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vluxseg8ei16_v_bf16mf4x8_tu( +// CHECK-RV64-SAME: { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0:[0-9]+]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vluxseg8.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf4x8_t test_vluxseg8ei16_v_bf16mf4x8_tu(vbfloat16mf4x8_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg8ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vluxseg8ei16_v_bf16mf2x8_tu( +// CHECK-RV64-SAME: { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vluxseg8.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf2x8_t test_vluxseg8ei16_v_bf16mf2x8_tu(vbfloat16mf2x8_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg8ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vluxseg8ei16_v_bf16m1x8_tu( +// CHECK-RV64-SAME: { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vluxseg8.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[RS2]], i64 [[VL]]) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16m1x8_t test_vluxseg8ei16_v_bf16m1x8_tu(vbfloat16m1x8_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg8ei16_tu(vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vluxseg8ei16_v_bf16mf4x8_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vluxseg8.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf4x8_t test_vluxseg8ei16_v_bf16mf4x8_tum(vbool64_t vm, + vbfloat16mf4x8_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, + size_t vl) { + return __riscv_vluxseg8ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vluxseg8ei16_v_bf16mf2x8_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vluxseg8.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf2x8_t test_vluxseg8ei16_v_bf16mf2x8_tum(vbool32_t vm, + vbfloat16mf2x8_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, + size_t vl) { + return __riscv_vluxseg8ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vluxseg8ei16_v_bf16m1x8_tum( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vluxseg8.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 2) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16m1x8_t test_vluxseg8ei16_v_bf16m1x8_tum(vbool16_t vm, + vbfloat16m1x8_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg8ei16_tum(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vluxseg8ei16_v_bf16mf4x8_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vluxseg8.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf4x8_t test_vluxseg8ei16_v_bf16mf4x8_tumu(vbool64_t vm, + vbfloat16mf4x8_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, + size_t vl) { + return __riscv_vluxseg8ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vluxseg8ei16_v_bf16mf2x8_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vluxseg8.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf2x8_t test_vluxseg8ei16_v_bf16mf2x8_tumu(vbool32_t vm, + vbfloat16mf2x8_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, + size_t vl) { + return __riscv_vluxseg8ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vluxseg8ei16_v_bf16m1x8_tumu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vluxseg8.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 0) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16m1x8_t test_vluxseg8ei16_v_bf16m1x8_tumu(vbool16_t vm, + vbfloat16m1x8_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg8ei16_tumu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vluxseg8ei16_v_bf16mf4x8_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vluxseg8.mask.nxv1bf16.nxv1i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf4x8_t test_vluxseg8ei16_v_bf16mf4x8_mu(vbool64_t vm, + vbfloat16mf4x8_t vd, + const __bf16 *rs1, + vuint16mf4_t rs2, size_t vl) { + return __riscv_vluxseg8ei16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vluxseg8ei16_v_bf16mf2x8_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vluxseg8.mask.nxv2bf16.nxv2i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16mf2x8_t test_vluxseg8ei16_v_bf16mf2x8_mu(vbool32_t vm, + vbfloat16mf2x8_t vd, + const __bf16 *rs1, + vuint16mf2_t rs2, size_t vl) { + return __riscv_vluxseg8ei16_mu(vm, vd, rs1, rs2, vl); +} + +// CHECK-RV64-LABEL: define dso_local { , , , , , , , } @test_vluxseg8ei16_v_bf16m1x8_mu( +// CHECK-RV64-SAME: [[VM:%.*]], { , , , , , , , } [[VD:%.*]], ptr noundef [[RS1:%.*]], [[RS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { +// CHECK-RV64-NEXT: entry: +// CHECK-RV64-NEXT: [[TMP0:%.*]] = extractvalue { , , , , , , , } [[VD]], 0 +// CHECK-RV64-NEXT: [[TMP1:%.*]] = extractvalue { , , , , , , , } [[VD]], 1 +// CHECK-RV64-NEXT: [[TMP2:%.*]] = extractvalue { , , , , , , , } [[VD]], 2 +// CHECK-RV64-NEXT: [[TMP3:%.*]] = extractvalue { , , , , , , , } [[VD]], 3 +// CHECK-RV64-NEXT: [[TMP4:%.*]] = extractvalue { , , , , , , , } [[VD]], 4 +// CHECK-RV64-NEXT: [[TMP5:%.*]] = extractvalue { , , , , , , , } [[VD]], 5 +// CHECK-RV64-NEXT: [[TMP6:%.*]] = extractvalue { , , , , , , , } [[VD]], 6 +// CHECK-RV64-NEXT: [[TMP7:%.*]] = extractvalue { , , , , , , , } [[VD]], 7 +// CHECK-RV64-NEXT: [[TMP8:%.*]] = call { , , , , , , , } @llvm.riscv.vluxseg8.mask.nxv4bf16.nxv4i16.i64( [[TMP0]], [[TMP1]], [[TMP2]], [[TMP3]], [[TMP4]], [[TMP5]], [[TMP6]], [[TMP7]], ptr [[RS1]], [[RS2]], [[VM]], i64 [[VL]], i64 1) +// CHECK-RV64-NEXT: ret { , , , , , , , } [[TMP8]] +// +vbfloat16m1x8_t test_vluxseg8ei16_v_bf16m1x8_mu(vbool16_t vm, + vbfloat16m1x8_t vd, + const __bf16 *rs1, + vuint16m1_t rs2, size_t vl) { + return __riscv_vluxseg8ei16_mu(vm, vd, rs1, rs2, vl); +} diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/vaesdf.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/vaesdf.c index 34fd46465c34a84ad0a55536b85be1258766f27e..646854e671d794cb61e31179dfb5e6e17691519c 100644 --- a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/vaesdf.c +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/vaesdf.c @@ -206,13 +206,3 @@ vuint32m8_t test_vaesdf_vv_u32m8_tu(vuint32m8_t vd, vuint32m8_t vs2, size_t vl) return __riscv_vaesdf_vv_tu(vd, vs2, vl); } -// CHECK-RV64-LABEL: define dso_local @test_vaesdf_vs_u32m8_u32m8_tu -// CHECK-RV64-SAME: ( [[VD:%.*]], [[VS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { -// CHECK-RV64-NEXT: entry: -// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vaesdf.vs.nxv16i32.nxv16i32.i64( [[VD]], [[VS2]], i64 [[VL]], i64 2) -// CHECK-RV64-NEXT: ret [[TMP0]] -// -vuint32m8_t test_vaesdf_vs_u32m8_u32m8_tu(vuint32m8_t vd, vuint32m8_t vs2, size_t vl) { - return __riscv_vaesdf_vs_tu(vd, vs2, vl); -} - diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/vaesdm.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/vaesdm.c index 2d0f8e7cafc7e88b6e2de982220df8469b7fcaec..90668f3f191bdcec897ce7dd24d86cddf9ac60d4 100644 --- a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/vaesdm.c +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/vaesdm.c @@ -206,13 +206,3 @@ vuint32m8_t test_vaesdm_vv_u32m8_tu(vuint32m8_t vd, vuint32m8_t vs2, size_t vl) return __riscv_vaesdm_vv_tu(vd, vs2, vl); } -// CHECK-RV64-LABEL: define dso_local @test_vaesdm_vs_u32m8_u32m8_tu -// CHECK-RV64-SAME: ( [[VD:%.*]], [[VS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { -// CHECK-RV64-NEXT: entry: -// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vaesdm.vs.nxv16i32.nxv16i32.i64( [[VD]], [[VS2]], i64 [[VL]], i64 2) -// CHECK-RV64-NEXT: ret [[TMP0]] -// -vuint32m8_t test_vaesdm_vs_u32m8_u32m8_tu(vuint32m8_t vd, vuint32m8_t vs2, size_t vl) { - return __riscv_vaesdm_vs_tu(vd, vs2, vl); -} - diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/vaesef.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/vaesef.c index 26518b9a709fec5e7766c782de543b3d65379e57..8bb3e69233ad3ddd506ef1bdbeaa36b4f9921915 100644 --- a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/vaesef.c +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/vaesef.c @@ -206,13 +206,3 @@ vuint32m8_t test_vaesef_vv_u32m8_tu(vuint32m8_t vd, vuint32m8_t vs2, size_t vl) return __riscv_vaesef_vv_tu(vd, vs2, vl); } -// CHECK-RV64-LABEL: define dso_local @test_vaesef_vs_u32m8_u32m8_tu -// CHECK-RV64-SAME: ( [[VD:%.*]], [[VS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { -// CHECK-RV64-NEXT: entry: -// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vaesef.vs.nxv16i32.nxv16i32.i64( [[VD]], [[VS2]], i64 [[VL]], i64 2) -// CHECK-RV64-NEXT: ret [[TMP0]] -// -vuint32m8_t test_vaesef_vs_u32m8_u32m8_tu(vuint32m8_t vd, vuint32m8_t vs2, size_t vl) { - return __riscv_vaesef_vs_tu(vd, vs2, vl); -} - diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/vaesem.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/vaesem.c index 67e13665eea8439cc2a4f0abf32cd14e12a67b3b..5a83675aa0e6dc5e05a5ee28bc5d1a2a3d051341 100644 --- a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/vaesem.c +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/vaesem.c @@ -206,13 +206,3 @@ vuint32m8_t test_vaesem_vv_u32m8_tu(vuint32m8_t vd, vuint32m8_t vs2, size_t vl) return __riscv_vaesem_vv_tu(vd, vs2, vl); } -// CHECK-RV64-LABEL: define dso_local @test_vaesem_vs_u32m8_u32m8_tu -// CHECK-RV64-SAME: ( [[VD:%.*]], [[VS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { -// CHECK-RV64-NEXT: entry: -// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vaesem.vs.nxv16i32.nxv16i32.i64( [[VD]], [[VS2]], i64 [[VL]], i64 2) -// CHECK-RV64-NEXT: ret [[TMP0]] -// -vuint32m8_t test_vaesem_vs_u32m8_u32m8_tu(vuint32m8_t vd, vuint32m8_t vs2, size_t vl) { - return __riscv_vaesem_vs_tu(vd, vs2, vl); -} - diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/vaesz.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/vaesz.c index 71698175d7b6b7a747a7a8191a73bf6060817e57..afc7827a18a15ae1a2f0e142cff415f3fb465c52 100644 --- a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/vaesz.c +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/vaesz.c @@ -156,13 +156,3 @@ vuint32m8_t test_vaesz_vs_u32m4_u32m8_tu(vuint32m8_t vd, vuint32m4_t vs2, size_t return __riscv_vaesz_tu(vd, vs2, vl); } -// CHECK-RV64-LABEL: define dso_local @test_vaesz_vs_u32m8_u32m8_tu -// CHECK-RV64-SAME: ( [[VD:%.*]], [[VS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { -// CHECK-RV64-NEXT: entry: -// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vaesz.vs.nxv16i32.nxv16i32.i64( [[VD]], [[VS2]], i64 [[VL]], i64 2) -// CHECK-RV64-NEXT: ret [[TMP0]] -// -vuint32m8_t test_vaesz_vs_u32m8_u32m8_tu(vuint32m8_t vd, vuint32m8_t vs2, size_t vl) { - return __riscv_vaesz_tu(vd, vs2, vl); -} - diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/vsm4r.c b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/vsm4r.c index 0df390bd0724a0eb3fcda654c098427940f21e73..7b70c4e2a790ffb64822a1393bd206205a368b39 100644 --- a/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/vsm4r.c +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-autogenerated/policy/overloaded/vsm4r.c @@ -206,13 +206,3 @@ vuint32m8_t test_vsm4r_vv_u32m8_tu(vuint32m8_t vd, vuint32m8_t vs2, size_t vl) { return __riscv_vsm4r_vv_tu(vd, vs2, vl); } -// CHECK-RV64-LABEL: define dso_local @test_vsm4r_vs_u32m8_u32m8_tu -// CHECK-RV64-SAME: ( [[VD:%.*]], [[VS2:%.*]], i64 noundef [[VL:%.*]]) #[[ATTR0]] { -// CHECK-RV64-NEXT: entry: -// CHECK-RV64-NEXT: [[TMP0:%.*]] = call @llvm.riscv.vsm4r.vs.nxv16i32.nxv16i32.i64( [[VD]], [[VS2]], i64 [[VL]], i64 2) -// CHECK-RV64-NEXT: ret [[TMP0]] -// -vuint32m8_t test_vsm4r_vs_u32m8_u32m8_tu(vuint32m8_t vd, vuint32m8_t vs2, size_t vl) { - return __riscv_vsm4r_vs_tu(vd, vs2, vl); -} - diff --git a/clang/test/CodeGen/SystemZ/builtins-systemz-zvector.c b/clang/test/CodeGen/SystemZ/builtins-systemz-zvector.c index 48d775b88878648d9f93ade6779a0eaf58b2da64..33f3dce73baea43bbf453257373b8551e3e7b6ee 100644 --- a/clang/test/CodeGen/SystemZ/builtins-systemz-zvector.c +++ b/clang/test/CodeGen/SystemZ/builtins-systemz-zvector.c @@ -2489,78 +2489,78 @@ void test_integer(void) { // CHECK-ASM: vno vuc = vec_cntlz(vsc); - // CHECK: call <16 x i8> @llvm.ctlz.v16i8(<16 x i8> %{{.*}}, i1 false) + // CHECK: call range(i8 0, 9) <16 x i8> @llvm.ctlz.v16i8(<16 x i8> %{{.*}}, i1 false) // CHECK-ASM: vclzb vuc = vec_cntlz(vuc); - // CHECK: call <16 x i8> @llvm.ctlz.v16i8(<16 x i8> %{{.*}}, i1 false) + // CHECK: call range(i8 0, 9) <16 x i8> @llvm.ctlz.v16i8(<16 x i8> %{{.*}}, i1 false) // CHECK-ASM: vclzb vus = vec_cntlz(vss); - // CHECK: call <8 x i16> @llvm.ctlz.v8i16(<8 x i16> %{{.*}}, i1 false) + // CHECK: call range(i16 0, 17) <8 x i16> @llvm.ctlz.v8i16(<8 x i16> %{{.*}}, i1 false) // CHECK-ASM: vclzh vus = vec_cntlz(vus); - // CHECK: call <8 x i16> @llvm.ctlz.v8i16(<8 x i16> %{{.*}}, i1 false) + // CHECK: call range(i16 0, 17) <8 x i16> @llvm.ctlz.v8i16(<8 x i16> %{{.*}}, i1 false) // CHECK-ASM: vclzh vui = vec_cntlz(vsi); - // CHECK: call <4 x i32> @llvm.ctlz.v4i32(<4 x i32> %{{.*}}, i1 false) + // CHECK: call range(i32 0, 33) <4 x i32> @llvm.ctlz.v4i32(<4 x i32> %{{.*}}, i1 false) // CHECK-ASM: vclzf vui = vec_cntlz(vui); - // CHECK: call <4 x i32> @llvm.ctlz.v4i32(<4 x i32> %{{.*}}, i1 false) + // CHECK: call range(i32 0, 33) <4 x i32> @llvm.ctlz.v4i32(<4 x i32> %{{.*}}, i1 false) // CHECK-ASM: vclzf vul = vec_cntlz(vsl); - // CHECK: call <2 x i64> @llvm.ctlz.v2i64(<2 x i64> %{{.*}}, i1 false) + // CHECK: call range(i64 0, 65) <2 x i64> @llvm.ctlz.v2i64(<2 x i64> %{{.*}}, i1 false) // CHECK-ASM: vclzg vul = vec_cntlz(vul); - // CHECK: call <2 x i64> @llvm.ctlz.v2i64(<2 x i64> %{{.*}}, i1 false) + // CHECK: call range(i64 0, 65) <2 x i64> @llvm.ctlz.v2i64(<2 x i64> %{{.*}}, i1 false) // CHECK-ASM: vclzg vuc = vec_cnttz(vsc); - // CHECK: call <16 x i8> @llvm.cttz.v16i8(<16 x i8> %{{.*}}, i1 false) + // CHECK: call range(i8 0, 9) <16 x i8> @llvm.cttz.v16i8(<16 x i8> %{{.*}}, i1 false) // CHECK-ASM: vctzb vuc = vec_cnttz(vuc); - // CHECK: call <16 x i8> @llvm.cttz.v16i8(<16 x i8> %{{.*}}, i1 false) + // CHECK: call range(i8 0, 9) <16 x i8> @llvm.cttz.v16i8(<16 x i8> %{{.*}}, i1 false) // CHECK-ASM: vctzb vus = vec_cnttz(vss); - // CHECK: call <8 x i16> @llvm.cttz.v8i16(<8 x i16> %{{.*}}, i1 false) + // CHECK: call range(i16 0, 17) <8 x i16> @llvm.cttz.v8i16(<8 x i16> %{{.*}}, i1 false) // CHECK-ASM: vctzh vus = vec_cnttz(vus); - // CHECK: call <8 x i16> @llvm.cttz.v8i16(<8 x i16> %{{.*}}, i1 false) + // CHECK: call range(i16 0, 17) <8 x i16> @llvm.cttz.v8i16(<8 x i16> %{{.*}}, i1 false) // CHECK-ASM: vctzh vui = vec_cnttz(vsi); - // CHECK: call <4 x i32> @llvm.cttz.v4i32(<4 x i32> %{{.*}}, i1 false) + // CHECK: call range(i32 0, 33) <4 x i32> @llvm.cttz.v4i32(<4 x i32> %{{.*}}, i1 false) // CHECK-ASM: vctzf vui = vec_cnttz(vui); - // CHECK: call <4 x i32> @llvm.cttz.v4i32(<4 x i32> %{{.*}}, i1 false) + // CHECK: call range(i32 0, 33) <4 x i32> @llvm.cttz.v4i32(<4 x i32> %{{.*}}, i1 false) // CHECK-ASM: vctzf vul = vec_cnttz(vsl); - // CHECK: call <2 x i64> @llvm.cttz.v2i64(<2 x i64> %{{.*}}, i1 false) + // CHECK: call range(i64 0, 65) <2 x i64> @llvm.cttz.v2i64(<2 x i64> %{{.*}}, i1 false) // CHECK-ASM: vctzg vul = vec_cnttz(vul); - // CHECK: call <2 x i64> @llvm.cttz.v2i64(<2 x i64> %{{.*}}, i1 false) + // CHECK: call range(i64 0, 65) <2 x i64> @llvm.cttz.v2i64(<2 x i64> %{{.*}}, i1 false) // CHECK-ASM: vctzg vuc = vec_popcnt(vsc); - // CHECK: call <16 x i8> @llvm.ctpop.v16i8(<16 x i8> %{{.*}}) + // CHECK: call range(i8 0, 9) <16 x i8> @llvm.ctpop.v16i8(<16 x i8> %{{.*}}) // CHECK-ASM: vpopct vuc = vec_popcnt(vuc); - // CHECK: call <16 x i8> @llvm.ctpop.v16i8(<16 x i8> %{{.*}}) + // CHECK: call range(i8 0, 9) <16 x i8> @llvm.ctpop.v16i8(<16 x i8> %{{.*}}) // CHECK-ASM: vpopct vus = vec_popcnt(vss); - // CHECK: call <8 x i16> @llvm.ctpop.v8i16(<8 x i16> %{{.*}}) + // CHECK: call range(i16 0, 17) <8 x i16> @llvm.ctpop.v8i16(<8 x i16> %{{.*}}) // (emulated) vus = vec_popcnt(vus); - // CHECK: call <8 x i16> @llvm.ctpop.v8i16(<8 x i16> %{{.*}}) + // CHECK: call range(i16 0, 17) <8 x i16> @llvm.ctpop.v8i16(<8 x i16> %{{.*}}) // (emulated) vui = vec_popcnt(vsi); - // CHECK: call <4 x i32> @llvm.ctpop.v4i32(<4 x i32> %{{.*}}) + // CHECK: call range(i32 0, 33) <4 x i32> @llvm.ctpop.v4i32(<4 x i32> %{{.*}}) // (emulated) vui = vec_popcnt(vui); - // CHECK: call <4 x i32> @llvm.ctpop.v4i32(<4 x i32> %{{.*}}) + // CHECK: call range(i32 0, 33) <4 x i32> @llvm.ctpop.v4i32(<4 x i32> %{{.*}}) // (emulated) vul = vec_popcnt(vsl); - // CHECK: call <2 x i64> @llvm.ctpop.v2i64(<2 x i64> %{{.*}}) + // CHECK: call range(i64 0, 65) <2 x i64> @llvm.ctpop.v2i64(<2 x i64> %{{.*}}) // (emulated) vul = vec_popcnt(vul); - // CHECK: call <2 x i64> @llvm.ctpop.v2i64(<2 x i64> %{{.*}}) + // CHECK: call range(i64 0, 65) <2 x i64> @llvm.ctpop.v2i64(<2 x i64> %{{.*}}) // (emulated) vsc = vec_rl(vsc, vuc); diff --git a/clang/test/CodeGen/SystemZ/builtins-systemz-zvector2.c b/clang/test/CodeGen/SystemZ/builtins-systemz-zvector2.c index 6c26b51c542e5db8a011d0fff5c2ca73008ac99b..15e72ecf51dac1e1cb61b391b29ffc4a7281cb73 100644 --- a/clang/test/CodeGen/SystemZ/builtins-systemz-zvector2.c +++ b/clang/test/CodeGen/SystemZ/builtins-systemz-zvector2.c @@ -577,28 +577,28 @@ void test_integer(void) { // CHECK-ASM: vnx vuc = vec_popcnt(vsc); - // CHECK: call <16 x i8> @llvm.ctpop.v16i8(<16 x i8> %{{.*}}) + // CHECK: call range(i8 0, 9) <16 x i8> @llvm.ctpop.v16i8(<16 x i8> %{{.*}}) // CHECK-ASM: vpopctb vuc = vec_popcnt(vuc); - // CHECK: call <16 x i8> @llvm.ctpop.v16i8(<16 x i8> %{{.*}}) + // CHECK: call range(i8 0, 9) <16 x i8> @llvm.ctpop.v16i8(<16 x i8> %{{.*}}) // CHECK-ASM: vpopctb vus = vec_popcnt(vss); - // CHECK: call <8 x i16> @llvm.ctpop.v8i16(<8 x i16> %{{.*}}) + // CHECK: call range(i16 0, 17) <8 x i16> @llvm.ctpop.v8i16(<8 x i16> %{{.*}}) // CHECK-ASM: vpopcth vus = vec_popcnt(vus); - // CHECK: call <8 x i16> @llvm.ctpop.v8i16(<8 x i16> %{{.*}}) + // CHECK: call range(i16 0, 17) <8 x i16> @llvm.ctpop.v8i16(<8 x i16> %{{.*}}) // CHECK-ASM: vpopcth vui = vec_popcnt(vsi); - // CHECK: call <4 x i32> @llvm.ctpop.v4i32(<4 x i32> %{{.*}}) + // CHECK: call range(i32 0, 33) <4 x i32> @llvm.ctpop.v4i32(<4 x i32> %{{.*}}) // CHECK-ASM: vpopctf vui = vec_popcnt(vui); - // CHECK: call <4 x i32> @llvm.ctpop.v4i32(<4 x i32> %{{.*}}) + // CHECK: call range(i32 0, 33) <4 x i32> @llvm.ctpop.v4i32(<4 x i32> %{{.*}}) // CHECK-ASM: vpopctf vul = vec_popcnt(vsl); - // CHECK: call <2 x i64> @llvm.ctpop.v2i64(<2 x i64> %{{.*}}) + // CHECK: call range(i64 0, 65) <2 x i64> @llvm.ctpop.v2i64(<2 x i64> %{{.*}}) // CHECK-ASM: vpopctg vul = vec_popcnt(vul); - // CHECK: call <2 x i64> @llvm.ctpop.v2i64(<2 x i64> %{{.*}}) + // CHECK: call range(i64 0, 65) <2 x i64> @llvm.ctpop.v2i64(<2 x i64> %{{.*}}) // CHECK-ASM: vpopctg vf = vec_slb(vf, vsi); diff --git a/clang/test/CodeGen/X86/ms-x86-intrinsics.c b/clang/test/CodeGen/X86/ms-x86-intrinsics.c index a1c90d71c8ebf58e066a7005b0ac45891f023e02..aa557c8e19a83d7b13e6d0d21033bf4440a257ef 100644 --- a/clang/test/CodeGen/X86/ms-x86-intrinsics.c +++ b/clang/test/CodeGen/X86/ms-x86-intrinsics.c @@ -48,7 +48,7 @@ long long test__readfsqword(unsigned long Offset) { __int64 test__emul(int a, int b) { return __emul(a, b); } -// CHECK-LABEL: define dso_local i64 @test__emul(i32 noundef %a, i32 noundef %b) +// CHECK-LABEL: define dso_local range(i64 -4611686016279904256, 4611686018427387905) i64 @test__emul(i32 noundef %a, i32 noundef %b) // CHECK: [[X:%[0-9]+]] = sext i32 %a to i64 // CHECK: [[Y:%[0-9]+]] = sext i32 %b to i64 // CHECK: [[RES:%[0-9]+]] = mul nsw i64 [[Y]], [[X]] @@ -57,7 +57,7 @@ __int64 test__emul(int a, int b) { unsigned __int64 test__emulu(unsigned int a, unsigned int b) { return __emulu(a, b); } -// CHECK-LABEL: define dso_local i64 @test__emulu(i32 noundef %a, i32 noundef %b) +// CHECK-LABEL: define dso_local range(i64 0, -8589934590) i64 @test__emulu(i32 noundef %a, i32 noundef %b) // CHECK: [[X:%[0-9]+]] = zext i32 %a to i64 // CHECK: [[Y:%[0-9]+]] = zext i32 %b to i64 // CHECK: [[RES:%[0-9]+]] = mul nuw i64 [[Y]], [[X]] @@ -108,13 +108,13 @@ long long test__readgsqword(unsigned long Offset) { __int64 test__mulh(__int64 a, __int64 b) { return __mulh(a, b); } -// CHECK-X64-LABEL: define dso_local i64 @test__mulh(i64 noundef %a, i64 noundef %b) +// CHECK-X64-LABEL: define dso_local range(i64 -4611686018427387904, 4611686018427387905) i64 @test__mulh(i64 noundef %a, i64 noundef %b) // CHECK-X64: = mul nsw i128 % unsigned __int64 test__umulh(unsigned __int64 a, unsigned __int64 b) { return __umulh(a, b); } -// CHECK-X64-LABEL: define dso_local i64 @test__umulh(i64 noundef %a, i64 noundef %b) +// CHECK-X64-LABEL: define dso_local range(i64 0, -1) i64 @test__umulh(i64 noundef %a, i64 noundef %b) // CHECK-X64: = mul nuw i128 % __int64 test_mul128(__int64 Multiplier, diff --git a/clang/test/CodeGen/aarch64-sve2p1-intrinsics/acle_sve2p1_fp_reduce.c b/clang/test/CodeGen/aarch64-sve2p1-intrinsics/acle_sve2p1_fp_reduce.c index e58cf4e49a37f92c8ca2db3d19db54beb5349430..9d5ffdafe8663e35a949c0fd7467ce70bb1f8c08 100644 --- a/clang/test/CodeGen/aarch64-sve2p1-intrinsics/acle_sve2p1_fp_reduce.c +++ b/clang/test/CodeGen/aarch64-sve2p1-intrinsics/acle_sve2p1_fp_reduce.c @@ -20,13 +20,13 @@ // CHECK-LABEL: @test_svaddqv_f16( // CHECK-NEXT: entry: // CHECK-NEXT: [[TMP0:%.*]] = tail call @llvm.aarch64.sve.convert.from.svbool.nxv8i1( [[PG:%.*]]) -// CHECK-NEXT: [[TMP1:%.*]] = tail call <8 x half> @llvm.aarch64.sve.addqv.v8f16.nxv8f16( [[TMP0]], [[OP:%.*]]) +// CHECK-NEXT: [[TMP1:%.*]] = tail call <8 x half> @llvm.aarch64.sve.faddqv.v8f16.nxv8f16( [[TMP0]], [[OP:%.*]]) // CHECK-NEXT: ret <8 x half> [[TMP1]] // // CPP-CHECK-LABEL: @_Z16test_svaddqv_f16u10__SVBool_tu13__SVFloat16_t( // CPP-CHECK-NEXT: entry: // CPP-CHECK-NEXT: [[TMP0:%.*]] = tail call @llvm.aarch64.sve.convert.from.svbool.nxv8i1( [[PG:%.*]]) -// CPP-CHECK-NEXT: [[TMP1:%.*]] = tail call <8 x half> @llvm.aarch64.sve.addqv.v8f16.nxv8f16( [[TMP0]], [[OP:%.*]]) +// CPP-CHECK-NEXT: [[TMP1:%.*]] = tail call <8 x half> @llvm.aarch64.sve.faddqv.v8f16.nxv8f16( [[TMP0]], [[OP:%.*]]) // CPP-CHECK-NEXT: ret <8 x half> [[TMP1]] // float16x8_t test_svaddqv_f16(svbool_t pg, svfloat16_t op) @@ -37,13 +37,13 @@ float16x8_t test_svaddqv_f16(svbool_t pg, svfloat16_t op) // CHECK-LABEL: @test_svaddqv_f32( // CHECK-NEXT: entry: // CHECK-NEXT: [[TMP0:%.*]] = tail call @llvm.aarch64.sve.convert.from.svbool.nxv4i1( [[PG:%.*]]) -// CHECK-NEXT: [[TMP1:%.*]] = tail call <4 x float> @llvm.aarch64.sve.addqv.v4f32.nxv4f32( [[TMP0]], [[OP:%.*]]) +// CHECK-NEXT: [[TMP1:%.*]] = tail call <4 x float> @llvm.aarch64.sve.faddqv.v4f32.nxv4f32( [[TMP0]], [[OP:%.*]]) // CHECK-NEXT: ret <4 x float> [[TMP1]] // // CPP-CHECK-LABEL: @_Z16test_svaddqv_f32u10__SVBool_tu13__SVFloat32_t( // CPP-CHECK-NEXT: entry: // CPP-CHECK-NEXT: [[TMP0:%.*]] = tail call @llvm.aarch64.sve.convert.from.svbool.nxv4i1( [[PG:%.*]]) -// CPP-CHECK-NEXT: [[TMP1:%.*]] = tail call <4 x float> @llvm.aarch64.sve.addqv.v4f32.nxv4f32( [[TMP0]], [[OP:%.*]]) +// CPP-CHECK-NEXT: [[TMP1:%.*]] = tail call <4 x float> @llvm.aarch64.sve.faddqv.v4f32.nxv4f32( [[TMP0]], [[OP:%.*]]) // CPP-CHECK-NEXT: ret <4 x float> [[TMP1]] // float32x4_t test_svaddqv_f32(svbool_t pg, svfloat32_t op) @@ -54,13 +54,13 @@ float32x4_t test_svaddqv_f32(svbool_t pg, svfloat32_t op) // CHECK-LABEL: @test_svaddqv_f64( // CHECK-NEXT: entry: // CHECK-NEXT: [[TMP0:%.*]] = tail call @llvm.aarch64.sve.convert.from.svbool.nxv2i1( [[PG:%.*]]) -// CHECK-NEXT: [[TMP1:%.*]] = tail call <2 x double> @llvm.aarch64.sve.addqv.v2f64.nxv2f64( [[TMP0]], [[OP:%.*]]) +// CHECK-NEXT: [[TMP1:%.*]] = tail call <2 x double> @llvm.aarch64.sve.faddqv.v2f64.nxv2f64( [[TMP0]], [[OP:%.*]]) // CHECK-NEXT: ret <2 x double> [[TMP1]] // // CPP-CHECK-LABEL: @_Z16test_svaddqv_f64u10__SVBool_tu13__SVFloat64_t( // CPP-CHECK-NEXT: entry: // CPP-CHECK-NEXT: [[TMP0:%.*]] = tail call @llvm.aarch64.sve.convert.from.svbool.nxv2i1( [[PG:%.*]]) -// CPP-CHECK-NEXT: [[TMP1:%.*]] = tail call <2 x double> @llvm.aarch64.sve.addqv.v2f64.nxv2f64( [[TMP0]], [[OP:%.*]]) +// CPP-CHECK-NEXT: [[TMP1:%.*]] = tail call <2 x double> @llvm.aarch64.sve.faddqv.v2f64.nxv2f64( [[TMP0]], [[OP:%.*]]) // CPP-CHECK-NEXT: ret <2 x double> [[TMP1]] // float64x2_t test_svaddqv_f64(svbool_t pg, svfloat64_t op) diff --git a/clang/test/CodeGen/attr-counted-by.c b/clang/test/CodeGen/attr-counted-by.c index 1fb39f9a3466675402c5bb51a1f04856d18eb79e..de30a00138ac8042ae06771eb6875d4ce767ff5f 100644 --- a/clang/test/CodeGen/attr-counted-by.c +++ b/clang/test/CodeGen/attr-counted-by.c @@ -66,7 +66,7 @@ struct anon_struct { // SANITIZE-WITH-ATTR-NEXT: [[TMP1:%.*]] = icmp ult i64 [[IDXPROM]], [[TMP0]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR-NEXT: br i1 [[TMP1]], label [[CONT3:%.*]], label [[HANDLER_OUT_OF_BOUNDS:%.*]], !prof [[PROF3:![0-9]+]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR: handler.out_of_bounds: -// SANITIZE-WITH-ATTR-NEXT: tail call void @__ubsan_handle_out_of_bounds_abort(ptr nonnull @[[GLOB2:[0-9]+]], i64 [[IDXPROM]]) #[[ATTR10:[0-9]+]], !nosanitize [[META2]] +// SANITIZE-WITH-ATTR-NEXT: tail call void @__ubsan_handle_out_of_bounds_abort(ptr nonnull @[[GLOB1:[0-9]+]], i64 [[IDXPROM]]) #[[ATTR10:[0-9]+]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR-NEXT: unreachable, !nosanitize [[META2]] // SANITIZE-WITH-ATTR: cont3: // SANITIZE-WITH-ATTR-NEXT: [[ARRAY:%.*]] = getelementptr inbounds i8, ptr [[P]], i64 12 @@ -114,7 +114,7 @@ void test1(struct annotated *p, int index, int val) { // SANITIZE-WITH-ATTR-NEXT: [[TMP1:%.*]] = icmp ugt i64 [[TMP0]], [[INDEX]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR-NEXT: br i1 [[TMP1]], label [[CONT3:%.*]], label [[HANDLER_OUT_OF_BOUNDS:%.*]], !prof [[PROF3]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR: handler.out_of_bounds: -// SANITIZE-WITH-ATTR-NEXT: tail call void @__ubsan_handle_out_of_bounds_abort(ptr nonnull @[[GLOB4:[0-9]+]], i64 [[INDEX]]) #[[ATTR10]], !nosanitize [[META2]] +// SANITIZE-WITH-ATTR-NEXT: tail call void @__ubsan_handle_out_of_bounds_abort(ptr nonnull @[[GLOB3:[0-9]+]], i64 [[INDEX]]) #[[ATTR10]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR-NEXT: unreachable, !nosanitize [[META2]] // SANITIZE-WITH-ATTR: cont3: // SANITIZE-WITH-ATTR-NEXT: [[ARRAY:%.*]] = getelementptr inbounds i8, ptr [[P]], i64 12 @@ -158,7 +158,7 @@ void test2(struct annotated *p, size_t index) { p->array[index] = __builtin_dynamic_object_size(p->array, 1); } -// SANITIZE-WITH-ATTR-LABEL: define dso_local i64 @test2_bdos( +// SANITIZE-WITH-ATTR-LABEL: define dso_local range(i64 -8589934592, 8589934589) i64 @test2_bdos( // SANITIZE-WITH-ATTR-SAME: ptr nocapture noundef readonly [[P:%.*]]) local_unnamed_addr #[[ATTR2:[0-9]+]] { // SANITIZE-WITH-ATTR-NEXT: entry: // SANITIZE-WITH-ATTR-NEXT: [[DOT_COUNTED_BY_GEP:%.*]] = getelementptr inbounds i8, ptr [[P]], i64 8 @@ -169,7 +169,7 @@ void test2(struct annotated *p, size_t index) { // SANITIZE-WITH-ATTR-NEXT: [[TMP3:%.*]] = select i1 [[TMP2]], i64 [[TMP1]], i64 0 // SANITIZE-WITH-ATTR-NEXT: ret i64 [[TMP3]] // -// NO-SANITIZE-WITH-ATTR-LABEL: define dso_local i64 @test2_bdos( +// NO-SANITIZE-WITH-ATTR-LABEL: define dso_local range(i64 -8589934592, 8589934589) i64 @test2_bdos( // NO-SANITIZE-WITH-ATTR-SAME: ptr nocapture noundef readonly [[P:%.*]]) local_unnamed_addr #[[ATTR2:[0-9]+]] { // NO-SANITIZE-WITH-ATTR-NEXT: entry: // NO-SANITIZE-WITH-ATTR-NEXT: [[DOT_COUNTED_BY_GEP:%.*]] = getelementptr inbounds i8, ptr [[P]], i64 8 @@ -203,7 +203,7 @@ size_t test2_bdos(struct annotated *p) { // SANITIZE-WITH-ATTR-NEXT: [[TMP1:%.*]] = icmp ugt i64 [[TMP0]], [[INDEX]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR-NEXT: br i1 [[TMP1]], label [[CONT3:%.*]], label [[HANDLER_OUT_OF_BOUNDS:%.*]], !prof [[PROF3]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR: handler.out_of_bounds: -// SANITIZE-WITH-ATTR-NEXT: tail call void @__ubsan_handle_out_of_bounds_abort(ptr nonnull @[[GLOB5:[0-9]+]], i64 [[INDEX]]) #[[ATTR10]], !nosanitize [[META2]] +// SANITIZE-WITH-ATTR-NEXT: tail call void @__ubsan_handle_out_of_bounds_abort(ptr nonnull @[[GLOB4:[0-9]+]], i64 [[INDEX]]) #[[ATTR10]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR-NEXT: unreachable, !nosanitize [[META2]] // SANITIZE-WITH-ATTR: cont3: // SANITIZE-WITH-ATTR-NEXT: [[ARRAY:%.*]] = getelementptr inbounds i8, ptr [[P]], i64 12 @@ -257,7 +257,7 @@ void test3(struct annotated *p, size_t index) { p->array[index] = __builtin_dynamic_object_size(p, 1); } -// SANITIZE-WITH-ATTR-LABEL: define dso_local i64 @test3_bdos( +// SANITIZE-WITH-ATTR-LABEL: define dso_local range(i64 0, 8589934601) i64 @test3_bdos( // SANITIZE-WITH-ATTR-SAME: ptr nocapture noundef readonly [[P:%.*]]) local_unnamed_addr #[[ATTR2]] { // SANITIZE-WITH-ATTR-NEXT: entry: // SANITIZE-WITH-ATTR-NEXT: [[DOT_COUNTED_BY_GEP:%.*]] = getelementptr inbounds i8, ptr [[P]], i64 8 @@ -270,7 +270,7 @@ void test3(struct annotated *p, size_t index) { // SANITIZE-WITH-ATTR-NEXT: [[TMP5:%.*]] = select i1 [[TMP4]], i64 [[TMP3]], i64 0 // SANITIZE-WITH-ATTR-NEXT: ret i64 [[TMP5]] // -// NO-SANITIZE-WITH-ATTR-LABEL: define dso_local i64 @test3_bdos( +// NO-SANITIZE-WITH-ATTR-LABEL: define dso_local range(i64 0, 8589934601) i64 @test3_bdos( // NO-SANITIZE-WITH-ATTR-SAME: ptr nocapture noundef readonly [[P:%.*]]) local_unnamed_addr #[[ATTR2]] { // NO-SANITIZE-WITH-ATTR-NEXT: entry: // NO-SANITIZE-WITH-ATTR-NEXT: [[DOT_COUNTED_BY_GEP:%.*]] = getelementptr inbounds i8, ptr [[P]], i64 8 @@ -308,7 +308,7 @@ size_t test3_bdos(struct annotated *p) { // SANITIZE-WITH-ATTR-NEXT: [[TMP1:%.*]] = icmp ult i64 [[IDXPROM]], [[TMP0]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR-NEXT: br i1 [[TMP1]], label [[CONT4:%.*]], label [[HANDLER_OUT_OF_BOUNDS:%.*]], !prof [[PROF3]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR: handler.out_of_bounds: -// SANITIZE-WITH-ATTR-NEXT: tail call void @__ubsan_handle_out_of_bounds_abort(ptr nonnull @[[GLOB6:[0-9]+]], i64 [[IDXPROM]]) #[[ATTR10]], !nosanitize [[META2]] +// SANITIZE-WITH-ATTR-NEXT: tail call void @__ubsan_handle_out_of_bounds_abort(ptr nonnull @[[GLOB5:[0-9]+]], i64 [[IDXPROM]]) #[[ATTR10]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR-NEXT: unreachable, !nosanitize [[META2]] // SANITIZE-WITH-ATTR: cont4: // SANITIZE-WITH-ATTR-NEXT: [[TMP2:%.*]] = icmp sgt i32 [[DOT_COUNTED_BY_LOAD]], 2 @@ -325,7 +325,7 @@ size_t test3_bdos(struct annotated *p) { // SANITIZE-WITH-ATTR-NEXT: [[TMP7:%.*]] = icmp ult i64 [[IDXPROM13]], [[TMP6]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR-NEXT: br i1 [[TMP7]], label [[CONT20:%.*]], label [[HANDLER_OUT_OF_BOUNDS16:%.*]], !prof [[PROF3]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR: handler.out_of_bounds16: -// SANITIZE-WITH-ATTR-NEXT: tail call void @__ubsan_handle_out_of_bounds_abort(ptr nonnull @[[GLOB7:[0-9]+]], i64 [[IDXPROM13]]) #[[ATTR10]], !nosanitize [[META2]] +// SANITIZE-WITH-ATTR-NEXT: tail call void @__ubsan_handle_out_of_bounds_abort(ptr nonnull @[[GLOB6:[0-9]+]], i64 [[IDXPROM13]]) #[[ATTR10]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR-NEXT: unreachable, !nosanitize [[META2]] // SANITIZE-WITH-ATTR: cont20: // SANITIZE-WITH-ATTR-NEXT: [[TMP8:%.*]] = icmp sgt i32 [[DOT_COUNTED_BY_LOAD7]], 3 @@ -342,7 +342,7 @@ size_t test3_bdos(struct annotated *p) { // SANITIZE-WITH-ATTR-NEXT: [[TMP13:%.*]] = icmp ult i64 [[IDXPROM30]], [[TMP12]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR-NEXT: br i1 [[TMP13]], label [[CONT37:%.*]], label [[HANDLER_OUT_OF_BOUNDS33:%.*]], !prof [[PROF3]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR: handler.out_of_bounds33: -// SANITIZE-WITH-ATTR-NEXT: tail call void @__ubsan_handle_out_of_bounds_abort(ptr nonnull @[[GLOB8:[0-9]+]], i64 [[IDXPROM30]]) #[[ATTR10]], !nosanitize [[META2]] +// SANITIZE-WITH-ATTR-NEXT: tail call void @__ubsan_handle_out_of_bounds_abort(ptr nonnull @[[GLOB7:[0-9]+]], i64 [[IDXPROM30]]) #[[ATTR10]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR-NEXT: unreachable, !nosanitize [[META2]] // SANITIZE-WITH-ATTR: cont37: // SANITIZE-WITH-ATTR-NEXT: [[ARRAYIDX35:%.*]] = getelementptr inbounds [0 x i32], ptr [[ARRAY]], i64 0, i64 [[IDXPROM30]] @@ -441,7 +441,7 @@ void test4(struct annotated *p, int index, int fam_idx) { p->array[index + 2] = (unsigned char)__builtin_dynamic_object_size(&(p->array[fam_idx]), 1); } -// SANITIZE-WITH-ATTR-LABEL: define dso_local i64 @test4_bdos( +// SANITIZE-WITH-ATTR-LABEL: define dso_local range(i64 -17179869180, 17179869181) i64 @test4_bdos( // SANITIZE-WITH-ATTR-SAME: ptr nocapture noundef readonly [[P:%.*]], i32 noundef [[INDEX:%.*]]) local_unnamed_addr #[[ATTR2]] { // SANITIZE-WITH-ATTR-NEXT: entry: // SANITIZE-WITH-ATTR-NEXT: [[DOT_COUNTED_BY_GEP:%.*]] = getelementptr inbounds i8, ptr [[P]], i64 8 @@ -456,7 +456,7 @@ void test4(struct annotated *p, int index, int fam_idx) { // SANITIZE-WITH-ATTR-NEXT: [[TMP7:%.*]] = select i1 [[TMP6]], i64 [[TMP3]], i64 0 // SANITIZE-WITH-ATTR-NEXT: ret i64 [[TMP7]] // -// NO-SANITIZE-WITH-ATTR-LABEL: define dso_local i64 @test4_bdos( +// NO-SANITIZE-WITH-ATTR-LABEL: define dso_local range(i64 -17179869180, 17179869181) i64 @test4_bdos( // NO-SANITIZE-WITH-ATTR-SAME: ptr nocapture noundef readonly [[P:%.*]], i32 noundef [[INDEX:%.*]]) local_unnamed_addr #[[ATTR2]] { // NO-SANITIZE-WITH-ATTR-NEXT: entry: // NO-SANITIZE-WITH-ATTR-NEXT: [[DOT_COUNTED_BY_GEP:%.*]] = getelementptr inbounds i8, ptr [[P]], i64 8 @@ -494,7 +494,7 @@ size_t test4_bdos(struct annotated *p, int index) { // SANITIZE-WITH-ATTR-NEXT: [[TMP0:%.*]] = icmp ugt i64 [[DOT_COUNTED_BY_LOAD]], [[IDXPROM]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR-NEXT: br i1 [[TMP0]], label [[CONT3:%.*]], label [[HANDLER_OUT_OF_BOUNDS:%.*]], !prof [[PROF3]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR: handler.out_of_bounds: -// SANITIZE-WITH-ATTR-NEXT: tail call void @__ubsan_handle_out_of_bounds_abort(ptr nonnull @[[GLOB9:[0-9]+]], i64 [[IDXPROM]]) #[[ATTR10]], !nosanitize [[META2]] +// SANITIZE-WITH-ATTR-NEXT: tail call void @__ubsan_handle_out_of_bounds_abort(ptr nonnull @[[GLOB8:[0-9]+]], i64 [[IDXPROM]]) #[[ATTR10]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR-NEXT: unreachable, !nosanitize [[META2]] // SANITIZE-WITH-ATTR: cont3: // SANITIZE-WITH-ATTR-NEXT: [[TMP1:%.*]] = getelementptr inbounds i8, ptr [[P]], i64 16 @@ -545,7 +545,7 @@ void test5(struct anon_struct *p, int index) { p->array[index] = __builtin_dynamic_object_size(p, 1); } -// SANITIZE-WITH-ATTR-LABEL: define dso_local i64 @test5_bdos( +// SANITIZE-WITH-ATTR-LABEL: define dso_local range(i64 16, 1) i64 @test5_bdos( // SANITIZE-WITH-ATTR-SAME: ptr nocapture noundef readonly [[P:%.*]]) local_unnamed_addr #[[ATTR2]] { // SANITIZE-WITH-ATTR-NEXT: entry: // SANITIZE-WITH-ATTR-NEXT: [[DOT_COUNTED_BY_GEP:%.*]] = getelementptr inbounds i8, ptr [[P]], i64 8 @@ -556,7 +556,7 @@ void test5(struct anon_struct *p, int index) { // SANITIZE-WITH-ATTR-NEXT: [[TMP2:%.*]] = select i1 [[DOTINV]], i64 0, i64 [[TMP1]] // SANITIZE-WITH-ATTR-NEXT: ret i64 [[TMP2]] // -// NO-SANITIZE-WITH-ATTR-LABEL: define dso_local i64 @test5_bdos( +// NO-SANITIZE-WITH-ATTR-LABEL: define dso_local range(i64 16, 1) i64 @test5_bdos( // NO-SANITIZE-WITH-ATTR-SAME: ptr nocapture noundef readonly [[P:%.*]]) local_unnamed_addr #[[ATTR2]] { // NO-SANITIZE-WITH-ATTR-NEXT: entry: // NO-SANITIZE-WITH-ATTR-NEXT: [[DOT_COUNTED_BY_GEP:%.*]] = getelementptr inbounds i8, ptr [[P]], i64 8 @@ -590,7 +590,7 @@ size_t test5_bdos(struct anon_struct *p) { // SANITIZE-WITH-ATTR-NEXT: [[TMP0:%.*]] = icmp ugt i64 [[DOT_COUNTED_BY_LOAD]], [[IDXPROM]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR-NEXT: br i1 [[TMP0]], label [[CONT3:%.*]], label [[HANDLER_OUT_OF_BOUNDS:%.*]], !prof [[PROF3]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR: handler.out_of_bounds: -// SANITIZE-WITH-ATTR-NEXT: tail call void @__ubsan_handle_out_of_bounds_abort(ptr nonnull @[[GLOB10:[0-9]+]], i64 [[IDXPROM]]) #[[ATTR10]], !nosanitize [[META2]] +// SANITIZE-WITH-ATTR-NEXT: tail call void @__ubsan_handle_out_of_bounds_abort(ptr nonnull @[[GLOB9:[0-9]+]], i64 [[IDXPROM]]) #[[ATTR10]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR-NEXT: unreachable, !nosanitize [[META2]] // SANITIZE-WITH-ATTR: cont3: // SANITIZE-WITH-ATTR-NEXT: [[TMP1:%.*]] = getelementptr inbounds i8, ptr [[P]], i64 16 @@ -683,7 +683,7 @@ size_t test6_bdos(struct anon_struct *p) { // SANITIZE-WITH-ATTR-NEXT: [[TMP2:%.*]] = icmp ult i64 [[IDXPROM]], [[TMP1]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR-NEXT: br i1 [[TMP2]], label [[CONT7:%.*]], label [[HANDLER_OUT_OF_BOUNDS:%.*]], !prof [[PROF3]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR: handler.out_of_bounds: -// SANITIZE-WITH-ATTR-NEXT: tail call void @__ubsan_handle_out_of_bounds_abort(ptr nonnull @[[GLOB12:[0-9]+]], i64 [[IDXPROM]]) #[[ATTR10]], !nosanitize [[META2]] +// SANITIZE-WITH-ATTR-NEXT: tail call void @__ubsan_handle_out_of_bounds_abort(ptr nonnull @[[GLOB11:[0-9]+]], i64 [[IDXPROM]]) #[[ATTR10]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR-NEXT: unreachable, !nosanitize [[META2]] // SANITIZE-WITH-ATTR: cont7: // SANITIZE-WITH-ATTR-NEXT: [[INTS:%.*]] = getelementptr inbounds i8, ptr [[P]], i64 9 @@ -756,7 +756,7 @@ size_t test7_bdos(struct union_of_fams *p) { // SANITIZE-WITH-ATTR-NEXT: [[TMP1:%.*]] = icmp ult i64 [[IDXPROM]], [[TMP0]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR-NEXT: br i1 [[TMP1]], label [[CONT9:%.*]], label [[HANDLER_OUT_OF_BOUNDS:%.*]], !prof [[PROF3]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR: handler.out_of_bounds: -// SANITIZE-WITH-ATTR-NEXT: tail call void @__ubsan_handle_out_of_bounds_abort(ptr nonnull @[[GLOB13:[0-9]+]], i64 [[IDXPROM]]) #[[ATTR10]], !nosanitize [[META2]] +// SANITIZE-WITH-ATTR-NEXT: tail call void @__ubsan_handle_out_of_bounds_abort(ptr nonnull @[[GLOB12:[0-9]+]], i64 [[IDXPROM]]) #[[ATTR10]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR-NEXT: unreachable, !nosanitize [[META2]] // SANITIZE-WITH-ATTR: cont9: // SANITIZE-WITH-ATTR-NEXT: [[INTS:%.*]] = getelementptr inbounds i8, ptr [[P]], i64 9 @@ -797,7 +797,7 @@ void test8(struct union_of_fams *p, int index) { p->ints[index] = __builtin_dynamic_object_size(p->ints, 1); } -// SANITIZE-WITH-ATTR-LABEL: define dso_local i64 @test8_bdos( +// SANITIZE-WITH-ATTR-LABEL: define dso_local range(i64 0, 256) i64 @test8_bdos( // SANITIZE-WITH-ATTR-SAME: ptr nocapture noundef readonly [[P:%.*]]) local_unnamed_addr #[[ATTR2]] { // SANITIZE-WITH-ATTR-NEXT: entry: // SANITIZE-WITH-ATTR-NEXT: [[DOT_COUNTED_BY_GEP:%.*]] = getelementptr inbounds i8, ptr [[P]], i64 8 @@ -805,7 +805,7 @@ void test8(struct union_of_fams *p, int index) { // SANITIZE-WITH-ATTR-NEXT: [[TMP0:%.*]] = zext i8 [[DOT_COUNTED_BY_LOAD]] to i64 // SANITIZE-WITH-ATTR-NEXT: ret i64 [[TMP0]] // -// NO-SANITIZE-WITH-ATTR-LABEL: define dso_local i64 @test8_bdos( +// NO-SANITIZE-WITH-ATTR-LABEL: define dso_local range(i64 0, 256) i64 @test8_bdos( // NO-SANITIZE-WITH-ATTR-SAME: ptr nocapture noundef readonly [[P:%.*]]) local_unnamed_addr #[[ATTR2]] { // NO-SANITIZE-WITH-ATTR-NEXT: entry: // NO-SANITIZE-WITH-ATTR-NEXT: [[DOT_COUNTED_BY_GEP:%.*]] = getelementptr inbounds i8, ptr [[P]], i64 8 @@ -955,7 +955,7 @@ void test10(struct union_of_fams *p, int index) { p->bytes[index] = (unsigned char)__builtin_dynamic_object_size(p->bytes, 1); } -// SANITIZE-WITH-ATTR-LABEL: define dso_local i64 @test10_bdos( +// SANITIZE-WITH-ATTR-LABEL: define dso_local range(i64 -2147483648, 2147483648) i64 @test10_bdos( // SANITIZE-WITH-ATTR-SAME: ptr nocapture noundef readonly [[P:%.*]]) local_unnamed_addr #[[ATTR2]] { // SANITIZE-WITH-ATTR-NEXT: entry: // SANITIZE-WITH-ATTR-NEXT: [[DOT_COUNTED_BY_GEP:%.*]] = getelementptr inbounds i8, ptr [[P]], i64 8 @@ -964,7 +964,7 @@ void test10(struct union_of_fams *p, int index) { // SANITIZE-WITH-ATTR-NEXT: [[TMP0:%.*]] = zext nneg i32 [[NARROW]] to i64 // SANITIZE-WITH-ATTR-NEXT: ret i64 [[TMP0]] // -// NO-SANITIZE-WITH-ATTR-LABEL: define dso_local i64 @test10_bdos( +// NO-SANITIZE-WITH-ATTR-LABEL: define dso_local range(i64 -2147483648, 2147483648) i64 @test10_bdos( // NO-SANITIZE-WITH-ATTR-SAME: ptr nocapture noundef readonly [[P:%.*]]) local_unnamed_addr #[[ATTR2]] { // NO-SANITIZE-WITH-ATTR-NEXT: entry: // NO-SANITIZE-WITH-ATTR-NEXT: [[DOT_COUNTED_BY_GEP:%.*]] = getelementptr inbounds i8, ptr [[P]], i64 8 @@ -1095,10 +1095,10 @@ int test12_a, test12_b; // SANITIZE-WITH-ATTR-NEXT: [[DOTNOT:%.*]] = icmp eq i32 [[DOTCOUNTED_BY_LOAD]], 0 // SANITIZE-WITH-ATTR-NEXT: br i1 [[DOTNOT]], label [[HANDLER_OUT_OF_BOUNDS4:%.*]], label [[HANDLER_TYPE_MISMATCH6:%.*]], !prof [[PROF10:![0-9]+]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR: handler.out_of_bounds4: -// SANITIZE-WITH-ATTR-NEXT: tail call void @__ubsan_handle_out_of_bounds_abort(ptr nonnull @[[GLOB19:[0-9]+]], i64 0) #[[ATTR10]], !nosanitize [[META2]] +// SANITIZE-WITH-ATTR-NEXT: tail call void @__ubsan_handle_out_of_bounds_abort(ptr nonnull @[[GLOB20:[0-9]+]], i64 0) #[[ATTR10]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR-NEXT: unreachable, !nosanitize [[META2]] // SANITIZE-WITH-ATTR: handler.type_mismatch6: -// SANITIZE-WITH-ATTR-NEXT: tail call void @__ubsan_handle_type_mismatch_v1_abort(ptr nonnull @[[GLOB20:[0-9]+]], i64 ptrtoint (ptr getelementptr inbounds ([[STRUCT_ANON_5:%.*]], ptr @test12_foo, i64 1, i32 0, i32 0, i32 0) to i64)) #[[ATTR10]], !nosanitize [[META2]] +// SANITIZE-WITH-ATTR-NEXT: tail call void @__ubsan_handle_type_mismatch_v1_abort(ptr nonnull @[[GLOB21:[0-9]+]], i64 ptrtoint (ptr getelementptr inbounds ([[STRUCT_ANON_5:%.*]], ptr @test12_foo, i64 1, i32 0, i32 0, i32 0) to i64)) #[[ATTR10]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR-NEXT: unreachable, !nosanitize [[META2]] // // NO-SANITIZE-WITH-ATTR-LABEL: define dso_local noundef i32 @test12( @@ -1188,7 +1188,7 @@ struct test13_bar { // SANITIZE-WITH-ATTR-NEXT: [[TMP2:%.*]] = icmp ugt i64 [[TMP1]], [[INDEX]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR-NEXT: br i1 [[TMP2]], label [[CONT5:%.*]], label [[HANDLER_OUT_OF_BOUNDS:%.*]], !prof [[PROF3]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR: handler.out_of_bounds: -// SANITIZE-WITH-ATTR-NEXT: tail call void @__ubsan_handle_out_of_bounds_abort(ptr nonnull @[[GLOB23:[0-9]+]], i64 [[INDEX]]) #[[ATTR10]], !nosanitize [[META2]] +// SANITIZE-WITH-ATTR-NEXT: tail call void @__ubsan_handle_out_of_bounds_abort(ptr nonnull @[[GLOB24:[0-9]+]], i64 [[INDEX]]) #[[ATTR10]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR-NEXT: unreachable, !nosanitize [[META2]] // SANITIZE-WITH-ATTR: cont5: // SANITIZE-WITH-ATTR-NEXT: [[REVMAP:%.*]] = getelementptr inbounds i8, ptr [[TMP0]], i64 16 @@ -1249,7 +1249,7 @@ struct test14_foo { // SANITIZE-WITH-ATTR-NEXT: br i1 [[TMP0]], label [[TRAP:%.*]], label [[HANDLER_OUT_OF_BOUNDS:%.*]], !prof [[PROF3]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR: handler.out_of_bounds: // SANITIZE-WITH-ATTR-NEXT: [[IDXPROM:%.*]] = sext i32 [[IDX]] to i64 -// SANITIZE-WITH-ATTR-NEXT: tail call void @__ubsan_handle_out_of_bounds_abort(ptr nonnull @[[GLOB24:[0-9]+]], i64 [[IDXPROM]]) #[[ATTR10]], !nosanitize [[META2]] +// SANITIZE-WITH-ATTR-NEXT: tail call void @__ubsan_handle_out_of_bounds_abort(ptr nonnull @[[GLOB25:[0-9]+]], i64 [[IDXPROM]]) #[[ATTR10]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR-NEXT: unreachable, !nosanitize [[META2]] // SANITIZE-WITH-ATTR: trap: // SANITIZE-WITH-ATTR-NEXT: tail call void @llvm.trap() #[[ATTR10]] @@ -1305,7 +1305,7 @@ int test14(int idx) { // SANITIZE-WITH-ATTR-NEXT: br i1 [[TMP0]], label [[TRAP:%.*]], label [[HANDLER_OUT_OF_BOUNDS:%.*]], !prof [[PROF3]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR: handler.out_of_bounds: // SANITIZE-WITH-ATTR-NEXT: [[IDXPROM:%.*]] = sext i32 [[IDX]] to i64 -// SANITIZE-WITH-ATTR-NEXT: tail call void @__ubsan_handle_out_of_bounds_abort(ptr nonnull @[[GLOB25:[0-9]+]], i64 [[IDXPROM]]) #[[ATTR10]], !nosanitize [[META2]] +// SANITIZE-WITH-ATTR-NEXT: tail call void @__ubsan_handle_out_of_bounds_abort(ptr nonnull @[[GLOB27:[0-9]+]], i64 [[IDXPROM]]) #[[ATTR10]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR-NEXT: unreachable, !nosanitize [[META2]] // SANITIZE-WITH-ATTR: trap: // SANITIZE-WITH-ATTR-NEXT: tail call void @llvm.trap() #[[ATTR10]] @@ -1326,7 +1326,7 @@ int test14(int idx) { // SANITIZE-WITHOUT-ATTR-NEXT: br i1 [[TMP0]], label [[TRAP:%.*]], label [[HANDLER_OUT_OF_BOUNDS:%.*]], !prof [[PROF8]], !nosanitize [[META9]] // SANITIZE-WITHOUT-ATTR: handler.out_of_bounds: // SANITIZE-WITHOUT-ATTR-NEXT: [[IDXPROM:%.*]] = sext i32 [[IDX]] to i64 -// SANITIZE-WITHOUT-ATTR-NEXT: tail call void @__ubsan_handle_out_of_bounds_abort(ptr nonnull @[[GLOB10:[0-9]+]], i64 [[IDXPROM]]) #[[ATTR8]], !nosanitize [[META9]] +// SANITIZE-WITHOUT-ATTR-NEXT: tail call void @__ubsan_handle_out_of_bounds_abort(ptr nonnull @[[GLOB11:[0-9]+]], i64 [[IDXPROM]]) #[[ATTR8]], !nosanitize [[META9]] // SANITIZE-WITHOUT-ATTR-NEXT: unreachable, !nosanitize [[META9]] // SANITIZE-WITHOUT-ATTR: trap: // SANITIZE-WITHOUT-ATTR-NEXT: tail call void @llvm.trap() #[[ATTR8]] @@ -1487,7 +1487,7 @@ struct tests_foo { // SANITIZE-WITH-ATTR-NEXT: [[TMP0:%.*]] = icmp ugt i32 [[DOTCOUNTED_BY_LOAD]], 10 // SANITIZE-WITH-ATTR-NEXT: br i1 [[TMP0]], label [[CONT4:%.*]], label [[HANDLER_OUT_OF_BOUNDS:%.*]], !prof [[PROF3]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR: handler.out_of_bounds: -// SANITIZE-WITH-ATTR-NEXT: tail call void @__ubsan_handle_out_of_bounds_abort(ptr nonnull @[[GLOB26:[0-9]+]], i64 10) #[[ATTR10]], !nosanitize [[META2]] +// SANITIZE-WITH-ATTR-NEXT: tail call void @__ubsan_handle_out_of_bounds_abort(ptr nonnull @[[GLOB28:[0-9]+]], i64 10) #[[ATTR10]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR-NEXT: unreachable, !nosanitize [[META2]] // SANITIZE-WITH-ATTR: cont4: // SANITIZE-WITH-ATTR-NEXT: [[ARRAYIDX2:%.*]] = getelementptr inbounds i8, ptr [[VAR]], i64 84 @@ -1528,7 +1528,7 @@ int test24(int c, struct tests_foo *var) { // SANITIZE-WITH-ATTR-NEXT: [[TMP1:%.*]] = icmp ugt i32 [[DOTCOUNTED_BY_LOAD]], 10 // SANITIZE-WITH-ATTR-NEXT: br i1 [[TMP1]], label [[CONT5:%.*]], label [[HANDLER_OUT_OF_BOUNDS:%.*]], !prof [[PROF3]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR: handler.out_of_bounds: -// SANITIZE-WITH-ATTR-NEXT: tail call void @__ubsan_handle_out_of_bounds_abort(ptr nonnull @[[GLOB27:[0-9]+]], i64 10) #[[ATTR10]], !nosanitize [[META2]] +// SANITIZE-WITH-ATTR-NEXT: tail call void @__ubsan_handle_out_of_bounds_abort(ptr nonnull @[[GLOB29:[0-9]+]], i64 10) #[[ATTR10]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR-NEXT: unreachable, !nosanitize [[META2]] // SANITIZE-WITH-ATTR: cont5: // SANITIZE-WITH-ATTR-NEXT: [[ARRAYIDX:%.*]] = getelementptr inbounds i8, ptr [[TMP0]], i64 44 @@ -1580,7 +1580,7 @@ struct test26_foo { // SANITIZE-WITH-ATTR-NEXT: [[TMP1:%.*]] = icmp ult i64 [[IDXPROM]], [[TMP0]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR-NEXT: br i1 [[TMP1]], label [[CONT5:%.*]], label [[HANDLER_OUT_OF_BOUNDS:%.*]], !prof [[PROF3]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR: handler.out_of_bounds: -// SANITIZE-WITH-ATTR-NEXT: tail call void @__ubsan_handle_out_of_bounds_abort(ptr nonnull @[[GLOB28:[0-9]+]], i64 [[IDXPROM]]) #[[ATTR10]], !nosanitize [[META2]] +// SANITIZE-WITH-ATTR-NEXT: tail call void @__ubsan_handle_out_of_bounds_abort(ptr nonnull @[[GLOB30:[0-9]+]], i64 [[IDXPROM]]) #[[ATTR10]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR-NEXT: unreachable, !nosanitize [[META2]] // SANITIZE-WITH-ATTR: cont5: // SANITIZE-WITH-ATTR-NEXT: [[ARR:%.*]] = getelementptr inbounds i8, ptr [[FOO]], i64 8 @@ -1651,7 +1651,7 @@ struct test27_foo { // SANITIZE-WITH-ATTR-NEXT: [[TMP1:%.*]] = icmp ult i64 [[IDXPROM]], [[TMP0]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR-NEXT: br i1 [[TMP1]], label [[CONT3:%.*]], label [[HANDLER_OUT_OF_BOUNDS:%.*]], !prof [[PROF3]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR: handler.out_of_bounds: -// SANITIZE-WITH-ATTR-NEXT: tail call void @__ubsan_handle_out_of_bounds_abort(ptr nonnull @[[GLOB30:[0-9]+]], i64 [[IDXPROM]]) #[[ATTR10]], !nosanitize [[META2]] +// SANITIZE-WITH-ATTR-NEXT: tail call void @__ubsan_handle_out_of_bounds_abort(ptr nonnull @[[GLOB32:[0-9]+]], i64 [[IDXPROM]]) #[[ATTR10]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR-NEXT: unreachable, !nosanitize [[META2]] // SANITIZE-WITH-ATTR: cont3: // SANITIZE-WITH-ATTR-NEXT: [[ENTRIES:%.*]] = getelementptr inbounds i8, ptr [[P]], i64 24 @@ -1717,7 +1717,7 @@ struct test28_foo { // SANITIZE-WITH-ATTR-NEXT: [[TMP4:%.*]] = icmp ult i64 [[IDXPROM]], [[TMP3]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR-NEXT: br i1 [[TMP4]], label [[CONT17:%.*]], label [[HANDLER_OUT_OF_BOUNDS:%.*]], !prof [[PROF3]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR: handler.out_of_bounds: -// SANITIZE-WITH-ATTR-NEXT: tail call void @__ubsan_handle_out_of_bounds_abort(ptr nonnull @[[GLOB31:[0-9]+]], i64 [[IDXPROM]]) #[[ATTR10]], !nosanitize [[META2]] +// SANITIZE-WITH-ATTR-NEXT: tail call void @__ubsan_handle_out_of_bounds_abort(ptr nonnull @[[GLOB34:[0-9]+]], i64 [[IDXPROM]]) #[[ATTR10]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR-NEXT: unreachable, !nosanitize [[META2]] // SANITIZE-WITH-ATTR: cont17: // SANITIZE-WITH-ATTR-NEXT: [[ARR:%.*]] = getelementptr inbounds i8, ptr [[TMP2]], i64 12 @@ -1779,7 +1779,7 @@ struct annotated_struct_array { // SANITIZE-WITH-ATTR-NEXT: [[TMP1:%.*]] = zext i32 [[IDX1]] to i64 // SANITIZE-WITH-ATTR-NEXT: br i1 [[TMP0]], label [[CONT3:%.*]], label [[HANDLER_OUT_OF_BOUNDS:%.*]], !prof [[PROF3]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR: handler.out_of_bounds: -// SANITIZE-WITH-ATTR-NEXT: tail call void @__ubsan_handle_out_of_bounds_abort(ptr nonnull @[[GLOB33:[0-9]+]], i64 [[TMP1]]) #[[ATTR10]], !nosanitize [[META2]] +// SANITIZE-WITH-ATTR-NEXT: tail call void @__ubsan_handle_out_of_bounds_abort(ptr nonnull @[[GLOB36:[0-9]+]], i64 [[TMP1]]) #[[ATTR10]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR-NEXT: unreachable, !nosanitize [[META2]] // SANITIZE-WITH-ATTR: cont3: // SANITIZE-WITH-ATTR-NEXT: [[ARRAYIDX:%.*]] = getelementptr inbounds [10 x ptr], ptr [[ANN]], i64 0, i64 [[TMP1]] @@ -1791,7 +1791,7 @@ struct annotated_struct_array { // SANITIZE-WITH-ATTR-NEXT: [[TMP4:%.*]] = icmp ult i64 [[IDXPROM15]], [[TMP3]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR-NEXT: br i1 [[TMP4]], label [[CONT20:%.*]], label [[HANDLER_OUT_OF_BOUNDS16:%.*]], !prof [[PROF3]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR: handler.out_of_bounds16: -// SANITIZE-WITH-ATTR-NEXT: tail call void @__ubsan_handle_out_of_bounds_abort(ptr nonnull @[[GLOB34:[0-9]+]], i64 [[IDXPROM15]]) #[[ATTR10]], !nosanitize [[META2]] +// SANITIZE-WITH-ATTR-NEXT: tail call void @__ubsan_handle_out_of_bounds_abort(ptr nonnull @[[GLOB37:[0-9]+]], i64 [[IDXPROM15]]) #[[ATTR10]], !nosanitize [[META2]] // SANITIZE-WITH-ATTR-NEXT: unreachable, !nosanitize [[META2]] // SANITIZE-WITH-ATTR: cont20: // SANITIZE-WITH-ATTR-NEXT: [[ARRAY:%.*]] = getelementptr inbounds i8, ptr [[TMP2]], i64 12 @@ -1826,7 +1826,7 @@ struct annotated_struct_array { // SANITIZE-WITHOUT-ATTR-NEXT: [[TMP1:%.*]] = zext i32 [[IDX1]] to i64 // SANITIZE-WITHOUT-ATTR-NEXT: br i1 [[TMP0]], label [[CONT21:%.*]], label [[HANDLER_OUT_OF_BOUNDS:%.*]], !prof [[PROF8]], !nosanitize [[META9]] // SANITIZE-WITHOUT-ATTR: handler.out_of_bounds: -// SANITIZE-WITHOUT-ATTR-NEXT: tail call void @__ubsan_handle_out_of_bounds_abort(ptr nonnull @[[GLOB12:[0-9]+]], i64 [[TMP1]]) #[[ATTR8]], !nosanitize [[META9]] +// SANITIZE-WITHOUT-ATTR-NEXT: tail call void @__ubsan_handle_out_of_bounds_abort(ptr nonnull @[[GLOB13:[0-9]+]], i64 [[TMP1]]) #[[ATTR8]], !nosanitize [[META9]] // SANITIZE-WITHOUT-ATTR-NEXT: unreachable, !nosanitize [[META9]] // SANITIZE-WITHOUT-ATTR: cont21: // SANITIZE-WITHOUT-ATTR-NEXT: [[ARRAYIDX:%.*]] = getelementptr inbounds [10 x ptr], ptr [[ANN]], i64 0, i64 [[TMP1]] diff --git a/clang/test/CodeGen/builtins-wasm.c b/clang/test/CodeGen/builtins-wasm.c index d486d12085f9fcece37da182858849cb3fb366a8..9a323da9a8e8465704f06afd6ddc29f50d2a691c 100644 --- a/clang/test/CodeGen/builtins-wasm.c +++ b/clang/test/CodeGen/builtins-wasm.c @@ -406,7 +406,7 @@ i32x4 bitselect(i32x4 x, i32x4 y, i32x4 c) { i8x16 popcnt(i8x16 x) { return __builtin_wasm_popcnt_i8x16(x); - // WEBASSEMBLY: call <16 x i8> @llvm.ctpop.v16i8(<16 x i8> %x) + // WEBASSEMBLY: call range(i8 0, 9) <16 x i8> @llvm.ctpop.v16i8(<16 x i8> %x) // WEBASSEMBLY-NEXT: ret } diff --git a/clang/test/CodeGen/ms-intrinsics-other.c b/clang/test/CodeGen/ms-intrinsics-other.c index 0e9dfe34b84cc7d89b1853f54a5d84c61f9dc3e6..fa8422e5bf19fb1f2ec653b564e3ca3cf9338c53 100644 --- a/clang/test/CodeGen/ms-intrinsics-other.c +++ b/clang/test/CodeGen/ms-intrinsics-other.c @@ -56,7 +56,7 @@ unsigned char test_BitScanForward(unsigned LONG *Index, unsigned LONG Mask) { // CHECK: [[RESULT:%[a-z0-9._]+]] = phi i8 [ 0, %[[ISZERO_LABEL:[a-z0-9._]+]] ], [ 1, %[[ISNOTZERO_LABEL]] ] // CHECK: ret i8 [[RESULT]] // CHECK: [[ISNOTZERO_LABEL]]: -// CHECK: [[INDEX:%[0-9]+]] = tail call i32 @llvm.cttz.i32(i32 %Mask, i1 true) +// CHECK: [[INDEX:%[0-9]+]] = tail call range(i32 0, 33) i32 @llvm.cttz.i32(i32 %Mask, i1 true) // CHECK: store i32 [[INDEX]], ptr %Index, align 4 // CHECK: br label %[[END_LABEL]] @@ -70,7 +70,7 @@ unsigned char test_BitScanReverse(unsigned LONG *Index, unsigned LONG Mask) { // CHECK: [[RESULT:%[a-z0-9._]+]] = phi i8 [ 0, %[[ISZERO_LABEL:[a-z0-9._]+]] ], [ 1, %[[ISNOTZERO_LABEL]] ] // CHECK: ret i8 [[RESULT]] // CHECK: [[ISNOTZERO_LABEL]]: -// CHECK: [[REVINDEX:%[0-9]+]] = tail call i32 @llvm.ctlz.i32(i32 %Mask, i1 true) +// CHECK: [[REVINDEX:%[0-9]+]] = tail call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 %Mask, i1 true) // CHECK: [[INDEX:%[0-9]+]] = xor i32 [[REVINDEX]], 31 // CHECK: store i32 [[INDEX]], ptr %Index, align 4 // CHECK: br label %[[END_LABEL]] @@ -86,7 +86,7 @@ unsigned char test_BitScanForward64(unsigned LONG *Index, unsigned __int64 Mask) // CHECK: [[RESULT:%[a-z0-9._]+]] = phi i8 [ 0, %[[ISZERO_LABEL:[a-z0-9._]+]] ], [ 1, %[[ISNOTZERO_LABEL]] ] // CHECK: ret i8 [[RESULT]] // CHECK: [[ISNOTZERO_LABEL]]: -// CHECK: [[INDEX:%[0-9]+]] = tail call i64 @llvm.cttz.i64(i64 %Mask, i1 true) +// CHECK: [[INDEX:%[0-9]+]] = tail call range(i64 0, 65) i64 @llvm.cttz.i64(i64 %Mask, i1 true) // CHECK: [[TRUNC_INDEX:%[0-9]+]] = trunc nuw nsw i64 [[INDEX]] to i32 // CHECK: store i32 [[TRUNC_INDEX]], ptr %Index, align 4 // CHECK: br label %[[END_LABEL]] @@ -101,7 +101,7 @@ unsigned char test_BitScanReverse64(unsigned LONG *Index, unsigned __int64 Mask) // CHECK: [[RESULT:%[a-z0-9._]+]] = phi i8 [ 0, %[[ISZERO_LABEL:[a-z0-9._]+]] ], [ 1, %[[ISNOTZERO_LABEL]] ] // CHECK: ret i8 [[RESULT]] // CHECK: [[ISNOTZERO_LABEL]]: -// CHECK: [[REVINDEX:%[0-9]+]] = tail call i64 @llvm.ctlz.i64(i64 %Mask, i1 true) +// CHECK: [[REVINDEX:%[0-9]+]] = tail call range(i64 0, 65) i64 @llvm.ctlz.i64(i64 %Mask, i1 true) // CHECK: [[TRUNC_REVINDEX:%[0-9]+]] = trunc nuw nsw i64 [[REVINDEX]] to i32 // CHECK: [[INDEX:%[0-9]+]] = xor i32 [[TRUNC_REVINDEX]], 63 // CHECK: store i32 [[INDEX]], ptr %Index, align 4 @@ -187,7 +187,7 @@ unsigned short test__lzcnt16(unsigned short x) { return __lzcnt16(x); } // CHECK: i16 @test__lzcnt16 -// CHECK: [[RESULT:%[0-9]+]] = tail call i16 @llvm.ctlz.i16(i16 %x, i1 false) +// CHECK: [[RESULT:%[0-9]+]] = tail call range(i16 0, 17) i16 @llvm.ctlz.i16(i16 %x, i1 false) // CHECK: ret i16 [[RESULT]] // CHECK: } @@ -195,7 +195,7 @@ unsigned int test__lzcnt(unsigned int x) { return __lzcnt(x); } // CHECK: i32 @test__lzcnt -// CHECK: [[RESULT:%[0-9]+]] = tail call i32 @llvm.ctlz.i32(i32 %x, i1 false) +// CHECK: [[RESULT:%[0-9]+]] = tail call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 %x, i1 false) // CHECK: ret i32 [[RESULT]] // CHECK: } @@ -203,7 +203,7 @@ unsigned __int64 test__lzcnt64(unsigned __int64 x) { return __lzcnt64(x); } // CHECK: i64 @test__lzcnt64 -// CHECK: [[RESULT:%[0-9]+]] = tail call i64 @llvm.ctlz.i64(i64 %x, i1 false) +// CHECK: [[RESULT:%[0-9]+]] = tail call range(i64 0, 65) i64 @llvm.ctlz.i64(i64 %x, i1 false) // CHECK: ret i64 [[RESULT]] // CHECK: } @@ -211,7 +211,7 @@ unsigned short test__popcnt16(unsigned short x) { return __popcnt16(x); } // CHECK: i16 @test__popcnt16 -// CHECK: [[RESULT:%[0-9]+]] = tail call i16 @llvm.ctpop.i16(i16 %x) +// CHECK: [[RESULT:%[0-9]+]] = tail call range(i16 0, 17) i16 @llvm.ctpop.i16(i16 %x) // CHECK: ret i16 [[RESULT]] // CHECK: } @@ -219,7 +219,7 @@ unsigned int test__popcnt(unsigned int x) { return __popcnt(x); } // CHECK: i32 @test__popcnt -// CHECK: [[RESULT:%[0-9]+]] = tail call i32 @llvm.ctpop.i32(i32 %x) +// CHECK: [[RESULT:%[0-9]+]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 %x) // CHECK: ret i32 [[RESULT]] // CHECK: } @@ -227,7 +227,7 @@ unsigned __int64 test__popcnt64(unsigned __int64 x) { return __popcnt64(x); } // CHECK: i64 @test__popcnt64 -// CHECK: [[RESULT:%[0-9]+]] = tail call i64 @llvm.ctpop.i64(i64 %x) +// CHECK: [[RESULT:%[0-9]+]] = tail call range(i64 0, 65) i64 @llvm.ctpop.i64(i64 %x) // CHECK: ret i64 [[RESULT]] // CHECK: } diff --git a/clang/test/CodeGen/ms-intrinsics.c b/clang/test/CodeGen/ms-intrinsics.c index 6eabd725e2f7c6b06d6959c86a1d0bafb05e48f7..c3d64fda0b901fd4afc7e334152fdb456421c1a5 100644 --- a/clang/test/CodeGen/ms-intrinsics.c +++ b/clang/test/CodeGen/ms-intrinsics.c @@ -157,7 +157,7 @@ unsigned char test_BitScanForward(unsigned long *Index, unsigned long Mask) { // CHECK: ret i8 [[RESULT]] // CHECK: [[ISNOTZERO_LABEL]]: // CHECK: [[IDXGEP:%[a-z0-9._]+]] = getelementptr inbounds i8, ptr %Index, {{i64|i32}} 4 -// CHECK: [[INDEX:%[0-9]+]] = tail call i32 @llvm.cttz.i32(i32 %Mask, i1 true) +// CHECK: [[INDEX:%[0-9]+]] = tail call range(i32 0, 33) i32 @llvm.cttz.i32(i32 %Mask, i1 true) // CHECK: store i32 [[INDEX]], ptr [[IDXGEP]], align 4 // CHECK: br label %[[END_LABEL]] @@ -172,7 +172,7 @@ unsigned char test_BitScanReverse(unsigned long *Index, unsigned long Mask) { // CHECK: ret i8 [[RESULT]] // CHECK: [[ISNOTZERO_LABEL]]: // CHECK: [[IDXGEP:%[a-z0-9._]+]] = getelementptr inbounds i8, ptr %Index, {{i64|i32}} 4 -// CHECK: [[REVINDEX:%[0-9]+]] = tail call i32 @llvm.ctlz.i32(i32 %Mask, i1 true) +// CHECK: [[REVINDEX:%[0-9]+]] = tail call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 %Mask, i1 true) // CHECK: [[INDEX:%[0-9]+]] = xor i32 [[REVINDEX]], 31 // CHECK: store i32 [[INDEX]], ptr [[IDXGEP]], align 4 // CHECK: br label %[[END_LABEL]] @@ -188,7 +188,7 @@ unsigned char test_BitScanForward64(unsigned long *Index, unsigned __int64 Mask) // CHECK-ARM-X64: [[RESULT:%[a-z0-9._]+]] = phi i8 [ 0, %[[ISZERO_LABEL:[a-z0-9._]+]] ], [ 1, %[[ISNOTZERO_LABEL]] ] // CHECK-ARM-X64: ret i8 [[RESULT]] // CHECK-ARM-X64: [[ISNOTZERO_LABEL]]: -// CHECK-ARM-X64: [[INDEX:%[0-9]+]] = tail call i64 @llvm.cttz.i64(i64 %Mask, i1 true) +// CHECK-ARM-X64: [[INDEX:%[0-9]+]] = tail call range(i64 0, 65) i64 @llvm.cttz.i64(i64 %Mask, i1 true) // CHECK-ARM-X64: [[TRUNC_INDEX:%[0-9]+]] = trunc nuw nsw i64 [[INDEX]] to i32 // CHECK-ARM-X64: store i32 [[TRUNC_INDEX]], ptr %Index, align 4 // CHECK-ARM-X64: br label %[[END_LABEL]] @@ -203,7 +203,7 @@ unsigned char test_BitScanReverse64(unsigned long *Index, unsigned __int64 Mask) // CHECK-ARM-X64: [[RESULT:%[a-z0-9._]+]] = phi i8 [ 0, %[[ISZERO_LABEL:[a-z0-9._]+]] ], [ 1, %[[ISNOTZERO_LABEL]] ] // CHECK-ARM-X64: ret i8 [[RESULT]] // CHECK-ARM-X64: [[ISNOTZERO_LABEL]]: -// CHECK-ARM-X64: [[REVINDEX:%[0-9]+]] = tail call i64 @llvm.ctlz.i64(i64 %Mask, i1 true) +// CHECK-ARM-X64: [[REVINDEX:%[0-9]+]] = tail call range(i64 0, 65) i64 @llvm.ctlz.i64(i64 %Mask, i1 true) // CHECK-ARM-X64: [[TRUNC_REVINDEX:%[0-9]+]] = trunc nuw nsw i64 [[REVINDEX]] to i32 // CHECK-ARM-X64: [[INDEX:%[0-9]+]] = xor i32 [[TRUNC_REVINDEX]], 63 // CHECK-ARM-X64: store i32 [[INDEX]], ptr %Index, align 4 diff --git a/clang/test/CodeGen/ms-mixed-ptr-sizes.c b/clang/test/CodeGen/ms-mixed-ptr-sizes.c index 89d05fd30b72c2bfb1ecbb3973deb17551d67bf2..51bea60eb39dce5abacc04eb49a7024da5e765d5 100644 --- a/clang/test/CodeGen/ms-mixed-ptr-sizes.c +++ b/clang/test/CodeGen/ms-mixed-ptr-sizes.c @@ -49,7 +49,7 @@ void test_other(struct Foo *f, __attribute__((address_space(10))) int *i) { } int test_compare1(int *__ptr32 __uptr i, int *__ptr64 j) { - // ALL-LABEL: define dso_local noundef i32 @test_compare1 + // ALL-LABEL: define dso_local range(i32 0, 2) i32 @test_compare1 // X64: %{{.+}} = addrspacecast ptr %j to ptr addrspace(271) // X64: %cmp = icmp eq ptr addrspace(271) %{{.+}}, %i // X86: %{{.+}} = addrspacecast ptr addrspace(272) %j to ptr addrspace(271) @@ -58,7 +58,7 @@ int test_compare1(int *__ptr32 __uptr i, int *__ptr64 j) { } int test_compare2(int *__ptr32 __sptr i, int *__ptr64 j) { - // ALL-LABEL: define dso_local noundef i32 @test_compare2 + // ALL-LABEL: define dso_local range(i32 0, 2) i32 @test_compare2 // X64: %{{.+}} = addrspacecast ptr %j to ptr addrspace(270) // X64: %cmp = icmp eq ptr addrspace(270) %{{.+}}, %i // X86: %{{.+}} = addrspacecast ptr addrspace(272) %j to ptr @@ -67,7 +67,7 @@ int test_compare2(int *__ptr32 __sptr i, int *__ptr64 j) { } int test_compare3(int *__ptr32 __uptr i, int *__ptr64 j) { - // ALL-LABEL: define dso_local noundef i32 @test_compare3 + // ALL-LABEL: define dso_local range(i32 0, 2) i32 @test_compare3 // X64: %{{.+}} = addrspacecast ptr addrspace(271) %i to ptr // X64: %cmp = icmp eq ptr %{{.+}}, %j // X86: %{{.+}} = addrspacecast ptr addrspace(271) %i to ptr addrspace(272) @@ -76,7 +76,7 @@ int test_compare3(int *__ptr32 __uptr i, int *__ptr64 j) { } int test_compare4(int *__ptr32 __sptr i, int *__ptr64 j) { - // ALL-LABEL: define dso_local noundef i32 @test_compare4 + // ALL-LABEL: define dso_local range(i32 0, 2) i32 @test_compare4 // X64: %{{.+}} = addrspacecast ptr addrspace(270) %i to ptr // X64: %cmp = icmp eq ptr %{{.+}}, %j // X86: %{{.+}} = addrspacecast ptr %i to ptr addrspace(272) diff --git a/clang/test/CodeGenCXX/cxx1y-sized-deallocation.cpp b/clang/test/CodeGenCXX/cxx1y-sized-deallocation.cpp index 4e15657251525e31e2c1e72d9be43214040f14fb..55913aff9c19b98543993474d7dbb4f83af3c4fc 100644 --- a/clang/test/CodeGenCXX/cxx1y-sized-deallocation.cpp +++ b/clang/test/CodeGenCXX/cxx1y-sized-deallocation.cpp @@ -1,12 +1,12 @@ // Check that delete exprs call the sized deallocation function if -// -fsized-deallocation is passed in both C++11 and C++14. +// -fsized-deallocation is passed in C++11 or std >= C++14. // RUN: %clang_cc1 -std=c++11 -fsized-deallocation %s -emit-llvm -triple x86_64-linux-gnu -o - | FileCheck %s -// RUN: %clang_cc1 -std=c++14 -fsized-deallocation %s -emit-llvm -triple x86_64-linux-gnu -o - | FileCheck %s +// RUN: %clang_cc1 -std=c++14 %s -emit-llvm -triple x86_64-linux-gnu -o - | FileCheck %s -// Check that we don't used sized deallocation without -fsized-deallocation and -// C++14. +// Check that we don't used sized deallocation with -fno-sized-deallocation or without C++14. // RUN: %clang_cc1 -std=c++11 %s -emit-llvm -triple x86_64-linux-gnu -o - | FileCheck %s --check-prefix=CHECK-UNSIZED -// RUN: %clang_cc1 -std=c++14 %s -emit-llvm -triple x86_64-linux-gnu -o - | FileCheck %s --check-prefix=CHECK-UNSIZED +// RUN: %clang_cc1 -std=c++14 %s -emit-llvm -triple x86_64-linux-gnu -fno-sized-deallocation -o - \ +// RUN: | FileCheck %s --check-prefix=CHECK-UNSIZED // CHECK-UNSIZED-NOT: _ZdlPvm // CHECK-UNSIZED-NOT: _ZdaPvm diff --git a/clang/test/CodeGenCXX/cxx1z-aligned-allocation.cpp b/clang/test/CodeGenCXX/cxx1z-aligned-allocation.cpp index ab2e4b3cdbbf9cf915d3826689e9fbdd6bfc4c9f..8823bc64a4368bbead683dec3b4ac623e3ea8459 100644 --- a/clang/test/CodeGenCXX/cxx1z-aligned-allocation.cpp +++ b/clang/test/CodeGenCXX/cxx1z-aligned-allocation.cpp @@ -1,10 +1,10 @@ // Check that delete exprs call aligned (de)allocation functions if // -faligned-allocation is passed in both C++11 and C++14. // RUN: %clang_cc1 -std=c++11 -fexceptions -fsized-deallocation -faligned-allocation %s -emit-llvm -triple x86_64-linux-gnu -o - | FileCheck %s -// RUN: %clang_cc1 -std=c++14 -fexceptions -fsized-deallocation -faligned-allocation %s -emit-llvm -triple x86_64-linux-gnu -o - | FileCheck %s -// RUN: %clang_cc1 -std=c++1z -fexceptions -fsized-deallocation %s -emit-llvm -triple x86_64-linux-gnu -o - | FileCheck %s +// RUN: %clang_cc1 -std=c++14 -fexceptions -faligned-allocation %s -emit-llvm -triple x86_64-linux-gnu -o - | FileCheck %s +// RUN: %clang_cc1 -std=c++1z -fexceptions %s -emit-llvm -triple x86_64-linux-gnu -o - | FileCheck %s -// RUN: %clang_cc1 -std=c++1z -fexceptions -fsized-deallocation %s -emit-llvm -triple x86_64-windows-msvc -o - | FileCheck %s --check-prefix=CHECK-MS +// RUN: %clang_cc1 -std=c++1z -fexceptions %s -emit-llvm -triple x86_64-windows-msvc -o - | FileCheck %s --check-prefix=CHECK-MS // Check that we don't used aligned (de)allocation without -faligned-allocation or C++1z. // RUN: %clang_cc1 -std=c++14 -DUNALIGNED -fexceptions %s -emit-llvm -triple x86_64-linux-gnu -o - | FileCheck %s --check-prefix=CHECK-UNALIGNED diff --git a/clang/test/CodeGenCXX/cxx2a-destroying-delete.cpp b/clang/test/CodeGenCXX/cxx2a-destroying-delete.cpp index 20264b67353a979cd024ab0e0fda342400fb888f..f6f4a2ff735cc4a2551d54eb4e60da87e947bfee 100644 --- a/clang/test/CodeGenCXX/cxx2a-destroying-delete.cpp +++ b/clang/test/CodeGenCXX/cxx2a-destroying-delete.cpp @@ -108,10 +108,10 @@ struct J { // CHECK-MSABI-LABEL: define {{.*}}@"?j@@ J *j() { // CHECK-ITANIUM: invoke {{.*}}@_ZN1JC1Ev( - // CHECK-ITANIUM: call {{.*}}@_ZdlPv( + // CHECK-ITANIUM: call {{.*}}@_ZdlPvm( // CHECK-NOT: } // CHECK-MSABI: invoke {{.*}}@"??0J@@Q{{AE|EAA}}@XZ"( - // CHECK-MSABI: call {{.*}}@"??3@YAXP{{E?}}AX@Z"( + // CHECK-MSABI: call {{.*}}@"??3@YAXP{{E?}}AX{{I|_K}}@Z"( return new J; // CHECK: } } diff --git a/clang/test/CodeGenCXX/delete-two-arg.cpp b/clang/test/CodeGenCXX/delete-two-arg.cpp index 552634f430a80c32c389f327d61f09c9999d0aee..a0dcd03bc5a92deff2778f2432d1bfc99f0f5b8b 100644 --- a/clang/test/CodeGenCXX/delete-two-arg.cpp +++ b/clang/test/CodeGenCXX/delete-two-arg.cpp @@ -43,7 +43,9 @@ namespace test2 { // CHECK-NEXT: br i1 [[T1]], // CHECK: [[T3:%.*]] = getelementptr inbounds i8, ptr [[T0]], i32 -4 // CHECK-NEXT: [[T5:%.*]] = load i32, ptr [[T3]] - // CHECK-NEXT: call void @_ZdaPv(ptr noundef [[T3]]) + // CHECK-NEXT: [[T6:%.*]] = mul i32 4, [[T5]] + // CHECK-NEXT: [[T7:%.*]] = add i32 [[T6]], 4 + // CHECK-NEXT: call void @_ZdaPvj(ptr noundef [[T3]], i32 noundef [[T7]]) // CHECK-NEXT: br label ::delete[] p; } diff --git a/clang/test/CodeGenCXX/delete.cpp b/clang/test/CodeGenCXX/delete.cpp index 1a418f48b65980c074475cf031ea14a557eff67d..d5b0dc67129102b06df58a8b78feb6cb84ce0d11 100644 --- a/clang/test/CodeGenCXX/delete.cpp +++ b/clang/test/CodeGenCXX/delete.cpp @@ -16,7 +16,7 @@ void t3(S *s) { // CHECK: icmp {{.*}} null // CHECK: br i1 - // CHECK: call void @_ZdlPv + // CHECK: call void @_ZdlPvm // Check the delete is inside the 'if !null' check unless we're optimizing // for size. FIXME: We could omit the branch entirely in this case. @@ -35,7 +35,7 @@ struct T { void t4(T *t) { // CHECK: call void @_ZN1TD1Ev // CHECK-SIZE-NEXT: br - // CHECK: call void @_ZdlPv + // CHECK: call void @_ZdlPvm delete t; } @@ -93,14 +93,16 @@ namespace test1 { // CHECK-NEXT: call void @_ZN5test11AD1Ev(ptr {{[^,]*}} [[CUR]]) // CHECK-NEXT: [[ISDONE:%.*]] = icmp eq ptr [[CUR]], [[BEGIN]] // CHECK-NEXT: br i1 [[ISDONE]] - // CHECK: call void @_ZdaPv(ptr noundef [[ALLOC]]) + // CHECK: [[MUL:%.*]] = mul i64 4, [[COUNT]] + // CHECK-NEXT: [[SIZE:%.*]] = add i64 [[MUL]], 8 + // CHECK-NEXT: call void @_ZdaPvm(ptr noundef [[ALLOC]], i64 noundef [[SIZE]]) } } namespace test2 { // CHECK-LABEL: define{{.*}} void @_ZN5test21fEPb void f(bool *b) { - // CHECK: call void @_ZdlPv(ptr + // CHECK: call void @_ZdlPvm(ptr{{.*}}i64 delete b; // CHECK: call void @_ZdaPv(ptr delete [] b; @@ -137,7 +139,7 @@ namespace test4 { // CHECK-NEXT: [[DTOR:%.*]] = load ptr, ptr [[T0]] // CHECK-NEXT: call void [[DTOR]](ptr {{[^,]*}} [[OBJ:%.*]]) // Call the global operator delete. - // CHECK-NEXT: call void @_ZdlPv(ptr noundef [[ALLOCATED]]) [[NUW:#[0-9]+]] + // CHECK-NEXT: call void @_ZdlPvm(ptr noundef [[ALLOCATED]], i64 noundef 8) [[NUW:#[0-9]+]] ::delete xp; } } diff --git a/clang/test/CodeGenCXX/dependent-template-alias.cpp b/clang/test/CodeGenCXX/dependent-template-alias.cpp new file mode 100644 index 0000000000000000000000000000000000000000..deb243f9fc88d0c2ad120b949abb64d576c73997 --- /dev/null +++ b/clang/test/CodeGenCXX/dependent-template-alias.cpp @@ -0,0 +1,21 @@ +// RUN: %clang_cc1 -triple x86_64-unk-unk -o - -emit-llvm -debug-info-kind=standalone -gtemplate-alias %s -gsimple-template-names=simple \ +// RUN: | FileCheck %s + +//// Check that -gtemplate-alias falls back to DW_TAG_typedef emission +//// for instantiation dependent type aliases. + +template +using A = int; + +template +struct S { + using AA = A; + AA aa; +}; + +S<0> s; + +// CHECK: !DIDerivedType(tag: DW_TAG_member, name: "aa", scope: ![[#]], file: ![[#]], line: [[#]], baseType: ![[AA:[0-9]+]], size: 32) +// CHECK: [[AA]] = !DIDerivedType(tag: DW_TAG_typedef, name: "AA", file: ![[#]], line: [[#]], baseType: ![[A:[0-9]+]]) +// CHECK: [[A]] = !DIDerivedType(tag: DW_TAG_typedef, name: "A", file: ![[#]], line: [[#]], baseType: ![[int:[0-9]+]]) +// CHECK: [[int]] = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed) diff --git a/clang/test/CodeGenCXX/dllimport.cpp b/clang/test/CodeGenCXX/dllimport.cpp index 6fec2f2982d4072100361fb7e7aedfbdbfab99bc..484866b45389f28298774de23c700af8791e383d 100644 --- a/clang/test/CodeGenCXX/dllimport.cpp +++ b/clang/test/CodeGenCXX/dllimport.cpp @@ -205,7 +205,7 @@ USEVAR(VarTmpl) // Functions //===----------------------------------------------------------------------===// -// GNU-DAG: declare dso_local void @_ZdlPv(ptr) +// GNU-DAG: declare dso_local void @_ZdlPv{{j|y}}(ptr, i{{32|64}}) // Import function declaration. // MSC-DAG: declare dllimport void @"?decl@@YAXXZ"() @@ -358,7 +358,7 @@ __declspec(dllimport) void operator delete(void*); __declspec(dllimport) inline int *ReferencingImportedNew() { return new int[2]; } // MO1-DAG: define available_externally dllimport ptr @"?ReferencingImportedNew@@YAPAHXZ" __declspec(dllimport) inline int *ReferencingImportedDelete() { delete (int*)nullptr; } -// MO1-DAG: define available_externally dllimport ptr @"?ReferencingImportedDelete@@YAPAHXZ" +// MO1-DAG: declare dllimport ptr @"?ReferencingImportedDelete@@YAPAHXZ" USE(ReferencingImportedNew) USE(ReferencingImportedDelete) struct ClassWithDtor { ~ClassWithDtor() {} }; diff --git a/clang/test/CodeGenCXX/new.cpp b/clang/test/CodeGenCXX/new.cpp index e278d9acfe9ee235b8349dc0388c6587e364753c..af225529c494e625c408fed5255c980dfd384dfa 100644 --- a/clang/test/CodeGenCXX/new.cpp +++ b/clang/test/CodeGenCXX/new.cpp @@ -15,7 +15,7 @@ void t1() { } // CHECK: declare noundef nonnull ptr @_Znwm(i64 noundef) [[ATTR_NOBUILTIN:#[^ ]*]] -// CHECK: declare void @_ZdlPv(ptr noundef) [[ATTR_NOBUILTIN_NOUNWIND:#[^ ]*]] +// CHECK: declare void @_ZdlPvm(ptr noundef, i64 noundef) [[ATTR_NOBUILTIN_NOUNWIND:#[^ ]*]] // CHECK: declare noundef nonnull ptr @_Znam(i64 noundef) [[ATTR_NOBUILTIN]] // CHECK: declare void @_ZdaPv(ptr noundef) [[ATTR_NOBUILTIN_NOUNWIND]] @@ -192,7 +192,7 @@ void f() { // CHECK: store i64 200 delete[] new (nothrow) Alloc[10][20]; // CHECK: call noalias noundef nonnull ptr @_Znwm - // CHECK: call void @_ZdlPv(ptr + // CHECK: call void @_ZdlPvm(ptr noundef {{%.*}}, i64 noundef 1) delete new bool; // CHECK: ret void } @@ -317,7 +317,7 @@ namespace N3664 { void f() { // CHECK: call noalias noundef nonnull ptr @_Znwm(i64 noundef 4) [[ATTR_BUILTIN_NEW:#[^ ]*]] int *p = new int; // expected-note {{allocated with 'new' here}} - // CHECK: call void @_ZdlPv({{.*}}) [[ATTR_BUILTIN_DELETE:#[^ ]*]] + // CHECK: call void @_ZdlPvm({{.*}}) [[ATTR_BUILTIN_DELETE:#[^ ]*]] delete p; // CHECK: call noalias noundef nonnull ptr @_Znam(i64 noundef 12) [[ATTR_BUILTIN_NEW]] diff --git a/clang/test/CodeGenCoroutines/coro-aligned-alloc-2.cpp b/clang/test/CodeGenCoroutines/coro-aligned-alloc-2.cpp index a3ee964a22a10b6c3075f878c8ae9b77c544597e..ecf991a2fb49405da1eb7fbe43d1ca98e001cf36 100644 --- a/clang/test/CodeGenCoroutines/coro-aligned-alloc-2.cpp +++ b/clang/test/CodeGenCoroutines/coro-aligned-alloc-2.cpp @@ -1,9 +1,7 @@ // Tests that the combination of -fcoro-aligned-allocation and -fsized-deallocation works well. // Test the compiler will chose sized deallocation correctly. -// This is only enabled with `-fsized-deallocation` which is off by default. // RUN: %clang_cc1 -triple x86_64-unknown-linux-gnu -std=c++20 \ // RUN: -fcoro-aligned-allocation -S -emit-llvm %s -o - -disable-llvm-passes \ -// RUN: -fsized-deallocation \ // RUN: | FileCheck %s #include "Inputs/coroutine.h" diff --git a/clang/test/CodeGenCoroutines/coro-aligned-alloc.cpp b/clang/test/CodeGenCoroutines/coro-aligned-alloc.cpp index d14c3d372ddb1730c3c403f0e27227e97be10815..b50d9f8f7674acdadfff6245c7883c1ade6125b3 100644 --- a/clang/test/CodeGenCoroutines/coro-aligned-alloc.cpp +++ b/clang/test/CodeGenCoroutines/coro-aligned-alloc.cpp @@ -26,8 +26,9 @@ struct task { // CHECK: %[[aligned_new:.+]] = call{{.*}}@_ZnwmSt11align_val_t({{.*}}%[[coro_size]],{{.*}}%[[coro_align]]) // CHECK: coro.free: +// CHECK: %[[coro_size_for_free:.+]] = call{{.*}}@llvm.coro.size // CHECK: %[[coro_align_for_free:.+]] = call{{.*}}@llvm.coro.align -// CHECK: call void @_ZdlPvSt11align_val_t({{.*}}[[coro_align_for_free]] +// CHECK: call void @_ZdlPvmSt11align_val_t({{.*}}%[[coro_size_for_free]],{{.*}}%[[coro_align_for_free]]) task f() { co_return 43; @@ -58,8 +59,9 @@ void *operator new(std::size_t, std::align_val_t, std::nothrow_t) noexcept; // CHECK: %[[aligned_new:.+]] = call{{.*}}@_ZnwmSt11align_val_tSt9nothrow_t({{.*}}%[[coro_size]],{{.*}}%[[coro_align]]) // CHECK: coro.free: +// CHECK: %[[coro_size_for_free:.+]] = call{{.*}}@llvm.coro.size // CHECK: %[[coro_align_for_free:.+]] = call{{.*}}@llvm.coro.align -// CHECK: call void @_ZdlPvSt11align_val_t({{.*}}[[coro_align_for_free]] +// CHECK: call void @_ZdlPvmSt11align_val_t({{.*}}%[[coro_size_for_free]],{{.*}}%[[coro_align_for_free]]) task2 f2() { co_return 43; diff --git a/clang/test/CodeGenCoroutines/coro-alloc.cpp b/clang/test/CodeGenCoroutines/coro-alloc.cpp index d026a0d7df2275fa3a272ff5e58fc8fb83f8e1b4..7b3be7e0b7f98d42199446d878cb71059dd93290 100644 --- a/clang/test/CodeGenCoroutines/coro-alloc.cpp +++ b/clang/test/CodeGenCoroutines/coro-alloc.cpp @@ -70,7 +70,8 @@ extern "C" void f0(global_new_delete_tag) { // CHECK: br i1 %[[NeedDealloc]], label %[[FreeBB:.+]], label %[[Afterwards:.+]] // CHECK: [[FreeBB]]: - // CHECK: call void @_ZdlPv(ptr noundef %[[MEM]]) + // CHECK: %[[SIZE:.+]] = call i64 @llvm.coro.size.i64() + // CHECK: call void @_ZdlPvm(ptr noundef %[[MEM]], i64 noundef %[[SIZE]]) // CHECK: br label %[[Afterwards]] // CHECK: [[Afterwards]]: @@ -99,7 +100,8 @@ extern "C" void f1(promise_new_tag ) { // CHECK: %[[FRAME:.+]] = call ptr @llvm.coro.begin( // CHECK: %[[MEM:.+]] = call ptr @llvm.coro.free(token %[[ID]], ptr %[[FRAME]]) - // CHECK: call void @_ZdlPv(ptr noundef %[[MEM]]) + // CHECK: %[[SIZE:.+]] = call i64 @llvm.coro.size.i64() + // CHECK: call void @_ZdlPvm(ptr noundef %[[MEM]], i64 noundef %[[SIZE]]) co_return; } diff --git a/clang/test/CodeGenCoroutines/coro-await.cpp b/clang/test/CodeGenCoroutines/coro-await.cpp index 75851d8805bb6e37d1308bcf7e6b03c112f87137..65bfb099468817961b14782fd0b20cc62f48fc52 100644 --- a/clang/test/CodeGenCoroutines/coro-await.cpp +++ b/clang/test/CodeGenCoroutines/coro-await.cpp @@ -73,7 +73,7 @@ extern "C" void f0() { // --------------------------- // Call coro.await.suspend // --------------------------- - // CHECK-NEXT: call void @llvm.coro.await.suspend.void(ptr %[[AWAITABLE]], ptr %[[FRAME]], ptr @__await_suspend_wrapper_f0_await) + // CHECK-NEXT: call void @llvm.coro.await.suspend.void(ptr %[[AWAITABLE]], ptr %[[FRAME]], ptr @f0.__await_suspend_wrapper__await) // ------------------------- // Generate a suspend point: // ------------------------- @@ -100,7 +100,7 @@ extern "C" void f0() { // CHECK: call i8 @llvm.coro.suspend(token %[[FINALSP_ID]], i1 true) // Await suspend wrapper - // CHECK: define{{.*}} @__await_suspend_wrapper_f0_await(ptr {{[^,]*}} %[[AWAITABLE_ARG:.+]], ptr {{[^,]*}} %[[FRAME_ARG:.+]]) + // CHECK: define{{.*}} @f0.__await_suspend_wrapper__await(ptr {{[^,]*}} %[[AWAITABLE_ARG:.+]], ptr {{[^,]*}} %[[FRAME_ARG:.+]]) // CHECK: store ptr %[[AWAITABLE_ARG]], ptr %[[AWAITABLE_TMP:.+]], // CHECK: store ptr %[[FRAME_ARG]], ptr %[[FRAME_TMP:.+]], // CHECK: %[[AWAITABLE:.+]] = load ptr, ptr %[[AWAITABLE_TMP]] @@ -149,7 +149,7 @@ extern "C" void f1(int) { // --------------------------- // Call coro.await.suspend // --------------------------- - // CHECK-NEXT: %[[YES:.+]] = call i1 @llvm.coro.await.suspend.bool(ptr %[[AWAITABLE]], ptr %[[FRAME]], ptr @__await_suspend_wrapper_f1_yield) + // CHECK-NEXT: %[[YES:.+]] = call i1 @llvm.coro.await.suspend.bool(ptr %[[AWAITABLE]], ptr %[[FRAME]], ptr @f1.__await_suspend_wrapper__yield) // ------------------------------------------- // See if await_suspend decided not to suspend // ------------------------------------------- @@ -162,7 +162,7 @@ extern "C" void f1(int) { // CHECK: call void @_ZN13suspend_maybe12await_resumeEv(ptr {{[^,]*}} %[[AWAITABLE]]) // Await suspend wrapper - // CHECK: define {{.*}} i1 @__await_suspend_wrapper_f1_yield(ptr {{[^,]*}} %[[AWAITABLE_ARG:.+]], ptr {{[^,]*}} %[[FRAME_ARG:.+]]) + // CHECK: define {{.*}} i1 @f1.__await_suspend_wrapper__yield(ptr {{[^,]*}} %[[AWAITABLE_ARG:.+]], ptr {{[^,]*}} %[[FRAME_ARG:.+]]) // CHECK: store ptr %[[AWAITABLE_ARG]], ptr %[[AWAITABLE_TMP:.+]], // CHECK: store ptr %[[FRAME_ARG]], ptr %[[FRAME_TMP:.+]], // CHECK: %[[AWAITABLE:.+]] = load ptr, ptr %[[AWAITABLE_TMP]] @@ -370,7 +370,7 @@ extern "C" void TestTailcall() { // --------------------------- // Call coro.await.suspend // --------------------------- - // CHECK-NEXT: %[[RESUMED:.+]] = call ptr @llvm.coro.await.suspend.handle(ptr %[[AWAITABLE]], ptr %[[FRAME]], ptr @__await_suspend_wrapper_TestTailcall_await) + // CHECK-NEXT: %[[RESUMED:.+]] = call ptr @llvm.coro.await.suspend.handle(ptr %[[AWAITABLE]], ptr %[[FRAME]], ptr @TestTailcall.__await_suspend_wrapper__await) // CHECK-NEXT: call void @llvm.coro.resume(ptr %[[RESUMED]]) // CHECK-NEXT: %[[OUTCOME:.+]] = call i8 @llvm.coro.suspend(token %[[SUSPEND_ID]], i1 false) // CHECK-NEXT: switch i8 %[[OUTCOME]], label %[[RET_BB:.+]] [ @@ -379,7 +379,7 @@ extern "C" void TestTailcall() { // CHECK-NEXT: ] // Await suspend wrapper - // CHECK: define {{.*}} ptr @__await_suspend_wrapper_TestTailcall_await(ptr {{[^,]*}} %[[AWAITABLE_ARG:.+]], ptr {{[^,]*}} %[[FRAME_ARG:.+]]) + // CHECK: define {{.*}} ptr @TestTailcall.__await_suspend_wrapper__await(ptr {{[^,]*}} %[[AWAITABLE_ARG:.+]], ptr {{[^,]*}} %[[FRAME_ARG:.+]]) // CHECK: store ptr %[[AWAITABLE_ARG]], ptr %[[AWAITABLE_TMP:.+]], // CHECK: store ptr %[[FRAME_ARG]], ptr %[[FRAME_TMP:.+]], // CHECK: %[[AWAITABLE:.+]] = load ptr, ptr %[[AWAITABLE_TMP]] diff --git a/clang/test/CodeGenCoroutines/coro-cleanup.cpp b/clang/test/CodeGenCoroutines/coro-cleanup.cpp index 98f150758e2d106d625a36ba35ffe16c9ef46d70..4e77ac25af1bf2374f7f17a88222dd8f38abd941 100644 --- a/clang/test/CodeGenCoroutines/coro-cleanup.cpp +++ b/clang/test/CodeGenCoroutines/coro-cleanup.cpp @@ -84,11 +84,13 @@ void f() { // CHECK: [[Cleanup]]: // CHECK: call void @_ZNSt16coroutine_traitsIJvEE12promise_typeD1Ev( // CHECK: %[[Mem0:.+]] = call ptr @llvm.coro.free( - // CHECK: call void @_ZdlPv(ptr noundef %[[Mem0]] + // CHECK: %[[SIZE:.+]] = call i64 @llvm.coro.size.i64() + // CHECK: call void @_ZdlPvm(ptr noundef %[[Mem0]], i64 noundef %[[SIZE]]) // CHECK: [[Dealloc]]: // THROWEND: %[[Mem:.+]] = call ptr @llvm.coro.free( - // THROWEND: call void @_ZdlPv(ptr noundef %[[Mem]]) + // THROWEND: %[[SIZE:.+]] = call i64 @llvm.coro.size.i64() + // THROWEND: call void @_ZdlPvm(ptr noundef %[[Mem]], i64 noundef %[[SIZE]]) co_return; } diff --git a/clang/test/CodeGenCoroutines/coro-dealloc.cpp b/clang/test/CodeGenCoroutines/coro-dealloc.cpp index 1f7d04b3689eb5a352fba07c90b080017d2ea271..656c9cbd3ef21dbd0a89d0c8f11374483d7b4e9f 100644 --- a/clang/test/CodeGenCoroutines/coro-dealloc.cpp +++ b/clang/test/CodeGenCoroutines/coro-dealloc.cpp @@ -1,6 +1,5 @@ // RUN: %clang_cc1 -triple x86_64-unknown-linux-gnu -std=c++20 \ // RUN: -S -emit-llvm %s -o - -disable-llvm-passes \ -// RUN: -fsized-deallocation \ // RUN: | FileCheck %s #include "Inputs/coroutine.h" @@ -21,7 +20,6 @@ struct task { }; // Test the compiler will chose sized deallocation correctly. -// This is only enabled with `-fsized-deallocation` which is off by default. void operator delete(void *ptr, std::size_t size) noexcept; // CHECK: define{{.*}}@_Z1fv diff --git a/clang/test/CodeGenCoroutines/coro-dwarf.cpp b/clang/test/CodeGenCoroutines/coro-dwarf.cpp index 2c9c827e6753d68e8a0e71449b896ab2df1ee453..f951b63dc117c3f199e86f8775f8141921aa41f1 100644 --- a/clang/test/CodeGenCoroutines/coro-dwarf.cpp +++ b/clang/test/CodeGenCoroutines/coro-dwarf.cpp @@ -71,14 +71,14 @@ void f_coro(int val, MoveOnly moParam, MoveAndCopy mcParam) { // CHECK: !{{[0-9]+}} = !DILocalVariable(name: "mcParam", arg: 3, scope: ![[SP]], file: !{{[0-9]+}}, line: {{[0-9]+}}, type: !{{[0-9]+}}) // CHECK: !{{[0-9]+}} = !DILocalVariable(name: "__promise", -// CHECK: !{{[0-9]+}} = distinct !DISubprogram(linkageName: "__await_suspend_wrapper__Z6f_coroi8MoveOnly11MoveAndCopy_init" +// CHECK: !{{[0-9]+}} = distinct !DISubprogram(linkageName: "_Z6f_coroi8MoveOnly11MoveAndCopy.__await_suspend_wrapper__init" // CHECK-NEXT: !{{[0-9]+}} = !DIFile // CHECK-NEXT: !{{[0-9]+}} = !DISubroutineType // CHECK-NEXT: !{{[0-9]+}} = !DILocalVariable(arg: 1, // CHECK-NEXT: !{{[0-9]+}} = !DILocation // CHECK-NEXT: !{{[0-9]+}} = !DILocalVariable(arg: 2, -// CHECK: !{{[0-9]+}} = distinct !DISubprogram(linkageName: "__await_suspend_wrapper__Z6f_coroi8MoveOnly11MoveAndCopy_final" +// CHECK: !{{[0-9]+}} = distinct !DISubprogram(linkageName: "_Z6f_coroi8MoveOnly11MoveAndCopy.__await_suspend_wrapper__final" // CHECK-NEXT: !{{[0-9]+}} = !DILocalVariable(arg: 1, // CHECK-NEXT: !{{[0-9]+}} = !DILocation // CHECK-NEXT: !{{[0-9]+}} = !DILocalVariable(arg: 2, diff --git a/clang/test/CodeGenCoroutines/coro-gro.cpp b/clang/test/CodeGenCoroutines/coro-gro.cpp index d4c3ff589e340a85f8ce79bb210ad4eeb2e529d5..b62134317cef2db1cd5e61a4fb93f145ec7c4397 100644 --- a/clang/test/CodeGenCoroutines/coro-gro.cpp +++ b/clang/test/CodeGenCoroutines/coro-gro.cpp @@ -51,7 +51,8 @@ int f() { // CHECK: call void @_ZNSt16coroutine_traitsIiJEE12promise_typeD1Ev( // CHECK: %[[Mem:.+]] = call ptr @llvm.coro.free( - // CHECK: call void @_ZdlPv(ptr noundef %[[Mem]]) + // CHECK: %[[SIZE:.+]] = call i64 @llvm.coro.size.i64() + // CHECK: call void @_ZdlPvm(ptr noundef %[[Mem]], i64 noundef %[[SIZE]]) // Initialize retval from Gro and destroy Gro // Note this also tests delaying initialization when Gro and function return diff --git a/clang/test/CodeGenCoroutines/pr56919.cpp b/clang/test/CodeGenCoroutines/pr56919.cpp index c7de08ef72d7f798383c4f779022a16746a4c0b7..baa8c27ce6649b00595c07bc3be2635d67105439 100644 --- a/clang/test/CodeGenCoroutines/pr56919.cpp +++ b/clang/test/CodeGenCoroutines/pr56919.cpp @@ -111,12 +111,15 @@ Task Bar() { co_await Baz(); } // CHECK: _Z3Quxv.destroy:{{.*}} // CHECK-NEXT: # -// CHECK-NEXT: jmp _ZdlPv +// CHECK-NEXT: movl $40, %esi +// CHECK-NEXT: jmp _ZdlPvm@PLT // CHECK: _Z3Bazv.destroy:{{.*}} // CHECK-NEXT: # -// CHECK-NEXT: jmp _ZdlPv +// CHECK-NEXT: movl $80, %esi +// CHECK-NEXT: jmp _ZdlPvm // CHECK: _Z3Barv.destroy:{{.*}} // CHECK-NEXT: # -// CHECK-NEXT: jmp _ZdlPv +// CHECK-NEXT: movl $120, %esi +// CHECK-NEXT: jmp _ZdlPvm diff --git a/clang/test/CodeGenCoroutines/pr65054.cpp b/clang/test/CodeGenCoroutines/pr65054.cpp index 7af9c04fca180e725cdf8fe58bf47d60416e1bcf..2d8b6dfe18d5521aa0e9ee810f7021be921ac9d3 100644 --- a/clang/test/CodeGenCoroutines/pr65054.cpp +++ b/clang/test/CodeGenCoroutines/pr65054.cpp @@ -48,6 +48,6 @@ MyTask FooBar() { } // CHECK-O0: define{{.*}}@_Z6FooBarv.resume -// CHECK-O0: call{{.*}}@__await_suspend_wrapper__Z6FooBarv_await( +// CHECK-O0: call{{.*}}@_Z6FooBarv.__await_suspend_wrapper__await( // CHECK-O0-NOT: store // CHECK-O0: ret void diff --git a/clang/test/CodeGenObjCXX/msabi-stret-arm64.mm b/clang/test/CodeGenObjCXX/msabi-stret-arm64.mm new file mode 100644 index 0000000000000000000000000000000000000000..3bbdbebc5cb576727159eea1a70b575e70d59bf8 --- /dev/null +++ b/clang/test/CodeGenObjCXX/msabi-stret-arm64.mm @@ -0,0 +1,77 @@ +// RUN: %clang_cc1 -triple aarch64-pc-windows-msvc -fobjc-runtime=gnustep-2.2 -fobjc-dispatch-method=non-legacy -emit-llvm -o - %s | FileCheck %s + +// Pass and return for type size <= 8 bytes. +struct S1 { + int a[2]; +}; + +// Pass and return hfa <= 8 bytes +struct F1 { + float a[2]; +}; + +// Pass and return for type size > 16 bytes. +struct S2 { + int a[5]; +}; + +// Pass and return aggregate (of size < 16 bytes) with non-trivial destructor. +// Sret and inreg: Returned in x0 +struct S3 { + int a[3]; + ~S3(); +}; +S3::~S3() { +} + + +@interface MsgTest { id isa; } @end +@implementation MsgTest +- (S1) smallS1 { + S1 x; + x.a[0] = 0; + x.a[1] = 1; + return x; + +} +- (F1) smallF1 { + F1 x; + x.a[0] = 0.2f; + x.a[1] = 0.5f; + return x; +} +- (S2) stretS2 { + S2 x; + for (int i = 0; i < 5; i++) { + x.a[i] = i; + } + return x; +} +- (S3) stretInRegS3 { + S3 x; + for (int i = 0; i < 3; i++) { + x.a[i] = i; + } + return x; +} ++ (S3) msgTestStretInRegS3 { + S3 x; + for (int i = 0; i < 3; i++) { + x.a[i] = i; + } + return x; +} +@end + +void test0(MsgTest *t) { + // CHECK: call {{.*}} @objc_msgSend + S1 ret = [t smallS1]; + // CHECK: call {{.*}} @objc_msgSend + F1 ret2 = [t smallF1]; + // CHECK: call {{.*}} @objc_msgSend_stret + S2 ret3 = [t stretS2]; + // CHECK: call {{.*}} @objc_msgSend_stret2 + S3 ret4 = [t stretInRegS3]; + // CHECK: call {{.*}} @objc_msgSend_stret2 + S3 ret5 = [MsgTest msgTestStretInRegS3]; +} diff --git a/clang/test/CodeGenOpenCL/builtins-generic-amdgcn.cl b/clang/test/CodeGenOpenCL/builtins-generic-amdgcn.cl index b093fcbf7d9894d3b38478b8254589e10ee4b572..37bea1ff93303941991b0bc4edd0af70e2f28bf2 100644 --- a/clang/test/CodeGenOpenCL/builtins-generic-amdgcn.cl +++ b/clang/test/CodeGenOpenCL/builtins-generic-amdgcn.cl @@ -4,14 +4,14 @@ #pragma OPENCL EXTENSION cl_khr_fp16 : enable // CHECK-LABEL: @test_builtin_clz( -// CHECK: tail call i32 @llvm.ctlz.i32(i32 %a, i1 true) +// CHECK: tail call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 %a, i1 true) void test_builtin_clz(global int* out, int a) { *out = __builtin_clz(a); } // CHECK-LABEL: @test_builtin_clzl( -// CHECK: tail call i64 @llvm.ctlz.i64(i64 %a, i1 true) +// CHECK: tail call range(i64 0, 65) i64 @llvm.ctlz.i64(i64 %a, i1 true) void test_builtin_clzl(global long* out, long a) { *out = __builtin_clzl(a); diff --git a/clang/test/Driver/aarch64-mcpu.c b/clang/test/Driver/aarch64-mcpu.c index 77ba43122b24531e4c01f3cbab3bc8c36180696d..ad4a5f9ac6fb805528410f6feaa343ef07c53150 100644 --- a/clang/test/Driver/aarch64-mcpu.c +++ b/clang/test/Driver/aarch64-mcpu.c @@ -64,10 +64,16 @@ // NEOVERSE-V1: "-cc1"{{.*}} "-triple" "aarch64{{.*}}" "-target-cpu" "neoverse-v1" // RUN: %clang --target=aarch64 -mcpu=neoverse-v2 -### -c %s 2>&1 | FileCheck -check-prefix=NEOVERSE-V2 %s // NEOVERSE-V2: "-cc1"{{.*}} "-triple" "aarch64{{.*}}" "-target-cpu" "neoverse-v2" +// RUN: %clang --target=aarch64 -mcpu=neoverse-v3 -### -c %s 2>&1 | FileCheck -check-prefix=NEOVERSE-V3 %s +// NEOVERSE-V3: "-cc1"{{.*}} "-triple" "aarch64{{.*}}" "-target-cpu" "neoverse-v3" +// RUN: %clang --target=aarch64 -mcpu=neoverse-v3ae -### -c %s 2>&1 | FileCheck -check-prefix=NEOVERSE-V3AE %s +// NEOVERSE-V3AE: "-cc1"{{.*}} "-triple" "aarch64{{.*}}" "-target-cpu" "neoverse-v3ae" // RUN: %clang --target=aarch64 -mcpu=neoverse-n1 -### -c %s 2>&1 | FileCheck -check-prefix=NEOVERSE-N1 %s // NEOVERSE-N1: "-cc1"{{.*}} "-triple" "aarch64{{.*}}" "-target-cpu" "neoverse-n1" // RUN: %clang --target=aarch64 -mcpu=neoverse-n2 -### -c %s 2>&1 | FileCheck -check-prefix=NEOVERSE-N2 %s // NEOVERSE-N2: "-cc1"{{.*}} "-triple" "aarch64{{.*}}" "-target-cpu" "neoverse-n2" +// RUN: %clang --target=aarch64 -mcpu=neoverse-n3 -### -c %s 2>&1 | FileCheck -check-prefix=NEOVERSE-N3 %s +// NEOVERSE-N3: "-cc1"{{.*}} "-triple" "aarch64{{.*}}" "-target-cpu" "neoverse-n3" // RUN: %clang --target=aarch64 -mcpu=neoverse-512tvb -### -c %s 2>&1 | FileCheck -check-prefix=NEOVERSE-512TVB %s // NEOVERSE-512TVB: "-cc1"{{.*}} "-triple" "aarch64{{.*}}" "-target-cpu" "neoverse-512tvb" // RUN: %clang --target=aarch64 -mcpu=cortex-a520 -### -c %s 2>&1 | FileCheck -check-prefix=CORTEX-A520 %s diff --git a/clang/test/Driver/amdgpu-toolchain.c b/clang/test/Driver/amdgpu-toolchain.c index 4300e7e9f66705b84b5c69fef21ccc34899b81db..faaff05004f6deb6249103f809e4207eddfc2e32 100644 --- a/clang/test/Driver/amdgpu-toolchain.c +++ b/clang/test/Driver/amdgpu-toolchain.c @@ -24,3 +24,7 @@ // RUN: -L. -fconvergent-functions %s 2>&1 | FileCheck -check-prefix=MCPU %s // LTO: clang{{.*}} "-flto=full"{{.*}}"-fconvergent-functions" // MCPU: ld.lld{{.*}}"-L."{{.*}}"-plugin-opt=mcpu=gfx906" + +// RUN: %clang -### --target=amdgcn-amd-amdhsa -mcpu=gfx906 -nogpulib \ +// RUN: -fuse-ld=ld %s 2>&1 | FileCheck -check-prefixes=LD %s +// LD: ld.lld" diff --git a/clang/test/Driver/cl-options.c b/clang/test/Driver/cl-options.c index 7731300ae9f5258583e1082107376085dfbc0572..75f49deca0653d556d53f462211c007c80554bf6 100644 --- a/clang/test/Driver/cl-options.c +++ b/clang/test/Driver/cl-options.c @@ -70,12 +70,16 @@ // fsanitize_address: -fsanitize=address // RUN: %clang_cl -### /FA -fprofile-instr-generate -- %s 2>&1 | FileCheck -check-prefix=CHECK-PROFILE-INSTR-GENERATE %s +// RUN: %clang_cl -### /FA -fprofile-instr-generate -fno-rtlib-defaultlib -frtlib-defaultlib -- %s 2>&1 | FileCheck -check-prefix=CHECK-PROFILE-INSTR-GENERATE %s // RUN: %clang_cl -### /FA -fprofile-instr-generate=/tmp/somefile.profraw -- %s 2>&1 | FileCheck -check-prefix=CHECK-PROFILE-INSTR-GENERATE-FILE %s // RUN: %clang_cl -### /FAcsu -fprofile-instr-generate -- %s 2>&1 | FileCheck -check-prefix=CHECK-PROFILE-INSTR-GENERATE %s // RUN: %clang_cl -### /FAcsu -fprofile-instr-generate=/tmp/somefile.profraw -- %s 2>&1 | FileCheck -check-prefix=CHECK-PROFILE-INSTR-GENERATE-FILE %s // CHECK-PROFILE-INSTR-GENERATE: "-fprofile-instrument=clang" "--dependent-lib=clang_rt.profile{{[^"]*}}.lib" // CHECK-PROFILE-INSTR-GENERATE-FILE: "-fprofile-instrument-path=/tmp/somefile.profraw" +// RUN: %clang_cl -### /FA -fprofile-instr-generate -fno-rtlib-defaultlib -- %s 2>&1 | FileCheck -check-prefix=CHECK-PROFILE-INSTR-GENERATE-NODEF %s +// CHECK-PROFILE-INSTR-GENERATE-NODEF-NOT: "--dependent-lib=clang_rt.profile{{[^"]*}}.lib" + // RUN: %clang_cl -### /FA -fprofile-generate -- %s 2>&1 | FileCheck -check-prefix=CHECK-PROFILE-GENERATE %s // RUN: %clang_cl -### /FAcsu -fprofile-generate -- %s 2>&1 | FileCheck -check-prefix=CHECK-PROFILE-GENERATE %s // CHECK-PROFILE-GENERATE: "-fprofile-instrument=llvm" "--dependent-lib=clang_rt.profile{{[^"]*}}.lib" diff --git a/clang/test/Driver/default-denormal-fp-math.c b/clang/test/Driver/default-denormal-fp-math.c index 5f87e151df49e41029289c45aa2b5639301aaf04..c04ad5c08b8d0d1c0563c01abcd2df5994566592 100644 --- a/clang/test/Driver/default-denormal-fp-math.c +++ b/clang/test/Driver/default-denormal-fp-math.c @@ -3,15 +3,6 @@ // RUN: %clang -### -target x86_64-unknown-linux-gnu --sysroot=%S/Inputs/basic_linux_tree -c %s -v 2>&1 | FileCheck -check-prefix=CHECK-IEEE %s -// crtfastmath enables ftz and daz -// RUN: %clang -### -target x86_64-unknown-linux-gnu -ffast-math --sysroot=%S/Inputs/basic_linux_tree -c %s -v 2>&1 | FileCheck -check-prefix=CHECK-PRESERVESIGN %s - -// crt not linked in with nostartfiles -// RUN: %clang -### -target x86_64-unknown-linux-gnu -ffast-math -nostartfiles --sysroot=%S/Inputs/basic_linux_tree -c %s -v 2>&1 | FileCheck -check-prefix=CHECK-IEEE %s - -// If there's no crtfastmath, don't assume ftz/daz -// RUN: %clang -### -target x86_64-unknown-linux-gnu -ffast-math --sysroot=/dev/null -c %s -v 2>&1 | FileCheck -check-prefix=CHECK-IEEE %s - // RUN: %clang -### -target x86_64-scei-ps4 -c %s -v 2>&1 | FileCheck -check-prefix=CHECK-PRESERVESIGN %s // Flag omitted for default diff --git a/clang/test/Driver/fast-math.c b/clang/test/Driver/fast-math.c index 882e81fd14d34a7f352f35aae5abeed153611994..b07d5732932cdb61b1daa350426351d9aad32f68 100644 --- a/clang/test/Driver/fast-math.c +++ b/clang/test/Driver/fast-math.c @@ -7,324 +7,309 @@ // Both of them use gcc driver for as. // // RUN: %clang -### -fno-honor-infinities -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-INFS %s +// RUN: | FileCheck --check-prefixes=CHECK,NINF,NO-NNAN,NO-FINITE-ONLY %s // infinites [sic] is a supported alternative spelling of infinities. // RUN: %clang -### -fno-honor-infinites -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-INFS %s -// CHECK-NO-INFS: "-cc1" -// CHECK-NO-INFS: "-menable-no-infs" +// RUN: | FileCheck --check-prefixes=CHECK,NINF,NO-NNAN,NO-FINITE-ONLY %s // // RUN: %clang -### -fno-fast-math -fno-honor-infinities -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-FAST-MATH-NO-INFS %s -// CHECK-NO-FAST-MATH-NO-INFS: "-cc1" -// CHECK-NO-FAST-MATH-NO-INFS: "-menable-no-infs" +// RUN: | FileCheck --check-prefixes=CHECK,NO-FAST,NINF,NO-NNAN,NO-FINITE-ONLY %s // // RUN: %clang -### -fno-honor-infinities -fno-fast-math -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-INFS-NO-FAST-MATH %s -// CHECK-NO-INFS-NO-FAST-MATH: "-cc1" -// CHECK-NO-INFS-NO-FAST-MATH-NOT: "-menable-no-infs" +// RUN: | FileCheck --check-prefixes=CHECK,NO-FAST,NO-NINF,NO-NNAN,NO-FINITE-ONLY %s // // RUN: %clang -### -fno-signed-zeros -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-SIGNED-ZEROS %s -// CHECK-NO-SIGNED-ZEROS: "-cc1" -// CHECK-NO-SIGNED-ZEROS: "-fno-signed-zeros" +// RUN: | FileCheck --check-prefixes=CHECK,NSZ,NOROUNDING %s // // RUN: %clang -### -fno-fast-math -fno-signed-zeros -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-FAST-MATH-NO-SIGNED-ZEROS %s -// CHECK-NO-FAST-MATH-NO-SIGNED-ZEROS: "-cc1" -// CHECK-NO-FAST-MATH-NO-SIGNED-ZEROS: "-fno-signed-zeros" +// RUN: | FileCheck --check-prefixes=CHECK,NO-FAST,NSZ %s // // RUN: %clang -### -fno-signed-zeros -fno-fast-math -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-SIGNED-ZEROS-NO-FAST-MATH %s -// CHECK-NO-SIGNED-ZEROS-NO-FAST-MATH: "-cc1" -// CHECK-NO-SIGNED-ZEROS-NO-FAST-MATH-NOT: "-fno-signed-zeros" +// RUN: | FileCheck --check-prefixes=CHECK,NO-FAST,NO-NSZ,NOROUNDING %s // // RUN: %clang -### -freciprocal-math -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-RECIPROCAL-MATH %s -// CHECK-RECIPROCAL-MATH: "-cc1" -// CHECK-RECIPROCAL-MATH: "-freciprocal-math" +// RUN: | FileCheck --check-prefixes=CHECK,ARCP,NOROUNDING %s // // RUN: %clang -### -fno-fast-math -freciprocal-math -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-FAST-MATH-RECIPROCAL-MATH %s -// CHECK-NO-FAST-MATH-RECIPROCAL-MATH: "-cc1" -// CHECK-NO-FAST-MATH-RECIPROCAL-MATH: "-freciprocal-math" +// RUN: | FileCheck --check-prefixes=CHECK,ARCP,NOROUNDING %s // // RUN: %clang -### -freciprocal-math -fno-fast-math -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-RECIPROCAL-MATH-NO-FAST-MATH %s -// CHECK-RECIPROCAL-MATH-NO-FAST-MATH: "-cc1" -// CHECK-RECIPROCAL-MATH-NO-FAST-MATH-NOT: "-freciprocal-math" +// RUN: | FileCheck --check-prefixes=CHECK,NO-ARCP,NOROUNDING %s // // RUN: %clang -### -fno-honor-nans -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-NANS %s -// CHECK-NO-NANS: "-cc1" -// CHECK-NO-NANS: "-menable-no-nans" +// RUN: | FileCheck --check-prefixes=CHECK,NNAN,NO-NINF,NO-FINITE-ONLY,NOROUNDING %s // // RUN: %clang -### -fno-fast-math -fno-honor-nans -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-FAST-MATH-NO-NANS %s -// CHECK-NO-FAST-MATH-NO-NANS: "-cc1" -// CHECK-NO-FAST-MATH-NO-NANS: "-menable-no-nans" +// RUN: | FileCheck --check-prefixes=CHECK,NO-FAST,NNAN,NO-NINF,NO-FINITE-ONLY,NOROUNDING %s // // RUN: %clang -### -fno-honor-nans -fno-fast-math -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-NANS-NO-FAST-MATH %s -// CHECK-NO-NANS-NO-FAST-MATH: "-cc1" -// CHECK-NO-NANS-NO-FAST-MATH-NOT: "-menable-no-nans" +// RUN: | FileCheck --check-prefixes=CHECK,NO-FAST,NO-NNAN,NO-NINF,NO-FINITE-ONLY,NOROUNDING %s // // RUN: %clang -### -ffast-math -fno-approx-func -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-FAST-MATH-NO-APPROX-FUNC %s -// CHECK-FAST-MATH-NO-APPROX-FUNC: "-cc1" -// CHECK-FAST-MATH-NO-APPROX-FUNC: "-menable-no-infs" -// CHECK-FAST-MATH-NO-APPROX-FUNC: "-menable-no-nans" -// CHECK-FAST-MATH-NO-APPROX-FUNC: "-fno-signed-zeros" -// CHECK-FAST-MATH-NO-APPROX-FUNC: "-mreassociate" -// CHECK-FAST-MATH-NO-APPROX-FUNC: "-freciprocal-math" -// CHECK-FAST-MATH-NO-APPROX-FUNC: "-ffp-contract=fast" -// CHECK-FAST-MATH-NO-APPROX-FUNC-NOT: "-ffast-math" -// CHECK-FAST-MATH-NO-APPROX-FUNC-NOT: "-fapprox-func" +// RUN: | FileCheck --check-prefixes=CHECK,NO-FAST,NINF,NNAN,FINITE-ONLY,NSZ,ARCP,NO-AFN,NO-ERRNO,NOROUNDING %s // // RUN: %clang -### -fno-approx-func -ffast-math -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-APPROX-FUNC-FAST-MATH %s -// CHECK-NO-APPROX-FUNC-FAST-MATH: "-cc1" -// CHECK-NO-APPROX-FUNC-FAST-MATH: "-ffast-math" +// RUN: | FileCheck --check-prefixes=CHECK,FAST,NINF,NNAN,FINITE-ONLY,NSZ,ARCP,AFN,NO-ERRNO,NOROUNDING %s // // RUN: %clang -### -fapprox-func -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-APPROX-FUNC %s -// CHECK-APPROX-FUNC: "-cc1" -// CHECK-APPROX-FUNC: "-fapprox-func" +// RUN: | FileCheck --check-prefixes=CHECK,AFN %s // // RUN: %clang -### -fno-fast-math -fapprox-func -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-FAST-MATH-APPROX-FUNC %s -// CHECK-NO-FAST-MATH-APPROX-FUNC: "-cc1" -// CHECK-NO-FAST-MATH-APPROX-FUNC: "-fapprox-func" +// RUN: | FileCheck --check-prefixes=CHECK,NO-FAST,AFN,NOROUNDING %s // // RUN: %clang -### -fapprox-func -fno-fast-math -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-APPROX-FUNC-NO-FAST-MATH %s -// CHECK-APPROX-FUNC-NO-FAST-MATH: "-cc1" -// CHECK-APPROX-FUNC-NO-FAST-MATH-NOT: "-fapprox-func" +// RUN: | FileCheck --check-prefixes=CHECK,NO-FAST,NO-AFN %s // // RUN: %clang -### -fmath-errno -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-MATH-ERRNO %s -// CHECK-MATH-ERRNO: "-cc1" -// CHECK-MATH-ERRNO: "-fmath-errno" +// RUN: | FileCheck --check-prefixes=CHECK,NO-FAST,ERRNO %s // // RUN: %clang -### -fmath-errno -fno-math-errno -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-MATH-ERRNO %s -// CHECK-NO-MATH-ERRNO: "-cc1" -// CHECK-NO-MATH-ERRNO-NOT: "-fmath-errno" +// RUN: | FileCheck --check-prefixes=CHECK,NO-ERRNO %s // // Target defaults for -fmath-errno (reusing the above checks). // RUN: %clang -### -target i686-unknown-linux -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-MATH-ERRNO %s +// RUN: | FileCheck --check-prefixes=CHECK,ERRNO %s // RUN: %clang -### -target i686-apple-darwin -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-MATH-ERRNO %s +// RUN: | FileCheck --check-prefixes=CHECK,NO-ERRNO %s // RUN: %clang -### -target x86_64-unknown-freebsd -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-MATH-ERRNO %s +// RUN: | FileCheck --check-prefixes=CHECK,NO-ERRNO %s // RUN: %clang -### -target x86_64-unknown-netbsd -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-MATH-ERRNO %s +// RUN: | FileCheck --check-prefixes=CHECK,NO-ERRNO %s // RUN: %clang -### -target x86_64-unknown-openbsd -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-MATH-ERRNO %s +// RUN: | FileCheck --check-prefixes=CHECK,NO-ERRNO %s // RUN: %clang -### --target=x86_64-unknown-haiku -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-MATH-ERRNO %s +// RUN: | FileCheck --check-prefixes=CHECK,NO-ERRNO %s // RUN: %clang -### -target x86_64-unknown-dragonfly -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-MATH-ERRNO %s +// RUN: | FileCheck --check-prefixes=CHECK,NO-ERRNO %s // RUN: %clang -### -target x86_64-fuchsia -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-MATH-ERRNO %s +// RUN: | FileCheck --check-prefixes=CHECK,NO-ERRNO %s // RUN: %clang -### -target x86_64-linux-android -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-MATH-ERRNO %s +// RUN: | FileCheck --check-prefixes=CHECK,NO-ERRNO %s // RUN: %clang -### -target x86_64-linux-musl -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-MATH-ERRNO %s +// RUN: | FileCheck --check-prefixes=CHECK,NO-ERRNO %s // RUN: %clang -### --target=amdgcn-amd-amdhsa -nogpuinc -nogpulib -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-MATH-ERRNO %s +// RUN: | FileCheck --check-prefixes=CHECK,NO-ERRNO %s // RUN: %clang -### -target amdgcn-amd-amdpal -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-MATH-ERRNO %s +// RUN: | FileCheck --check-prefixes=CHECK,NO-ERRNO %s // RUN: %clang -### -target amdgcn-mesa-mesa3d -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-MATH-ERRNO %s +// RUN: | FileCheck --check-prefixes=CHECK,NO-ERRNO %s // // Check that -ffast-math disables -fmath-errno, and -fno-fast-math merely // preserves the target default. Also check various flag set operations between // the two flags. (Resuses above checks.) // RUN: %clang -### -ffast-math -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-MATH-ERRNO %s +// RUN: | FileCheck --check-prefixes=CHECK,NO-ERRNO %s // RUN: %clang -### -fmath-errno -ffast-math -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-MATH-ERRNO %s +// RUN: | FileCheck --check-prefixes=CHECK,NO-ERRNO %s // RUN: %clang -### -ffast-math -fmath-errno -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-MATH-ERRNO %s +// RUN: | FileCheck --check-prefixes=CHECK,ERRNO %s // RUN: %clang -### -target i686-unknown-linux -fno-fast-math -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-MATH-ERRNO %s +// RUN: | FileCheck --check-prefixes=CHECK,ERRNO %s // RUN: %clang -### -target i686-unknown-linux -fno-math-errno -fno-fast-math -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-MATH-ERRNO %s +// RUN: | FileCheck --check-prefixes=CHECK,ERRNO %s // RUN: %clang -### -target i686-apple-darwin -fno-fast-math -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-MATH-ERRNO %s +// RUN: | FileCheck --check-prefixes=CHECK,NO-ERRNO %s // RUN: %clang -### -target i686-apple-darwin -fno-math-errno -fno-fast-math -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-MATH-ERRNO %s +// RUN: | FileCheck --check-prefixes=CHECK,NO-ERRNO %s // RUN: %clang -### -fno-fast-math -fno-math-errno -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-MATH-ERRNO %s +// RUN: | FileCheck --check-prefixes=CHECK,NO-ERRNO %s // // RUN: %clang -### -fno-math-errno -fassociative-math -freciprocal-math \ // RUN: -fno-signed-zeros -fno-trapping-math -fapprox-func -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-UNSAFE-MATH %s -// CHECK-UNSAFE-MATH: "-cc1" -// CHECK-UNSAFE-MATH: "-funsafe-math-optimizations" -// CHECK-UNSAFE-MATH: "-mreassociate" +// RUN: | FileCheck --check-prefixes=CHECK,NO-ERRNO,UNSAFE,ARCP,NSZ,NO-TRAPPING,REASSOC %s // // RUN: %clang -### -fno-fast-math -fno-math-errno -fassociative-math -freciprocal-math \ // RUN: -fno-signed-zeros -fno-trapping-math -fapprox-func -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-FAST-MATH-UNSAFE-MATH %s -// CHECK-NO-FAST-MATH-UNSAFE-MATH: "-cc1" -// CHECK-NO-FAST-MATH-UNSAFE-MATH: "-funsafe-math-optimizations" -// CHECK-NO-FAST-MATH-UNSAFE-MATH: "-mreassociate" +// RUN: | FileCheck --check-prefixes=CHECK,NO-ERRNO,UNSAFE,ARCP,NSZ,NO-TRAPPING,REASSOC %s // The 2nd -fno-fast-math overrides -fassociative-math. // RUN: %clang -### -fno-fast-math -fno-math-errno -fassociative-math -freciprocal-math \ // RUN: -fno-fast-math -fno-signed-zeros -fno-trapping-math -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-UNSAFE-MATH-NO-FAST-MATH %s -// CHECK-UNSAFE-MATH-NO-FAST-MATH: "-cc1" -// CHECK-UNSAFE-MATH-NO-FAST-MATH-NOT: "-funsafe-math-optimizations" -// CHECK-UNSAFE-MATH-NO-FAST-MATH-NOT: "-mreassociate" +// RUN: | FileCheck --check-prefixes=CHECK,NO-UNSAFE,NO-REASSOC,NO-ARCP,NSZ,NO-TRAPPING %s // // Check that various umbrella flags also enable these frontend options. // RUN: %clang -### -ffast-math -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-INFS %s -// RUN: %clang -### -ffast-math -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-NANS %s -// RUN: %clang -### -ffast-math -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-UNSAFE-MATH %s +// RUN: | FileCheck --check-prefixes=CHECK,FAST,NINF,NNAN,FINITE-ONLY,REASSOC,NSZ,ARCP,AFN,CONTRACT-FAST,NO-ERRNO,NOROUNDING %s // RUN: %clang -### -ffinite-math-only -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-INFS %s -// RUN: %clang -### -ffinite-math-only -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-NANS %s +// RUN: | FileCheck --check-prefixes=CHECK,NINF,NNAN,FINITE-ONLY %s // RUN: %clang -### -funsafe-math-optimizations -fno-math-errno -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-UNSAFE-MATH %s +// RUN: | FileCheck --check-prefixes=CHECK,NO-FAST,NO-NNAN,NO-NINF,NO-FINITE-ONLY,REASSOC,NSZ,ARCP,AFN,CONTRACT-FAST,NO-ERRNO,NOROUNDING %s // // One umbrella flag is *really* weird and also changes the semantics of the // program by adding a special preprocessor macro. Check that the frontend flag // modeling this semantic change is provided. Also check that the flag is not // present if any of the optimizations are disabled. -// RUN: %clang -### -ffast-math -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-FAST-MATH %s // RUN: %clang -### -fno-fast-math -ffast-math -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-FAST-MATH %s +// RUN: | FileCheck --check-prefixes=CHECK,FAST,NINF,NNAN,FINITE-ONLY,REASSOC,NSZ,ARCP,AFN,CONTRACT-FAST,NO-ERRNO,NOROUNDING %s // RUN: %clang -### -funsafe-math-optimizations -ffinite-math-only \ // RUN: -fno-math-errno -ffp-contract=fast -fno-rounding-math -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-FAST-MATH %s +// RUN: | FileCheck --check-prefixes=CHECK,FAST,NINF,NNAN,FINITE-ONLY,NSZ,ARCP,AFN,CONTRACT-FAST,NO-ERRNO,NOROUNDING %s // RUN: %clang -### -fno-honor-infinities -fno-honor-nans -fno-math-errno \ // RUN: -fassociative-math -freciprocal-math -fno-signed-zeros -fapprox-func \ // RUN: -fno-trapping-math -ffp-contract=fast -fno-rounding-math -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-FAST-MATH %s -// CHECK-FAST-MATH: "-cc1" -// CHECK-FAST-MATH: "-ffast-math" -// CHECK-FAST-MATH: "-ffinite-math-only" +// RUN: | FileCheck --check-prefixes=CHECK,FAST,NINF,NNAN,FINITE-ONLY,NSZ,ARCP,AFN,CONTRACT-FAST,NO-ERRNO,NOROUNDING %s // // RUN: %clang -### -ffast-math -fno-fast-math -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-FAST-MATH %s +// RUN: | FileCheck --check-prefixes=CHECK,NO-FAST,NO-NINF,NO-NNAN,NO-FINITE-ONLY,NO-REASSOC,NO-NSZ,NO-ARCP,NO-AFN,NOROUNDING %s // RUN: %clang -### -ffast-math -fno-finite-math-only -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-FAST-MATH %s +// RUN: | FileCheck --check-prefixes=CHECK,NO-FAST,NO-NINF,NO-NNAN,NO-FINITE-ONLY,REASSOC,NSZ,ARCP,AFN,CONTRACT-FAST,NOROUNDING %s + +// FIXME: This case leaves nnan and ninf. That seems wrong! // RUN: %clang -### -ffast-math -fno-unsafe-math-optimizations -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-FAST-MATH %s +// RUN: | FileCheck --check-prefixes=CHECK,NO-FAST,NINF,NNAN,FINITE-ONLY,NO-REASSOC,NO-NSZ,NO-ARCP,NO-AFN,NOROUNDING %s // RUN: %clang -### -ffast-math -fmath-errno -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-FAST-MATH %s +// RUN: | FileCheck --check-prefixes=CHECK,NO-FAST,NINF,NNAN,FINITE-ONLY,REASSOC,NSZ,ARCP,AFN,CONTRACT-FAST,ERRNO,NOROUNDING %s // RUN: %clang -### -ffast-math -fno-associative-math -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-FAST-MATH --check-prefix=CHECK-ASSOC-MATH %s -// CHECK-NO-FAST-MATH: "-cc1" -// CHECK-NO-FAST-MATH-NOT: "-ffast-math" -// CHECK-ASSOC-MATH-NOT: "-mreassociate" +// RUN: | FileCheck --check-prefixes=CHECK,NO-FAST,NINF,NNAN,FINITE-ONLY,NO-REASSOC,NSZ,ARCP,AFN,CONTRACT-FAST,NO-ERRNO,NOROUNDING %s // // Check various means of disabling these flags, including disabling them after // they've been enabled via an umbrella flag. // RUN: %clang -### -fno-honor-infinities -fhonor-infinities -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-NO-INFS %s +// RUN: | FileCheck --check-prefixes=CHECK,NO-NINF,NO-NNAN,NO-FINITE-ONLY %s // RUN: %clang -### -ffinite-math-only -fhonor-infinities -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-NO-INFS %s +// RUN: | FileCheck --check-prefixes=CHECK,NO-NINF,NNAN,NO-FINITE-ONLY %s // RUN: %clang -### -ffinite-math-only -fno-finite-math-only -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-NO-INFS %s +// RUN: | FileCheck --check-prefixes=CHECK,NO-NINF,NO-NNAN,NO-FINITE-ONLY %s // RUN: %clang -### -ffast-math -fhonor-infinities -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-NO-INFS %s +// RUN: | FileCheck --check-prefixes=CHECK,NO-FAST,NO-NINF,NNAN,NO-FINITE-ONLY,REASSOC,NSZ,ARCP,AFN,CONTRACT-FAST,NO-ERRNO,NOROUNDING %s // RUN: %clang -### -ffast-math -fno-finite-math-only -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-NO-INFS %s -// CHECK-NO-NO-INFS: "-cc1" -// CHECK-NO-NO-INFS-NOT: "-menable-no-infs" -// CHECK-NO-NO-INFS-NOT: "-ffinite-math-only" -// CHECK-NO-NO-INFS: "-o" +// RUN: | FileCheck --check-prefixes=CHECK,NO-FAST,NO-NINF,NO-NNAN,NO-FINITE-ONLY,REASSOC,NSZ,ARCP,AFN,CONTRACT-FAST,NO-ERRNO,NOROUNDING %s // // RUN: %clang -### -fno-honor-nans -fhonor-nans -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-NO-NANS %s +// RUN: | FileCheck --check-prefixes=CHECK,NO-NINF,NO-NNAN,NO-FINITE-ONLY %s // RUN: %clang -### -ffinite-math-only -fhonor-nans -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-NO-NANS %s +// RUN: | FileCheck --check-prefixes=CHECK,NINF,NO-NNAN,NO-FINITE-ONLY %s // RUN: %clang -### -ffinite-math-only -fno-finite-math-only -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-NO-NANS %s +// RUN: | FileCheck --check-prefixes=CHECK,NO-NINF,NO-NNAN,NO-FINITE-ONLY %s // RUN: %clang -### -ffast-math -fhonor-nans -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-NO-NANS %s +// RUN: | FileCheck --check-prefixes=CHECK,NINF,NO-NNAN,NO-FINITE-ONLY %s // RUN: %clang -### -ffast-math -fno-finite-math-only -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-NO-NANS %s -// CHECK-NO-NO-NANS: "-cc1" -// CHECK-NO-NO-NANS-NOT: "-menable-no-nans" -// CHECK-NO-NO-NANS-NOT: "-ffinite-math-only" -// CHECK-NO-NO-NANS: "-o" +// RUN: | FileCheck --check-prefixes=CHECK,NO-NINF,NO-NNAN,NO-FINITE-ONLY %s // A later inverted option overrides an earlier option. // RUN: %clang -### -fassociative-math -freciprocal-math -fno-signed-zeros \ // RUN: -fno-trapping-math -fno-associative-math -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-UNSAFE-MATH %s +// RUN: | FileCheck --check-prefixes=CHECK,NO-REASSOC,ARCP,NSZ,NO-TRAPPING %s + +// RUN: %clang -### -funsafe-math-optimizations -fno-associative-math -c %s 2>&1 \ +// RUN: | FileCheck --check-prefixes=CHECK,NO-UNSAFE,NO-REASSOC,ARCP,NSZ,AFN %s -// RUN: %clang -### -funsafe-math-optimizations -fno-associative-math -c %s \ -// RUN: 2>&1 | FileCheck --check-prefix=CHECK-NO-UNSAFE-MATH %s +// RUN: %clang -### -funsafe-math-optimizations -fno-reciprocal-math -c %s 2>&1 \ +// RUN: | FileCheck --check-prefixes=CHECK,NO-UNSAFE,REASSOC,NO-ARCP,NSZ,AFN %s -// RUN: %clang -### -funsafe-math-optimizations -fno-reciprocal-math -c %s \ -// RUN: 2>&1 | FileCheck --check-prefix=CHECK-NO-UNSAFE-MATH %s +// reassoc requires nsz // RUN: %clang -### -funsafe-math-optimizations -fsigned-zeros -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-UNSAFE-MATH %s +// RUN: | FileCheck --check-prefixes=CHECK,NO-UNSAFE,NO-REASSOC,ARCP,NO-NSZ,AFN %s + +// FIXME: Shouldn't trapping math disable all unsafe math? // RUN: %clang -### -funsafe-math-optimizations -ftrapping-math -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-UNSAFE-MATH %s +// RUN: | FileCheck --check-prefixes=CHECK,NO-UNSAFE,ARCP,NSZ,AFN,TRAPPING %s + // RUN: %clang -### -funsafe-math-optimizations -fno-unsafe-math-optimizations \ // RUN: -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-UNSAFE-MATH %s +// RUN: | FileCheck --check-prefixes=CHECK,NO-UNSAFE,NO-REASSOC,NO-ARCP,NO-NSZ,NO-AFN %s // RUN: %clang -### -ffast-math -fno-associative-math -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-UNSAFE-MATH %s +// RUN: | FileCheck --check-prefixes=CHECK,NO-UNSAFE,NO-REASSOC,ARCP,NSZ,AFN %s // RUN: %clang -### -ffast-math -fno-reciprocal-math -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-UNSAFE-MATH %s +// RUN: | FileCheck --check-prefixes=CHECK,NO-FAST,NO-UNSAFE,NNAN,NINF,FINITE-ONLY,REASSOC,NO-ARCP,CONTRACT-FAST,NSZ,AFN %s + +// reassoc requires nsz // RUN: %clang -### -ffast-math -fsigned-zeros -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-UNSAFE-MATH %s -// RUN: %clang -### -ffast-math -ftrapping-math -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-UNSAFE-MATH %s -// RUN: %clang -### -ffast-math -fno-unsafe-math-optimizations -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-UNSAFE-MATH %s +// RUN: | FileCheck --check-prefixes=CHECK,NO-FAST,NO-UNSAFE,NNAN,NINF,FINITE-ONLY,NO-REASSOC,ARCP,CONTRACT-FAST,NO-NSZ,AFN %s -// CHECK-NO-UNSAFE-MATH: "-cc1" -// CHECK-NO-UNSAFE-MATH-NOT: "-funsafe-math-optimizations" -// CHECK-NO_UNSAFE-MATH-NOT: "-mreassociate" -// CHECK-NO-UNSAFE-MATH: "-o" +// FIXME: Shouldn't trapping math disable unsafe math? +// RUN: %clang -### -ffast-math -ftrapping-math -c %s 2>&1 \ +// RUN: | FileCheck --check-prefixes=CHECK,NO-FAST,NO-UNSAFE,ARCP,NSZ,AFN,TRAPPING %s +// FIXME: -fno-unsafe-math-optimizations shouldn't imply trapping math +// RUN: %clang -### -ffast-math -fno-unsafe-math-optimizations -c %s 2>&1 \ +// RUN: | FileCheck --check-prefixes=CHECK,NO-FAST,NO-UNSAFE,NO-ARCP,NO-NSZ,NO-AFN,TRAPPING %s // Reassociate is allowed because it does not require reciprocal-math. // RUN: %clang -### -fassociative-math -freciprocal-math -fno-signed-zeros \ // RUN: -fno-trapping-math -fno-reciprocal-math -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-REASSOC-NO-UNSAFE-MATH %s - -// CHECK-REASSOC-NO-UNSAFE-MATH: "-cc1" -// CHECK-REASSOC-NO_UNSAFE-MATH-NOT: "-funsafe-math-optimizations" -// CHECK-REASSOC-NO_UNSAFE-MATH: "-mreassociate" -// CHECK-REASSOC-NO-UNSAFE-MATH-NOT: "-funsafe-math-optimizations" -// CHECK-REASSOC-NO-UNSAFE-MATH: "-o" +// RUN: | FileCheck --check-prefixes=CHECK,REASSOC,NO-ARCP,NSZ,NO-TRAPPING %s // In these runs, reassociate is not allowed because both no-signed-zeros and no-trapping-math are required. // RUN: %clang -### -fassociative-math -freciprocal-math -fno-signed-zeros \ // RUN: -fno-trapping-math -fsigned-zeros -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-REASSOC-NO-UNSAFE-MATH %s +// RUN: | FileCheck --check-prefixes=CHECK,NO-REASSOC,ARCP,NO-NSZ,NO-TRAPPING %s // RUN: %clang -### -fassociative-math -freciprocal-math -fno-signed-zeros \ // RUN: -fno-trapping-math -ftrapping-math -c %s 2>&1 \ -// RUN: | FileCheck --check-prefix=CHECK-NO-REASSOC-NO-UNSAFE-MATH %s +// RUN: | FileCheck --check-prefixes=CHECK,NO-REASSOC,ARCP,NSZ,TRAPPING %s + +// The checks below allow stringing together prefixes to select the expected +// set of cc1 options for any combination of floating-point options. +// This is based on the assumption that the order of the flags when rendered +// is stable, so the negative checks only need to appear where the option would +// appear if used. + +// start marker +// CHECK: "-cc1" + +// NO-NINF-NOT: "-menable-no-infs" +// NINF-SAME: "-menable-no-infs" + +// NO-NNAN-NOT: "-menable-no-nans" +// NNAN-SAME: "-menable-no-nans" + +// NO-AFN-NOT: "-fapprox-func" +// AFN-SAME: "-fapprox-func" + +// NO-ERRNO-NOT: "-fmath-errno" +// ERRNO-SAME: "-fmath-errno" + +// NO-UNSAFE-NOT: "-funsafe-math-optimizations" +// UNSAFE-SAME: "-funsafe-math-optimizations" + +// NO-NSZ-NOT: "-fno-signed-zeros" +// NSZ-SAME: "-fno-signed-zeros" + +// NO-REASSOC-NOT: "-mreassociate" +// REASSOC-SAME: "-mreassociate" + +// NO-ARCP-NOT: "-freciprocal-math" +// ARCP-SAME: "-freciprocal-math" + +// NO-DENORM-NOT: "-fdenormal-fp-math" +// DENORM-IEEE-SAME: "-fdenormal-fp-math=ieee,ieee" +// DENORM-PS-SAME: "-fdenormal-fp-math=preserve-sign,preserve-sign" +// DENORM-PZ-SAME: "-fdenormal-fp-math=positive-zero,positive-zero" + +// NO-CONTRACT-NOT: "-ffp-contract" +// CONTRACT-OFF-SAME: "-ffp-contract=off" +// CONTRACT-ON-SAME: "-ffp-contract=on" +// CONTRACT-FAST-SAME: "-ffp-contract=fast" + +// This one is odd because -frounding-math is the default +// NO-NOROUNDING-NOT: "-fno-rounding-math" +// NOROUNDING-SAME: "-fno-rounding-math" + +// NO-TRAPPING-NOT: "-ffp-exception-behavior=strict" +// NO-TRAPPING-NOT: "-ffp-exception-behavior=maytrap" +// TRAPPING-SAME: "-ffp-exception-behavior=strict" + +// NO-FAST-NOT: "-ffast-math" +// FAST-SAME: "-ffast-math" + +// NO-FINITE-ONLY-NOT: "-ffinite-math-only" +// FINITE-ONLY-SAME: "-ffinite-math-only" + +// NO-CX-RANGE-NOT: "-complex-range" +// CX-RANGE-FULL-SAME: "-complex-range=full" +// CX-RANGE-PROMO-SAME: "-complex-range=promoted" +// CX-RANGE-IMPRO-SAME: "-complex-range=improved" +// CX-RANGE-BASIC-SAME: "-complex-range=basic" -// CHECK-NO-REASSOC-NO-UNSAFE-MATH: "-cc1" -// CHECK-NO-REASSOC-NO_UNSAFE-MATH-NOT: "-funsafe-math-optimizations" -// CHECK-NO-REASSOC-NO_UNSAFE-MATH-NOT: "-mreassociate" -// CHECK-NO-REASSOC-NO_UNSAFE-MATH-NOT: "-funsafe-math-optimizations" -// CHECK-NO-REASSOC-NO-UNSAFE-MATH: "-o" +// end marker +// CHECK-SAME: "-o" // This isn't fast-math, but the option is handled in the same place as other FP params. diff --git a/clang/test/Driver/integrated-as.c b/clang/test/Driver/integrated-as.c index e78fde873cf47f3d535c2b9d7faadefc008991f6..b0a26f6011b0c781b48a48427d903db9cb8d866b 100644 --- a/clang/test/Driver/integrated-as.c +++ b/clang/test/Driver/integrated-as.c @@ -3,7 +3,7 @@ // RUN: %clang -### -c -save-temps -integrated-as --target=x86_64 %s 2>&1 | FileCheck %s // CHECK: cc1as -// CHECK: -mrelax-all +// CHECK-NOT: -mrelax-all // RISC-V does not enable -mrelax-all // RUN: %clang -### -c -save-temps -integrated-as --target=riscv64 %s 2>&1 | FileCheck %s -check-prefix=RISCV-RELAX diff --git a/clang/test/Driver/linux-ld.c b/clang/test/Driver/linux-ld.c index d918f4f2d7dbd98f2f5b7b9d19818202d66365c7..958e682b6c3c11026c9d1bd7f514098ac01adbb2 100644 --- a/clang/test/Driver/linux-ld.c +++ b/clang/test/Driver/linux-ld.c @@ -1446,6 +1446,32 @@ // RUN: %clang --target=i386-unknown-linux -no-pie -### %s -ffast-math \ // RUN: --sysroot=%S/Inputs/basic_linux_tree 2>&1 \ // RUN: | FileCheck --check-prefix=CHECK-NOCRTFASTMATH %s +// Don't link crtfastmath.o with -shared +// RUN: %clang --target=x86_64-unknown-linux -no-pie -### %s -ffast-math -shared \ +// RUN: --sysroot=%S/Inputs/basic_linux_tree 2>&1 \ +// RUN: | FileCheck --check-prefix=CHECK-NOCRTFASTMATH %s +// RUN: %clang --target=x86_64-unknown-linux -no-pie -### %s -Ofast -shared \ +// RUN: --sysroot=%S/Inputs/basic_linux_tree 2>&1 \ +// RUN: | FileCheck --check-prefix=CHECK-NOCRTFASTMATH %s +// Check for effects of -mdaz-ftz +// RUN: %clang --target=x86_64-unknown-linux -### %s -ffast-math -shared -mdaz-ftz \ +// RUN: --sysroot=%S/Inputs/basic_linux_tree 2>&1 \ +// RUN: | FileCheck --check-prefix=CHECK-CRTFASTMATH %s +// RUN: %clang --target=x86_64-unknown-linux -no-pie -### %s -ffast-math -mdaz-ftz \ +// RUN: --sysroot=%S/Inputs/basic_linux_tree 2>&1 \ +// RUN: | FileCheck --check-prefix=CHECK-CRTFASTMATH %s +// RUN: %clang --target=x86_64-unknown-linux -no-pie -### %s -mdaz-ftz \ +// RUN: --sysroot=%S/Inputs/basic_linux_tree 2>&1 \ +// RUN: | FileCheck --check-prefix=CHECK-CRTFASTMATH %s +// RUN: %clang --target=x86_64-unknown-linux -### %s -ffast-math -shared -mno-daz-ftz \ +// RUN: --sysroot=%S/Inputs/basic_linux_tree 2>&1 \ +// RUN: | FileCheck --check-prefix=CHECK-NOCRTFASTMATH %s +// RUN: %clang --target=x86_64-unknown-linux -no-pie -### %s -ffast-math -mno-daz-ftz \ +// RUN: --sysroot=%S/Inputs/basic_linux_tree 2>&1 \ +// RUN: | FileCheck --check-prefix=CHECK-NOCRTFASTMATH %s +// RUN: %clang --target=x86_64-unknown-linux -no-pie -### %s -mno-daz-ftz \ +// RUN: --sysroot=%S/Inputs/basic_linux_tree 2>&1 \ +// RUN: | FileCheck --check-prefix=CHECK-NOCRTFASTMATH %s // CHECK-CRTFASTMATH: usr/lib/gcc/x86_64-unknown-linux/10.2.0{{/|\\\\}}crtfastmath.o // CHECK-NOCRTFASTMATH-NOT: crtfastmath.o diff --git a/clang/test/Driver/sanitizer-ld.c b/clang/test/Driver/sanitizer-ld.c index f5657e47626e1dc90dab11e76077c50e9538024d..7289d09697b4d09611c5a5c729e8c1390e2f58ff 100644 --- a/clang/test/Driver/sanitizer-ld.c +++ b/clang/test/Driver/sanitizer-ld.c @@ -802,10 +802,24 @@ // RUN: --target=i686-pc-windows \ // RUN: --sysroot=%S/Inputs/basic_linux_tree \ // RUN: | FileCheck --check-prefix=CHECK-CFI-STATS-WIN32 %s +// RUN: not %clang -fsanitize=cfi -fsanitize-stats -### %s 2>&1 \ +// RUN: --target=i686-pc-windows \ +// RUN: -fno-rtlib-defaultlib \ +// RUN: -frtlib-defaultlib \ +// RUN: --sysroot=%S/Inputs/basic_linux_tree \ +// RUN: | FileCheck --check-prefix=CHECK-CFI-STATS-WIN32 %s // CHECK-CFI-STATS-WIN32: "--dependent-lib=clang_rt.stats_client{{(-i386)?}}.lib" // CHECK-CFI-STATS-WIN32: "--dependent-lib=clang_rt.stats{{(-i386)?}}.lib" // CHECK-CFI-STATS-WIN32: "--linker-option=/include:___sanitizer_stats_register" +// RUN: not %clang -fsanitize=cfi -fsanitize-stats -### %s 2>&1 \ +// RUN: --target=i686-pc-windows \ +// RUN: -fno-rtlib-defaultlib \ +// RUN: --sysroot=%S/Inputs/basic_linux_tree \ +// RUN: | FileCheck --check-prefix=CHECK-CFI-STATS-WIN32-NODEF %s +// CHECK-CFI-STATS-WIN32-NODEF-NOT: "--dependent-lib=clang_rt.stats_client{{(-i386)?}}.lib" +// CHECK-CFI-STATS-WIN32-NODEF-NOT: "--dependent-lib=clang_rt.stats{{(-i386)?}}.lib" + // RUN: %clang -### %s 2>&1 \ // RUN: --target=arm-linux-androideabi -fuse-ld=ld -fsanitize=safe-stack \ // RUN: --sysroot=%S/Inputs/basic_android_tree \ diff --git a/clang/test/ExtractAPI/anonymous_record_no_typedef.c b/clang/test/ExtractAPI/anonymous_record_no_typedef.c index 049e8b1f85bb96afab5ab352110068667faa8367..71e460afb1283327ff18a42e893059dc2c08ea91 100644 --- a/clang/test/ExtractAPI/anonymous_record_no_typedef.c +++ b/clang/test/ExtractAPI/anonymous_record_no_typedef.c @@ -1,417 +1,182 @@ -// XFAIL: * // RUN: rm -rf %t -// RUN: split-file %s %t -// RUN: sed -e "s@INPUT_DIR@%{/t:regex_replacement}@g" \ -// RUN: %t/reference.output.json.in >> %t/reference.output.json -// RUN: %clang_cc1 -extract-api --pretty-sgf -triple arm64-apple-macosx \ -// RUN: -x c-header %t/input.h -o %t/output.json -verify +// RUN: %clang_cc1 -extract-api --pretty-sgf --emit-sgf-symbol-labels-for-testing \ +// RUN: -triple arm64-apple-macosx -isystem %S -fretain-comments-from-system-headers \ +// RUN: -x c-header %s -o %t/output.symbols.json -verify -// Generator version is not consistent across test runs, normalize it. -// RUN: sed -e "s@\"generator\": \".*\"@\"generator\": \"?\"@g" \ -// RUN: %t/output.json >> %t/output-normalized.json -// RUN: diff %t/reference.output.json %t/output-normalized.json +// RUN: FileCheck %s --input-file %t/output.symbols.json --check-prefix GLOBAL +// RUN: FileCheck %s --input-file %t/output.symbols.json --check-prefix PREFIX +// RUN: FileCheck %s --input-file %t/output.symbols.json --check-prefix CONTENT +/// A global variable with an anonymous struct type. +struct { char *prefix; char *content; } global; +// GLOBAL-LABEL: "!testLabel": "c:@global" +// GLOBAL: "declarationFragments": [ +// GLOBAL-NEXT: { +// GLOBAL-NEXT: "kind": "keyword", +// GLOBAL-NEXT: "spelling": "struct" +// GLOBAL-NEXT: }, +// GLOBAL-NEXT: { +// GLOBAL-NEXT: "kind": "text", +// GLOBAL-NEXT: "spelling": " { ... } " +// GLOBAL-NEXT: }, +// GLOBAL-NEXT: { +// GLOBAL-NEXT: "kind": "identifier", +// GLOBAL-NEXT: "spelling": "global" +// GLOBAL-NEXT: }, +// GLOBAL-NEXT: { +// GLOBAL-NEXT: "kind": "text", +// GLOBAL-NEXT: "spelling": ";" +// GLOBAL-NEXT: } +// GLOBAL-NEXT: ], +// GLOBAL: "text": "A global variable with an anonymous struct type." +// GLOBAL: "kind": { +// GLOBAL-NEXT: "displayName": "Global Variable", +// GLOBAL-NEXT: "identifier": "c.var" +// GLOBAL: "title": "global" +// GLOBAL: "pathComponents": [ +// GLOBAL-NEXT: "global" +// GLOBAL-NEXT:] + +// PREFIX: "!testRelLabel": "memberOf $ c:@S@anonymous_record_no_typedef.c@{{[0-9]+}}@FI@prefix $ c:@global" +// PREFIX-LABEL: "!testLabel": "c:@S@anonymous_record_no_typedef.c@{{[0-9]+}}@FI@prefix" +// PREFIX: "title": "prefix" +// PREFIX: "pathComponents": [ +// PREFIX-NEXT: "global", +// PREFIX-NEXT: "prefix" +// PREFIX-NEXT: ] + +// CONTENT: "!testRelLabel": "memberOf $ c:@S@anonymous_record_no_typedef.c@{{[0-9]+}}@FI@content $ c:@global" +// CONTENT-LABEL: "!testLabel": "c:@S@anonymous_record_no_typedef.c@{{[0-9]+}}@FI@content" +// CONTENT: "title": "content" +// CONTENT: "pathComponents": [ +// CONTENT-NEXT: "global", +// CONTENT-NEXT: "content" +// CONTENT-NEXT: ] -//--- input.h /// A Vehicle struct Vehicle { + // RUN: FileCheck %s --input-file %t/output.symbols.json --check-prefix TYPE + // RUN: FileCheck %s --input-file %t/output.symbols.json --check-prefix BICYCLE + // RUN: FileCheck %s --input-file %t/output.symbols.json --check-prefix CAR /// The type of vehicle. enum { Bicycle, Car } type; + // TYPE-LABEL: "!testLabel": "c:@S@Vehicle@FI@type" + // TYPE: "declarationFragments": [ + // TYPE-NEXT: { + // TYPE-NEXT: "kind": "keyword", + // TYPE-NEXT: "spelling": "enum" + // TYPE-NEXT: }, + // TYPE-NEXT: { + // TYPE-NEXT: "kind": "text", + // TYPE-NEXT: "spelling": " { ... } " + // TYPE-NEXT: }, + // TYPE-NEXT: { + // TYPE-NEXT: "kind": "identifier", + // TYPE-NEXT: "spelling": "type" + // TYPE-NEXT: }, + // TYPE-NEXT: { + // TYPE-NEXT: "kind": "text", + // TYPE-NEXT: "spelling": ";" + // TYPE-NEXT: } + // TYPE-NEXT: ], + // TYPE: "text": "The type of vehicle." + // TYPE: "title": "type" + + // BICYCLE: "!testRelLabel": "memberOf $ c:@S@Vehicle@E@anonymous_record_no_typedef.c@{{[0-9]+}}@Bicycle $ c:@S@Vehicle@FI@type" + // BICYCLE-LABEL: "!testLabel": "c:@S@Vehicle@E@anonymous_record_no_typedef.c@{{[0-9]+}}@Bicycle" + // BICYCLE: "title": "Bicycle" + // BICYCLE: "pathComponents": [ + // BICYCLE-NEXT: "Vehicle", + // BICYCLE-NEXT: "type", + // BICYCLE-NEXT: "Bicycle" + // BICYCLE-NEXT: ] + // CAR: "!testRelLabel": "memberOf $ c:@S@Vehicle@E@anonymous_record_no_typedef.c@{{[0-9]+}}@Car $ c:@S@Vehicle@FI@type" + // CAR-LABEL: "!testLabel": "c:@S@Vehicle@E@anonymous_record_no_typedef.c@{{[0-9]+}}@Car" + // CAR: "title": "Car" + // CAR: "pathComponents": [ + // CAR-NEXT: "Vehicle", + // CAR-NEXT: "type", + // CAR-NEXT: "Car" + // CAR-NEXT: ] + + // RUN: FileCheck %s --input-file %t/output.symbols.json --check-prefix INFORMATION + // RUN: FileCheck %s --input-file %t/output.symbols.json --check-prefix WHEELS + // RUN: FileCheck %s --input-file %t/output.symbols.json --check-prefix NAME /// The information about the vehicle. - struct { + union { int wheels; char *name; } information; + // INFORMATION-LABEL: "!testLabel": "c:@S@Vehicle@FI@information" + // INFORMATION: "declarationFragments": [ + // INFORMATION-NEXT: { + // INFORMATION-NEXT: "kind": "keyword", + // INFORMATION-NEXT: "spelling": "union" + // INFORMATION-NEXT: }, + // INFORMATION-NEXT: { + // INFORMATION-NEXT: "kind": "text", + // INFORMATION-NEXT: "spelling": " { ... } " + // INFORMATION-NEXT: }, + // INFORMATION-NEXT: { + // INFORMATION-NEXT: "kind": "identifier", + // INFORMATION-NEXT: "spelling": "information" + // INFORMATION-NEXT: }, + // INFORMATION-NEXT: { + // INFORMATION-NEXT: "kind": "text", + // INFORMATION-NEXT: "spelling": ";" + // INFORMATION-NEXT: } + // INFORMATION-NEXT: ], + // INFORMATION: "text": "The information about the vehicle." + // INFORMATION: "title": "information" + + // WHEELS: "!testRelLabel": "memberOf $ c:@S@Vehicle@U@anonymous_record_no_typedef.c@{{[0-9]+}}@FI@wheels $ c:@S@Vehicle@FI@information" + // WHEELS-LABEL: "!testLabel": "c:@S@Vehicle@U@anonymous_record_no_typedef.c@{{[0-9]+}}@FI@wheels" + // WHEELS: "title": "wheels" + // WHEELS: "pathComponents": [ + // WHEELS-NEXT: "Vehicle", + // WHEELS-NEXT: "information", + // WHEELS-NEXT: "wheels" + // WHEELS-NEXT: ] + + // NAME: "!testRelLabel": "memberOf $ c:@S@Vehicle@U@anonymous_record_no_typedef.c@{{[0-9]+}}@FI@name $ c:@S@Vehicle@FI@information" + // NAME-LABEL: "!testLabel": "c:@S@Vehicle@U@anonymous_record_no_typedef.c@{{[0-9]+}}@FI@name" + // NAME: "title": "name" + // NAME: "pathComponents": [ + // NAME-NEXT: "Vehicle", + // NAME-NEXT: "information", + // NAME-NEXT: "name" + // NAME-NEXT: ] }; -// expected-no-diagnostics -//--- reference.output.json.in -{ - "metadata": { - "formatVersion": { - "major": 0, - "minor": 5, - "patch": 3 - }, - "generator": "?" - }, - "module": { - "name": "", - "platform": { - "architecture": "arm64", - "operatingSystem": { - "minimumVersion": { - "major": 11, - "minor": 0, - "patch": 0 - }, - "name": "macosx" - }, - "vendor": "apple" - } - }, - "relationships": [ - { - "kind": "memberOf", - "source": "c:@S@Vehicle@E@input.h@64@Bicycle", - "target": "c:@S@Vehicle@E@input.h@64", - "targetFallback": "Vehicle::enum (unnamed)" - }, - { - "kind": "memberOf", - "source": "c:@S@Vehicle@E@input.h@64@Car", - "target": "c:@S@Vehicle@E@input.h@64", - "targetFallback": "Vehicle::enum (unnamed)" - }, - { - "kind": "memberOf", - "source": "c:@S@Vehicle@FI@type", - "target": "c:@S@Vehicle", - "targetFallback": "Vehicle" - }, - { - "kind": "memberOf", - "source": "c:@S@Vehicle@FI@information", - "target": "c:@S@Vehicle", - "targetFallback": "Vehicle" - } - ], - "symbols": [ - { - "accessLevel": "public", - "declarationFragments": [ - { - "kind": "keyword", - "spelling": "enum" - }, - { - "kind": "text", - "spelling": ": " - }, - { - "kind": "typeIdentifier", - "preciseIdentifier": "c:i", - "spelling": "unsigned int" - }, - { - "kind": "text", - "spelling": ";" - } - ], - "docComment": { - "lines": [ - { - "range": { - "end": { - "character": 28, - "line": 2 - }, - "start": { - "character": 8, - "line": 2 - } - }, - "text": "The type of vehicle." - } - ] - }, - "identifier": { - "interfaceLanguage": "c", - "precise": "c:@S@Vehicle@E@input.h@64" - }, - "kind": { - "displayName": "Enumeration", - "identifier": "c.enum" - }, - "location": { - "position": { - "character": 4, - "line": 3 - }, - "uri": "file://INPUT_DIR/input.h" - }, - "names": { - "navigator": [ - { - "kind": "identifier", - "spelling": "Vehicle::enum (unnamed)" - } - ], - "title": "Vehicle::enum (unnamed)" - }, - "pathComponents": [ - "Vehicle::enum (unnamed)" - ] - }, - { - "accessLevel": "public", - "declarationFragments": [ - { - "kind": "identifier", - "spelling": "Bicycle" - } - ], - "identifier": { - "interfaceLanguage": "c", - "precise": "c:@S@Vehicle@E@input.h@64@Bicycle" - }, - "kind": { - "displayName": "Enumeration Case", - "identifier": "c.enum.case" - }, - "location": { - "position": { - "character": 8, - "line": 4 - }, - "uri": "file://INPUT_DIR/input.h" - }, - "names": { - "navigator": [ - { - "kind": "identifier", - "spelling": "Bicycle" - } - ], - "subHeading": [ - { - "kind": "identifier", - "spelling": "Bicycle" - } - ], - "title": "Bicycle" - }, - "pathComponents": [ - "Vehicle::enum (unnamed)", - "Bicycle" - ] - }, - { - "accessLevel": "public", - "declarationFragments": [ - { - "kind": "identifier", - "spelling": "Car" - } - ], - "identifier": { - "interfaceLanguage": "c", - "precise": "c:@S@Vehicle@E@input.h@64@Car" - }, - "kind": { - "displayName": "Enumeration Case", - "identifier": "c.enum.case" - }, - "location": { - "position": { - "character": 8, - "line": 5 - }, - "uri": "file://INPUT_DIR/input.h" - }, - "names": { - "navigator": [ - { - "kind": "identifier", - "spelling": "Car" - } - ], - "subHeading": [ - { - "kind": "identifier", - "spelling": "Car" - } - ], - "title": "Car" - }, - "pathComponents": [ - "Vehicle::enum (unnamed)", - "Car" - ] - }, - { - "accessLevel": "public", - "declarationFragments": [ - { - "kind": "keyword", - "spelling": "struct" - }, - { - "kind": "text", - "spelling": " " - }, - { - "kind": "identifier", - "spelling": "Vehicle" - }, - { - "kind": "text", - "spelling": ";" - } - ], - "docComment": { - "lines": [ - { - "range": { - "end": { - "character": 13, - "line": 0 - }, - "start": { - "character": 4, - "line": 0 - } - }, - "text": "A Vehicle" - } - ] - }, - "identifier": { - "interfaceLanguage": "c", - "precise": "c:@S@Vehicle" - }, - "kind": { - "displayName": "Structure", - "identifier": "c.struct" - }, - "location": { - "position": { - "character": 7, - "line": 1 - }, - "uri": "file://INPUT_DIR/input.h" - }, - "names": { - "navigator": [ - { - "kind": "identifier", - "spelling": "Vehicle" - } - ], - "subHeading": [ - { - "kind": "identifier", - "spelling": "Vehicle" - } - ], - "title": "Vehicle" - }, - "pathComponents": [ - "Vehicle" - ] - }, - { - "accessLevel": "public", - "declarationFragments": [ - { - "kind": "keyword", - "spelling": "enum" - }, - { - "kind": "text", - "spelling": " " - }, - { - "kind": "identifier", - "spelling": "type" - }, - { - "kind": "text", - "spelling": ";" - } - ], - "identifier": { - "interfaceLanguage": "c", - "precise": "c:@S@Vehicle@FI@type" - }, - "kind": { - "displayName": "Instance Property", - "identifier": "c.property" - }, - "location": { - "position": { - "character": 6, - "line": 6 - }, - "uri": "file://INPUT_DIR/input.h" - }, - "names": { - "navigator": [ - { - "kind": "identifier", - "spelling": "type" - } - ], - "subHeading": [ - { - "kind": "identifier", - "spelling": "type" - } - ], - "title": "type" - }, - "pathComponents": [ - "Vehicle", - "type" - ] - }, - { - "accessLevel": "public", - "declarationFragments": [ - { - "kind": "keyword", - "spelling": "struct" - }, - { - "kind": "text", - "spelling": " " - }, - { - "kind": "identifier", - "spelling": "information" - }, - { - "kind": "text", - "spelling": ";" - } - ], - "identifier": { - "interfaceLanguage": "c", - "precise": "c:@S@Vehicle@FI@information" - }, - "kind": { - "displayName": "Instance Property", - "identifier": "c.property" - }, - "location": { - "position": { - "character": 6, - "line": 12 - }, - "uri": "file://INPUT_DIR/input.h" - }, - "names": { - "navigator": [ - { - "kind": "identifier", - "spelling": "information" - } - ], - "subHeading": [ - { - "kind": "identifier", - "spelling": "information" - } - ], - "title": "information" - }, - "pathComponents": [ - "Vehicle", - "information" - ] - } - ] -} +// RUN: FileCheck %s --input-file %t/output.symbols.json --check-prefix GLOBALENUM +enum { + GlobalCase, + GlobalOtherCase +}; +// GLOBALENUM-DAG: "!testRelLabel": "memberOf $ c:@Ea@GlobalCase@GlobalCase $ c:@Ea@GlobalCase" +// GLOBALENUM-DAG: "!testRelLabel": "memberOf $ c:@Ea@GlobalCase@GlobalOtherCase $ c:@Ea@GlobalCase" +// GLOBALENUM-LABEL: "!testLabel": "c:@Ea@GlobalCase" +// GLOBALENUM: "declarationFragments": [ +// GLOBALENUM-NEXT: { +// GLOBALENUM-NEXT: "kind": "keyword", +// GLOBALENUM-NEXT: "spelling": "enum" +// GLOBALENUM-NEXT: }, +// GLOBALENUM-NEXT: { +// GLOBALENUM-NEXT: "kind": "text", +// GLOBALENUM-NEXT: "spelling": " : " +// GLOBALENUM-NEXT: }, +// GLOBALENUM-NEXT: { +// GLOBALENUM-NEXT: "kind": "typeIdentifier", +// GLOBALENUM-NEXT: "preciseIdentifier": "c:i", +// GLOBALENUM-NEXT: "spelling": "unsigned int" +// GLOBALENUM-NEXT: }, +// GLOBALENUM-NEXT: { +// GLOBALENUM-NEXT: "kind": "text", +// GLOBALENUM-NEXT: "spelling": " { ... };" +// GLOBALENUM-NEXT: } +// GLOBALENUM-NEXT: ] + +// expected-no-diagnostics diff --git a/clang/test/ExtractAPI/enum.c b/clang/test/ExtractAPI/enum.c index 1cdf45ca3cdf4ba0d097a736e7477167ff5a3987..67e003834a7d58243236c59554e372e3bb8d4f1c 100644 --- a/clang/test/ExtractAPI/enum.c +++ b/clang/test/ExtractAPI/enum.c @@ -147,7 +147,7 @@ enum { }, { "kind": "text", - "spelling": ": " + "spelling": " : " }, { "kind": "typeIdentifier", @@ -459,7 +459,7 @@ enum { }, { "kind": "text", - "spelling": ": " + "spelling": " : " }, { "kind": "typeIdentifier", @@ -686,7 +686,7 @@ enum { }, { "kind": "text", - "spelling": ": " + "spelling": " : " }, { "kind": "typeIdentifier", @@ -695,7 +695,7 @@ enum { }, { "kind": "text", - "spelling": ";" + "spelling": " { ... };" } ], "identifier": { @@ -778,7 +778,7 @@ enum { }, { "kind": "text", - "spelling": ": " + "spelling": " : " }, { "kind": "typeIdentifier", @@ -787,7 +787,7 @@ enum { }, { "kind": "text", - "spelling": ";" + "spelling": " { ... };" } ], "identifier": { diff --git a/clang/test/ExtractAPI/function_noexcepts.cpp b/clang/test/ExtractAPI/function_noexcepts.cpp index d95eaaa7e769a5a226ef30ca18680be655475f33..fc18ecb04fefd012b3c8e85c9229660040c2cdad 100644 --- a/clang/test/ExtractAPI/function_noexcepts.cpp +++ b/clang/test/ExtractAPI/function_noexcepts.cpp @@ -63,11 +63,7 @@ void getFooBar() noexcept(false); }, { "kind": "text", - "spelling": "()" - }, - { - "kind": "text", - "spelling": " " + "spelling": "() " }, { "kind": "keyword", @@ -139,11 +135,7 @@ void getFooBar() noexcept(false); }, { "kind": "text", - "spelling": "()" - }, - { - "kind": "text", - "spelling": " " + "spelling": "() " }, { "kind": "keyword", @@ -223,11 +215,7 @@ void getFooBar() noexcept(false); }, { "kind": "text", - "spelling": "()" - }, - { - "kind": "text", - "spelling": " " + "spelling": "() " }, { "kind": "keyword", diff --git a/clang/test/ExtractAPI/methods.cpp b/clang/test/ExtractAPI/methods.cpp index 412c0bb3f903c3d51db897a4f566941dd0fa1a2c..67f04b4d33db833aa883d070c8bf018baa0f5131 100644 --- a/clang/test/ExtractAPI/methods.cpp +++ b/clang/test/ExtractAPI/methods.cpp @@ -81,11 +81,7 @@ class Foo { // SETL-NEXT: }, // SETL-NEXT: { // SETL-NEXT: "kind": "text", - // SETL-NEXT: "spelling": ")" - // SETL-NEXT: }, - // SETL-NEXT: { - // SETL-NEXT: "kind": "text", - // SETL-NEXT: "spelling": " " + // SETL-NEXT: "spelling": ") " // SETL-NEXT: }, // SETL-NEXT: { // SETL-NEXT: "kind": "keyword", diff --git a/clang/test/ExtractAPI/objc_block.m b/clang/test/ExtractAPI/objc_block.m index 4a4335ec09832d65f80fb891bce9529590e8371d..4761a864f5349f5d03ba947be8ac66814fca5d51 100644 --- a/clang/test/ExtractAPI/objc_block.m +++ b/clang/test/ExtractAPI/objc_block.m @@ -35,11 +35,7 @@ // NOPARAM-NEXT: }, // NOPARAM-NEXT: { // NOPARAM-NEXT: "kind": "text", -// NOPARAM-NEXT: "spelling": " (^" -// NOPARAM-NEXT: }, -// NOPARAM-NEXT: { -// NOPARAM-NEXT: "kind": "text", -// NOPARAM-NEXT: "spelling": ")()) " +// NOPARAM-NEXT: "spelling": " (^)()) " // NOPARAM-NEXT: }, // NOPARAM-NEXT: { // NOPARAM-NEXT: "kind": "internalParam", @@ -65,11 +61,7 @@ // NOPARAM-NEXT: }, // NOPARAM-NEXT: { // NOPARAM-NEXT: "kind": "text", -// NOPARAM-NEXT: "spelling": " (^" -// NOPARAM-NEXT: }, -// NOPARAM-NEXT: { -// NOPARAM-NEXT: "kind": "text", -// NOPARAM-NEXT: "spelling": ")()) " +// NOPARAM-NEXT: "spelling": " (^)()) " // NOPARAM-NEXT: }, // NOPARAM-NEXT: { // NOPARAM-NEXT: "kind": "internalParam", @@ -120,11 +112,7 @@ // PARAM-NEXT: }, // PARAM-NEXT: { // PARAM-NEXT: "kind": "text", -// PARAM-NEXT: "spelling": " (^" -// PARAM-NEXT: }, -// PARAM-NEXT: { -// PARAM-NEXT: "kind": "text", -// PARAM-NEXT: "spelling": ")(" +// PARAM-NEXT: "spelling": " (^)(" // PARAM-NEXT: }, // PARAM-NEXT: { // PARAM-NEXT: "kind": "typeIdentifier", @@ -167,11 +155,7 @@ // PARAM-NEXT: }, // PARAM-NEXT: { // PARAM-NEXT: "kind": "text", -// PARAM-NEXT: "spelling": " (^" -// PARAM-NEXT: }, -// PARAM-NEXT: { -// PARAM-NEXT: "kind": "text", -// PARAM-NEXT: "spelling": ")(" +// PARAM-NEXT: "spelling": " (^)(" // PARAM-NEXT: }, // PARAM-NEXT: { // PARAM-NEXT: "kind": "typeIdentifier", @@ -239,11 +223,7 @@ // MULTIPARAM-NEXT: }, // MULTIPARAM-NEXT: { // MULTIPARAM-NEXT: "kind": "text", -// MULTIPARAM-NEXT: "spelling": " (^" -// MULTIPARAM-NEXT: }, -// MULTIPARAM-NEXT: { -// MULTIPARAM-NEXT: "kind": "text", -// MULTIPARAM-NEXT: "spelling": ")(" +// MULTIPARAM-NEXT: "spelling": " (^)(" // MULTIPARAM-NEXT: }, // MULTIPARAM-NEXT: { // MULTIPARAM-NEXT: "kind": "typeIdentifier", @@ -303,11 +283,7 @@ // MULTIPARAM-NEXT: }, // MULTIPARAM-NEXT: { // MULTIPARAM-NEXT: "kind": "text", -// MULTIPARAM-NEXT: "spelling": " (^" -// MULTIPARAM-NEXT: }, -// MULTIPARAM-NEXT: { -// MULTIPARAM-NEXT: "kind": "text", -// MULTIPARAM-NEXT: "spelling": ")(" +// MULTIPARAM-NEXT: "spelling": " (^)(" // MULTIPARAM-NEXT: }, // MULTIPARAM-NEXT: { // MULTIPARAM-NEXT: "kind": "typeIdentifier", @@ -392,11 +368,7 @@ // VARIADIC-NEXT: }, // VARIADIC-NEXT: { // VARIADIC-NEXT: "kind": "text", -// VARIADIC-NEXT: "spelling": " (^" -// VARIADIC-NEXT: }, -// VARIADIC-NEXT: { -// VARIADIC-NEXT: "kind": "text", -// VARIADIC-NEXT: "spelling": ")(" +// VARIADIC-NEXT: "spelling": " (^)(" // VARIADIC-NEXT: }, // VARIADIC-NEXT: { // VARIADIC-NEXT: "kind": "typeIdentifier", @@ -439,11 +411,7 @@ // VARIADIC-NEXT: }, // VARIADIC-NEXT: { // VARIADIC-NEXT: "kind": "text", -// VARIADIC-NEXT: "spelling": " (^" -// VARIADIC-NEXT: }, -// VARIADIC-NEXT: { -// VARIADIC-NEXT: "kind": "text", -// VARIADIC-NEXT: "spelling": ")(" +// VARIADIC-NEXT: "spelling": " (^)(" // VARIADIC-NEXT: }, // VARIADIC-NEXT: { // VARIADIC-NEXT: "kind": "typeIdentifier", diff --git a/clang/test/ExtractAPI/typedef_anonymous_record.c b/clang/test/ExtractAPI/typedef_anonymous_record.c index 9e00ff752546546eacfc700090382dd0c260810a..9c03e9e190ed6bb15f986203d60fb48a9d1e6761 100644 --- a/clang/test/ExtractAPI/typedef_anonymous_record.c +++ b/clang/test/ExtractAPI/typedef_anonymous_record.c @@ -21,7 +21,7 @@ typedef struct { } MyStruct; // MYSTRUCT-NEXT: }, // MYSTRUCT-NEXT: { // MYSTRUCT-NEXT: "kind": "text", -// MYSTRUCT-NEXT: "spelling": " " +// MYSTRUCT-NEXT: "spelling": " { ... } " // MYSTRUCT-NEXT: }, // MYSTRUCT-NEXT: { // MYSTRUCT-NEXT: "kind": "identifier", @@ -97,7 +97,7 @@ typedef enum { Case } MyEnum; // MYENUM-NEXT: }, // MYENUM-NEXT: { // MYENUM-NEXT: "kind": "text", -// MYENUM-NEXT: "spelling": " " +// MYENUM-NEXT: "spelling": " { ... } " // MYENUM-NEXT: }, // MYENUM-NEXT: { // MYENUM-NEXT: "kind": "identifier", diff --git a/clang/test/ExtractAPI/typedef_struct_enum.c b/clang/test/ExtractAPI/typedef_struct_enum.c index fb6fbe987624f8681a20dd6abf00ae8022ce9fb5..64b7186756660fba7e1e42f9759d7dc675d2af13 100644 --- a/clang/test/ExtractAPI/typedef_struct_enum.c +++ b/clang/test/ExtractAPI/typedef_struct_enum.c @@ -72,7 +72,7 @@ typedef enum Test2 { // TEST2-NEXT: }, // TEST2-NEXT: { // TEST2-NEXT: "kind": "text", -// TEST2-NEXT: "spelling": ": " +// TEST2-NEXT: "spelling": " : " // TEST2-NEXT: }, // TEST2-NEXT: { // TEST2-NEXT: "kind": "typeIdentifier", diff --git a/clang/test/Frontend/ast-dump-on-llvm.ll b/clang/test/Frontend/ast-dump-on-llvm.ll new file mode 100644 index 0000000000000000000000000000000000000000..cdacfde4ba848ce36175f0fe27169d64660e7044 --- /dev/null +++ b/clang/test/Frontend/ast-dump-on-llvm.ll @@ -0,0 +1,29 @@ +; RUN: not %clang_cc1 -triple x86_64-unknown-unknown -ast-dump %s -o - 2>&1 | FileCheck %s --check-prefix=CHECK-AST-DUMP +; RUN: not %clang_cc1 -triple x86_64-unknown-unknown -ast-dump=json %s -o - 2>&1 | FileCheck %s --check-prefix=CHECK-AST-DUMP-EQ-JSON +; RUN: not %clang_cc1 -triple x86_64-unknown-unknown -ast-dump=default %s -o - 2>&1 | FileCheck %s --check-prefix=CHECK-AST-DUMP-EQ-DEFAULT +; RUN: not %clang_cc1 -triple x86_64-unknown-unknown -ast-dump-all %s -o - 2>&1 | FileCheck %s --check-prefix=CHECK-AST-DUMP-ALL +; RUN: not %clang_cc1 -triple x86_64-unknown-unknown -ast-dump-all=json %s -o - 2>&1 | FileCheck %s --check-prefix=CHECK-AST-DUMP-ALL-EQ-JSON +; RUN: not %clang_cc1 -triple x86_64-unknown-unknown -ast-dump-all=default %s -o - 2>&1 | FileCheck %s --check-prefix=CHECK-AST-DUMP-ALL-EQ-DEFAULT + +; RUN: not %clang_cc1 -triple x86_64-unknown-unknown -ast-print %s -o - 2>&1 | FileCheck %s --check-prefix=CHECK-AST-PRINT +; RUN: not %clang_cc1 -triple x86_64-unknown-unknown -ast-view %s -o - 2>&1 | FileCheck %s --check-prefix=CHECK-AST-VIEW +; RUN: not %clang_cc1 -triple x86_64-unknown-unknown -ast-list %s -o - 2>&1 | FileCheck %s --check-prefix=CHECK-AST-LIST +; RUN: not %clang_cc1 -triple x86_64-unknown-unknown -ast-dump-lookups %s -o - 2>&1 | FileCheck %s --check-prefix=CHECK-AST-DUMP-LOOKUP +; RUN: not %clang_cc1 -triple x86_64-unknown-unknown -ast-dump-filter=FunctionDecl %s -o - 2>&1 | FileCheck %s --check-prefix=CHECK-AST-DUMP-FILTER-EQ +; RUN: not %clang_cc1 -triple x86_64-unknown-unknown -ast-dump-decl-types %s -o - 2>&1 | FileCheck %s --check-prefix=CHECK-AST-DUMP-DECL-TYPES +; RUN: not %clang_cc1 -triple x86_64-unknown-unknown -fsyntax-only %s -o - 2>&1 | FileCheck %s --check-prefix=CHECK-SYNTAX-ONLY + + +; CHECK-AST-DUMP: fatal error: cannot apply AST actions to LLVM IR file '{{.*}}' +; CHECK-AST-DUMP-EQ-JSON: fatal error: cannot apply AST actions to LLVM IR file '{{.*}}' +; CHECK-AST-DUMP-EQ-DEFAULT: fatal error: cannot apply AST actions to LLVM IR file '{{.*}}' +; CHECK-AST-DUMP-ALL: fatal error: cannot apply AST actions to LLVM IR file '{{.*}}' +; CHECK-AST-DUMP-ALL-EQ-JSON: fatal error: cannot apply AST actions to LLVM IR file '{{.*}}' +; CHECK-AST-DUMP-ALL-EQ-DEFAULT: fatal error: cannot apply AST actions to LLVM IR file '{{.*}}' +; CHECK-AST-PRINT: fatal error: cannot apply AST actions to LLVM IR file '{{.*}}' +; CHECK-AST-VIEW: fatal error: cannot apply AST actions to LLVM IR file '{{.*}}' +; CHECK-AST-LIST: fatal error: cannot apply AST actions to LLVM IR file '{{.*}}' +; CHECK-AST-DUMP-LOOKUP: fatal error: cannot apply AST actions to LLVM IR file '{{.*}}' +; CHECK-AST-DUMP-FILTER-EQ: fatal error: cannot apply AST actions to LLVM IR file '{{.*}}' +; CHECK-AST-DUMP-DECL-TYPES: fatal error: cannot apply AST actions to LLVM IR file '{{.*}}' +; CHECK-SYNTAX-ONLY: fatal error: cannot apply AST actions to LLVM IR file '{{.*}}' diff --git a/clang/test/Headers/wasm.c b/clang/test/Headers/wasm.c index 57f8b6d0db176a29ac71454b1f0c3e1c41aaf3b1..b22d87a5f8b7005d6732a079a83af93d833889b7 100644 --- a/clang/test/Headers/wasm.c +++ b/clang/test/Headers/wasm.c @@ -1572,7 +1572,7 @@ uint32_t test_i8x16_bitmask(v128_t a) { // CHECK-LABEL: @test_i8x16_popcnt( // CHECK-NEXT: entry: // CHECK-NEXT: [[TMP0:%.*]] = bitcast <4 x i32> [[A:%.*]] to <16 x i8> -// CHECK-NEXT: [[TMP1:%.*]] = tail call <16 x i8> @llvm.ctpop.v16i8(<16 x i8> [[TMP0]]), !range [[RNG5:![0-9]+]] +// CHECK-NEXT: [[TMP1:%.*]] = tail call range(i8 0, 9) <16 x i8> @llvm.ctpop.v16i8(<16 x i8> [[TMP0]]) // CHECK-NEXT: [[TMP2:%.*]] = bitcast <16 x i8> [[TMP1]] to <4 x i32> // CHECK-NEXT: ret <4 x i32> [[TMP2]] // diff --git a/clang/test/Interpreter/fail.cpp b/clang/test/Interpreter/fail.cpp index 4e301f37548f1f993737ab71833f66278efc29ef..633d92794325c2b30f3bf7914abb939dfcd8c70d 100644 --- a/clang/test/Interpreter/fail.cpp +++ b/clang/test/Interpreter/fail.cpp @@ -1,12 +1,19 @@ -// FIXME: There're some inconsistencies between interactive and non-interactive -// modes. For example, when clang-repl runs in the interactive mode, issues an -// error, and then successfully recovers if we decide it's a success then for -// the non-interactive mode the exit code should be a failure. -// RUN: clang-repl "int x = 10;" "int y=7; err;" "int y = 10;" // REQUIRES: host-supports-jit // UNSUPPORTED: system-aix -// RUN: cat %s | not clang-repl | FileCheck %s -BOOM! +// clang-repl can be called from the prompt in non-interactive mode as a +// calculator in shell scripts, for example. In that case if there is an error +// we should set the exit code as failure. +// RUN: not clang-repl "int x = 10;" "int y=7; err;" "int y = 10;" + +// In interactive (REPL) mode, we can have errors but we should exit with +// success because errors in the input code are part of the interactive use. +// RUN: cat %s | clang-repl | FileCheck %s + +// However, interactive mode should fail when we specified -verify and there +// was a diagnostic mismatches. This will make the testsuite fail as intended. +// RUN: cat %s | not clang-repl -Xcc -Xclang -Xcc -verify | FileCheck %s + +BOOM! // expected-error {{intended to fail the -verify test}} extern "C" int printf(const char *, ...); int i = 42; auto r1 = printf("i = %d\n", i); diff --git a/clang/test/Lexer/cxx-features.cpp b/clang/test/Lexer/cxx-features.cpp index baaa9d4434e9b7c3994528b785324a1257125479..738c3196660647dfeaac49379b8037abe06dc15b 100644 --- a/clang/test/Lexer/cxx-features.cpp +++ b/clang/test/Lexer/cxx-features.cpp @@ -1,17 +1,17 @@ // RUN: %clang_cc1 -std=c++98 -fcxx-exceptions -verify %s // RUN: %clang_cc1 -std=c++11 -fcxx-exceptions -verify %s -// RUN: %clang_cc1 -std=c++14 -fcxx-exceptions -fsized-deallocation -verify %s -// RUN: %clang_cc1 -std=c++17 -fcxx-exceptions -fsized-deallocation -verify %s -// RUN: %clang_cc1 -std=c++20 -fcxx-exceptions -fsized-deallocation -verify %s -// RUN: %clang_cc1 -std=c++23 -fcxx-exceptions -fsized-deallocation -verify %s -// RUN: %clang_cc1 -std=c++2c -fcxx-exceptions -fsized-deallocation -verify %s +// RUN: %clang_cc1 -std=c++14 -fcxx-exceptions -verify %s +// RUN: %clang_cc1 -std=c++17 -fcxx-exceptions -verify %s +// RUN: %clang_cc1 -std=c++20 -fcxx-exceptions -verify %s +// RUN: %clang_cc1 -std=c++23 -fcxx-exceptions -verify %s +// RUN: %clang_cc1 -std=c++2c -fcxx-exceptions -verify %s // -// RUN: %clang_cc1 -std=c++17 -fcxx-exceptions -fsized-deallocation -frelaxed-template-template-args -DRELAXED_TEMPLATE_TEMPLATE_ARGS=1 -verify %s -// RUN: %clang_cc1 -std=c++17 -fcxx-exceptions -fsized-deallocation -DCONCEPTS_TS=1 -verify %s -// RUN: %clang_cc1 -std=c++14 -fno-rtti -fno-threadsafe-statics -verify %s -DNO_EXCEPTIONS -DNO_RTTI -DNO_THREADSAFE_STATICS -fsized-deallocation -// RUN: %clang_cc1 -std=c++14 -fchar8_t -DNO_EXCEPTIONS -DCHAR8_T -verify -fsized-deallocation %s -// RUN: %clang_cc1 -std=c++2a -fno-char8_t -DNO_EXCEPTIONS -DNO_CHAR8_T -verify -fsized-deallocation %s +// RUN: %clang_cc1 -std=c++17 -fcxx-exceptions -frelaxed-template-template-args -DRELAXED_TEMPLATE_TEMPLATE_ARGS=1 -verify %s +// RUN: %clang_cc1 -std=c++17 -fcxx-exceptions -DCONCEPTS_TS=1 -verify %s +// RUN: %clang_cc1 -std=c++14 -fno-rtti -fno-threadsafe-statics -verify %s -DNO_EXCEPTIONS -DNO_RTTI -DNO_THREADSAFE_STATICS +// RUN: %clang_cc1 -std=c++14 -fchar8_t -DNO_EXCEPTIONS -DCHAR8_T -verify %s +// RUN: %clang_cc1 -std=c++2a -fno-char8_t -DNO_EXCEPTIONS -DNO_CHAR8_T -verify %s // expected-no-diagnostics diff --git a/clang/test/Misc/target-invalid-cpu-note.c b/clang/test/Misc/target-invalid-cpu-note.c index 9c91c4157cd6a06ba015b4b0a3f4f4414bd4545b..21d80b7134508f74a25235ea1847c5b077615bfe 100644 --- a/clang/test/Misc/target-invalid-cpu-note.c +++ b/clang/test/Misc/target-invalid-cpu-note.c @@ -5,11 +5,11 @@ // RUN: not %clang_cc1 -triple arm64--- -target-cpu not-a-cpu -fsyntax-only %s 2>&1 | FileCheck %s --check-prefix AARCH64 // AARCH64: error: unknown target CPU 'not-a-cpu' -// AARCH64-NEXT: note: valid target CPU values are: cortex-a34, cortex-a35, cortex-a53, cortex-a55, cortex-a510, cortex-a520, cortex-a520ae, cortex-a57, cortex-a65, cortex-a65ae, cortex-a72, cortex-a73, cortex-a75, cortex-a76, cortex-a76ae, cortex-a77, cortex-a78, cortex-a78ae, cortex-a78c, cortex-a710, cortex-a715, cortex-a720, cortex-a720ae, cortex-r82, cortex-x1, cortex-x1c, cortex-x2, cortex-x3, cortex-x4, neoverse-e1, neoverse-n1, neoverse-n2, neoverse-512tvb, neoverse-v1, neoverse-v2, cyclone, apple-a7, apple-a8, apple-a9, apple-a10, apple-a11, apple-a12, apple-a13, apple-a14, apple-a15, apple-a16, apple-a17, apple-m1, apple-m2, apple-m3, apple-s4, apple-s5, exynos-m3, exynos-m4, exynos-m5, falkor, saphira, kryo, thunderx2t99, thunderx3t110, thunderx, thunderxt88, thunderxt81, thunderxt83, tsv110, a64fx, carmel, ampere1, ampere1a, ampere1b, cobalt-100, grace{{$}} +// AARCH64-NEXT: note: valid target CPU values are: cortex-a34, cortex-a35, cortex-a53, cortex-a55, cortex-a510, cortex-a520, cortex-a520ae, cortex-a57, cortex-a65, cortex-a65ae, cortex-a72, cortex-a73, cortex-a75, cortex-a76, cortex-a76ae, cortex-a77, cortex-a78, cortex-a78ae, cortex-a78c, cortex-a710, cortex-a715, cortex-a720, cortex-a720ae, cortex-r82, cortex-x1, cortex-x1c, cortex-x2, cortex-x3, cortex-x4, neoverse-e1, neoverse-n1, neoverse-n2, neoverse-n3, neoverse-512tvb, neoverse-v1, neoverse-v2, neoverse-v3, neoverse-v3ae, cyclone, apple-a7, apple-a8, apple-a9, apple-a10, apple-a11, apple-a12, apple-a13, apple-a14, apple-a15, apple-a16, apple-a17, apple-m1, apple-m2, apple-m3, apple-s4, apple-s5, exynos-m3, exynos-m4, exynos-m5, falkor, saphira, kryo, thunderx2t99, thunderx3t110, thunderx, thunderxt88, thunderxt81, thunderxt83, tsv110, a64fx, carmel, ampere1, ampere1a, ampere1b, cobalt-100, grace{{$}} // RUN: not %clang_cc1 -triple arm64--- -tune-cpu not-a-cpu -fsyntax-only %s 2>&1 | FileCheck %s --check-prefix TUNE_AARCH64 // TUNE_AARCH64: error: unknown target CPU 'not-a-cpu' -// TUNE_AARCH64-NEXT: note: valid target CPU values are: cortex-a34, cortex-a35, cortex-a53, cortex-a55, cortex-a510, cortex-a520, cortex-a520ae, cortex-a57, cortex-a65, cortex-a65ae, cortex-a72, cortex-a73, cortex-a75, cortex-a76, cortex-a76ae, cortex-a77, cortex-a78, cortex-a78ae, cortex-a78c, cortex-a710, cortex-a715, cortex-a720, cortex-a720ae, cortex-r82, cortex-x1, cortex-x1c, cortex-x2, cortex-x3, cortex-x4, neoverse-e1, neoverse-n1, neoverse-n2, neoverse-512tvb, neoverse-v1, neoverse-v2, cyclone, apple-a7, apple-a8, apple-a9, apple-a10, apple-a11, apple-a12, apple-a13, apple-a14, apple-a15, apple-a16, apple-a17, apple-m1, apple-m2, apple-m3, apple-s4, apple-s5, exynos-m3, exynos-m4, exynos-m5, falkor, saphira, kryo, thunderx2t99, thunderx3t110, thunderx, thunderxt88, thunderxt81, thunderxt83, tsv110, a64fx, carmel, ampere1, ampere1a, ampere1b, cobalt-100, grace{{$}} +// TUNE_AARCH64-NEXT: note: valid target CPU values are: cortex-a34, cortex-a35, cortex-a53, cortex-a55, cortex-a510, cortex-a520, cortex-a520ae, cortex-a57, cortex-a65, cortex-a65ae, cortex-a72, cortex-a73, cortex-a75, cortex-a76, cortex-a76ae, cortex-a77, cortex-a78, cortex-a78ae, cortex-a78c, cortex-a710, cortex-a715, cortex-a720, cortex-a720ae, cortex-r82, cortex-x1, cortex-x1c, cortex-x2, cortex-x3, cortex-x4, neoverse-e1, neoverse-n1, neoverse-n2, neoverse-n3, neoverse-512tvb, neoverse-v1, neoverse-v2, neoverse-v3, neoverse-v3ae, cyclone, apple-a7, apple-a8, apple-a9, apple-a10, apple-a11, apple-a12, apple-a13, apple-a14, apple-a15, apple-a16, apple-a17, apple-m1, apple-m2, apple-m3, apple-s4, apple-s5, exynos-m3, exynos-m4, exynos-m5, falkor, saphira, kryo, thunderx2t99, thunderx3t110, thunderx, thunderxt88, thunderxt81, thunderxt83, tsv110, a64fx, carmel, ampere1, ampere1a, ampere1b, cobalt-100, grace{{$}} // RUN: not %clang_cc1 -triple i386--- -target-cpu not-a-cpu -fsyntax-only %s 2>&1 | FileCheck %s --check-prefix X86 // X86: error: unknown target CPU 'not-a-cpu' diff --git a/clang/test/Modules/prune-non-affecting-module-map-files-textual.c b/clang/test/Modules/prune-non-affecting-module-map-files-textual.c new file mode 100644 index 0000000000000000000000000000000000000000..fce325d4774c270647fbd2a2eaf2fff7a15daada --- /dev/null +++ b/clang/test/Modules/prune-non-affecting-module-map-files-textual.c @@ -0,0 +1,46 @@ +// This test checks that a module map with a textual header can be marked as +// non-affecting. + +// RUN: rm -rf %t && mkdir %t +// RUN: split-file %s %t + +//--- X.modulemap +module X { textual header "X.h" } +//--- X.h +typedef int X_int; + +//--- Y.modulemap +module Y { textual header "Y.h" } +//--- Y.h +typedef int Y_int; + +//--- A.modulemap +module A { header "A.h" export * } +//--- A.h +#include "X.h" + +// RUN: %clang_cc1 -fmodules -emit-module %t/A.modulemap -fmodule-name=A -o %t/A0.pcm \ +// RUN: -fmodule-map-file=%t/X.modulemap +// RUN: %clang_cc1 -fsyntax-only -module-file-info %t/A0.pcm | FileCheck %s --check-prefix=A0 --implicit-check-not=Y.modulemap +// A0: Input file: {{.*}}X.modulemap + +// RUN: %clang_cc1 -fmodules -emit-module %t/A.modulemap -fmodule-name=A -o %t/A1.pcm \ +// RUN: -fmodule-map-file=%t/X.modulemap -fmodule-map-file=%t/Y.modulemap +// RUN: %clang_cc1 -fsyntax-only -module-file-info %t/A0.pcm | FileCheck %s --check-prefix=A1 \ +// RUN: --implicit-check-not=Y.modulemap +// A1: Input file: {{.*}}X.modulemap + +// RUN: diff %t/A0.pcm %t/A1.pcm + +//--- B.modulemap +module B { header "B.h" export * } +//--- B.h +#include "A.h" +typedef X_int B_int; + +// RUN: %clang_cc1 -fmodules -emit-module %t/B.modulemap -fmodule-name=B -o %t/B.pcm \ +// RUN: -fmodule-file=A=%t/A0.pcm \ +// RUN: -fmodule-map-file=%t/A.modulemap -fmodule-map-file=%t/X.modulemap -fmodule-map-file=%t/Y.modulemap +// RUN: %clang_cc1 -fsyntax-only -module-file-info %t/B.pcm | FileCheck %s --check-prefix=B \ +// RUN: --implicit-check-not=X.modulemap --implicit-check-not=Y.modulemap +// B: Input file: {{.*}}B.modulemap diff --git a/clang/test/OpenMP/task_depend_messages.cpp b/clang/test/OpenMP/task_depend_messages.cpp index 388595bef4de1be5851f84d626fd2d8910e7d239..3f39c55527b5d482bf086d45d22ba14b0499b80c 100644 --- a/clang/test/OpenMP/task_depend_messages.cpp +++ b/clang/test/OpenMP/task_depend_messages.cpp @@ -62,7 +62,7 @@ int main(int argc, char **argv, char *env[]) { #pragma omp task depend(in : argv[ : argc][1 : argc - 1]) #pragma omp task depend(in : arr[0]) #pragma omp task depend(depobj:argc) // omp45-error {{expected 'in', 'out', 'inout' or 'mutexinoutset' in OpenMP clause 'depend'}} omp50-error {{expected lvalue expression of 'omp_depend_t' type, not 'int'}} omp51-error {{expected lvalue expression of 'omp_depend_t' type, not 'int'}} - #pragma omp task depend(depobj : argv[ : argc][1 : argc - 1]) // omp45-error {{expected 'in', 'out', 'inout' or 'mutexinoutset' in OpenMP clause 'depend'}} omp50-error {{expected lvalue expression of 'omp_depend_t' type, not ''}} omp51-error {{expected lvalue expression of 'omp_depend_t' type, not ''}} + #pragma omp task depend(depobj : argv[ : argc][1 : argc - 1]) // omp45-error {{expected 'in', 'out', 'inout' or 'mutexinoutset' in OpenMP clause 'depend'}} omp50-error {{expected lvalue expression of 'omp_depend_t' type, not ''}} omp51-error {{expected lvalue expression of 'omp_depend_t' type, not ''}} #pragma omp task depend(depobj : arr[0]) // omp45-error {{expected 'in', 'out', 'inout' or 'mutexinoutset' in OpenMP clause 'depend'}} #pragma omp task depend(in : ([ // expected-error {{expected variable name or 'this' in lambda capture list}} expected-error {{expected ')'}} expected-note {{to match this '('}} #pragma omp task depend(in : ([] // expected-error {{expected body of lambda expression}} expected-error {{expected ')'}} expected-note {{to match this '('}} diff --git a/clang/test/PCH/cxx1z-aligned-alloc.cpp b/clang/test/PCH/cxx1z-aligned-alloc.cpp index c1becbde3bf2ce623aa421e4c39da23440e95880..cccd6285978455fa12b9927bb0483b1f61d82918 100644 --- a/clang/test/PCH/cxx1z-aligned-alloc.cpp +++ b/clang/test/PCH/cxx1z-aligned-alloc.cpp @@ -1,12 +1,12 @@ // No PCH: -// RUN: %clang_cc1 -pedantic -fsized-deallocation -std=c++1z -include %s -verify %s +// RUN: %clang_cc1 -pedantic -std=c++1z -include %s -verify %s // // With PCH: -// RUN: %clang_cc1 -pedantic -fsized-deallocation -std=c++1z -emit-pch %s -o %t -// RUN: %clang_cc1 -pedantic -fsized-deallocation -std=c++1z -include-pch %t -verify %s +// RUN: %clang_cc1 -pedantic -std=c++1z -emit-pch %s -o %t +// RUN: %clang_cc1 -pedantic -std=c++1z -include-pch %t -verify %s -// RUN: %clang_cc1 -pedantic -fsized-deallocation -std=c++1z -emit-pch -fpch-instantiate-templates %s -o %t -// RUN: %clang_cc1 -pedantic -fsized-deallocation -std=c++1z -include-pch %t -verify %s +// RUN: %clang_cc1 -pedantic -std=c++1z -emit-pch -fpch-instantiate-templates %s -o %t +// RUN: %clang_cc1 -pedantic -std=c++1z -include-pch %t -verify %s // expected-no-diagnostics diff --git a/clang/test/ParserOpenACC/parse-cache-construct.cpp b/clang/test/ParserOpenACC/parse-cache-construct.cpp index f0a35824696d8c1bffc5be256a5680bf0a24ee5b..f1c71e8b5847866f1ce605e238f01f2c25b2354b 100644 --- a/clang/test/ParserOpenACC/parse-cache-construct.cpp +++ b/clang/test/ParserOpenACC/parse-cache-construct.cpp @@ -72,14 +72,12 @@ void use() { #pragma acc cache(Arrs.MemArr[3].array[1:4]) } for (int i = 0; i < 10; ++i) { - // FIXME: Once we have a new array-section type to represent OpenACC as - // well, change this error message. - // expected-error@+2{{OpenMP array section is not allowed here}} + // expected-error@+2{{OpenACC sub-array is not allowed here}} // expected-warning@+1{{OpenACC construct 'cache' not yet implemented, pragma ignored}} #pragma acc cache(Arrs.MemArr[3:4].array[1:4]) } for (int i = 0; i < 10; ++i) { - // expected-error@+2{{OpenMP array section is not allowed here}} + // expected-error@+2{{OpenACC sub-array is not allowed here}} // expected-warning@+1{{OpenACC construct 'cache' not yet implemented, pragma ignored}} #pragma acc cache(Arrs.MemArr[3:4].array[4]) } diff --git a/clang/test/ParserOpenACC/parse-clauses.c b/clang/test/ParserOpenACC/parse-clauses.c index 799f22b8c120e599c2fdcf775934a2928ec5b264..ee2cb2d1501deae78c840e1b481546be372b3e19 100644 --- a/clang/test/ParserOpenACC/parse-clauses.c +++ b/clang/test/ParserOpenACC/parse-clauses.c @@ -482,13 +482,13 @@ void VarListClauses() { #pragma acc serial copy(HasMem.MemArr[3].array[1:4]), seq for(;;){} - // expected-error@+3{{OpenMP array section is not allowed here}} + // expected-error@+3{{OpenACC sub-array is not allowed here}} // expected-warning@+2{{OpenACC clause 'copy' not yet implemented, clause ignored}} // expected-warning@+1{{OpenACC clause 'seq' not yet implemented, clause ignored}} #pragma acc serial copy(HasMem.MemArr[1:3].array[1]), seq for(;;){} - // expected-error@+3{{OpenMP array section is not allowed here}} + // expected-error@+3{{OpenACC sub-array is not allowed here}} // expected-warning@+2{{OpenACC clause 'copy' not yet implemented, clause ignored}} // expected-warning@+1{{OpenACC clause 'seq' not yet implemented, clause ignored}} #pragma acc serial copy(HasMem.MemArr[1:3].array[1:2]), seq diff --git a/clang/test/Preprocessor/predefined-macros-hlsl.hlsl b/clang/test/Preprocessor/predefined-macros-hlsl.hlsl index 251362cd03c0f81783214190349746dad9d185bf..cc5233fbcb2aca3ea23eac8745cb26bb08754e0e 100644 --- a/clang/test/Preprocessor/predefined-macros-hlsl.hlsl +++ b/clang/test/Preprocessor/predefined-macros-hlsl.hlsl @@ -1,14 +1,19 @@ -// RUN: %clang_cc1 %s -E -dM -o - -triple dxil-pc-shadermodel6.0-amplification | FileCheck -match-full-lines %s --check-prefixes=CHECK,AMPLIFICATION -// RUN: %clang_cc1 %s -E -dM -o - -triple dxil-pc-shadermodel6.0-compute | FileCheck -match-full-lines %s --check-prefixes=CHECK,COMPUTE -// RUN: %clang_cc1 %s -E -dM -o - -triple dxil-pc-shadermodel6.0-domain | FileCheck -match-full-lines %s --check-prefixes=CHECK,DOMAIN -// RUN: %clang_cc1 %s -E -dM -o - -triple dxil-pc-shadermodel6.0-geometry | FileCheck -match-full-lines %s --check-prefixes=CHECK,GEOMETRY -// RUN: %clang_cc1 %s -E -dM -o - -triple dxil-pc-shadermodel6.0-hull | FileCheck -match-full-lines %s --check-prefixes=CHECK,HULL -// RUN: %clang_cc1 %s -E -dM -o - -triple dxil-pc-shadermodel6.0-library | FileCheck -match-full-lines %s --check-prefixes=CHECK,LIBRARY -// RUN: %clang_cc1 %s -E -dM -o - -triple dxil-pc-shadermodel6.0-mesh | FileCheck -match-full-lines %s --check-prefixes=CHECK,MESH -// RUN: %clang_cc1 %s -E -dM -o - -triple dxil-pc-shadermodel6.0-pixel | FileCheck -match-full-lines %s --check-prefixes=CHECK,PIXEL -// RUN: %clang_cc1 %s -E -dM -o - -triple dxil-pc-shadermodel6.0-vertex | FileCheck -match-full-lines %s --check-prefixes=CHECK,VERTEX +// RUN: %clang_cc1 %s -E -dM -o - -triple dxil-pc-shadermodel6.0-amplification | FileCheck -match-full-lines %s --check-prefixes=CHECK,AMPLIFICATION,NOHALF +// RUN: %clang_cc1 %s -E -dM -o - -triple dxil-pc-shadermodel6.0-compute | FileCheck -match-full-lines %s --check-prefixes=CHECK,COMPUTE,NOHALF +// RUN: %clang_cc1 %s -E -dM -o - -triple dxil-pc-shadermodel6.0-domain | FileCheck -match-full-lines %s --check-prefixes=CHECK,DOMAIN,NOHALF +// RUN: %clang_cc1 %s -E -dM -o - -triple dxil-pc-shadermodel6.0-geometry | FileCheck -match-full-lines %s --check-prefixes=CHECK,GEOMETRY,NOHALF +// RUN: %clang_cc1 %s -E -dM -o - -triple dxil-pc-shadermodel6.0-hull | FileCheck -match-full-lines %s --check-prefixes=CHECK,HULL,NOHALF +// RUN: %clang_cc1 %s -E -dM -o - -triple dxil-pc-shadermodel6.0-library | FileCheck -match-full-lines %s --check-prefixes=CHECK,LIBRARY,NOHALF +// RUN: %clang_cc1 %s -E -dM -o - -triple dxil-pc-shadermodel6.0-mesh | FileCheck -match-full-lines %s --check-prefixes=CHECK,MESH,NOHALF +// RUN: %clang_cc1 %s -E -dM -o - -triple dxil-pc-shadermodel6.0-pixel | FileCheck -match-full-lines %s --check-prefixes=CHECK,PIXEL,NOHALF +// RUN: %clang_cc1 %s -E -dM -o - -triple dxil-pc-shadermodel6.0-vertex | FileCheck -match-full-lines %s --check-prefixes=CHECK,VERTEX,NOHALF +// RUN: %clang_cc1 %s -E -dM -o - -triple dxil-pc-shadermodel6.3-vertex -fnative-half-type | FileCheck -match-full-lines %s --check-prefixes=CHECK,VERTEX,HALF + +// HALF: #define __HLSL_ENABLE_16_BIT 1 +// NOHALF-NOT: __HLSL_ENABLE_16_BIT // CHECK: #define __HLSL_VERSION 2021 + // CHECK: #define __SHADER_STAGE_AMPLIFICATION 14 // CHECK: #define __SHADER_STAGE_COMPUTE 5 // CHECK: #define __SHADER_STAGE_DOMAIN 4 diff --git a/clang/test/Preprocessor/riscv-target-features.c b/clang/test/Preprocessor/riscv-target-features.c index 646043681fe330cf1f1281214ca22ecf6e0858cb..ee4f81cd654bca2c4690acd936671faf00405189 100644 --- a/clang/test/Preprocessor/riscv-target-features.c +++ b/clang/test/Preprocessor/riscv-target-features.c @@ -174,6 +174,7 @@ // CHECK-NOT: __riscv_ssqosid{{.*$}} // CHECK-NOT: __riscv_supm{{.*$}} // CHECK-NOT: __riscv_zaamo {{.*$}} +// CHECK-NOT: __riscv_zabha {{.*$}} // CHECK-NOT: __riscv_zalasr {{.*$}} // CHECK-NOT: __riscv_zalrsc {{.*$}} // CHECK-NOT: __riscv_zfbfmin {{.*$}} @@ -698,10 +699,10 @@ // CHECK-ZA64RS-EXT: __riscv_za64rs 1000000{{$}} // RUN: %clang --target=riscv32 \ -// RUN: -march=rv32i_zacas1p0 -E -dM %s \ +// RUN: -march=rv32ia_zacas1p0 -E -dM %s \ // RUN: -o - | FileCheck --check-prefix=CHECK-ZACAS-EXT %s // RUN: %clang --target=riscv64 \ -// RUN: -march=rv64i_zacas1p0 -E -dM %s \ +// RUN: -march=rv64ia_zacas1p0 -E -dM %s \ // RUN: -o - | FileCheck --check-prefix=CHECK-ZACAS-EXT %s // CHECK-ZACAS-EXT: __riscv_zacas 1000000{{$}} @@ -1552,6 +1553,14 @@ // RUN: -o - | FileCheck --check-prefix=CHECK-ZAAMO-EXT %s // CHECK-ZAAMO-EXT: __riscv_zaamo 2000{{$}} +// RUN: %clang --target=riscv32 -menable-experimental-extensions \ +// RUN: -march=rv32ia_zabha1p0 -E -dM %s \ +// RUN: -o - | FileCheck --check-prefix=CHECK-ZABHA-EXT %s +// RUN: %clang --target=riscv64 -menable-experimental-extensions \ +// RUN: -march=rv64ia_zabha1p0 -E -dM %s \ +// RUN: -o - | FileCheck --check-prefix=CHECK-ZABHA-EXT %s +// CHECK-ZABHA-EXT: __riscv_zabha 1000000{{$}} + // RUN: %clang --target=riscv32 -menable-experimental-extensions \ // RUN: -march=rv32i_zalasr0p1 -E -dM %s \ // RUN: -o - | FileCheck --check-prefix=CHECK-ZALASR-EXT %s diff --git a/clang/test/Preprocessor/wasm-target-features.c b/clang/test/Preprocessor/wasm-target-features.c index eccd432aa8eee66d12bf146a291bf0f6cd10696c..32e24ad1b71656eca04d6db46b3bc730576a531d 100644 --- a/clang/test/Preprocessor/wasm-target-features.c +++ b/clang/test/Preprocessor/wasm-target-features.c @@ -1,38 +1,29 @@ // RUN: %clang -E -dM %s -o - 2>&1 \ -// RUN: -target wasm32-unknown-unknown -msimd128 \ -// RUN: | FileCheck %s -check-prefix=SIMD128 -// RUN: %clang -E -dM %s -o - 2>&1 \ -// RUN: -target wasm64-unknown-unknown -msimd128 \ -// RUN: | FileCheck %s -check-prefix=SIMD128 -// -// SIMD128:#define __wasm_simd128__ 1{{$}} - -// RUN: %clang -E -dM %s -o - 2>&1 \ -// RUN: -target wasm32-unknown-unknown -mrelaxed-simd \ -// RUN: | FileCheck %s -check-prefix=RELAXED-SIMD +// RUN: -target wasm32-unknown-unknown -matomics \ +// RUN: | FileCheck %s -check-prefix=ATOMICS // RUN: %clang -E -dM %s -o - 2>&1 \ -// RUN: -target wasm64-unknown-unknown -mrelaxed-simd \ -// RUN: | FileCheck %s -check-prefix=RELAXED-SIMD +// RUN: -target wasm64-unknown-unknown -matomics \ +// RUN: | FileCheck %s -check-prefix=ATOMICS // -// RELAXED-SIMD:#define __wasm_relaxed_simd__ 1{{$}} +// ATOMICS: #define __wasm_atomics__ 1{{$}} // RUN: %clang -E -dM %s -o - 2>&1 \ -// RUN: -target wasm32-unknown-unknown -mnontrapping-fptoint \ -// RUN: | FileCheck %s -check-prefix=NONTRAPPING-FPTOINT +// RUN: -target wasm32-unknown-unknown -pthread \ +// RUN: | FileCheck %s -check-prefix=PTHREAD // RUN: %clang -E -dM %s -o - 2>&1 \ -// RUN: -target wasm64-unknown-unknown -mnontrapping-fptoint \ -// RUN: | FileCheck %s -check-prefix=NONTRAPPING-FPTOINT +// RUN: -target wasm64-unknown-unknown -pthread \ +// RUN: | FileCheck %s -check-prefix=PTHREAD // -// NONTRAPPING-FPTOINT:#define __wasm_nontrapping_fptoint__ 1{{$}} +// PTHREAD: #define __wasm_atomics__ 1{{$}} // RUN: %clang -E -dM %s -o - 2>&1 \ -// RUN: -target wasm32-unknown-unknown -msign-ext \ -// RUN: | FileCheck %s -check-prefix=SIGN-EXT +// RUN: -target wasm32-unknown-unknown -mbulk-memory \ +// RUN: | FileCheck %s -check-prefix=BULK-MEMORY // RUN: %clang -E -dM %s -o - 2>&1 \ -// RUN: -target wasm64-unknown-unknown -msign-ext \ -// RUN: | FileCheck %s -check-prefix=SIGN-EXT +// RUN: -target wasm64-unknown-unknown -mbulk-memory \ +// RUN: | FileCheck %s -check-prefix=BULK-MEMORY // -// SIGN-EXT:#define __wasm_sign_ext__ 1{{$}} +// BULK-MEMORY: #define __wasm_bulk_memory__ 1{{$}} // RUN: %clang -E -dM %s -o - 2>&1 \ // RUN: -target wasm32-unknown-unknown -mexception-handling \ @@ -41,34 +32,34 @@ // RUN: -target wasm64-unknown-unknown -mexception-handling \ // RUN: | FileCheck %s -check-prefix=EXCEPTION-HANDLING // -// EXCEPTION-HANDLING:#define __wasm_exception_handling__ 1{{$}} +// EXCEPTION-HANDLING: #define __wasm_exception_handling__ 1{{$}} // RUN: %clang -E -dM %s -o - 2>&1 \ -// RUN: -target wasm32-unknown-unknown -mbulk-memory \ -// RUN: | FileCheck %s -check-prefix=BULK-MEMORY +// RUN: -target wasm32-unknown-unknown -mextended-const \ +// RUN: | FileCheck %s -check-prefix=EXTENDED-CONST // RUN: %clang -E -dM %s -o - 2>&1 \ -// RUN: -target wasm64-unknown-unknown -mbulk-memory \ -// RUN: | FileCheck %s -check-prefix=BULK-MEMORY +// RUN: -target wasm64-unknown-unknown -mextended-const \ +// RUN: | FileCheck %s -check-prefix=EXTENDED-CONST // -// BULK-MEMORY:#define __wasm_bulk_memory__ 1{{$}} +// EXTENDED-CONST: #define __wasm_extended_const__ 1{{$}} // RUN: %clang -E -dM %s -o - 2>&1 \ -// RUN: -target wasm32-unknown-unknown -matomics \ -// RUN: | FileCheck %s -check-prefix=ATOMICS +// RUN: -target wasm32-unknown-unknown -mmultimemory \ +// RUN: | FileCheck %s -check-prefix=MULTIMEMORY // RUN: %clang -E -dM %s -o - 2>&1 \ -// RUN: -target wasm64-unknown-unknown -matomics \ -// RUN: | FileCheck %s -check-prefix=ATOMICS +// RUN: -target wasm64-unknown-unknown -mmultimemory \ +// RUN: | FileCheck %s -check-prefix=MULTIMEMORY // -// ATOMICS:#define __wasm_atomics__ 1{{$}} +// MULTIMEMORY: #define __wasm_multimemory__ 1{{$}} // RUN: %clang -E -dM %s -o - 2>&1 \ -// RUN: -target wasm32-unknown-unknown -pthread \ -// RUN: | FileCheck %s -check-prefix=PTHREAD +// RUN: -target wasm32-unknown-unknown -mmultivalue \ +// RUN: | FileCheck %s -check-prefix=MULTIVALUE // RUN: %clang -E -dM %s -o - 2>&1 \ -// RUN: -target wasm64-unknown-unknown -pthread \ -// RUN: | FileCheck %s -check-prefix=PTHREAD +// RUN: -target wasm64-unknown-unknown -mmultivalue \ +// RUN: | FileCheck %s -check-prefix=MULTIVALUE // -// PTHREAD:#define __wasm_atomics__ 1{{$}} +// MULTIVALUE: #define __wasm_multivalue__ 1{{$}} // RUN: %clang -E -dM %s -o - 2>&1 \ // RUN: -target wasm32-unknown-unknown -mmutable-globals \ @@ -77,26 +68,17 @@ // RUN: -target wasm64-unknown-unknown -mmutable-globals \ // RUN: | FileCheck %s -check-prefix=MUTABLE-GLOBALS // -// MUTABLE-GLOBALS:#define __wasm_mutable_globals__ 1{{$}} +// MUTABLE-GLOBALS: #define __wasm_mutable_globals__ 1{{$}} // RUN: %clang -E -dM %s -o - 2>&1 \ -// RUN: -target wasm32-unknown-unknown -mmultivalue \ -// RUN: | FileCheck %s -check-prefix=MULTIVALUE +// RUN: -target wasm32-unknown-unknown -mnontrapping-fptoint \ +// RUN: | FileCheck %s -check-prefix=NONTRAPPING-FPTOINT // RUN: %clang -E -dM %s -o - 2>&1 \ -// RUN: -target wasm64-unknown-unknown -mmultivalue \ -// RUN: | FileCheck %s -check-prefix=MULTIVALUE +// RUN: -target wasm64-unknown-unknown -mnontrapping-fptoint \ +// RUN: | FileCheck %s -check-prefix=NONTRAPPING-FPTOINT // -// MULTIVALUE:#define __wasm_multivalue__ 1{{$}} +// NONTRAPPING-FPTOINT: #define __wasm_nontrapping_fptoint__ 1{{$}} -// RUN: %clang -E -dM %s -o - 2>&1 \ -// RUN: -target wasm32-unknown-unknown -mtail-call \ -// RUN: | FileCheck %s -check-prefix=TAIL-CALL -// RUN: %clang -E -dM %s -o - 2>&1 \ -// RUN: -target wasm64-unknown-unknown -mtail-call \ -// RUN: | FileCheck %s -check-prefix=TAIL-CALL -// -// TAIL-CALL:#define __wasm_tail_call__ 1{{$}} -// // RUN: %clang -E -dM %s -o - 2>&1 \ // RUN: -target wasm32-unknown-unknown -mreference-types \ // RUN: | FileCheck %s -check-prefix=REFERENCE-TYPES @@ -104,26 +86,43 @@ // RUN: -target wasm64-unknown-unknown -mreference-types \ // RUN: | FileCheck %s -check-prefix=REFERENCE-TYPES // -// REFERENCE-TYPES:#define __wasm_reference_types__ 1{{$}} -// +// REFERENCE-TYPES: #define __wasm_reference_types__ 1{{$}} + // RUN: %clang -E -dM %s -o - 2>&1 \ -// RUN: -target wasm32-unknown-unknown -mextended-const \ -// RUN: | FileCheck %s -check-prefix=EXTENDED-CONST +// RUN: -target wasm32-unknown-unknown -mrelaxed-simd \ +// RUN: | FileCheck %s -check-prefix=RELAXED-SIMD // RUN: %clang -E -dM %s -o - 2>&1 \ -// RUN: -target wasm64-unknown-unknown -mextended-const \ -// RUN: | FileCheck %s -check-prefix=EXTENDED-CONST +// RUN: -target wasm64-unknown-unknown -mrelaxed-simd \ +// RUN: | FileCheck %s -check-prefix=RELAXED-SIMD // -// EXTENDED-CONST:#define __wasm_extended_const__ 1{{$}} +// RELAXED-SIMD: #define __wasm_relaxed_simd__ 1{{$}} + +// RUN: %clang -E -dM %s -o - 2>&1 \ +// RUN: -target wasm32-unknown-unknown -msign-ext \ +// RUN: | FileCheck %s -check-prefix=SIGN-EXT +// RUN: %clang -E -dM %s -o - 2>&1 \ +// RUN: -target wasm64-unknown-unknown -msign-ext \ +// RUN: | FileCheck %s -check-prefix=SIGN-EXT // +// SIGN-EXT: #define __wasm_sign_ext__ 1{{$}} + // RUN: %clang -E -dM %s -o - 2>&1 \ -// RUN: -target wasm32-unknown-unknown -mmultimemory \ -// RUN: | FileCheck %s -check-prefix=MULTIMEMORY +// RUN: -target wasm32-unknown-unknown -msimd128 \ +// RUN: | FileCheck %s -check-prefix=SIMD128 // RUN: %clang -E -dM %s -o - 2>&1 \ -// RUN: -target wasm64-unknown-unknown -mmultimemory \ -// RUN: | FileCheck %s -check-prefix=MULTIMEMORY +// RUN: -target wasm64-unknown-unknown -msimd128 \ +// RUN: | FileCheck %s -check-prefix=SIMD128 // -// MULTIMEMORY:#define __wasm_multimemory__ 1{{$}} +// SIMD128: #define __wasm_simd128__ 1{{$}} + +// RUN: %clang -E -dM %s -o - 2>&1 \ +// RUN: -target wasm32-unknown-unknown -mtail-call \ +// RUN: | FileCheck %s -check-prefix=TAIL-CALL +// RUN: %clang -E -dM %s -o - 2>&1 \ +// RUN: -target wasm64-unknown-unknown -mtail-call \ +// RUN: | FileCheck %s -check-prefix=TAIL-CALL // +// TAIL-CALL: #define __wasm_tail_call__ 1{{$}} // RUN: %clang -E -dM %s -o - 2>&1 \ // RUN: -target wasm32-unknown-unknown -mcpu=mvp \ @@ -132,20 +131,30 @@ // RUN: -target wasm64-unknown-unknown -mcpu=mvp \ // RUN: | FileCheck %s -check-prefix=MVP // -// MVP-NOT:#define __wasm_simd128__ -// MVP-NOT:#define __wasm_nontrapping_fptoint__ -// MVP-NOT:#define __wasm_sign_ext__ -// MVP-NOT:#define __wasm_exception_handling__ -// MVP-NOT:#define __wasm_bulk_memory__ -// MVP-NOT:#define __wasm_atomics__ -// MVP-NOT:#define __wasm_mutable_globals__ -// MVP-NOT:#define __wasm_multivalue__ -// MVP-NOT:#define __wasm_tail_call__ -// MVP-NOT:#define __wasm_reference_types__ -// MVP-NOT:#define __wasm_extended_const__ -// MVP-NOT:#define __wasm_multimemory__ -// MVP-NOT:#define __wasm_relaxed_simd__ +// MVP-NOT: #define __wasm_atomics__ 1{{$}} +// MVP-NOT: #define __wasm_bulk_memory__ 1{{$}} +// MVP-NOT: #define __wasm_exception_handling__ 1{{$}} +// MVP-NOT: #define __wasm_extended_const__ 1{{$}} +// MVP-NOT: #define __wasm_multimemory__ 1{{$}} +// MVP-NOT: #define __wasm_multivalue__ 1{{$}} +// MVP-NOT: #define __wasm_mutable_globals__ 1{{$}} +// MVP-NOT: #define __wasm_nontrapping_fptoint__ 1{{$}} +// MVP-NOT: #define __wasm_reference_types__ 1{{$}} +// MVP-NOT: #define __wasm_relaxed_simd__ 1{{$}} +// MVP-NOT: #define __wasm_sign_ext__ 1{{$}} +// MVP-NOT: #define __wasm_simd128__ 1{{$}} +// MVP-NOT: #define __wasm_tail_call__ 1{{$}} +// RUN: %clang -E -dM %s -o - 2>&1 \ +// RUN: -target wasm32-unknown-unknown -mcpu=generic \ +// RUN: | FileCheck %s -check-prefix=GENERIC-INCLUDE +// RUN: %clang -E -dM %s -o - 2>&1 \ +// RUN: -target wasm64-unknown-unknown -mcpu=generic \ +// RUN: | FileCheck %s -check-prefix=GENERIC-INCLUDE +// +// GENERIC-INCLUDE-DAG: #define __wasm_mutable_globals__ 1{{$}} +// GENERIC-INCLUDE-DAG: #define __wasm_sign_ext__ 1{{$}} +// // RUN: %clang -E -dM %s -o - 2>&1 \ // RUN: -target wasm32-unknown-unknown -mcpu=generic \ // RUN: | FileCheck %s -check-prefix=GENERIC @@ -153,19 +162,35 @@ // RUN: -target wasm64-unknown-unknown -mcpu=generic \ // RUN: | FileCheck %s -check-prefix=GENERIC // -// GENERIC-DAG:#define __wasm_sign_ext__ 1{{$}} -// GENERIC-DAG:#define __wasm_mutable_globals__ 1{{$}} -// GENERIC-NOT:#define __wasm_nontrapping_fptoint__ 1{{$}} -// GENERIC-NOT:#define __wasm_bulk_memory__ 1{{$}} -// GENERIC-NOT:#define __wasm_simd128__ 1{{$}} -// GENERIC-NOT:#define __wasm_atomics__ 1{{$}} -// GENERIC-NOT:#define __wasm_tail_call__ 1{{$}} -// GENERIC-NOT:#define __wasm_multimemory__ 1{{$}} -// GENERIC-NOT:#define __wasm_exception_handling__ 1{{$}} -// GENERIC-NOT:#define __wasm_multivalue__ 1{{$}} -// GENERIC-NOT:#define __wasm_reference_types__ 1{{$}} -// GENERIC-NOT:#define __wasm_extended_const__ 1{{$}} +// GENERIC-NOT: #define __wasm_atomics__ 1{{$}} +// GENERIC-NOT: #define __wasm_bulk_memory__ 1{{$}} +// GENERIC-NOT: #define __wasm_exception_handling__ 1{{$}} +// GENERIC-NOT: #define __wasm_extended_const__ 1{{$}} +// GENERIC-NOT: #define __wasm_multimemory__ 1{{$}} +// GENERIC-NOT: #define __wasm_multivalue__ 1{{$}} +// GENERIC-NOT: #define __wasm_nontrapping_fptoint__ 1{{$}} +// GENERIC-NOT: #define __wasm_reference_types__ 1{{$}} +// GENERIC-NOT: #define __wasm_relaxed_simd__ 1{{$}} +// GENERIC-NOT: #define __wasm_simd128__ 1{{$}} +// GENERIC-NOT: #define __wasm_tail_call__ 1{{$}} +// RUN: %clang -E -dM %s -o - 2>&1 \ +// RUN: -target wasm32-unknown-unknown -mcpu=bleeding-edge \ +// RUN: | FileCheck %s -check-prefix=BLEEDING-EDGE-INCLUDE +// RUN: %clang -E -dM %s -o - 2>&1 \ +// RUN: -target wasm64-unknown-unknown -mcpu=bleeding-edge \ +// RUN: | FileCheck %s -check-prefix=BLEEDING-EDGE-INCLUDE +// +// BLEEDING-EDGE-INCLUDE-DAG: #define __wasm_atomics__ 1{{$}} +// BLEEDING-EDGE-INCLUDE-DAG: #define __wasm_bulk_memory__ 1{{$}} +// BLEEDING-EDGE-INCLUDE-DAG: #define __wasm_multimemory__ 1{{$}} +// BLEEDING-EDGE-INCLUDE-DAG: #define __wasm_mutable_globals__ 1{{$}} +// BLEEDING-EDGE-INCLUDE-DAG: #define __wasm_nontrapping_fptoint__ 1{{$}} +// BLEEDING-EDGE-INCLUDE-DAG: #define __wasm_reference_types__ 1{{$}} +// BLEEDING-EDGE-INCLUDE-DAG: #define __wasm_sign_ext__ 1{{$}} +// BLEEDING-EDGE-INCLUDE-DAG: #define __wasm_simd128__ 1{{$}} +// BLEEDING-EDGE-INCLUDE-DAG: #define __wasm_tail_call__ 1{{$}} +// // RUN: %clang -E -dM %s -o - 2>&1 \ // RUN: -target wasm32-unknown-unknown -mcpu=bleeding-edge \ // RUN: | FileCheck %s -check-prefix=BLEEDING-EDGE @@ -173,19 +198,10 @@ // RUN: -target wasm64-unknown-unknown -mcpu=bleeding-edge \ // RUN: | FileCheck %s -check-prefix=BLEEDING-EDGE // -// BLEEDING-EDGE-DAG:#define __wasm_nontrapping_fptoint__ 1{{$}} -// BLEEDING-EDGE-DAG:#define __wasm_sign_ext__ 1{{$}} -// BLEEDING-EDGE-DAG:#define __wasm_bulk_memory__ 1{{$}} -// BLEEDING-EDGE-DAG:#define __wasm_simd128__ 1{{$}} -// BLEEDING-EDGE-DAG:#define __wasm_atomics__ 1{{$}} -// BLEEDING-EDGE-DAG:#define __wasm_mutable_globals__ 1{{$}} -// BLEEDING-EDGE-DAG:#define __wasm_tail_call__ 1{{$}} -// BLEEDING-EDGE-DAG:#define __wasm_multimemory__ 1{{$}} -// BLEEDING-EDGE-NOT:#define __wasm_exception_handling__ 1{{$}} -// BLEEDING-EDGE-NOT:#define __wasm_multivalue__ 1{{$}} -// BLEEDING-EDGE-NOT:#define __wasm_reference_types__ 1{{$}} -// BLEEDING-EDGE-NOT:#define __wasm_extended_const__ 1{{$}} -// BLEEDING-EDGE-NOT:#define __wasm_relaxed_simd__ 1{{$}} +// BLEEDING-EDGE-NOT: #define __wasm_exception_handling__ 1{{$}} +// BLEEDING-EDGE-NOT: #define __wasm_extended_const__ 1{{$}} +// BLEEDING-EDGE-NOT: #define __wasm_multivalue__ 1{{$}} +// BLEEDING-EDGE-NOT: #define __wasm_relaxed_simd__ 1{{$}} // RUN: %clang -E -dM %s -o - 2>&1 \ // RUN: -target wasm32-unknown-unknown -mcpu=bleeding-edge -mno-simd128 \ @@ -194,4 +210,4 @@ // RUN: -target wasm64-unknown-unknown -mcpu=bleeding-edge -mno-simd128 \ // RUN: | FileCheck %s -check-prefix=BLEEDING-EDGE-NO-SIMD128 // -// BLEEDING-EDGE-NO-SIMD128-NOT:#define __wasm_simd128__ +// BLEEDING-EDGE-NO-SIMD128-NOT: #define __wasm_simd128__ 1{{$}} diff --git a/clang/test/Sema/aarch64-incompat-sm-builtin-calls.c b/clang/test/Sema/aarch64-incompat-sm-builtin-calls.c index 6a1feeb9bf53976325eda4e393c738a392c103b9..e55e84a61034fa927a55622f8b13c87606d747b9 100644 --- a/clang/test/Sema/aarch64-incompat-sm-builtin-calls.c +++ b/clang/test/Sema/aarch64-incompat-sm-builtin-calls.c @@ -33,7 +33,8 @@ svuint32_t incompat_sve_sm(svbool_t pg, svuint32_t a, int16_t b) __arm_streaming return __builtin_sve_svld1_gather_u32base_index_u32(pg, a, b); } -// expected-warning@+1 {{passing/returning a VL-dependent argument to/from a __arm_locally_streaming function. The streaming and non-streaming vector lengths may be different}} +// expected-warning@+2 {{returning a VL-dependent argument from a locally streaming function is undefined behaviour when the streaming and non-streaming vector lengths are different at runtime}} +// expected-warning@+1 {{passing a VL-dependent argument to a locally streaming function is undefined behaviour when the streaming and non-streaming vector lengths are different at runtime}} __arm_locally_streaming svuint32_t incompat_sve_ls(svbool_t pg, svuint32_t a, int64_t b) { // expected-warning@+1 {{builtin call has undefined behaviour when called from a streaming function}} return __builtin_sve_svld1_gather_u32base_index_u32(pg, a, b); @@ -49,7 +50,8 @@ svuint32_t incompat_sve2_sm(svbool_t pg, svuint32_t a, int64_t b) __arm_streamin return __builtin_sve_svldnt1_gather_u32base_index_u32(pg, a, b); } -// expected-warning@+1 {{passing/returning a VL-dependent argument to/from a __arm_locally_streaming function. The streaming and non-streaming vector lengths may be different}} +// expected-warning@+2 {{returning a VL-dependent argument from a locally streaming function is undefined behaviour when the streaming and non-streaming vector lengths are different at runtime}} +// expected-warning@+1 {{passing a VL-dependent argument to a locally streaming function is undefined behaviour when the streaming and non-streaming vector lengths are different at runtime}} __arm_locally_streaming svuint32_t incompat_sve2_ls(svbool_t pg, svuint32_t a, int64_t b) { // expected-warning@+1 {{builtin call has undefined behaviour when called from a streaming function}} return __builtin_sve_svldnt1_gather_u32base_index_u32(pg, a, b); @@ -70,7 +72,8 @@ svfloat64_t streaming_caller_sve(svbool_t pg, svfloat64_t a, float64_t b) __arm_ return svadd_n_f64_m(pg, a, b); } -// expected-warning@+1 {{passing/returning a VL-dependent argument to/from a __arm_locally_streaming function. The streaming and non-streaming vector lengths may be different}} +// expected-warning@+2 {{returning a VL-dependent argument from a locally streaming function is undefined behaviour when the streaming and non-streaming vector lengths are different at runtime}} +// expected-warning@+1 {{passing a VL-dependent argument to a locally streaming function is undefined behaviour when the streaming and non-streaming vector lengths are different at runtime}} __arm_locally_streaming svfloat64_t locally_streaming_caller_sve(svbool_t pg, svfloat64_t a, float64_t b) { // expected-no-warning return svadd_n_f64_m(pg, a, b); @@ -86,7 +89,8 @@ svint16_t streaming_caller_sve2(svint16_t op1, svint16_t op2) __arm_streaming { return svmul_lane_s16(op1, op2, 0); } -// expected-warning@+1 {{passing/returning a VL-dependent argument to/from a __arm_locally_streaming function. The streaming and non-streaming vector lengths may be different}} +// expected-warning@+2 {{returning a VL-dependent argument from a locally streaming function is undefined behaviour when the streaming and non-streaming vector lengths are different at runtime}} +// expected-warning@+1 {{passing a VL-dependent argument to a locally streaming function is undefined behaviour when the streaming and non-streaming vector lengths are different at runtime}} __arm_locally_streaming svint16_t locally_streaming_caller_sve2(svint16_t op1, svint16_t op2) { // expected-no-warning return svmul_lane_s16(op1, op2, 0); diff --git a/clang/test/Sema/aarch64-sme-func-attrs.c b/clang/test/Sema/aarch64-sme-func-attrs.c index 12de16509ccb8d276282c14263614d83e29dc6b3..3d90723d32f1e7da9e94b4dbaea5afa2d5811134 100644 --- a/clang/test/Sema/aarch64-sme-func-attrs.c +++ b/clang/test/Sema/aarch64-sme-func-attrs.c @@ -509,73 +509,73 @@ void sme_no_streaming_with_vl_arg(__SVInt8_t a) { } __SVInt8_t sme_no_streaming_returns_vl(void) { __SVInt8_t r; return r; } -// expected-warning@+2 {{passing/returning a VL-dependent argument to/from a __arm_locally_streaming function. The streaming and non-streaming vector lengths may be different}} -// expected-cpp-warning@+1 {{passing/returning a VL-dependent argument to/from a __arm_locally_streaming function. The streaming and non-streaming vector lengths may be different}} +// expected-warning@+2 {{passing a VL-dependent argument to a locally streaming function is undefined behaviour when the streaming and non-streaming vector lengths are different at runtime}} +// expected-cpp-warning@+1 {{passing a VL-dependent argument to a locally streaming function is undefined behaviour when the streaming and non-streaming vector lengths are different at runtime}} __arm_locally_streaming void sme_locally_streaming_with_vl_arg(__SVInt8_t a) { } -// expected-warning@+2 {{passing/returning a VL-dependent argument to/from a __arm_locally_streaming function. The streaming and non-streaming vector lengths may be different}} -// expected-cpp-warning@+1 {{passing/returning a VL-dependent argument to/from a __arm_locally_streaming function. The streaming and non-streaming vector lengths may be different}} +// expected-warning@+2 {{returning a VL-dependent argument from a locally streaming function is undefined behaviour when the streaming and non-streaming vector lengths are different at runtime}} +// expected-cpp-warning@+1 {{returning a VL-dependent argument from a locally streaming function is undefined behaviour when the streaming and non-streaming vector lengths are different at runtime}} __arm_locally_streaming __SVInt8_t sme_locally_streaming_returns_vl(void) { __SVInt8_t r; return r; } void sme_no_streaming_calling_streaming_with_vl_args() { __SVInt8_t a; - // expected-warning@+2 {{passing a VL-dependent argument to/from a function that has a different streaming-mode. The streaming and non-streaming vector lengths may be different}} - // expected-cpp-warning@+1 {{passing a VL-dependent argument to/from a function that has a different streaming-mode. The streaming and non-streaming vector lengths may be different}} + // expected-warning@+2 {{passing a VL-dependent argument to a function with a different streaming-mode is undefined behaviour when the streaming and non-streaming vector lengths are different at runtime}} + // expected-cpp-warning@+1 {{passing a VL-dependent argument to a function with a different streaming-mode is undefined behaviour when the streaming and non-streaming vector lengths are different at runtime}} sme_streaming_with_vl_arg(a); } void sme_no_streaming_calling_streaming_with_return_vl() { - // expected-warning@+2 {{passing a VL-dependent argument to/from a function that has a different streaming-mode. The streaming and non-streaming vector lengths may be different}} - // expected-cpp-warning@+1 {{passing a VL-dependent argument to/from a function that has a different streaming-mode. The streaming and non-streaming vector lengths may be different}} + // expected-warning@+2 {{returning a VL-dependent argument from a function with a different streaming-mode is undefined behaviour when the streaming and non-streaming vector lengths are different at runtime}} + // expected-cpp-warning@+1 {{returning a VL-dependent argument from a function with a different streaming-mode is undefined behaviour when the streaming and non-streaming vector lengths are different at runtime}} __SVInt8_t r = sme_streaming_returns_vl(); } void sme_streaming_calling_non_streaming_with_vl_args(void) __arm_streaming { __SVInt8_t a; - // expected-warning@+2 {{passing a VL-dependent argument to/from a function that has a different streaming-mode. The streaming and non-streaming vector lengths may be different}} - // expected-cpp-warning@+1 {{passing a VL-dependent argument to/from a function that has a different streaming-mode. The streaming and non-streaming vector lengths may be different}} + // expected-warning@+2 {{passing a VL-dependent argument to a function with a different streaming-mode is undefined behaviour when the streaming and non-streaming vector lengths are different at runtime}} + // expected-cpp-warning@+1 {{passing a VL-dependent argument to a function with a different streaming-mode is undefined behaviour when the streaming and non-streaming vector lengths are different at runtime}} sme_no_streaming_with_vl_arg(a); } void sme_streaming_calling_non_streaming_with_return_vl(void) __arm_streaming { - // expected-warning@+2 {{passing a VL-dependent argument to/from a function that has a different streaming-mode. The streaming and non-streaming vector lengths may be different}} - // expected-cpp-warning@+1 {{passing a VL-dependent argument to/from a function that has a different streaming-mode. The streaming and non-streaming vector lengths may be different}} + // expected-warning@+2 {{returning a VL-dependent argument from a function with a different streaming-mode is undefined behaviour when the streaming and non-streaming vector lengths are different at runtime}} + // expected-cpp-warning@+1 {{returning a VL-dependent argument from a function with a different streaming-mode is undefined behaviour when the streaming and non-streaming vector lengths are different at runtime}} __SVInt8_t r = sme_no_streaming_returns_vl(); } void sme_no_streaming_calling_streaming_with_vl_args_param(__SVInt8_t arg, void (*sc)( __SVInt8_t arg) __arm_streaming) { - // expected-warning@+2 {{passing a VL-dependent argument to/from a function that has a different streaming-mode. The streaming and non-streaming vector lengths may be different}} - // expected-cpp-warning@+1 {{passing a VL-dependent argument to/from a function that has a different streaming-mode. The streaming and non-streaming vector lengths may be different}} + // expected-warning@+2 {{passing a VL-dependent argument to a function with a different streaming-mode is undefined behaviour when the streaming and non-streaming vector lengths are different at runtime}} + // expected-cpp-warning@+1 {{passing a VL-dependent argument to a function with a different streaming-mode is undefined behaviour when the streaming and non-streaming vector lengths are different at runtime}} sc(arg); } __SVInt8_t sme_no_streaming_calling_streaming_return_vl_param(__SVInt8_t (*s)(void) __arm_streaming) { - // expected-warning@+2 {{passing a VL-dependent argument to/from a function that has a different streaming-mode. The streaming and non-streaming vector lengths may be different}} - // expected-cpp-warning@+1 {{passing a VL-dependent argument to/from a function that has a different streaming-mode. The streaming and non-streaming vector lengths may be different}} + // expected-warning@+2 {{returning a VL-dependent argument from a function with a different streaming-mode is undefined behaviour when the streaming and non-streaming vector lengths are different at runtime}} + // expected-cpp-warning@+1 {{returning a VL-dependent argument from a function with a different streaming-mode is undefined behaviour when the streaming and non-streaming vector lengths are different at runtime}} return s(); } void sme_streaming_compatible_calling_streaming_with_vl_args(__SVInt8_t arg) __arm_streaming_compatible { - // expected-warning@+2 {{passing a VL-dependent argument to/from a function that has a different streaming-mode. The streaming and non-streaming vector lengths may be different}} - // expected-cpp-warning@+1 {{passing a VL-dependent argument to/from a function that has a different streaming-mode. The streaming and non-streaming vector lengths may be different}} + // expected-warning@+2 {{passing a VL-dependent argument to a function with a different streaming-mode is undefined behaviour when the streaming and non-streaming vector lengths are different at runtime}} + // expected-cpp-warning@+1 {{passing a VL-dependent argument to a function with a different streaming-mode is undefined behaviour when the streaming and non-streaming vector lengths are different at runtime}} sme_streaming_with_vl_arg(arg); } void sme_streaming_compatible_calling_sme_streaming_return_vl(void) __arm_streaming_compatible { - // expected-warning@+2 {{passing a VL-dependent argument to/from a function that has a different streaming-mode. The streaming and non-streaming vector lengths may be different}} - // expected-cpp-warning@+1 {{passing a VL-dependent argument to/from a function that has a different streaming-mode. The streaming and non-streaming vector lengths may be different}} + // expected-warning@+2 {{returning a VL-dependent argument from a function with a different streaming-mode is undefined behaviour when the streaming and non-streaming vector lengths are different at runtime}} + // expected-cpp-warning@+1 {{returning a VL-dependent argument from a function with a different streaming-mode is undefined behaviour when the streaming and non-streaming vector lengths are different at runtime}} __SVInt8_t r = sme_streaming_returns_vl(); } void sme_streaming_compatible_calling_no_streaming_with_vl_args(__SVInt8_t arg) __arm_streaming_compatible { - // expected-warning@+2 {{passing a VL-dependent argument to/from a function that has a different streaming-mode. The streaming and non-streaming vector lengths may be different}} - // expected-cpp-warning@+1 {{passing a VL-dependent argument to/from a function that has a different streaming-mode. The streaming and non-streaming vector lengths may be different}} + // expected-warning@+2 {{passing a VL-dependent argument to a function with a different streaming-mode is undefined behaviour when the streaming and non-streaming vector lengths are different at runtime}} + // expected-cpp-warning@+1 {{passing a VL-dependent argument to a function with a different streaming-mode is undefined behaviour when the streaming and non-streaming vector lengths are different at runtime}} sme_no_streaming_with_vl_arg(arg); } void sme_streaming_compatible_calling_no_sme_streaming_return_vl(void) __arm_streaming_compatible { - // expected-warning@+2 {{passing a VL-dependent argument to/from a function that has a different streaming-mode. The streaming and non-streaming vector lengths may be different}} - // expected-cpp-warning@+1 {{passing a VL-dependent argument to/from a function that has a different streaming-mode. The streaming and non-streaming vector lengths may be different}} + // expected-warning@+2 {{returning a VL-dependent argument from a function with a different streaming-mode is undefined behaviour when the streaming and non-streaming vector lengths are different at runtime}} + // expected-cpp-warning@+1 {{returning a VL-dependent argument from a function with a different streaming-mode is undefined behaviour when the streaming and non-streaming vector lengths are different at runtime}} __SVInt8_t r = sme_no_streaming_returns_vl(); } diff --git a/clang/test/SemaCXX/MicrosoftExtensions.cpp b/clang/test/SemaCXX/MicrosoftExtensions.cpp index 7286217b1644f3ee00eb64e7fc979a5259b12471..98c19975095bbee83c19bc501b647a4a048799bd 100644 --- a/clang/test/SemaCXX/MicrosoftExtensions.cpp +++ b/clang/test/SemaCXX/MicrosoftExtensions.cpp @@ -571,11 +571,17 @@ class PR34109_class { virtual ~PR34109_class() {} }; +#if !defined(__cpp_sized_deallocation) void operator delete(void *) throw(); // expected-note@-1 {{previous declaration is here}} __declspec(dllexport) void operator delete(void *) throw(); // expected-error@-1 {{redeclaration of 'operator delete' cannot add 'dllexport' attribute}} - +#else +void operator delete(void *, unsigned int) throw(); +// expected-note@-1 {{previous declaration is here}} +__declspec(dllexport) void operator delete(void *, unsigned int) throw(); +// expected-error@-1 {{redeclaration of 'operator delete' cannot add 'dllexport' attribute}} +#endif void PR34109(int* a) { delete a; } diff --git a/clang/test/SemaCXX/PR41441.cpp b/clang/test/SemaCXX/PR41441.cpp deleted file mode 100644 index 3f60b6e209207a8fe787b1912c6aaa2f7ed19013..0000000000000000000000000000000000000000 --- a/clang/test/SemaCXX/PR41441.cpp +++ /dev/null @@ -1,32 +0,0 @@ -// RUN: %clang --target=x86_64-pc-linux -S -fno-discard-value-names -emit-llvm -o - %s | FileCheck %s - -namespace std { - using size_t = decltype(sizeof(int)); -}; -void* operator new[](std::size_t, void*) noexcept; - -// CHECK: call void @llvm.memset.p0.i64(ptr align 1 %x, i8 0, i64 8, i1 false) -// CHECK: call void @llvm.memset.p0.i64(ptr align 16 %x, i8 0, i64 32, i1 false) -template -void f() -{ - typedef TYPE TArray[8]; - - TArray x; - new(&x) TArray(); -} - -template -void f1() { - int (*x)[1] = new int[1][1]; -} -template void f1(); -void f2() { - int (*x)[1] = new int[1][1]; -} - -int main() -{ - f(); - f(); -} diff --git a/clang/test/SemaCXX/builtin-operator-new-delete.cpp b/clang/test/SemaCXX/builtin-operator-new-delete.cpp index 6fcff92dc0952a46a99c95a42343d948f918b35a..db15616803e373914239ab81aa917966b2459add 100644 --- a/clang/test/SemaCXX/builtin-operator-new-delete.cpp +++ b/clang/test/SemaCXX/builtin-operator-new-delete.cpp @@ -1,4 +1,4 @@ -// RUN: %clang_cc1 -std=c++1z -fsyntax-only -verify %s +// RUN: %clang_cc1 -std=c++1z -fno-sized-deallocation -fsyntax-only -verify %s // RUN: %clang_cc1 -std=c++03 -fsyntax-only -verify %s // RUN: %clang_cc1 -std=c++03 -faligned-allocation -fsyntax-only -verify %s // RUN: %clang_cc1 -std=c++11 -fsyntax-only -verify %s diff --git a/clang/test/SemaCXX/cxx1y-sized-deallocation.cpp b/clang/test/SemaCXX/cxx1y-sized-deallocation.cpp index 3ec65a6a64d1ccf786b57d195e297aae5efd2699..462f1725bb1c26927e3ea7241f73ffa3c70c21b0 100644 --- a/clang/test/SemaCXX/cxx1y-sized-deallocation.cpp +++ b/clang/test/SemaCXX/cxx1y-sized-deallocation.cpp @@ -1,4 +1,4 @@ -// RUN: %clang_cc1 -std=c++1y -verify %s -fsized-deallocation -fexceptions -fcxx-exceptions +// RUN: %clang_cc1 -std=c++1y -verify %s -fexceptions -fcxx-exceptions using size_t = decltype(sizeof(0)); void operator delete(void *, size_t) noexcept; // expected-note {{'operator delete' declared here}} diff --git a/clang/test/SemaCXX/cxx2a-consteval.cpp b/clang/test/SemaCXX/cxx2a-consteval.cpp index 192621225a543c694784aa6ba4737fc252d94f98..e198074372072d98043575fd15b27392d7093724 100644 --- a/clang/test/SemaCXX/cxx2a-consteval.cpp +++ b/clang/test/SemaCXX/cxx2a-consteval.cpp @@ -260,6 +260,26 @@ int(*test)(int) = l1; } +namespace consteval_lambda_in_template { +struct S { + int *value; + constexpr S(int v) : value(new int {v}) {} + constexpr ~S() { delete value; } +}; +consteval S fn() { return S(5); } + +template +void fn2() { + (void)[]() consteval -> int { + return *(fn().value); // OK, immediate context + }; +} + +void caller() { + fn2(); +} +} + namespace std { template struct remove_reference { using type = T; }; diff --git a/clang/test/SemaCXX/template-specialization.cpp b/clang/test/SemaCXX/template-specialization.cpp index 7b26ff9f5c5ba4982dfce2e9b52cbb6ff710d8d2..eabb84f2e13d3ec5a86da42e3b563f4e28b535af 100644 --- a/clang/test/SemaCXX/template-specialization.cpp +++ b/clang/test/SemaCXX/template-specialization.cpp @@ -52,3 +52,31 @@ void instantiate() { } } + +namespace GH89374 { + +struct A {}; + +template +struct MatrixBase { // #GH89374-MatrixBase + template + Derived &operator=(const MatrixBase &); // #GH89374-copy-assignment +}; + +template +struct solve_retval; + +template +struct solve_retval : MatrixBase > {}; +// expected-error@-1 {{partial specialization of 'solve_retval' does not use any of its template parameters}} + +void ApproximateChebyshev() { + MatrixBase c; + c = solve_retval(); + // expected-error@-1 {{no viable overloaded '='}} + // expected-note@#GH89374-copy-assignment {{candidate template ignored: could not match 'MatrixBase' against 'solve_retval'}} + // expected-note@#GH89374-MatrixBase {{candidate function (the implicit copy assignment operator) not viable: no known conversion from 'solve_retval' to 'const MatrixBase' for 1st argument}} + // expected-note@#GH89374-MatrixBase {{candidate function (the implicit move assignment operator) not viable: no known conversion from 'solve_retval' to 'MatrixBase' for 1st argument}} +} + +} // namespace GH89374 diff --git a/clang/test/SemaCXX/unavailable_aligned_allocation.cpp b/clang/test/SemaCXX/unavailable_aligned_allocation.cpp index be593eafe11d6aa16f7d50ba22db342bf7441de0..45fdec606ad1b3a0a3bef21855925988a495992c 100644 --- a/clang/test/SemaCXX/unavailable_aligned_allocation.cpp +++ b/clang/test/SemaCXX/unavailable_aligned_allocation.cpp @@ -75,7 +75,7 @@ void testOveraligned() { // expected-error-re@-22 {{aligned deallocation function of type 'void (void *, enum std::align_val_t) noexcept' is {{only|not}} available on}} // expected-note@-23 {{if you supply your own aligned allocation functions}} -// expected-error-re@-24 {{aligned deallocation function of type 'void (void *, enum std::align_val_t) noexcept' is {{only|not}} available on}} +// expected-error-re@-24 {{aligned deallocation function of type 'void (void *, std::size_t, std::align_val_t) noexcept' is {{only|not}} available on}} // expected-note@-25 {{if you supply your own aligned allocation functions}} // expected-error-re@-26 {{aligned allocation function of type 'void *(std::size_t, std::align_val_t, const std::nothrow_t &) noexcept' is {{only|not}} available on}} @@ -143,19 +143,19 @@ OveralignedS2::~OveralignedS2() {} // expected-no-diagnostics #else #if defined(IOS) -// expected-error@-6 {{aligned deallocation function of type 'void (void *, enum std::align_val_t) noexcept' is only available on iOS 11 or newer}}} +// expected-error@-6 {{aligned deallocation function of type 'void (void *, std::size_t, std::align_val_t) noexcept' is only available on iOS 11 or newer}}} // expected-note@-7 {{if you supply your own aligned allocation functions}} #elif defined(TVOS) -// expected-error@-9 {{aligned deallocation function of type 'void (void *, enum std::align_val_t) noexcept' is only available on tvOS 11 or newer}}} +// expected-error@-9 {{aligned deallocation function of type 'void (void *, std::size_t, std::align_val_t) noexcept' is only available on tvOS 11 or newer}}} // expected-note@-10 {{if you supply your own aligned allocation functions}} #elif defined(WATCHOS) -// expected-error@-12 {{aligned deallocation function of type 'void (void *, enum std::align_val_t) noexcept' is only available on watchOS 4 or newer}}} +// expected-error@-12 {{aligned deallocation function of type 'void (void *, std::size_t, std::align_val_t) noexcept' is only available on watchOS 4 or newer}}} // expected-note@-13 {{if you supply your own aligned allocation functions}} #elif defined(MACOS) -// expected-error@-15 {{aligned deallocation function of type 'void (void *, enum std::align_val_t) noexcept' is only available on macOS 10.13 or newer}}} +// expected-error@-15 {{aligned deallocation function of type 'void (void *, std::size_t, std::align_val_t) noexcept' is only available on macOS 10.13 or newer}}} // expected-note@-16 {{if you supply your own aligned allocation functions}} #elif defined(ZOS) -// expected-error@-18 {{aligned deallocation function of type 'void (void *, enum std::align_val_t) noexcept' is not available on z/OS}}} +// expected-error@-18 {{aligned deallocation function of type 'void (void *, std::size_t, std::align_val_t) noexcept' is not available on z/OS}}} // expected-note@-19 {{if you supply your own aligned allocation functions}} #endif #endif @@ -209,6 +209,9 @@ void *operator new(std::size_t __sz, std::align_val_t) { void operator delete(void *p, std::align_val_t) { } +void operator delete(void *p, std::size_t __sz, std::align_val_t) { +} + void testOveraligned2() { auto p = new ((std::align_val_t)8) OveralignedS; delete p; diff --git a/clang/test/TestRunner.sh b/clang/test/TestRunner.sh deleted file mode 100755 index f96d3d552d2ee63019d6e9052152e3a88896f748..0000000000000000000000000000000000000000 --- a/clang/test/TestRunner.sh +++ /dev/null @@ -1,13 +0,0 @@ -#!/bin/sh -# -# TestRunner.sh - Backward compatible utility for testing an individual file. - -# Find where this script is. -Dir=$(dirname $(which $0)) -AbsDir=$(cd $Dir; pwd) - -# Find 'lit', assuming standard layout. -lit=$AbsDir/../../../utils/lit/lit.py - -# Dispatch to lit. -$lit "$@" diff --git a/clang/tools/c-index-test/c-index-test.c b/clang/tools/c-index-test/c-index-test.c index 21619888cfa5f3f3d835ce767eb566658ea62852..e078e9bdce027a6a2f3b8b0b25ece3a69d8c85d6 100644 --- a/clang/tools/c-index-test/c-index-test.c +++ b/clang/tools/c-index-test/c-index-test.c @@ -464,10 +464,10 @@ static void PrintRange(CXSourceRange R, const char *str) { CXFile begin_file, end_file; unsigned begin_line, begin_column, end_line, end_column; - clang_getSpellingLocation(clang_getRangeStart(R), - &begin_file, &begin_line, &begin_column, 0); - clang_getSpellingLocation(clang_getRangeEnd(R), - &end_file, &end_line, &end_column, 0); + clang_getFileLocation(clang_getRangeStart(R), &begin_file, &begin_line, + &begin_column, 0); + clang_getFileLocation(clang_getRangeEnd(R), &end_file, &end_line, &end_column, + 0); if (!begin_file || !end_file) return; @@ -849,13 +849,13 @@ static void PrintCursor(CXCursor Cursor, const char *CommentSchemaFile) { printf(", "); Loc = clang_getCursorLocation(Ovl); - clang_getSpellingLocation(Loc, 0, &line, &column, 0); + clang_getFileLocation(Loc, 0, &line, &column, 0); printf("%d:%d", line, column); } printf("]"); } else { CXSourceLocation Loc = clang_getCursorLocation(Referenced); - clang_getSpellingLocation(Loc, 0, &line, &column, 0); + clang_getFileLocation(Loc, 0, &line, &column, 0); printf(":%d:%d", line, column); } @@ -1047,7 +1047,7 @@ static void PrintCursor(CXCursor Cursor, const char *CommentSchemaFile) { if (!clang_equalCursors(SpecializationOf, clang_getNullCursor())) { CXSourceLocation Loc = clang_getCursorLocation(SpecializationOf); CXString Name = clang_getCursorSpelling(SpecializationOf); - clang_getSpellingLocation(Loc, 0, &line, &column, 0); + clang_getFileLocation(Loc, 0, &line, &column, 0); printf(" [Specialization of %s:%d:%d]", clang_getCString(Name), line, column); clang_disposeString(Name); @@ -1094,7 +1094,7 @@ static void PrintCursor(CXCursor Cursor, const char *CommentSchemaFile) { printf(" [Overrides "); for (I = 0; I != num_overridden; ++I) { CXSourceLocation Loc = clang_getCursorLocation(overridden[I]); - clang_getSpellingLocation(Loc, 0, &line, &column, 0); + clang_getFileLocation(Loc, 0, &line, &column, 0); lineCols[I].line = line; lineCols[I].col = column; } @@ -1257,8 +1257,8 @@ void PrintDiagnostic(CXDiagnostic Diagnostic) { fprintf(stderr, "%s\n", clang_getCString(Msg)); clang_disposeString(Msg); - clang_getSpellingLocation(clang_getDiagnosticLocation(Diagnostic), - &file, 0, 0, 0); + clang_getFileLocation(clang_getDiagnosticLocation(Diagnostic), &file, 0, 0, + 0); if (!file) return; @@ -1271,9 +1271,8 @@ void PrintDiagnostic(CXDiagnostic Diagnostic) { CXSourceLocation end = clang_getRangeEnd(range); unsigned start_line, start_column, end_line, end_column; CXFile start_file, end_file; - clang_getSpellingLocation(start, &start_file, &start_line, - &start_column, 0); - clang_getSpellingLocation(end, &end_file, &end_line, &end_column, 0); + clang_getFileLocation(start, &start_file, &start_line, &start_column, 0); + clang_getFileLocation(end, &end_file, &end_line, &end_column, 0); if (clang_equalLocations(start, end)) { /* Insertion. */ if (start_file == file) @@ -1356,7 +1355,7 @@ enum CXChildVisitResult FilteredPrintingVisitor(CXCursor Cursor, if (!Data->Filter || (Cursor.kind == *(enum CXCursorKind *)Data->Filter)) { CXSourceLocation Loc = clang_getCursorLocation(Cursor); unsigned line, column; - clang_getSpellingLocation(Loc, 0, &line, &column, 0); + clang_getFileLocation(Loc, 0, &line, &column, 0); printf("// %s: %s:%d:%d: ", FileCheckPrefix, GetCursorSource(Cursor), line, column); PrintCursor(Cursor, Data->CommentSchemaFile); @@ -1417,7 +1416,7 @@ static enum CXChildVisitResult FunctionScanVisitor(CXCursor Cursor, curColumn++; Loc = clang_getCursorLocation(Cursor); - clang_getSpellingLocation(Loc, &file, 0, 0, 0); + clang_getFileLocation(Loc, &file, 0, 0, 0); source = clang_getFileName(file); if (clang_getCString(source)) { @@ -1483,8 +1482,7 @@ void InclusionVisitor(CXFile includedFile, CXSourceLocation *includeStack, for (i = 0; i < includeStackLen; ++i) { CXFile includingFile; unsigned line, column; - clang_getSpellingLocation(includeStack[i], &includingFile, &line, - &column, 0); + clang_getFileLocation(includeStack[i], &includingFile, &line, &column, 0); fname = clang_getFileName(includingFile); printf(" %s:%d:%d\n", clang_getCString(fname), line, column); clang_disposeString(fname); @@ -2984,7 +2982,7 @@ static void inspect_print_cursor(CXCursor Cursor) { CXString Spelling; const char *cspell; unsigned line, column; - clang_getSpellingLocation(CursorLoc, 0, &line, &column, 0); + clang_getFileLocation(CursorLoc, 0, &line, &column, 0); printf("%d:%d ", line, column); PrintCursor(Cursor, NULL); PrintCursorExtent(Cursor); @@ -3100,7 +3098,7 @@ static void inspect_evaluate_cursor(CXCursor Cursor) { unsigned line, column; CXEvalResult ER; - clang_getSpellingLocation(CursorLoc, 0, &line, &column, 0); + clang_getFileLocation(CursorLoc, 0, &line, &column, 0); printf("%d:%d ", line, column); PrintCursor(Cursor, NULL); PrintCursorExtent(Cursor); @@ -3135,7 +3133,7 @@ static void inspect_macroinfo_cursor(CXCursor Cursor) { CXString Spelling; const char *cspell; unsigned line, column; - clang_getSpellingLocation(CursorLoc, 0, &line, &column, 0); + clang_getFileLocation(CursorLoc, 0, &line, &column, 0); printf("%d:%d ", line, column); PrintCursor(Cursor, NULL); PrintCursorExtent(Cursor); @@ -4328,10 +4326,10 @@ int perform_token_annotation(int argc, const char **argv) { skipped_ranges = clang_getSkippedRanges(TU, file); for (i = 0; i != skipped_ranges->count; ++i) { unsigned start_line, start_column, end_line, end_column; - clang_getSpellingLocation(clang_getRangeStart(skipped_ranges->ranges[i]), - 0, &start_line, &start_column, 0); - clang_getSpellingLocation(clang_getRangeEnd(skipped_ranges->ranges[i]), - 0, &end_line, &end_column, 0); + clang_getFileLocation(clang_getRangeStart(skipped_ranges->ranges[i]), 0, + &start_line, &start_column, 0); + clang_getFileLocation(clang_getRangeEnd(skipped_ranges->ranges[i]), 0, + &end_line, &end_column, 0); printf("Skipping: "); PrintExtent(stdout, start_line, start_column, end_line, end_column); printf("\n"); @@ -4351,10 +4349,10 @@ int perform_token_annotation(int argc, const char **argv) { case CXToken_Literal: kind = "Literal"; break; case CXToken_Comment: kind = "Comment"; break; } - clang_getSpellingLocation(clang_getRangeStart(extent), - 0, &start_line, &start_column, 0); - clang_getSpellingLocation(clang_getRangeEnd(extent), - 0, &end_line, &end_column, 0); + clang_getFileLocation(clang_getRangeStart(extent), 0, &start_line, + &start_column, 0); + clang_getFileLocation(clang_getRangeEnd(extent), 0, &end_line, &end_column, + 0); printf("%s: \"%s\" ", kind, clang_getCString(spelling)); clang_disposeString(spelling); PrintExtent(stdout, start_line, start_column, end_line, end_column); diff --git a/clang/tools/clang-installapi/Options.cpp b/clang/tools/clang-installapi/Options.cpp index 191e944ae91e036ea2d8c17f8019da19587f019f..ae5b697b8eb9e00171488b17c2a24ac88ffbea03 100644 --- a/clang/tools/clang-installapi/Options.cpp +++ b/clang/tools/clang-installapi/Options.cpp @@ -594,9 +594,7 @@ getInterfaceFile(const StringRef Filename) { std::unique_ptr IF; switch (identify_magic(Buffer->getBuffer())) { case file_magic::macho_dynamically_linked_shared_lib: - LLVM_FALLTHROUGH; case file_magic::macho_dynamically_linked_shared_lib_stub: - LLVM_FALLTHROUGH; case file_magic::macho_universal_binary: return DylibReader::get(Buffer->getMemBufferRef()); break; diff --git a/clang/tools/clang-repl/CMakeLists.txt b/clang/tools/clang-repl/CMakeLists.txt index d3dec1984b78d2834bf9ab7cafd46f2fbfbcbce2..2b7d5f01418919eca4dbb03c810d624c7ea87ae7 100644 --- a/clang/tools/clang-repl/CMakeLists.txt +++ b/clang/tools/clang-repl/CMakeLists.txt @@ -11,6 +11,65 @@ add_clang_tool(clang-repl ClangRepl.cpp ) +if(MSVC) + set_target_properties(clang-repl PROPERTIES WINDOWS_EXPORT_ALL_SYMBOLS 1) + + # RTTI/C++ symbols + set(clang_repl_exports ${clang_repl_exports} ??_7type_info@@6B@ + ?__type_info_root_node@@3U__type_info_node@@A + ?nothrow@std@@3Unothrow_t@1@B + ) + + # Compiler added symbols for static variables. NOT for VStudio < 2015 + set(clang_repl_exports ${clang_repl_exports} _Init_thread_abort _Init_thread_epoch + _Init_thread_footer _Init_thread_header _tls_index + ) + + if(CMAKE_SIZEOF_VOID_P EQUAL 8) + # new/delete variants needed when linking to static msvc runtime (esp. Debug) + set(clang_repl_exports ${clang_repl_exports} + ??2@YAPEAX_K@Z + ??3@YAXPEAX@Z + ??_U@YAPEAX_K@Z + ??_V@YAXPEAX@Z + ??3@YAXPEAX_K@Z + ??6?$basic_ostream@DU?$char_traits@D@std@@@std@@QEAAAEAV01@H@Z + ??6?$basic_ostream@DU?$char_traits@D@std@@@std@@QEAAAEAV01@M@Z + ??6?$basic_ostream@DU?$char_traits@D@std@@@std@@QEAAAEAV01@N@Z + ??6?$basic_ostream@DU?$char_traits@D@std@@@std@@QEAAAEAV01@PEBX@Z + ??6?$basic_ostream@DU?$char_traits@D@std@@@std@@QEAAAEAV01@P6AAEAV01@AEAV01@@Z@Z + ??$?6U?$char_traits@D@std@@@std@@YAAEAV?$basic_ostream@DU?$char_traits@D@std@@@0@AEAV10@D@Z + ??$?6U?$char_traits@D@std@@@std@@YAAEAV?$basic_ostream@DU?$char_traits@D@std@@@0@AEAV10@PEBD@Z + ?_Facet_Register@std@@YAXPEAV_Facet_base@1@@Z + ) + else() + set(clang_repl_exports ${clang_repl_exports} + ??2@YAPAXI@Z + ??3@YAXPAX@Z + ??3@YAXPAXI@Z + ??_U@YAPAXI@Z + ??_V@YAXPAX@Z + ??_V@YAXPAXI@Z + ??6?$basic_ostream@DU?$char_traits@D@std@@@std@@QAEAAV01@H@Z + ??6?$basic_ostream@DU?$char_traits@D@std@@@std@@QAEAAV01@M@Z + ??6?$basic_ostream@DU?$char_traits@D@std@@@std@@QAEAAV01@N@Z + ??6?$basic_ostream@DU?$char_traits@D@std@@@std@@QAEAAV01@PBX@Z + ??6?$basic_ostream@DU?$char_traits@D@std@@@std@@QAEAAV01@P6AAAV01@AAV01@@Z@Z + ??$?6U?$char_traits@D@std@@@std@@YAAAV?$basic_ostream@DU?$char_traits@D@std@@@0@AAV10@D@Z + ??$?6U?$char_traits@D@std@@@std@@YAAAV?$basic_ostream@DU?$char_traits@D@std@@@0@AAV10@PBD@Z + ?_Facet_Register@std@@YAXPAV_Facet_base@1@@Z + ) + endif() + + # List to '/EXPORT:sym0 /EXPORT:sym1 /EXPORT:sym2 ...' + foreach(sym ${clang_repl_exports}) + set(clang_repl_link_str "${clang_repl_link_str} /EXPORT:${sym}") + endforeach(sym ${clang_repl_exports}) + + set_property(TARGET clang-repl APPEND_STRING PROPERTY LINK_FLAGS ${clang_repl_link_str}) + +endif(MSVC) + clang_target_link_libraries(clang-repl PRIVATE clangAST clangBasic diff --git a/clang/tools/clang-repl/ClangRepl.cpp b/clang/tools/clang-repl/ClangRepl.cpp index aecf61b97fc7192cf7897b5b4d3ae53ceceb895f..9cfc70462893dd6420c190ad70c3328f1a2372fe 100644 --- a/clang/tools/clang-repl/ClangRepl.cpp +++ b/clang/tools/clang-repl/ClangRepl.cpp @@ -215,13 +215,15 @@ int main(int argc, const char **argv) { } else Interp = ExitOnErr(clang::Interpreter::create(std::move(CI))); + bool HasError = false; + for (const std::string &input : OptInputs) { - if (auto Err = Interp->ParseAndExecute(input)) + if (auto Err = Interp->ParseAndExecute(input)) { llvm::logAllUnhandledErrors(std::move(Err), llvm::errs(), "error: "); + HasError = true; + } } - bool HasError = false; - if (OptInputs.empty()) { llvm::LineEditor LE("clang-repl"); std::string Input; @@ -241,18 +243,13 @@ int main(int argc, const char **argv) { break; } if (Input == R"(%undo)") { - if (auto Err = Interp->Undo()) { + if (auto Err = Interp->Undo()) llvm::logAllUnhandledErrors(std::move(Err), llvm::errs(), "error: "); - HasError = true; - } } else if (Input.rfind("%lib ", 0) == 0) { - if (auto Err = Interp->LoadDynamicLibrary(Input.data() + 5)) { + if (auto Err = Interp->LoadDynamicLibrary(Input.data() + 5)) llvm::logAllUnhandledErrors(std::move(Err), llvm::errs(), "error: "); - HasError = true; - } } else if (auto Err = Interp->ParseAndExecute(Input)) { llvm::logAllUnhandledErrors(std::move(Err), llvm::errs(), "error: "); - HasError = true; } Input = ""; diff --git a/clang/tools/driver/cc1_main.cpp b/clang/tools/driver/cc1_main.cpp index b5c6be3c557bb374c1f5f835d692db80634cae3f..2aebc6d3c017826447cd181789cf1d553864e960 100644 --- a/clang/tools/driver/cc1_main.cpp +++ b/clang/tools/driver/cc1_main.cpp @@ -39,7 +39,6 @@ #include "llvm/Support/ManagedStatic.h" #include "llvm/Support/Path.h" #include "llvm/Support/Process.h" -#include "llvm/Support/RISCVISAInfo.h" #include "llvm/Support/Signals.h" #include "llvm/Support/TargetSelect.h" #include "llvm/Support/TimeProfiler.h" @@ -48,6 +47,7 @@ #include "llvm/Target/TargetMachine.h" #include "llvm/TargetParser/AArch64TargetParser.h" #include "llvm/TargetParser/ARMTargetParser.h" +#include "llvm/TargetParser/RISCVISAInfo.h" #include #ifdef CLANG_HAVE_RLIMITS diff --git a/clang/tools/libclang/CIndex.cpp b/clang/tools/libclang/CIndex.cpp index 74163f30e19b1dca7fae73c145b5bef39cccada5..398a11a57035586c51bbfaa4f98ab63d87aa9d83 100644 --- a/clang/tools/libclang/CIndex.cpp +++ b/clang/tools/libclang/CIndex.cpp @@ -5713,8 +5713,8 @@ CXString clang_getCursorKindSpelling(enum CXCursorKind Kind) { return cxstring::createRef("UnaryOperator"); case CXCursor_ArraySubscriptExpr: return cxstring::createRef("ArraySubscriptExpr"); - case CXCursor_OMPArraySectionExpr: - return cxstring::createRef("OMPArraySectionExpr"); + case CXCursor_ArraySectionExpr: + return cxstring::createRef("ArraySectionExpr"); case CXCursor_OMPArrayShapingExpr: return cxstring::createRef("OMPArrayShapingExpr"); case CXCursor_OMPIteratorExpr: diff --git a/clang/tools/libclang/CXCursor.cpp b/clang/tools/libclang/CXCursor.cpp index 454bf75498618962812d27c4cb6dc734baec62ac..9325a16d2a8486a3659accad055fb3d66c31f172 100644 --- a/clang/tools/libclang/CXCursor.cpp +++ b/clang/tools/libclang/CXCursor.cpp @@ -423,8 +423,8 @@ CXCursor cxcursor::MakeCXCursor(const Stmt *S, const Decl *Parent, K = CXCursor_UnexposedExpr; break; - case Stmt::OMPArraySectionExprClass: - K = CXCursor_OMPArraySectionExpr; + case Stmt::ArraySectionExprClass: + K = CXCursor_ArraySectionExpr; break; case Stmt::OMPArrayShapingExprClass: diff --git a/clang/tools/libclang/CXSourceLocation.cpp b/clang/tools/libclang/CXSourceLocation.cpp index ba70cbfee8995f25b9cef3e5f0cf59606331eb27..53cb71f7276f29913894e73b584865a12860cad7 100644 --- a/clang/tools/libclang/CXSourceLocation.cpp +++ b/clang/tools/libclang/CXSourceLocation.cpp @@ -319,8 +319,7 @@ void clang_getSpellingLocation(CXSourceLocation location, const SourceManager &SM = *static_cast(location.ptr_data[0]); - // FIXME: This should call SourceManager::getSpellingLoc(). - SourceLocation SpellLoc = SM.getFileLoc(Loc); + SourceLocation SpellLoc = SM.getSpellingLoc(Loc); std::pair LocInfo = SM.getDecomposedLoc(SpellLoc); FileID FID = LocInfo.first; unsigned FileOffset = LocInfo.second; diff --git a/clang/unittests/Analysis/FlowSensitive/TransferTest.cpp b/clang/unittests/Analysis/FlowSensitive/TransferTest.cpp index 215e208615ac239d1d6f3ba489c3bf8691698125..301bec32c0cf1ddc7a358d5fa22df7116d43025a 100644 --- a/clang/unittests/Analysis/FlowSensitive/TransferTest.cpp +++ b/clang/unittests/Analysis/FlowSensitive/TransferTest.cpp @@ -3309,6 +3309,28 @@ TEST(TransferTest, ResultObjectLocationPropagatesThroughConditionalOperator) { }); } +TEST(TransferTest, ResultObjectLocationDontVisitNestedRecordDecl) { + // This is a crash repro. + // We used to crash because when propagating result objects, we would visit + // nested record and function declarations, but we don't model fields used + // only in these. + std::string Code = R"( + struct S1 {}; + struct S2 { S1 s1; }; + void target() { + struct Nested { + void f() { + S2 s2 = { S1() }; + } + }; + } + )"; + runDataflow( + Code, + [](const llvm::StringMap> &Results, + ASTContext &ASTCtx) {}); +} + TEST(TransferTest, StaticCast) { std::string Code = R"( void target(int Foo) { @@ -3348,20 +3370,11 @@ TEST(TransferTest, IntegralCast) { Code, [](const llvm::StringMap> &Results, ASTContext &ASTCtx) { - ASSERT_THAT(Results.keys(), UnorderedElementsAre("p")); const Environment &Env = getEnvironmentAtAnnotation(Results, "p"); - const ValueDecl *FooDecl = findValueDecl(ASTCtx, "Foo"); - ASSERT_THAT(FooDecl, NotNull()); - - const ValueDecl *BarDecl = findValueDecl(ASTCtx, "Bar"); - ASSERT_THAT(BarDecl, NotNull()); - - const auto *FooVal = Env.getValue(*FooDecl); - const auto *BarVal = Env.getValue(*BarDecl); - EXPECT_TRUE(isa(FooVal)); - EXPECT_TRUE(isa(BarVal)); - EXPECT_EQ(FooVal, BarVal); + const auto &FooVal = getValueForDecl(ASTCtx, Env, "Foo"); + const auto &BarVal = getValueForDecl(ASTCtx, Env, "Bar"); + EXPECT_EQ(&FooVal, &BarVal); }); } @@ -3376,17 +3389,10 @@ TEST(TransferTest, IntegraltoBooleanCast) { Code, [](const llvm::StringMap> &Results, ASTContext &ASTCtx) { - ASSERT_THAT(Results.keys(), UnorderedElementsAre("p")); const Environment &Env = getEnvironmentAtAnnotation(Results, "p"); - const ValueDecl *FooDecl = findValueDecl(ASTCtx, "Foo"); - ASSERT_THAT(FooDecl, NotNull()); - - const ValueDecl *BarDecl = findValueDecl(ASTCtx, "Bar"); - ASSERT_THAT(BarDecl, NotNull()); - - const auto *FooVal = Env.getValue(*FooDecl); - const auto *BarVal = Env.getValue(*BarDecl); + const auto &FooVal = getValueForDecl(ASTCtx, Env, "Foo"); + const auto &BarVal = getValueForDecl(ASTCtx, Env, "Bar"); EXPECT_TRUE(isa(FooVal)); EXPECT_TRUE(isa(BarVal)); }); @@ -3404,23 +3410,38 @@ TEST(TransferTest, IntegralToBooleanCastFromBool) { Code, [](const llvm::StringMap> &Results, ASTContext &ASTCtx) { - ASSERT_THAT(Results.keys(), UnorderedElementsAre("p")); const Environment &Env = getEnvironmentAtAnnotation(Results, "p"); - const ValueDecl *FooDecl = findValueDecl(ASTCtx, "Foo"); - ASSERT_THAT(FooDecl, NotNull()); - - const ValueDecl *BarDecl = findValueDecl(ASTCtx, "Bar"); - ASSERT_THAT(BarDecl, NotNull()); - - const auto *FooVal = Env.getValue(*FooDecl); - const auto *BarVal = Env.getValue(*BarDecl); - EXPECT_TRUE(isa(FooVal)); - EXPECT_TRUE(isa(BarVal)); - EXPECT_EQ(FooVal, BarVal); + const auto &FooVal = getValueForDecl(ASTCtx, Env, "Foo"); + const auto &BarVal = getValueForDecl(ASTCtx, Env, "Bar"); + EXPECT_EQ(&FooVal, &BarVal); }); } +TEST(TransferTest, WidenBoolValueInIntegerVariable) { + // This is a crash repro. + // This test sets up a case where we perform widening on an integer variable + // that contains a `BoolValue` for the previous iteration and an + // `IntegerValue` for the current iteration. We used to crash on this because + // `widenDistinctValues()` assumed that if the previous iteration had a + // `BoolValue`, the current iteration would too. + // FIXME: The real fix here is to make sure we never store `BoolValue`s in + // integer variables; see also the comment in `widenDistinctValues()`. + std::string Code = R"cc( + struct S { + int i; + S *next; + }; + void target(S *s) { + for (; s; s = s->next) + s->i = false; + } + )cc"; + runDataflow(Code, + [](const llvm::StringMap> &, + ASTContext &) {}); +} + TEST(TransferTest, NullToPointerCast) { std::string Code = R"( using my_nullptr_t = decltype(nullptr); @@ -5336,6 +5357,38 @@ TEST(TransferTest, ConditionalOperatorLocation) { }); } +TEST(TransferTest, ConditionalOperatorOnConstantExpr) { + // This is a regression test: We used to crash when a `ConstantExpr` was used + // in the branches of a conditional operator. + std::string Code = R"cc( + consteval bool identity(bool B) { return B; } + void target(bool Cond) { + bool JoinTrueTrue = Cond ? identity(true) : identity(true); + bool JoinTrueFalse = Cond ? identity(true) : identity(false); + // [[p]] + } + )cc"; + runDataflow( + Code, + [](const llvm::StringMap> &Results, + ASTContext &ASTCtx) { + Environment Env = getEnvironmentAtAnnotation(Results, "p").fork(); + + auto &JoinTrueTrue = + getValueForDecl(ASTCtx, Env, "JoinTrueTrue"); + // FIXME: This test documents the current behavior, namely that we + // don't actually use the constant result of the `ConstantExpr` and + // instead treat it like a normal function call. + EXPECT_EQ(JoinTrueTrue.formula().kind(), Formula::Kind::AtomRef); + // EXPECT_TRUE(JoinTrueTrue.formula().literal()); + + auto &JoinTrueFalse = + getValueForDecl(ASTCtx, Env, "JoinTrueFalse"); + EXPECT_EQ(JoinTrueFalse.formula().kind(), Formula::Kind::AtomRef); + }, + LangStandard::lang_cxx20); +} + TEST(TransferTest, IfStmtBranchExtendsFlowCondition) { std::string Code = R"( void target(bool Foo) { diff --git a/clang/unittests/Format/SortIncludesTest.cpp b/clang/unittests/Format/SortIncludesTest.cpp index 772eb53806b4b115add911062a5d2451d09c9fe6..824fa0078cd037e9f578d1c824393f071a813cc4 100644 --- a/clang/unittests/Format/SortIncludesTest.cpp +++ b/clang/unittests/Format/SortIncludesTest.cpp @@ -6,19 +6,19 @@ // //===----------------------------------------------------------------------===// -#include "FormatTestUtils.h" +#include "FormatTestBase.h" #include "clang/Format/Format.h" #include "llvm/ADT/StringRef.h" #include "llvm/Support/Debug.h" #include "gtest/gtest.h" -#define DEBUG_TYPE "format-test" +#define DEBUG_TYPE "sort-includes-test" namespace clang { namespace format { namespace { -class SortIncludesTest : public ::testing::Test { +class SortIncludesTest : public test::FormatTestBase { protected: std::vector GetCodeRange(StringRef Code) { return std::vector(1, tooling::Range(0, Code.size())); @@ -821,6 +821,122 @@ TEST_F(SortIncludesTest, CalculatesCorrectCursorPositionWithRegrouping) { EXPECT_EQ(27u, newCursor(Code, 28)); // Start of last line } +TEST_F(SortIncludesTest, + CalculatesCorrectCursorPositionWhenNoReplacementsWithRegroupingAndCRLF) { + Style.IncludeBlocks = Style.IBS_Regroup; + FmtStyle.LineEnding = FormatStyle::LE_CRLF; + Style.IncludeCategories = { + {"^\"a\"", 0, 0, false}, {"^\"b\"", 1, 1, false}, {".*", 2, 2, false}}; + std::string Code = "#include \"a\"\r\n" // Start of line: 0 + "\r\n" // Start of line: 14 + "#include \"b\"\r\n" // Start of line: 16 + "\r\n" // Start of line: 30 + "#include \"c\"\r\n" // Start of line: 32 + "\r\n" // Start of line: 46 + "int i;"; // Start of line: 48 + verifyNoChange(Code); + EXPECT_EQ(0u, newCursor(Code, 0)); + EXPECT_EQ(14u, newCursor(Code, 14)); + EXPECT_EQ(16u, newCursor(Code, 16)); + EXPECT_EQ(30u, newCursor(Code, 30)); + EXPECT_EQ(32u, newCursor(Code, 32)); + EXPECT_EQ(46u, newCursor(Code, 46)); + EXPECT_EQ(48u, newCursor(Code, 48)); +} + +TEST_F( + SortIncludesTest, + CalculatesCorrectCursorPositionWhenRemoveLinesReplacementsWithRegroupingAndCRLF) { + Style.IncludeBlocks = Style.IBS_Regroup; + FmtStyle.LineEnding = FormatStyle::LE_CRLF; + Style.IncludeCategories = {{".*", 0, 0, false}}; + std::string Code = "#include \"a\"\r\n" // Start of line: 0 + "\r\n" // Start of line: 14 + "#include \"b\"\r\n" // Start of line: 16 + "\r\n" // Start of line: 30 + "#include \"c\"\r\n" // Start of line: 32 + "\r\n" // Start of line: 46 + "int i;"; // Start of line: 48 + std::string Expected = "#include \"a\"\r\n" // Start of line: 0 + "#include \"b\"\r\n" // Start of line: 14 + "#include \"c\"\r\n" // Start of line: 28 + "\r\n" // Start of line: 42 + "int i;"; // Start of line: 44 + EXPECT_EQ(Expected, sort(Code)); + EXPECT_EQ(0u, newCursor(Code, 0)); + EXPECT_EQ( + 14u, + newCursor(Code, 14)); // cursor on empty line in include block is ignored + EXPECT_EQ(14u, newCursor(Code, 16)); + EXPECT_EQ( + 30u, + newCursor(Code, 30)); // cursor on empty line in include block is ignored + EXPECT_EQ(28u, newCursor(Code, 32)); + EXPECT_EQ(42u, newCursor(Code, 46)); + EXPECT_EQ(44u, newCursor(Code, 48)); +} + +// FIXME: the tests below should pass. +#if 0 +TEST_F( + SortIncludesTest, + CalculatesCorrectCursorPositionWhenNewLineReplacementsWithRegroupingAndCRLF) { + Style.IncludeBlocks = Style.IBS_Regroup; + FmtStyle.LineEnding = FormatStyle::LE_CRLF; + Style.IncludeCategories = { + {"^\"a\"", 0, 0, false}, {"^\"b\"", 1, 1, false}, {".*", 2, 2, false}}; + std::string Code = "#include \"a\"\r\n" // Start of line: 0 + "#include \"b\"\r\n" // Start of line: 14 + "#include \"c\"\r\n" // Start of line: 28 + "\r\n" // Start of line: 42 + "int i;"; // Start of line: 44 + std::string Expected = "#include \"a\"\r\n" // Start of line: 0 + "\r\n" // Start of line: 14 + "#include \"b\"\r\n" // Start of line: 16 + "\r\n" // Start of line: 30 + "#include \"c\"\r\n" // Start of line: 32 + "\r\n" // Start of line: 46 + "int i;"; // Start of line: 48 + EXPECT_EQ(Expected, sort(Code)); + EXPECT_EQ(0u, newCursor(Code, 0)); + EXPECT_EQ(15u, newCursor(Code, 16)); + EXPECT_EQ(30u, newCursor(Code, 32)); + EXPECT_EQ(44u, newCursor(Code, 46)); + EXPECT_EQ(46u, newCursor(Code, 48)); +} + +TEST_F( + SortIncludesTest, + CalculatesCorrectCursorPositionWhenNoNewLineReplacementsWithRegroupingAndCRLF) { + Style.IncludeBlocks = Style.IBS_Regroup; + FmtStyle.LineEnding = FormatStyle::LE_CRLF; + Style.IncludeCategories = { + {"^\"a\"", 0, 0, false}, {"^\"b\"", 1, 1, false}, {".*", 2, 2, false}}; + std::string Code = "#include \"a\"\r\n" // Start of line: 0 + "\r\n" // Start of line: 14 + "#include \"c\"\r\n" // Start of line: 16 + "\r\n" // Start of line: 30 + "#include \"b\"\r\n" // Start of line: 32 + "\r\n" // Start of line: 46 + "int i;"; // Start of line: 48 + std::string Expected = "#include \"a\"\r\n" // Start of line: 0 + "\r\n" // Start of line: 14 + "#include \"b\"\r\n" // Start of line: 16 + "\r\n" // Start of line: 30 + "#include \"c\"\r\n" // Start of line: 32 + "\r\n" // Start of line: 46 + "int i;"; // Start of line: 48 + EXPECT_EQ(Expected, sort(Code)); + EXPECT_EQ(0u, newCursor(Code, 0)); + EXPECT_EQ(14u, newCursor(Code, 14)); + EXPECT_EQ(30u, newCursor(Code, 32)); + EXPECT_EQ(30u, newCursor(Code, 30)); + EXPECT_EQ(15u, newCursor(Code, 15)); + EXPECT_EQ(44u, newCursor(Code, 46)); + EXPECT_EQ(46u, newCursor(Code, 48)); +} +#endif + TEST_F(SortIncludesTest, DeduplicateIncludes) { EXPECT_EQ("#include \n" "#include \n" diff --git a/clang/unittests/Format/TokenAnnotatorTest.cpp b/clang/unittests/Format/TokenAnnotatorTest.cpp index 34999b7376397b62c74f239f18da88544fa0308d..dff5251d2e94065d4aae4c00ce1c4b929b655b97 100644 --- a/clang/unittests/Format/TokenAnnotatorTest.cpp +++ b/clang/unittests/Format/TokenAnnotatorTest.cpp @@ -2855,6 +2855,83 @@ TEST_F(TokenAnnotatorTest, BraceKind) { ASSERT_EQ(Tokens.size(), 18u) << Tokens; EXPECT_BRACE_KIND(Tokens[8], BK_BracedInit); EXPECT_BRACE_KIND(Tokens[16], BK_BracedInit); + + Tokens = annotate("struct {};"); + ASSERT_EQ(Tokens.size(), 5u) << Tokens; + EXPECT_BRACE_KIND(Tokens[1], BK_Block); + EXPECT_BRACE_KIND(Tokens[2], BK_Block); + + Tokens = annotate("struct : Base {};"); + ASSERT_EQ(Tokens.size(), 7u) << Tokens; + EXPECT_BRACE_KIND(Tokens[3], BK_Block); + EXPECT_BRACE_KIND(Tokens[4], BK_Block); + + Tokens = annotate("struct Foo {};"); + ASSERT_EQ(Tokens.size(), 6u) << Tokens; + EXPECT_BRACE_KIND(Tokens[2], BK_Block); + EXPECT_BRACE_KIND(Tokens[3], BK_Block); + + Tokens = annotate("struct ::Foo {};"); + ASSERT_EQ(Tokens.size(), 7u) << Tokens; + EXPECT_BRACE_KIND(Tokens[3], BK_Block); + EXPECT_BRACE_KIND(Tokens[4], BK_Block); + + Tokens = annotate("struct NS::Foo {};"); + ASSERT_EQ(Tokens.size(), 8u) << Tokens; + EXPECT_BRACE_KIND(Tokens[4], BK_Block); + EXPECT_BRACE_KIND(Tokens[5], BK_Block); + + Tokens = annotate("struct Foo {};"); + ASSERT_EQ(Tokens.size(), 9u) << Tokens; + EXPECT_BRACE_KIND(Tokens[5], BK_Block); + EXPECT_BRACE_KIND(Tokens[6], BK_Block); + + Tokens = annotate("struct Foo final {};"); + ASSERT_EQ(Tokens.size(), 7u) << Tokens; + EXPECT_BRACE_KIND(Tokens[3], BK_Block); + EXPECT_BRACE_KIND(Tokens[4], BK_Block); + + Tokens = annotate("struct [[foo]] [[bar]] Foo final : Base1, Base2 {};"); + ASSERT_EQ(Tokens.size(), 21u) << Tokens; + EXPECT_BRACE_KIND(Tokens[17], BK_Block); + EXPECT_BRACE_KIND(Tokens[18], BK_Block); + + Tokens = annotate("struct Foo x{};"); + ASSERT_EQ(Tokens.size(), 7u) << Tokens; + EXPECT_BRACE_KIND(Tokens[3], BK_BracedInit); + EXPECT_BRACE_KIND(Tokens[4], BK_BracedInit); + + Tokens = annotate("struct ::Foo x{};"); + ASSERT_EQ(Tokens.size(), 8u) << Tokens; + EXPECT_BRACE_KIND(Tokens[4], BK_BracedInit); + EXPECT_BRACE_KIND(Tokens[5], BK_BracedInit); + + Tokens = annotate("struct NS::Foo x{};"); + ASSERT_EQ(Tokens.size(), 9u) << Tokens; + EXPECT_BRACE_KIND(Tokens[5], BK_BracedInit); + EXPECT_BRACE_KIND(Tokens[6], BK_BracedInit); + + Tokens = annotate("struct Foo x{};"); + ASSERT_EQ(Tokens.size(), 10u) << Tokens; + EXPECT_BRACE_KIND(Tokens[6], BK_BracedInit); + EXPECT_BRACE_KIND(Tokens[7], BK_BracedInit); + + Tokens = annotate("#ifdef DEBUG_ENABLED\n" + "#else\n" + "#endif\n" + "class RenderingServer : Object {\n" + "#ifndef DISABLE_DEPRECATED\n" + " enum Features {\n" + " FEATURE_SHADERS,\n" + " FEATURE_MULTITHREADED,\n" + " };\n" + "#endif\n" + "};"); + ASSERT_EQ(Tokens.size(), 29u) << Tokens; + EXPECT_BRACE_KIND(Tokens[11], BK_Block); + EXPECT_BRACE_KIND(Tokens[17], BK_Block); + EXPECT_BRACE_KIND(Tokens[22], BK_Block); + EXPECT_BRACE_KIND(Tokens[26], BK_Block); } TEST_F(TokenAnnotatorTest, UnderstandsElaboratedTypeSpecifier) { diff --git a/clang/unittests/Interpreter/CMakeLists.txt b/clang/unittests/Interpreter/CMakeLists.txt index e5a77e77de75cdbafd99f878e0dbdd51f1e3e391..bc831d33bf3d54b8de0f6453a359dcb5d4323313 100644 --- a/clang/unittests/Interpreter/CMakeLists.txt +++ b/clang/unittests/Interpreter/CMakeLists.txt @@ -29,3 +29,62 @@ if(NOT WIN32) endif() export_executable_symbols(ClangReplInterpreterTests) + +if(MSVC) + set_target_properties(ClangReplInterpreterTests PROPERTIES WINDOWS_EXPORT_ALL_SYMBOLS 1) + + # RTTI/C++ symbols + set(ClangReplInterpreterTests_exports ${ClangReplInterpreterTests_exports} ??_7type_info@@6B@ + ?__type_info_root_node@@3U__type_info_node@@A + ?nothrow@std@@3Unothrow_t@1@B + ) + + # Compiler added symbols for static variables. NOT for VStudio < 2015 + set(ClangReplInterpreterTests_exports ${ClangReplInterpreterTests_exports} _Init_thread_abort _Init_thread_epoch + _Init_thread_footer _Init_thread_header _tls_index + ) + + if(CMAKE_SIZEOF_VOID_P EQUAL 8) + # new/delete variants needed when linking to static msvc runtime (esp. Debug) + set(ClangReplInterpreterTests_exports ${ClangReplInterpreterTests_exports} + ??2@YAPEAX_K@Z + ??3@YAXPEAX@Z + ??_U@YAPEAX_K@Z + ??_V@YAXPEAX@Z + ??3@YAXPEAX_K@Z + ??6?$basic_ostream@DU?$char_traits@D@std@@@std@@QEAAAEAV01@H@Z + ??6?$basic_ostream@DU?$char_traits@D@std@@@std@@QEAAAEAV01@M@Z + ??6?$basic_ostream@DU?$char_traits@D@std@@@std@@QEAAAEAV01@N@Z + ??6?$basic_ostream@DU?$char_traits@D@std@@@std@@QEAAAEAV01@PEBX@Z + ??6?$basic_ostream@DU?$char_traits@D@std@@@std@@QEAAAEAV01@P6AAEAV01@AEAV01@@Z@Z + ??$?6U?$char_traits@D@std@@@std@@YAAEAV?$basic_ostream@DU?$char_traits@D@std@@@0@AEAV10@D@Z + ??$?6U?$char_traits@D@std@@@std@@YAAEAV?$basic_ostream@DU?$char_traits@D@std@@@0@AEAV10@PEBD@Z + ?_Facet_Register@std@@YAXPEAV_Facet_base@1@@Z + ) + else() + set(ClangReplInterpreterTests_exports ${ClangReplInterpreterTests_exports} + ??2@YAPAXI@Z + ??3@YAXPAX@Z + ??3@YAXPAXI@Z + ??_U@YAPAXI@Z + ??_V@YAXPAX@Z + ??_V@YAXPAXI@Z + ??6?$basic_ostream@DU?$char_traits@D@std@@@std@@QAEAAV01@H@Z + ??6?$basic_ostream@DU?$char_traits@D@std@@@std@@QAEAAV01@M@Z + ??6?$basic_ostream@DU?$char_traits@D@std@@@std@@QAEAAV01@N@Z + ??6?$basic_ostream@DU?$char_traits@D@std@@@std@@QAEAAV01@PBX@Z + ??6?$basic_ostream@DU?$char_traits@D@std@@@std@@QAEAAV01@P6AAAV01@AAV01@@Z@Z + ??$?6U?$char_traits@D@std@@@std@@YAAAV?$basic_ostream@DU?$char_traits@D@std@@@0@AAV10@D@Z + ??$?6U?$char_traits@D@std@@@std@@YAAAV?$basic_ostream@DU?$char_traits@D@std@@@0@AAV10@PBD@Z + ?_Facet_Register@std@@YAXPAV_Facet_base@1@@Z + ) + endif() + + # List to '/EXPORT:sym0 /EXPORT:sym1 /EXPORT:sym2 ...' + foreach(sym ${ClangReplInterpreterTests_exports}) + set(ClangReplInterpreterTests_link_str "${ClangReplInterpreterTests_link_str} /EXPORT:${sym}") + endforeach(sym ${ClangReplInterpreterTests_exports}) + + set_property(TARGET ClangReplInterpreterTests APPEND_STRING PROPERTY LINK_FLAGS ${ClangReplInterpreterTests_link_str}) + +endif(MSVC) diff --git a/clang/unittests/StaticAnalyzer/CallEventTest.cpp b/clang/unittests/StaticAnalyzer/CallEventTest.cpp index adbfe02a284dc51d44bcc460e39864d529cee4d4..7c4132788ca7e502a8f5013c4ed12a1284b53208 100644 --- a/clang/unittests/StaticAnalyzer/CallEventTest.cpp +++ b/clang/unittests/StaticAnalyzer/CallEventTest.cpp @@ -76,7 +76,7 @@ TEST(CXXDeallocatorCall, SimpleDestructor) { } )", Diags)); - EXPECT_EQ(Diags, "test.CXXDeallocator: NumArgs: 1\n"); + EXPECT_EQ(Diags, "test.CXXDeallocator: NumArgs: 2\n"); } } // namespace diff --git a/clang/unittests/libclang/LibclangTest.cpp b/clang/unittests/libclang/LibclangTest.cpp index 87075a46d75187b0d8a1e2c3fa4be877a93f00ae..6de4d02bf74f4ffc5c983ae69f1a340bf4d40540 100644 --- a/clang/unittests/libclang/LibclangTest.cpp +++ b/clang/unittests/libclang/LibclangTest.cpp @@ -1292,6 +1292,37 @@ void func() {} EXPECT_EQ(attrCount, 1); } +TEST_F(LibclangParseTest, clang_getSpellingLocation) { + std::string fileName = "main.c"; + WriteFile(fileName, "#define X(value) int x = value;\nX(42)\n"); + + ClangTU = clang_parseTranslationUnit(Index, fileName.c_str(), nullptr, 0, + nullptr, 0, TUFlags); + + int declarationCount = 0; + Traverse([&declarationCount](CXCursor cursor, + CXCursor parent) -> CXChildVisitResult { + if (cursor.kind == CXCursor_VarDecl) { + declarationCount++; + + CXSourceLocation cxl = clang_getCursorLocation(cursor); + unsigned line; + + // We expect clang_getFileLocation to return the expansion location, + // whereas clang_getSpellingLocation should resolve the macro expansion + // and return the location of the macro definition. + clang_getFileLocation(cxl, nullptr, &line, nullptr, nullptr); + EXPECT_EQ(line, 2U); + clang_getSpellingLocation(cxl, nullptr, &line, nullptr, nullptr); + EXPECT_EQ(line, 1U); + } + + return CXChildVisit_Recurse; + }); + + EXPECT_EQ(declarationCount, 1); +} + class LibclangRewriteTest : public LibclangParseTest { public: CXRewriter Rew = nullptr; diff --git a/clang/utils/TableGen/RISCVVEmitter.cpp b/clang/utils/TableGen/RISCVVEmitter.cpp index 5e41ef9f9d2684037988014b79d87755847959d7..48cd83cabfc7d032bb207243fabe8ee2bfeef513 100644 --- a/clang/utils/TableGen/RISCVVEmitter.cpp +++ b/clang/utils/TableGen/RISCVVEmitter.cpp @@ -670,6 +670,7 @@ void RVVEmitter::createRVVIntrinsics( .Case("Zvksed", RVV_REQ_Zvksed) .Case("Zvksh", RVV_REQ_Zvksh) .Case("Zvfbfwma", RVV_REQ_Zvfbfwma) + .Case("Zvfbfmin", RVV_REQ_Zvfbfmin) .Case("Experimental", RVV_REQ_Experimental) .Default(RVV_REQ_None); assert(RequireExt != RVV_REQ_None && "Unrecognized required feature?"); diff --git a/clang/www/cxx_status.html b/clang/www/cxx_status.html index c233171e63c811748c852237a454c79403181be9..96705224ee4abc593ee99c444b2e5fd45956a8f3 100755 --- a/clang/www/cxx_status.html +++ b/clang/www/cxx_status.html @@ -1258,12 +1258,11 @@ code. This issue is expected to be rectified soon.

-(7): In Clang 3.7 and later, sized deallocation is only enabled -if the user passes the -fsized-deallocation flag. The user must -supply definitions of the sized deallocation functions, either by providing them -explicitly or by using a C++ standard library that does. libstdc++ -added these functions in version 5.0, and libc++ added them in -version 3.7. +(7): The user must supply definitions of the sized deallocation + functions, either by providing them explicitly or by using a C++ standard library + that does. libstdc++ added these functions in version 5.0, and + libc++ added them in version 3.7. The user can also use the + -fno-sized-deallocation option to disable sized deallocation.

diff --git a/compiler-rt/lib/fuzzer/build.sh b/compiler-rt/lib/fuzzer/build.sh index f7f329c0d19c765ca898338abe4dbd0c3153c013..f58fd9557ce3d5c0a670d88c54911f08f51efa03 100755 --- a/compiler-rt/lib/fuzzer/build.sh +++ b/compiler-rt/lib/fuzzer/build.sh @@ -2,7 +2,7 @@ LIBFUZZER_SRC_DIR=$(dirname $0) CXX="${CXX:-clang}" for f in $LIBFUZZER_SRC_DIR/*.cpp; do - $CXX -g -O2 -fno-omit-frame-pointer -std=c++14 $f -c & + $CXX -g -O2 -fno-omit-frame-pointer -std=c++17 $f -c & done wait rm -f libFuzzer.a diff --git a/compiler-rt/lib/sanitizer_common/sanitizer_symbolizer_markup.cpp b/compiler-rt/lib/sanitizer_common/sanitizer_symbolizer_markup.cpp index b2a1069a9a61cc1951d2df0a0ed452729117058c..31d91ef3c7392894295b80eecdc4df3a451c0732 100644 --- a/compiler-rt/lib/sanitizer_common/sanitizer_symbolizer_markup.cpp +++ b/compiler-rt/lib/sanitizer_common/sanitizer_symbolizer_markup.cpp @@ -28,7 +28,7 @@ void MarkupStackTracePrinter::RenderData(InternalScopedString *buffer, const char *format, const DataInfo *DI, const char *strip_path_prefix) { RenderContext(buffer); - buffer->AppendF(kFormatData, DI->start); + buffer->AppendF(kFormatData, reinterpret_cast(DI->start)); } bool MarkupStackTracePrinter::RenderNeedsSymbolization(const char *format) { @@ -43,12 +43,13 @@ void MarkupStackTracePrinter::RenderFrame(InternalScopedString *buffer, const char *strip_path_prefix) { CHECK(!RenderNeedsSymbolization(format)); RenderContext(buffer); - buffer->AppendF(kFormatFrame, frame_no, address); + buffer->AppendF(kFormatFrame, frame_no, reinterpret_cast(address)); } bool MarkupSymbolizerTool::SymbolizePC(uptr addr, SymbolizedStack *stack) { char buffer[kFormatFunctionMax]; - internal_snprintf(buffer, sizeof(buffer), kFormatFunction, addr); + internal_snprintf(buffer, sizeof(buffer), kFormatFunction, + reinterpret_cast(addr)); stack->info.function = internal_strdup(buffer); return true; } @@ -118,7 +119,8 @@ static void RenderMmaps(InternalScopedString *buffer, // module.base_address == dlpi_addr // range.beg == dlpi_addr + p_vaddr // relative address == p_vaddr == range.beg - module.base_address - buffer->AppendF(kFormatMmap, range.beg, range.end - range.beg, moduleId, + buffer->AppendF(kFormatMmap, reinterpret_cast(range.beg), + range.end - range.beg, static_cast(moduleId), accessBuffer.data(), range.beg - module.base_address()); buffer->Append("\n"); diff --git a/compiler-rt/lib/sanitizer_common/sanitizer_symbolizer_markup_constants.h b/compiler-rt/lib/sanitizer_common/sanitizer_symbolizer_markup_constants.h index 83643504e1289eab9da68731d9832312695dc2f0..a43661eaecf2ff348984c33b8518926dffb163b8 100644 --- a/compiler-rt/lib/sanitizer_common/sanitizer_symbolizer_markup_constants.h +++ b/compiler-rt/lib/sanitizer_common/sanitizer_symbolizer_markup_constants.h @@ -33,13 +33,13 @@ constexpr uptr kFormatFunctionMax = 64; // More than big enough for 64-bit hex. constexpr const char *kFormatData = "{{{data:%p}}}"; // One frame in a backtrace (printed on a line by itself). -constexpr const char *kFormatFrame = "{{{bt:%u:%p}}}"; +constexpr const char *kFormatFrame = "{{{bt:%d:%p}}}"; // Module contextual element. -constexpr const char *kFormatModule = "{{{module:%d:%s:elf:%s}}}"; +constexpr const char *kFormatModule = "{{{module:%zu:%s:elf:%s}}}"; // mmap for a module segment. -constexpr const char *kFormatMmap = "{{{mmap:%p:0x%x:load:%d:%s:0x%x}}}"; +constexpr const char *kFormatMmap = "{{{mmap:%p:0x%zx:load:%d:%s:0x%zx}}}"; // Dump trigger element. #define FORMAT_DUMPFILE "{{{dumpfile:%s:%s}}}" diff --git a/compiler-rt/lib/scudo/standalone/mem_map_fuchsia.cpp b/compiler-rt/lib/scudo/standalone/mem_map_fuchsia.cpp index 28e5a11a37f257318fc4fad94d0add526f3c1338..fc793abf44cda5cd14e4fff35750175ea69cbe26 100644 --- a/compiler-rt/lib/scudo/standalone/mem_map_fuchsia.cpp +++ b/compiler-rt/lib/scudo/standalone/mem_map_fuchsia.cpp @@ -84,6 +84,13 @@ static zx_handle_t getPlaceholderVmo() { return Vmo; } +// Checks if MAP_ALLOWNOMEM allows the given error code. +static bool IsNoMemError(zx_status_t Status) { + // Note: _zx_vmar_map returns ZX_ERR_NO_RESOURCES if the VMAR does not contain + // a suitable free spot. + return Status == ZX_ERR_NO_MEMORY || Status == ZX_ERR_NO_RESOURCES; +} + MemMapFuchsia::MemMapFuchsia(uptr Base, uptr Capacity) : MapAddr(Base), WindowBase(Base), WindowSize(Capacity) { // Create the VMO. @@ -101,9 +108,9 @@ bool MemMapFuchsia::mapImpl(UNUSED uptr Addr, uptr Size, const char *Name, // Create the VMO. zx_status_t Status = _zx_vmo_create(Size, 0, &Vmo); if (UNLIKELY(Status != ZX_OK)) { - if (Status != ZX_ERR_NO_MEMORY || !AllowNoMem) - dieOnError(Status, "zx_vmo_create", Size); - return false; + if (AllowNoMem && IsNoMemError(Status)) + return false; + dieOnError(Status, "zx_vmo_create", Size); } if (Name != nullptr) @@ -116,15 +123,15 @@ bool MemMapFuchsia::mapImpl(UNUSED uptr Addr, uptr Size, const char *Name, Status = _zx_vmar_map(_zx_vmar_root_self(), MapFlags, 0, Vmo, 0, Size, &MapAddr); if (UNLIKELY(Status != ZX_OK)) { - if (Status != ZX_ERR_NO_MEMORY || !AllowNoMem) - dieOnError(Status, "zx_vmar_map", Size); - - Status = _zx_handle_close(Vmo); - CHECK_EQ(Status, ZX_OK); + if (AllowNoMem && IsNoMemError(Status)) { + Status = _zx_handle_close(Vmo); + CHECK_EQ(Status, ZX_OK); - MapAddr = 0; - Vmo = ZX_HANDLE_INVALID; - return false; + MapAddr = 0; + Vmo = ZX_HANDLE_INVALID; + return false; + } + dieOnError(Status, "zx_vmar_map", Size); } if (PreCommit) { @@ -187,9 +194,9 @@ bool MemMapFuchsia::remapImpl(uptr Addr, uptr Size, const char *Name, _zx_vmar_map(_zx_vmar_root_self(), MapFlags, Addr - getRootVmarBase(), Vmo, Addr - MapAddr, Size, &MappedAddr); if (UNLIKELY(Status != ZX_OK)) { - if (Status != ZX_ERR_NO_MEMORY || !AllowNoMem) - dieOnError(Status, "zx_vmar_map", Size); - return false; + if (AllowNoMem && IsNoMemError(Status)) + return false; + dieOnError(Status, "zx_vmar_map", Size); } DCHECK_EQ(Addr, MappedAddr); @@ -227,9 +234,9 @@ bool ReservedMemoryFuchsia::createImpl(UNUSED uptr Addr, uptr Size, zx_status_t Status = _zx_vmar_map(_zx_vmar_root_self(), ZX_VM_ALLOW_FAULTS, 0, getPlaceholderVmo(), 0, Size, &Base); if (UNLIKELY(Status != ZX_OK)) { - if (Status != ZX_ERR_NO_MEMORY || !AllowNoMem) - dieOnError(Status, "zx_vmar_map", Size); - return false; + if (AllowNoMem && IsNoMemError(Status)) + return false; + dieOnError(Status, "zx_vmar_map", Size); } Capacity = Size; diff --git a/compiler-rt/lib/scudo/standalone/primary64.h b/compiler-rt/lib/scudo/standalone/primary64.h index 61d57976ae43b6b1e4e53e9c4089687bbc654448..d6119051b1622f2d517e315a68fba54b21b7ece8 100644 --- a/compiler-rt/lib/scudo/standalone/primary64.h +++ b/compiler-rt/lib/scudo/standalone/primary64.h @@ -884,9 +884,10 @@ private: ScopedLock ML(Region->MMLock); const bool RegionIsExhausted = Region->Exhausted; - if (!RegionIsExhausted) + if (!RegionIsExhausted) { PopCount = populateFreeListAndPopBlocks(C, ClassId, Region, ToArray, MaxBlockCount); + } ReportRegionExhausted = !RegionIsExhausted && Region->Exhausted; { @@ -1019,7 +1020,6 @@ private: MAP_ALLOWNOMEM))) { Printf("Can't reserve pages for size class %zu.\n", getSizeByClassId(ClassId)); - Region->Exhausted = true; return 0U; } initRegion(Region, ClassId, diff --git a/compiler-rt/test/CMakeLists.txt b/compiler-rt/test/CMakeLists.txt index edc007aaf477a74ac58e9585d9ee680e43b0d5f4..8805cc8f798f18bd4113cd11722be0e278ddc927 100644 --- a/compiler-rt/test/CMakeLists.txt +++ b/compiler-rt/test/CMakeLists.txt @@ -92,6 +92,9 @@ if(COMPILER_RT_CAN_EXECUTE_TESTS) if(COMPILER_RT_BUILD_PROFILE AND COMPILER_RT_HAS_PROFILE) compiler_rt_test_runtime(profile) endif() + if(COMPILER_RT_BUILD_CTX_PROFILE) + compiler_rt_test_runtime(ctx_profile) + endif() if(COMPILER_RT_BUILD_MEMPROF) compiler_rt_test_runtime(memprof) endif() diff --git a/compiler-rt/test/ctx_profile/CMakeLists.txt b/compiler-rt/test/ctx_profile/CMakeLists.txt new file mode 100644 index 0000000000000000000000000000000000000000..23c6fb16ed1f40e4f559322613a0d2260b7afd22 --- /dev/null +++ b/compiler-rt/test/ctx_profile/CMakeLists.txt @@ -0,0 +1,21 @@ +set(CTX_PROFILE_LIT_SOURCE_DIR ${CMAKE_CURRENT_SOURCE_DIR}) + +set(CTX_PROFILE_TESTSUITES) + +# Add unit tests. +if(COMPILER_RT_INCLUDE_TESTS) + foreach(arch ${CTX_PROFILE_SUPPORTED_ARCH}) + string(TOUPPER ${arch} ARCH_UPPER_CASE) + set(CONFIG_NAME ${ARCH_UPPER_CASE}${OS_NAME}Config) + configure_lit_site_cfg( + ${CMAKE_CURRENT_SOURCE_DIR}/Unit/lit.site.cfg.py.in + ${CMAKE_CURRENT_BINARY_DIR}/Unit/${CONFIG_NAME}/lit.site.cfg.py) + list(APPEND CTX_PROFILE_TEST_DEPS CtxProfileUnitTests) + list(APPEND CTX_PROFILE_TESTSUITES ${CMAKE_CURRENT_BINARY_DIR}/Unit/${CONFIG_NAME}) + endforeach() +endif() + +add_lit_testsuite(check-ctx_profile "Running the Contextual Profiler tests" + ${CTX_PROFILE_TESTSUITES} + DEPENDS ${CTX_PROFILE_TEST_DEPS}) +set_target_properties(check-ctx_profile PROPERTIES FOLDER "Compiler-RT Misc") diff --git a/compiler-rt/test/ctx_profile/Unit/lit.site.cfg.py.in b/compiler-rt/test/ctx_profile/Unit/lit.site.cfg.py.in new file mode 100644 index 0000000000000000000000000000000000000000..3fa9a7a2780e2473f20e0cbe5c05d1e634f9de3f --- /dev/null +++ b/compiler-rt/test/ctx_profile/Unit/lit.site.cfg.py.in @@ -0,0 +1,28 @@ +@LIT_SITE_CFG_IN_HEADER@ + +import os +import platform +import re +import shlex + +# Load common config for all compiler-rt unit tests. +lit_config.load_config(config, "@COMPILER_RT_BINARY_DIR@/unittests/lit.common.unit.configured") + +# Setup config name. +config.name = 'CtxProfile-Unit' +config.target_arch = "@arch@" +assert config.target_arch == 'x86_64' + +config.test_exec_root = os.path.join("@COMPILER_RT_BINARY_DIR@", + "lib", "ctx_profile", "tests") + +config.test_source_root = config.test_exec_root + +# When LLVM_ENABLE_PER_TARGET_RUNTIME_DIR=on, the initial value of +# config.compiler_rt_libdir (COMPILER_RT_RESOLVED_LIBRARY_OUTPUT_DIR) has the +# host triple as the trailing path component. The value is incorrect for i386 +# tests on x86_64 hosts and vice versa. But, since only x86_64 is enabled as +# target, and we don't support different environments for building and, +# respectively, running tests, we we only need to fix up the x86_64 case. +if config.enable_per_target_runtime_dir and config.target_arch != config.host_arch: + config.compiler_rt_libdir = re.sub(r'/i386(?=-[^/]+$)', '/x86_64', config.compiler_rt_libdir) diff --git a/compiler-rt/test/memprof/CMakeLists.txt b/compiler-rt/test/memprof/CMakeLists.txt index 3f0ba3812485d2042a942937e5e4737c8732abe0..fa6a4cd5f0b76ab6121d8303716163183f5ef9eb 100644 --- a/compiler-rt/test/memprof/CMakeLists.txt +++ b/compiler-rt/test/memprof/CMakeLists.txt @@ -43,6 +43,19 @@ foreach(arch ${MEMPROF_TEST_ARCH}) ${CMAKE_CURRENT_BINARY_DIR}/${CONFIG_NAME}) endforeach() +# Add unit tests. +if(COMPILER_RT_INCLUDE_TESTS) + foreach(arch ${MEMPROF_TEST_ARCH}) + string(TOUPPER ${arch} ARCH_UPPER_CASE) + set(CONFIG_NAME ${ARCH_UPPER_CASE}${OS_NAME}Config) + configure_lit_site_cfg( + ${CMAKE_CURRENT_SOURCE_DIR}/Unit/lit.site.cfg.py.in + ${CMAKE_CURRENT_BINARY_DIR}/Unit/${CONFIG_NAME}/lit.site.cfg.py) + list(APPEND MEMPROF_TEST_DEPS MemProfUnitTests) + list(APPEND MEMPROF_TESTSUITES ${CMAKE_CURRENT_BINARY_DIR}/Unit/${CONFIG_NAME}) + endforeach() +endif() + add_lit_testsuite(check-memprof "Running the MemProfiler tests" ${MEMPROF_TESTSUITES} DEPENDS ${MEMPROF_TEST_DEPS}) diff --git a/compiler-rt/test/memprof/Unit/lit.site.cfg.py.in b/compiler-rt/test/memprof/Unit/lit.site.cfg.py.in new file mode 100644 index 0000000000000000000000000000000000000000..1e2442a1487a4373ba3e0d0f4d39751ef11a7387 --- /dev/null +++ b/compiler-rt/test/memprof/Unit/lit.site.cfg.py.in @@ -0,0 +1,31 @@ +@LIT_SITE_CFG_IN_HEADER@ + +import os +import platform +import re +import shlex + +# Load common config for all compiler-rt unit tests. +lit_config.load_config(config, "@COMPILER_RT_BINARY_DIR@/unittests/lit.common.unit.configured") + +# Setup config name. +config.name = 'MemProfiler-Unit' +config.target_arch = "@arch@" +assert config.target_arch == 'x86_64' + +config.test_exec_root = os.path.join("@COMPILER_RT_BINARY_DIR@", + "lib", "memprof", "tests") + +config.test_source_root = config.test_exec_root + +# When LLVM_ENABLE_PER_TARGET_RUNTIME_DIR=on, the initial value of +# config.compiler_rt_libdir (COMPILER_RT_RESOLVED_LIBRARY_OUTPUT_DIR) has the +# host triple as the trailing path component. The value is incorrect for i386 +# tests on x86_64 hosts and vice versa. But, since only x86_64 is enabled as +# target, and we don't support different environments for building and, +# respectively, running tests, we we only need to fix up the x86_64 case. +if config.enable_per_target_runtime_dir and config.target_arch != config.host_arch: + config.compiler_rt_libdir = re.sub(r'/i386(?=-[^/]+$)', '/x86_64', config.compiler_rt_libdir) + +if not config.parallelism_group: + config.parallelism_group = 'shadow-memory' diff --git a/flang/docs/Preprocessing.md b/flang/docs/Preprocessing.md index 3c523472f39bd018e5516b43f7acc0dcabedc2bc..0b70d857833cef03d2ba8aed0d00311d6e778f9a 100644 --- a/flang/docs/Preprocessing.md +++ b/flang/docs/Preprocessing.md @@ -93,6 +93,9 @@ local: * If a `#define` or `#undef` directive appears among continuation lines, it may or may not affect text in the continued statement that appeared before the directive. +* A backslash at the end of a free form source line is a continuation + marker, with no space skipping or special handling of a leading `&` + on the next line. ## Behavior that few compilers properly support (or none), but should: diff --git a/flang/include/flang/Common/visit.h b/flang/include/flang/Common/visit.h index 4d0897301e01db71dabf40dd58fb17ba5e45bad9..d867338be7e0f5bcc98b7a5aa788a4b303c0c4c6 100644 --- a/flang/include/flang/Common/visit.h +++ b/flang/include/flang/Common/visit.h @@ -40,11 +40,17 @@ inline RT_API_ATTRS RESULT Log2VisitHelper( return visitor(std::get<(LOW + N)>(std::forward(u))...); \ } VISIT_CASE_N(1) + [[fallthrough]]; VISIT_CASE_N(2) + [[fallthrough]]; VISIT_CASE_N(3) + [[fallthrough]]; VISIT_CASE_N(4) + [[fallthrough]]; VISIT_CASE_N(5) + [[fallthrough]]; VISIT_CASE_N(6) + [[fallthrough]]; VISIT_CASE_N(7) #undef VISIT_CASE_N } @@ -82,7 +88,7 @@ inline RT_API_ATTRS auto visit(VISITOR &&visitor, VARIANT &&...u) // Some versions of clang have bugs that cause compilation to hang // on these templates. MSVC and older GCC versions may work but are // not well tested. So enable only for GCC 9 and better. -#if __GNUC__ < 9 +#if __GNUC__ < 9 && !defined(__clang__) #define FLANG_USE_STD_VISIT #endif diff --git a/flang/include/flang/Lower/Allocatable.h b/flang/include/flang/Lower/Allocatable.h index d3c16de377c1d7a8c1a6581bfe683f270c7e23d0..e8738f0407e77ffe3f4f1ed6632074e38614015d 100644 --- a/flang/include/flang/Lower/Allocatable.h +++ b/flang/include/flang/Lower/Allocatable.h @@ -55,12 +55,14 @@ void genDeallocateStmt(AbstractConverter &converter, void genDeallocateBox(AbstractConverter &converter, const fir::MutableBoxValue &box, mlir::Location loc, + const Fortran::semantics::Symbol *sym = nullptr, mlir::Value declaredTypeDesc = {}); /// Deallocate an allocatable if it is allocated at the end of its lifetime. void genDeallocateIfAllocated(AbstractConverter &converter, const fir::MutableBoxValue &box, - mlir::Location loc); + mlir::Location loc, + const Fortran::semantics::Symbol *sym = nullptr); /// Create a MutableBoxValue for an allocatable or pointer entity. /// If the variables is a local variable that is not a dummy, it will be diff --git a/flang/include/flang/Optimizer/Builder/IntrinsicCall.h b/flang/include/flang/Optimizer/Builder/IntrinsicCall.h index 6927488517e63b8775354ad117dd9982e0856219..604f2bd969eed51a7331fccb7887bd3443a04d25 100644 --- a/flang/include/flang/Optimizer/Builder/IntrinsicCall.h +++ b/flang/include/flang/Optimizer/Builder/IntrinsicCall.h @@ -335,6 +335,8 @@ struct IntrinsicLibrary { mlir::Value genSelectedRealKind(mlir::Type, llvm::ArrayRef); mlir::Value genSetExponent(mlir::Type resultType, llvm::ArrayRef args); + fir::ExtendedValue genShape(mlir::Type resultType, + llvm::ArrayRef); template mlir::Value genShift(mlir::Type resultType, llvm::ArrayRef); mlir::Value genShiftA(mlir::Type resultType, llvm::ArrayRef); diff --git a/flang/include/flang/Optimizer/Transforms/Passes.h b/flang/include/flang/Optimizer/Transforms/Passes.h index 4d290d87d4cc9576459177468ed4f19c5f46e568..547fe742967a4f3989cb2e42f7389e7695e2f670 100644 --- a/flang/include/flang/Optimizer/Transforms/Passes.h +++ b/flang/include/flang/Optimizer/Transforms/Passes.h @@ -37,8 +37,7 @@ namespace fir { #define GEN_PASS_DECL_ANNOTATECONSTANTOPERANDS #define GEN_PASS_DECL_ARRAYVALUECOPY #define GEN_PASS_DECL_CHARACTERCONVERSION -#define GEN_PASS_DECL_CFGCONVERSIONONFUNC -#define GEN_PASS_DECL_CFGCONVERSIONONREDUCTION +#define GEN_PASS_DECL_CFGCONVERSION #define GEN_PASS_DECL_EXTERNALNAMECONVERSION #define GEN_PASS_DECL_MEMREFDATAFLOWOPT #define GEN_PASS_DECL_SIMPLIFYINTRINSICS @@ -47,30 +46,24 @@ namespace fir { #define GEN_PASS_DECL_ALGEBRAICSIMPLIFICATION #define GEN_PASS_DECL_POLYMORPHICOPCONVERSION #define GEN_PASS_DECL_OPENACCDATAOPERANDCONVERSION +#define GEN_PASS_DECL_ADDDEBUGINFO +#define GEN_PASS_DECL_STACKARRAYS +#define GEN_PASS_DECL_LOOPVERSIONING #include "flang/Optimizer/Transforms/Passes.h.inc" std::unique_ptr createAffineDemotionPass(); std::unique_ptr createArrayValueCopyPass(fir::ArrayValueCopyOptions options = {}); -std::unique_ptr createFirToCfgOnFuncPass(); -std::unique_ptr createFirToCfgOnReductionPass(); -std::unique_ptr createCharacterConversionPass(); std::unique_ptr createExternalNameConversionPass(); std::unique_ptr createExternalNameConversionPass(bool appendUnderscore); std::unique_ptr createMemDataFlowOptPass(); std::unique_ptr createPromoteToAffinePass(); -std::unique_ptr createMemoryAllocationPass(); -std::unique_ptr createStackArraysPass(); std::unique_ptr createAliasTagsPass(); -std::unique_ptr createSimplifyIntrinsicsPass(); -std::unique_ptr createAddDebugInfoPass(); -std::unique_ptr createLoopVersioningPass(); - std::unique_ptr -createMemoryAllocationPass(bool dynOnHeap, std::size_t maxStackSize); +createAddDebugInfoPass(fir::AddDebugInfoOptions options = {}); + std::unique_ptr createAnnotateConstantOperandsPass(); -std::unique_ptr createSimplifyRegionLitePass(); std::unique_ptr createAlgebraicSimplificationPass(); std::unique_ptr createAlgebraicSimplificationPass(const mlir::GreedyRewriteConfig &config); diff --git a/flang/include/flang/Optimizer/Transforms/Passes.td b/flang/include/flang/Optimizer/Transforms/Passes.td index 467b7e1c472ec02d3e5a5c5c4a46f227ee00c719..020b8a6b64a9e00ffbd5532acfa477970b6ea333 100644 --- a/flang/include/flang/Optimizer/Transforms/Passes.td +++ b/flang/include/flang/Optimizer/Transforms/Passes.td @@ -127,7 +127,6 @@ def CharacterConversion : Pass<"character-conversion"> { By default the translation is to naively zero-extend or truncate a code point to fit the destination size. }]; - let constructor = "::fir::createCharacterConversionPass()"; let dependentDialects = [ "fir::FIROpsDialect" ]; let options = [ Option<"useRuntimeCalls", "use-runtime-calls", @@ -137,8 +136,7 @@ def CharacterConversion : Pass<"character-conversion"> { ]; } -class CFGConversionBase - : Pass<"cfg-conversion-on-" # optExt # "-opt", operation> { +def CFGConversion : Pass<"cfg-conversion"> { let summary = "Convert FIR structured control flow ops to CFG ops."; let description = [{ Transform the `fir.do_loop`, `fir.if`, `fir.iterate_while` and @@ -157,14 +155,6 @@ class CFGConversionBase ]; } -def CFGConversionOnFunc : CFGConversionBase<"func", "mlir::func::FuncOp"> { - let constructor = "::fir::createFirToCfgOnFuncPass()"; -} - -def CFGConversionOnReduction : CFGConversionBase<"reduce", "mlir::omp::DeclareReductionOp"> { - let constructor = "::fir::createFirToCfgOnReductionPass()"; -} - def ExternalNameConversion : Pass<"external-name-interop", "mlir::ModuleOp"> { let summary = "Convert name for external interoperability"; let description = [{ @@ -202,6 +192,25 @@ def AddDebugInfo : Pass<"add-debug-info", "mlir::ModuleOp"> { let dependentDialects = [ "fir::FIROpsDialect", "mlir::func::FuncDialect", "mlir::LLVM::LLVMDialect" ]; + let options = [ + Option<"debugLevel", "debug-level", + "mlir::LLVM::DIEmissionKind", + /*default=*/"mlir::LLVM::DIEmissionKind::Full", + "debug level", + [{::llvm::cl::values( + clEnumValN(mlir::LLVM::DIEmissionKind::Full, "Full", "Emit full debug info"), + clEnumValN(mlir::LLVM::DIEmissionKind::LineTablesOnly, "LineTablesOnly", "Emit line tables only"), + clEnumValN(mlir::LLVM::DIEmissionKind::None, "None", "Emit no debug information") + )}] + >, + Option<"isOptimized", "is-optimized", + "bool", /*default=*/"false", + "is optimized.">, + Option<"inputFilename", "file-name", + "std::string", + /*default=*/"std::string{}", + "name of the input source file">, + ]; } // This needs to be a "mlir::ModuleOp" pass, because it inserts simplified @@ -215,7 +224,6 @@ def SimplifyIntrinsics : Pass<"simplify-intrinsics", "mlir::ModuleOp"> { simplified function. The simplified function is added to the current module. This function can be inlined by a general purpose inlining pass. }]; - let constructor = "::fir::createSimplifyIntrinsicsPass()"; let options = [ Option<"enableExperimental", "enable-experimental", "bool", @@ -239,7 +247,6 @@ def MemoryAllocationOpt : Pass<"memory-allocation-opt", "mlir::func::FuncOp"> { "std::size_t", /*default=*/"~static_cast(0)", "Set maximum number of elements of an array allocated on the stack."> ]; - let constructor = "::fir::createMemoryAllocationPass()"; } def StackArrays : Pass<"stack-arrays", "mlir::ModuleOp"> { @@ -249,7 +256,6 @@ def StackArrays : Pass<"stack-arrays", "mlir::ModuleOp"> { allocations. }]; let dependentDialects = [ "fir::FIROpsDialect" ]; - let constructor = "::fir::createStackArraysPass()"; } def AddAliasTags : Pass<"fir-add-alias-tags", "mlir::ModuleOp"> { @@ -277,7 +283,6 @@ def SimplifyRegionLite : Pass<"simplify-region-lite", "mlir::ModuleOp"> { let description = [{ Run region DCE and erase unreachable blocks in regions. }]; - let constructor = "::fir::createSimplifyRegionLitePass()"; } def AlgebraicSimplification : Pass<"flang-algebraic-simplification"> { @@ -314,7 +319,6 @@ def LoopVersioning : Pass<"loop-versioning", "mlir::func::FuncOp"> { an array has element sized stride. The element sizes stride allows some loops to be vectorized as well as other loop optimizations. }]; - let constructor = "::fir::createLoopVersioningPass()"; let dependentDialects = [ "fir::FIROpsDialect" ]; } diff --git a/flang/include/flang/Parser/parse-tree.h b/flang/include/flang/Parser/parse-tree.h index d7c23755c57b2bdc76b4a01cac4f08f8a5d0e8ce..4641f9d20d5b9566dd97e6c43f7bc6e328fb156a 100644 --- a/flang/include/flang/Parser/parse-tree.h +++ b/flang/include/flang/Parser/parse-tree.h @@ -455,7 +455,8 @@ struct SpecificationPart { struct InternalSubprogram { UNION_CLASS_BOILERPLATE(InternalSubprogram); std::variant, - common::Indirection> + common::Indirection, + common::Indirection> u; }; diff --git a/flang/include/flang/Parser/preprocessor.h b/flang/include/flang/Parser/preprocessor.h index 630d5273d427c6e84dfaef7993ed407f968e00f5..c3076435be5f0bddfad89e76bad6e230087c3c5e 100644 --- a/flang/include/flang/Parser/preprocessor.h +++ b/flang/include/flang/Parser/preprocessor.h @@ -81,6 +81,7 @@ public: void Undefine(std::string macro); bool IsNameDefined(const CharBlock &); bool IsFunctionLikeDefinition(const CharBlock &); + bool AnyDefinitions() const { return !definitions_.empty(); } // When called with partialFunctionLikeMacro not null, MacroReplacement() // and ReplaceMacros() handle an unclosed function-like macro reference diff --git a/flang/include/flang/Runtime/descriptor.h b/flang/include/flang/Runtime/descriptor.h index 96d56d9b43a62ba982e2c0883598541130c14fd4..1b0b7e23ce6ccdcd4c417d00b15f60d8575eb7dc 100644 --- a/flang/include/flang/Runtime/descriptor.h +++ b/flang/include/flang/Runtime/descriptor.h @@ -456,6 +456,7 @@ public: assert(descriptor().rank() <= maxRank); assert(descriptor().SizeInBytes() <= byteSize); if (DescriptorAddendum * addendum{descriptor().Addendum()}) { + (void)addendum; assert(hasAddendum); assert(addendum->LenParameters() <= maxLengthTypeParameters); } else { diff --git a/flang/include/flang/Runtime/numeric.h b/flang/include/flang/Runtime/numeric.h index 3d9cb8b5b0acdc0a7bff5b99c8ed15c40c96e0e6..7d3f91360c8cfb1dde466dfdc140b10f787ce017 100644 --- a/flang/include/flang/Runtime/numeric.h +++ b/flang/include/flang/Runtime/numeric.h @@ -356,10 +356,18 @@ CppTypeFor RTDECL(Scale16)( CppTypeFor, std::int64_t); #endif +// SELECTED_CHAR_KIND +CppTypeFor RTDECL(SelectedCharKind)( + const char *, int, const char *, std::size_t); + // SELECTED_INT_KIND CppTypeFor RTDECL(SelectedIntKind)( const char *, int, void *, int); +// SELECTED_LOGICAL_KIND +CppTypeFor RTDECL(SelectedLogicalKind)( + const char *, int, void *, int); + // SELECTED_REAL_KIND CppTypeFor RTDECL(SelectedRealKind)( const char *, int, void *, int, void *, int, void *, int); diff --git a/flang/include/flang/Tools/CLOptions.inc b/flang/include/flang/Tools/CLOptions.inc index 44ff2b3f70ff688bbd851e8a01afef7bf66baa4a..8f197038f2ba5b8b45022a53789a0a98233fcdf8 100644 --- a/flang/include/flang/Tools/CLOptions.inc +++ b/flang/include/flang/Tools/CLOptions.inc @@ -87,8 +87,6 @@ DisableOption(BoxedProcedureRewrite, "boxed-procedure-rewrite", DisableOption(ExternalNameConversion, "external-name-interop", "convert names with external convention"); -// TODO: remove once these are used for non-codegen passes -#if !defined(FLANG_EXCLUDE_CODEGEN) using PassConstructor = std::unique_ptr(); template @@ -108,7 +106,12 @@ void addNestedPassToAllTopLevelOperations( addNestedPassToOps(pm, ctor); } -#endif + +void addNestedPassToAllTopLevelOperationsConditionally(mlir::PassManager &pm, + llvm::cl::opt &disabled, PassConstructor ctor) { + if (!disabled) + addNestedPassToAllTopLevelOperations(pm, ctor); +} /// Generic for adding a pass to the pass manager if it is not disabled. template @@ -146,10 +149,8 @@ static void addCanonicalizerPassWithoutRegionSimplification( } inline void addCfgConversionPass(mlir::PassManager &pm) { - addNestedPassConditionally( - pm, disableCfgConversion, fir::createFirToCfgOnFuncPass); - addNestedPassConditionally( - pm, disableCfgConversion, fir::createFirToCfgOnReductionPass); + addNestedPassToAllTopLevelOperationsConditionally( + pm, disableCfgConversion, fir::createCFGConversion); } inline void addAVC( @@ -162,8 +163,8 @@ inline void addAVC( inline void addMemoryAllocationOpt(mlir::PassManager &pm) { addNestedPassConditionally(pm, disableFirMao, [&]() { - return fir::createMemoryAllocationPass( - dynamicArrayStackToHeapAllocation, arrayStackAllocationThreshold); + return fir::createMemoryAllocationOpt( + {dynamicArrayStackToHeapAllocation, arrayStackAllocationThreshold}); }); } @@ -179,9 +180,27 @@ inline void addTargetRewritePass(mlir::PassManager &pm) { }); } -inline void addDebugInfoPass(mlir::PassManager &pm) { - addPassConditionally( - pm, disableDebugInfo, [&]() { return fir::createAddDebugInfoPass(); }); +inline mlir::LLVM::DIEmissionKind getEmissionKind( + llvm::codegenoptions::DebugInfoKind kind) { + switch (kind) { + case llvm::codegenoptions::DebugInfoKind::FullDebugInfo: + return mlir::LLVM::DIEmissionKind::Full; + case llvm::codegenoptions::DebugInfoKind::DebugLineTablesOnly: + return mlir::LLVM::DIEmissionKind::LineTablesOnly; + default: + return mlir::LLVM::DIEmissionKind::None; + } +} + +inline void addDebugInfoPass(mlir::PassManager &pm, + llvm::codegenoptions::DebugInfoKind debugLevel, + llvm::OptimizationLevel optLevel, llvm::StringRef inputFilename) { + fir::AddDebugInfoOptions options; + options.debugLevel = getEmissionKind(debugLevel); + options.isOptimized = optLevel != llvm::OptimizationLevel::O0; + options.inputFilename = inputFilename; + addPassConditionally(pm, disableDebugInfo, + [&]() { return fir::createAddDebugInfoPass(options); }); } inline void addFIRToLLVMPass( @@ -224,22 +243,22 @@ inline void createDefaultFIROptimizerPassPipeline( config.enableRegionSimplification = false; pm.addPass(mlir::createCSEPass()); fir::addAVC(pm, pc.OptLevel); - pm.addNestedPass(fir::createCharacterConversionPass()); + addNestedPassToAllTopLevelOperations(pm, fir::createCharacterConversion); pm.addPass(mlir::createCanonicalizerPass(config)); - pm.addPass(fir::createSimplifyRegionLitePass()); + pm.addPass(fir::createSimplifyRegionLite()); if (pc.OptLevel.isOptimizingForSpeed()) { // These passes may increase code size. - pm.addPass(fir::createSimplifyIntrinsicsPass()); + pm.addPass(fir::createSimplifyIntrinsics()); pm.addPass(fir::createAlgebraicSimplificationPass(config)); } if (pc.LoopVersioning) - pm.addPass(fir::createLoopVersioningPass()); + pm.addPass(fir::createLoopVersioning()); pm.addPass(mlir::createCSEPass()); if (pc.StackArrays) - pm.addPass(fir::createStackArraysPass()); + pm.addPass(fir::createStackArrays()); else fir::addMemoryAllocationOpt(pm); @@ -248,7 +267,7 @@ inline void createDefaultFIROptimizerPassPipeline( llvm::StringMap pipelines; pm.addPass(mlir::createInlinerPass( pipelines, addCanonicalizerPassWithoutRegionSimplification)); - pm.addPass(fir::createSimplifyRegionLitePass()); + pm.addPass(fir::createSimplifyRegionLite()); pm.addPass(mlir::createCSEPass()); // Polymorphic types @@ -262,7 +281,7 @@ inline void createDefaultFIROptimizerPassPipeline( pm.addPass(mlir::createConvertSCFToCFPass()); pm.addPass(mlir::createCanonicalizerPass(config)); - pm.addPass(fir::createSimplifyRegionLitePass()); + pm.addPass(fir::createSimplifyRegionLite()); pm.addPass(mlir::createCSEPass()); } @@ -307,32 +326,21 @@ inline void createOpenMPFIRPassPipeline( } #if !defined(FLANG_EXCLUDE_CODEGEN) -inline void createDebugPasses( - mlir::PassManager &pm, llvm::codegenoptions::DebugInfoKind debugLevel) { - // Currently only -g1, -g, -gline-tables-only supported - switch (debugLevel) { - case llvm::codegenoptions::DebugLineTablesOnly: - addDebugInfoPass(pm); - return; - case llvm::codegenoptions::NoDebugInfo: - return; - default: - // TODO: Add cases and passes for other debug options. - // All other debug options not implemented yet, currently emits warning - // and generates as much debug information as possible. - addDebugInfoPass(pm); - return; - } +inline void createDebugPasses(mlir::PassManager &pm, + llvm::codegenoptions::DebugInfoKind debugLevel, + llvm::OptimizationLevel OptLevel, llvm::StringRef inputFilename) { + if (debugLevel != llvm::codegenoptions::NoDebugInfo) + addDebugInfoPass(pm, debugLevel, OptLevel, inputFilename); } -inline void createDefaultFIRCodeGenPassPipeline( - mlir::PassManager &pm, MLIRToLLVMPassPipelineConfig config) { +inline void createDefaultFIRCodeGenPassPipeline(mlir::PassManager &pm, + MLIRToLLVMPassPipelineConfig config, llvm::StringRef inputFilename = {}) { fir::addBoxedProcedurePass(pm); addNestedPassToAllTopLevelOperations(pm, fir::createAbstractResultOpt); fir::addCodeGenRewritePass(pm); fir::addTargetRewritePass(pm); fir::addExternalNameConversionPass(pm, config.Underscoring); - fir::createDebugPasses(pm, config.DebugInfo); + fir::createDebugPasses(pm, config.DebugInfo, config.OptLevel, inputFilename); if (config.VScaleMin != 0) pm.addPass(fir::createVScaleAttrPass({config.VScaleMin, config.VScaleMax})); @@ -366,15 +374,16 @@ inline void createDefaultFIRCodeGenPassPipeline( /// \param pm - MLIR pass manager that will hold the pipeline definition /// \param optLevel - optimization level used for creating FIR optimization /// passes pipeline -inline void createMLIRToLLVMPassPipeline( - mlir::PassManager &pm, const MLIRToLLVMPassPipelineConfig &config) { +inline void createMLIRToLLVMPassPipeline(mlir::PassManager &pm, + const MLIRToLLVMPassPipelineConfig &config, + llvm::StringRef inputFilename = {}) { fir::createHLFIRToFIRPassPipeline(pm, config.OptLevel); // Add default optimizer pass pipeline. fir::createDefaultFIROptimizerPassPipeline(pm, config); // Add codegen pass pipeline. - fir::createDefaultFIRCodeGenPassPipeline(pm, config); + fir::createDefaultFIRCodeGenPassPipeline(pm, config, inputFilename); } #undef FLANG_EXCLUDE_CODEGEN #endif diff --git a/flang/lib/Evaluate/intrinsics.cpp b/flang/lib/Evaluate/intrinsics.cpp index f07f94b1a022c9f02db49c4b6be527690714694d..1b73cadb682d988278b5da7f8ef8b2e309632d66 100644 --- a/flang/lib/Evaluate/intrinsics.cpp +++ b/flang/lib/Evaluate/intrinsics.cpp @@ -777,7 +777,9 @@ static const IntrinsicInterface genericIntrinsicFunction[]{ {"identity", SameType, Rank::scalar, Optionality::optional}, {"ordered", AnyLogical, Rank::scalar, Optionality::optional}}, SameType, Rank::scalar, IntrinsicClass::transformationalFunction}, - {"repeat", {{"string", SameCharNoLen, Rank::scalar}, {"ncopies", AnyInt}}, + {"repeat", + {{"string", SameCharNoLen, Rank::scalar}, + {"ncopies", AnyInt, Rank::scalar}}, SameCharNoLen, Rank::scalar, IntrinsicClass::transformationalFunction}, {"reshape", {{"source", SameType, Rank::array}, {"shape", AnyInt, Rank::shape}, diff --git a/flang/lib/Evaluate/type.cpp b/flang/lib/Evaluate/type.cpp index a369e07f94a1fbebbbb62d2cf032cbb528c6c61d..ee1e5b398d9b02451ba3ceb409117c8678c8aff6 100644 --- a/flang/lib/Evaluate/type.cpp +++ b/flang/lib/Evaluate/type.cpp @@ -731,7 +731,7 @@ bool SomeKind::operator==( return PointeeComparison(derivedTypeSpec_, that.derivedTypeSpec_); } -int SelectedCharKind(const std::string &s, int defaultKind) { // 16.9.168 +int SelectedCharKind(const std::string &s, int defaultKind) { // F'2023 16.9.180 auto lower{parser::ToLowerCaseLetters(s)}; auto n{lower.size()}; while (n > 0 && lower[0] == ' ') { diff --git a/flang/lib/Frontend/FrontendActions.cpp b/flang/lib/Frontend/FrontendActions.cpp index 8f251997ed401b819e2741422577e73e3272f68b..531616e7926acaebddd79b6752370adb6c1152e4 100644 --- a/flang/lib/Frontend/FrontendActions.cpp +++ b/flang/lib/Frontend/FrontendActions.cpp @@ -63,10 +63,10 @@ #include "llvm/Support/ErrorHandling.h" #include "llvm/Support/FileSystem.h" #include "llvm/Support/Path.h" -#include "llvm/Support/RISCVISAInfo.h" #include "llvm/Support/SourceMgr.h" #include "llvm/Support/ToolOutputFile.h" #include "llvm/Target/TargetMachine.h" +#include "llvm/TargetParser/RISCVISAInfo.h" #include "llvm/TargetParser/RISCVTargetParser.h" #include "llvm/Transforms/Utils/ModuleUtils.h" #include @@ -809,7 +809,7 @@ void CodeGenAction::generateLLVMIR() { } // Create the pass pipeline - fir::createMLIRToLLVMPassPipeline(pm, config); + fir::createMLIRToLLVMPassPipeline(pm, config, getCurrentFile()); (void)mlir::applyPassManagerCLOptions(pm); // run the pass manager @@ -861,7 +861,6 @@ getOutputStream(CompilerInstance &ci, llvm::StringRef inFile, return ci.createDefaultOutputFile( /*Binary=*/false, inFile, /*extension=*/"ll"); case BackendActionTy::Backend_EmitFIR: - LLVM_FALLTHROUGH; case BackendActionTy::Backend_EmitHLFIR: return ci.createDefaultOutputFile( /*Binary=*/false, inFile, /*extension=*/"mlir"); diff --git a/flang/lib/Lower/Allocatable.cpp b/flang/lib/Lower/Allocatable.cpp index 38f61528d7e28add5a500e16dcdd25a954e5fd61..8e84ea2fc5d5223df3cb98b335b007bdeb9a37c0 100644 --- a/flang/lib/Lower/Allocatable.cpp +++ b/flang/lib/Lower/Allocatable.cpp @@ -859,18 +859,20 @@ genDeallocate(fir::FirOpBuilder &builder, void Fortran::lower::genDeallocateBox( Fortran::lower::AbstractConverter &converter, const fir::MutableBoxValue &box, mlir::Location loc, - mlir::Value declaredTypeDesc) { + const Fortran::semantics::Symbol *sym, mlir::Value declaredTypeDesc) { const Fortran::lower::SomeExpr *statExpr = nullptr; const Fortran::lower::SomeExpr *errMsgExpr = nullptr; ErrorManager errorManager; errorManager.init(converter, loc, statExpr, errMsgExpr); fir::FirOpBuilder &builder = converter.getFirOpBuilder(); - genDeallocate(builder, converter, loc, box, errorManager, declaredTypeDesc); + genDeallocate(builder, converter, loc, box, errorManager, declaredTypeDesc, + sym); } void Fortran::lower::genDeallocateIfAllocated( Fortran::lower::AbstractConverter &converter, - const fir::MutableBoxValue &box, mlir::Location loc) { + const fir::MutableBoxValue &box, mlir::Location loc, + const Fortran::semantics::Symbol *sym) { fir::FirOpBuilder &builder = converter.getFirOpBuilder(); mlir::Value isAllocated = fir::factory::genIsAllocatedOrAssociatedTest(builder, loc, box); @@ -880,9 +882,9 @@ void Fortran::lower::genDeallocateIfAllocated( eleType.isa() && box.isPolymorphic()) { mlir::Value declaredTypeDesc = builder.create( loc, mlir::TypeAttr::get(eleType)); - genDeallocateBox(converter, box, loc, declaredTypeDesc); + genDeallocateBox(converter, box, loc, sym, declaredTypeDesc); } else { - genDeallocateBox(converter, box, loc); + genDeallocateBox(converter, box, loc, sym); } }) .end(); diff --git a/flang/lib/Lower/Bridge.cpp b/flang/lib/Lower/Bridge.cpp index 8b62fe8c022f802272733773f16b3684d93378ca..f66607dfa22f1bda8112a94f3c7151185b369ef9 100644 --- a/flang/lib/Lower/Bridge.cpp +++ b/flang/lib/Lower/Bridge.cpp @@ -3794,7 +3794,9 @@ private: auto needCleanup = fir::getIntIfConstant(cleanup); if (needCleanup && *needCleanup) temps.push_back(temp); - addSymbol(sym, temp, /*forced=*/true); + addSymbol(sym, + hlfir::translateToExtendedValue(loc, builder, temp).first, + /*forced=*/true); builder.create(loc, addr, temp, transferKindAttr); ++nbDeviceResidentObject; @@ -3810,12 +3812,14 @@ private: mlir::Location loc = getCurrentLocation(); fir::FirOpBuilder &builder = getFirOpBuilder(); + bool isInDeviceContext = + builder.getRegion().getParentOfType(); bool isCUDATransfer = Fortran::evaluate::HasCUDAAttrs(assign.lhs) || Fortran::evaluate::HasCUDAAttrs(assign.rhs); bool hasCUDAImplicitTransfer = Fortran::evaluate::HasCUDAImplicitTransfer(assign.rhs); llvm::SmallVector implicitTemps; - if (hasCUDAImplicitTransfer) + if (hasCUDAImplicitTransfer && !isInDeviceContext) implicitTemps = genCUDAImplicitDataTransfer(builder, loc, assign); // Gather some information about the assignment that will impact how it is @@ -3874,13 +3878,13 @@ private: Fortran::lower::StatementContext localStmtCtx; hlfir::Entity rhs = evaluateRhs(localStmtCtx); hlfir::Entity lhs = evaluateLhs(localStmtCtx); - if (isCUDATransfer && !hasCUDAImplicitTransfer) + if (isCUDATransfer && !hasCUDAImplicitTransfer && !isInDeviceContext) genCUDADataTransfer(builder, loc, assign, lhs, rhs); else builder.create(loc, rhs, lhs, isWholeAllocatableAssignment, keepLhsLengthInAllocatableAssignment); - if (hasCUDAImplicitTransfer) { + if (hasCUDAImplicitTransfer && !isInDeviceContext) { localSymbols.popScope(); for (mlir::Value temp : implicitTemps) builder.create(loc, temp); diff --git a/flang/lib/Lower/ConvertVariable.cpp b/flang/lib/Lower/ConvertVariable.cpp index 2d2d9eba905bdd519f24e305e3b5edc34b1d3a35..21db0cac11bf6ac3cbacde79b3406d36ce414fb3 100644 --- a/flang/lib/Lower/ConvertVariable.cpp +++ b/flang/lib/Lower/ConvertVariable.cpp @@ -916,13 +916,14 @@ static void instantiateLocal(Fortran::lower::AbstractConverter &converter, break; case VariableCleanUp::Deallocate: auto *converterPtr = &converter; - converter.getFctCtx().attachCleanup([converterPtr, loc, exv]() { + auto *sym = &var.getSymbol(); + converter.getFctCtx().attachCleanup([converterPtr, loc, exv, sym]() { const fir::MutableBoxValue *mutableBox = exv.getBoxOf(); assert(mutableBox && "trying to deallocate entity not lowered as allocatable"); Fortran::lower::genDeallocateIfAllocated(*converterPtr, *mutableBox, - loc); + loc, sym); }); } } @@ -1715,7 +1716,8 @@ void Fortran::lower::genDeclareSymbol( const fir::ExtendedValue &exv, fir::FortranVariableFlagsEnum extraFlags, bool force) { if (converter.getLoweringOptions().getLowerToHighLevelFIR() && - !Fortran::semantics::IsProcedure(sym) && + (!Fortran::semantics::IsProcedure(sym) || + Fortran::semantics::IsPointer(sym)) && !sym.detailsIf()) { fir::FirOpBuilder &builder = converter.getFirOpBuilder(); const mlir::Location loc = genLocation(converter, sym); diff --git a/flang/lib/Lower/HostAssociations.cpp b/flang/lib/Lower/HostAssociations.cpp index 8eb548eb2bd5fe488900fcc4ea907eadd98b2da2..2e2656356719f80c4e15a86d92fd71c9a4bcd433 100644 --- a/flang/lib/Lower/HostAssociations.cpp +++ b/flang/lib/Lower/HostAssociations.cpp @@ -182,10 +182,10 @@ class CapturedProcedure : public CapturedSymbols { public: static mlir::Type getType(Fortran::lower::AbstractConverter &converter, const Fortran::semantics::Symbol &sym) { + mlir::Type funTy = Fortran::lower::getDummyProcedureType(sym, converter); if (Fortran::semantics::IsPointer(sym)) - TODO(converter.getCurrentLocation(), - "capture procedure pointer in internal procedure"); - return Fortran::lower::getDummyProcedureType(sym, converter); + return fir::ReferenceType::get(funTy); + return funTy; } static void instantiateHostTuple(const InstantiateHostTuple &args, diff --git a/flang/lib/Lower/OpenACC.cpp b/flang/lib/Lower/OpenACC.cpp index d933c07aba0e0c05c2392db9d8bbcd79e9e0d0dd..b56bdedc07bf53531d96b6f469b839240e4c7898 100644 --- a/flang/lib/Lower/OpenACC.cpp +++ b/flang/lib/Lower/OpenACC.cpp @@ -4187,21 +4187,27 @@ void Fortran::lower::attachDeclarePostDeallocAction( std::stringstream fctName; fctName << converter.mangleName(sym) << declarePostDeallocSuffix.str(); - mlir::Operation &op = builder.getInsertionBlock()->back(); - if (op.hasAttr(mlir::acc::getDeclareActionAttrName())) { - auto attr = op.getAttrOfType( + mlir::Operation *op = &builder.getInsertionBlock()->back(); + if (auto resOp = mlir::dyn_cast(*op)) { + assert(resOp.getOperands().size() == 0 && + "expect only fir.result op with no operand"); + op = op->getPrevNode(); + } + assert(op && "expect operation to attach the post deallocation action"); + if (op->hasAttr(mlir::acc::getDeclareActionAttrName())) { + auto attr = op->getAttrOfType( mlir::acc::getDeclareActionAttrName()); - op.setAttr(mlir::acc::getDeclareActionAttrName(), - mlir::acc::DeclareActionAttr::get( - builder.getContext(), attr.getPreAlloc(), - attr.getPostAlloc(), attr.getPreDealloc(), - /*postDealloc=*/builder.getSymbolRefAttr(fctName.str()))); + op->setAttr(mlir::acc::getDeclareActionAttrName(), + mlir::acc::DeclareActionAttr::get( + builder.getContext(), attr.getPreAlloc(), + attr.getPostAlloc(), attr.getPreDealloc(), + /*postDealloc=*/builder.getSymbolRefAttr(fctName.str()))); } else { - op.setAttr(mlir::acc::getDeclareActionAttrName(), - mlir::acc::DeclareActionAttr::get( - builder.getContext(), - /*preAlloc=*/{}, /*postAlloc=*/{}, /*preDealloc=*/{}, - /*postDealloc=*/builder.getSymbolRefAttr(fctName.str()))); + op->setAttr(mlir::acc::getDeclareActionAttrName(), + mlir::acc::DeclareActionAttr::get( + builder.getContext(), + /*preAlloc=*/{}, /*postAlloc=*/{}, /*preDealloc=*/{}, + /*postDealloc=*/builder.getSymbolRefAttr(fctName.str()))); } } diff --git a/flang/lib/Lower/OpenMP/DataSharingProcessor.cpp b/flang/lib/Lower/OpenMP/DataSharingProcessor.cpp index 8bb2f83282b5565fd651f439f42f55b84443cd34..d94c32375c0dc3f8c772d25a51834e9969c0071d 100644 --- a/flang/lib/Lower/OpenMP/DataSharingProcessor.cpp +++ b/flang/lib/Lower/OpenMP/DataSharingProcessor.cpp @@ -135,6 +135,12 @@ void DataSharingProcessor::insertBarrier() { } void DataSharingProcessor::insertLastPrivateCompare(mlir::Operation *op) { + mlir::omp::LoopNestOp loopOp; + if (auto wrapper = mlir::dyn_cast(op)) + loopOp = wrapper.isWrapper() + ? mlir::cast(wrapper.getWrappedLoop()) + : nullptr; + bool cmpCreated = false; mlir::OpBuilder::InsertionGuard guard(firOpBuilder); for (const omp::Clause &clause : clauses) { @@ -214,18 +220,20 @@ void DataSharingProcessor::insertLastPrivateCompare(mlir::Operation *op) { // Update the original variable just before exiting the worksharing // loop. Conversion as follows: // - // omp.wsloop { - // omp.wsloop { ... - // ... store - // store ===> %v = arith.addi %iv, %step - // omp.yield %cmp = %step < 0 ? %v < %ub : %v > %ub - // } fir.if %cmp { - // fir.store %v to %loopIV - // ^%lpv_update_blk: - // } - // omp.yield - // } - // + // omp.wsloop { omp.wsloop { + // omp.loop_nest { omp.loop_nest { + // ... ... + // store ===> store + // omp.yield %v = arith.addi %iv, %step + // } %cmp = %step < 0 ? %v < %ub : %v > %ub + // omp.terminator fir.if %cmp { + // } fir.store %v to %loopIV + // ^%lpv_update_blk: + // } + // omp.yield + // } + // omp.terminator + // } // Only generate the compare once in presence of multiple LastPrivate // clauses. @@ -233,14 +241,13 @@ void DataSharingProcessor::insertLastPrivateCompare(mlir::Operation *op) { continue; cmpCreated = true; - mlir::Location loc = op->getLoc(); - mlir::Operation *lastOper = op->getRegion(0).back().getTerminator(); + mlir::Location loc = loopOp.getLoc(); + mlir::Operation *lastOper = loopOp.getRegion().back().getTerminator(); firOpBuilder.setInsertionPoint(lastOper); - mlir::Value iv = op->getRegion(0).front().getArguments()[0]; - mlir::Value ub = - mlir::dyn_cast(op).getUpperBound()[0]; - mlir::Value step = mlir::dyn_cast(op).getStep()[0]; + mlir::Value iv = loopOp.getIVs()[0]; + mlir::Value ub = loopOp.getUpperBound()[0]; + mlir::Value step = loopOp.getStep()[0]; // v = iv + step // cmp = step < 0 ? v < ub : v > ub @@ -259,7 +266,7 @@ void DataSharingProcessor::insertLastPrivateCompare(mlir::Operation *op) { auto ifOp = firOpBuilder.create(loc, cmpOp, /*else*/ false); firOpBuilder.setInsertionPointToStart(&ifOp.getThenRegion().front()); assert(loopIV && "loopIV was not set"); - firOpBuilder.create(op->getLoc(), v, loopIV); + firOpBuilder.create(loopOp.getLoc(), v, loopIV); lastPrivIP = firOpBuilder.saveInsertionPoint(); } else { TODO(converter.getCurrentLocation(), @@ -332,6 +339,7 @@ void DataSharingProcessor::defaultPrivatize( if (!Fortran::semantics::IsProcedure(*sym) && !sym->GetUltimate().has() && !sym->GetUltimate().has() && + !Fortran::semantics::IsImpliedDoIndex(sym->GetUltimate()) && !symbolsInNestedRegions.contains(sym) && !symbolsInParentRegions.contains(sym) && !privatizedSymbols.contains(sym)) diff --git a/flang/lib/Lower/OpenMP/OpenMP.cpp b/flang/lib/Lower/OpenMP/OpenMP.cpp index e932f7c284bca89fc60cc6ab0115ef687a8e5807..f454f5a45a5150ded64e8f351aa53027b350a55f 100644 --- a/flang/lib/Lower/OpenMP/OpenMP.cpp +++ b/flang/lib/Lower/OpenMP/OpenMP.cpp @@ -366,10 +366,29 @@ getDeclareTargetFunctionDevice( return std::nullopt; } -static llvm::SmallVector +/// Set up the entry block of the given `omp.loop_nest` operation, adding a +/// block argument for each loop induction variable and allocating and +/// initializing a private value to hold each of them. +/// +/// This function can also bind the symbols of any variables that should match +/// block arguments on parent loop wrapper operations attached to the same +/// loop. This allows the introduction of any necessary `hlfir.declare` +/// operations inside of the entry block of the `omp.loop_nest` operation and +/// not directly under any of the wrappers, which would invalidate them. +/// +/// \param [in] op - the loop nest operation. +/// \param [in] converter - PFT to MLIR conversion interface. +/// \param [in] loc - location. +/// \param [in] args - symbols of induction variables. +/// \param [in] wrapperSyms - symbols of variables to be mapped to loop wrapper +/// entry block arguments. +/// \param [in] wrapperArgs - entry block arguments of parent loop wrappers. +static void genLoopVars(mlir::Operation *op, Fortran::lower::AbstractConverter &converter, mlir::Location &loc, - llvm::ArrayRef args) { + llvm::ArrayRef args, + llvm::ArrayRef wrapperSyms = {}, + llvm::ArrayRef wrapperArgs = {}) { fir::FirOpBuilder &firOpBuilder = converter.getFirOpBuilder(); auto ®ion = op->getRegion(0); @@ -380,6 +399,12 @@ genLoopVars(mlir::Operation *op, Fortran::lower::AbstractConverter &converter, llvm::SmallVector tiv(args.size(), loopVarType); llvm::SmallVector locs(args.size(), loc); firOpBuilder.createBlock(®ion, {}, tiv, locs); + + // Bind the entry block arguments of parent wrappers to the corresponding + // symbols. + for (auto [arg, prv] : llvm::zip_equal(wrapperSyms, wrapperArgs)) + converter.bindSymbol(*arg, prv); + // The argument is not currently in memory, so make a temporary for the // argument, and store it there, then bind that location to the argument. mlir::Operation *storeOp = nullptr; @@ -389,7 +414,6 @@ genLoopVars(mlir::Operation *op, Fortran::lower::AbstractConverter &converter, createAndSetPrivatizedLoopVar(converter, loc, indexVal, argSymbol); } firOpBuilder.setInsertionPointAfter(storeOp); - return llvm::SmallVector(args); } static void genReductionVars( @@ -410,58 +434,6 @@ static void genReductionVars( } } -static llvm::SmallVector -genLoopAndReductionVars( - mlir::Operation *op, Fortran::lower::AbstractConverter &converter, - mlir::Location &loc, - llvm::ArrayRef loopArgs, - llvm::ArrayRef reductionArgs, - llvm::ArrayRef reductionTypes) { - fir::FirOpBuilder &firOpBuilder = converter.getFirOpBuilder(); - - llvm::SmallVector blockArgTypes; - llvm::SmallVector blockArgLocs; - blockArgTypes.reserve(loopArgs.size() + reductionArgs.size()); - blockArgLocs.reserve(blockArgTypes.size()); - mlir::Block *entryBlock; - - if (loopArgs.size()) { - std::size_t loopVarTypeSize = 0; - for (const Fortran::semantics::Symbol *arg : loopArgs) - loopVarTypeSize = std::max(loopVarTypeSize, arg->GetUltimate().size()); - mlir::Type loopVarType = getLoopVarType(converter, loopVarTypeSize); - std::fill_n(std::back_inserter(blockArgTypes), loopArgs.size(), - loopVarType); - std::fill_n(std::back_inserter(blockArgLocs), loopArgs.size(), loc); - } - if (reductionArgs.size()) { - llvm::copy(reductionTypes, std::back_inserter(blockArgTypes)); - std::fill_n(std::back_inserter(blockArgLocs), reductionArgs.size(), loc); - } - entryBlock = firOpBuilder.createBlock(&op->getRegion(0), {}, blockArgTypes, - blockArgLocs); - // The argument is not currently in memory, so make a temporary for the - // argument, and store it there, then bind that location to the argument. - if (loopArgs.size()) { - mlir::Operation *storeOp = nullptr; - for (auto [argIndex, argSymbol] : llvm::enumerate(loopArgs)) { - mlir::Value indexVal = - fir::getBase(op->getRegion(0).front().getArgument(argIndex)); - storeOp = - createAndSetPrivatizedLoopVar(converter, loc, indexVal, argSymbol); - } - firOpBuilder.setInsertionPointAfter(storeOp); - } - // Bind the reduction arguments to their block arguments - for (auto [arg, prv] : llvm::zip_equal( - reductionArgs, - llvm::drop_begin(entryBlock->getArguments(), loopArgs.size()))) { - converter.bindSymbol(*arg, prv); - } - - return llvm::SmallVector(loopArgs); -} - static void markDeclareTarget(mlir::Operation *op, Fortran::lower::AbstractConverter &converter, @@ -1270,20 +1242,16 @@ static void genTeamsClauses(Fortran::lower::AbstractConverter &converter, static void genWsloopClauses( Fortran::lower::AbstractConverter &converter, Fortran::semantics::SemanticsContext &semaCtx, - Fortran::lower::StatementContext &stmtCtx, - Fortran::lower::pft::Evaluation &eval, const List &clauses, + Fortran::lower::StatementContext &stmtCtx, const List &clauses, mlir::Location loc, mlir::omp::WsloopClauseOps &clauseOps, - llvm::SmallVectorImpl &iv, llvm::SmallVectorImpl &reductionTypes, llvm::SmallVectorImpl &reductionSyms) { fir::FirOpBuilder &firOpBuilder = converter.getFirOpBuilder(); ClauseProcessor cp(converter, semaCtx, clauses); - cp.processCollapse(loc, eval, clauseOps, iv); cp.processNowait(clauseOps); cp.processOrdered(clauseOps); cp.processReduction(loc, clauseOps, &reductionTypes, &reductionSyms); cp.processSchedule(stmtCtx, clauseOps); - clauseOps.loopInclusiveAttr = firOpBuilder.getUnitAttr(); // TODO Support delayed privatization. if (ReductionProcessor::doReductionByRef(clauseOps.reductionVars)) @@ -1526,7 +1494,8 @@ genSimdOp(Fortran::lower::AbstractConverter &converter, auto *nestedEval = getCollapsedLoopEval(eval, getCollapseValue(clauses)); auto ivCallback = [&](mlir::Operation *op) { - return genLoopVars(op, converter, loc, iv); + genLoopVars(op, converter, loc, iv); + return iv; }; createBodyOfOp(*loopOp, @@ -1801,32 +1770,48 @@ genWsloopOp(Fortran::lower::AbstractConverter &converter, Fortran::semantics::SemanticsContext &semaCtx, Fortran::lower::pft::Evaluation &eval, mlir::Location loc, const List &clauses) { + fir::FirOpBuilder &firOpBuilder = converter.getFirOpBuilder(); DataSharingProcessor dsp(converter, semaCtx, clauses, eval); dsp.processStep1(); Fortran::lower::StatementContext stmtCtx; - mlir::omp::WsloopClauseOps clauseOps; + mlir::omp::LoopNestClauseOps loopClauseOps; + mlir::omp::WsloopClauseOps wsClauseOps; llvm::SmallVector iv; llvm::SmallVector reductionTypes; llvm::SmallVector reductionSyms; - genWsloopClauses(converter, semaCtx, stmtCtx, eval, clauses, loc, clauseOps, - iv, reductionTypes, reductionSyms); + genLoopNestClauses(converter, semaCtx, eval, clauses, loc, loopClauseOps, iv); + genWsloopClauses(converter, semaCtx, stmtCtx, clauses, loc, wsClauseOps, + reductionTypes, reductionSyms); + + // Create omp.wsloop wrapper and populate entry block arguments with reduction + // variables. + auto wsloopOp = firOpBuilder.create(loc, wsClauseOps); + llvm::SmallVector reductionLocs(reductionSyms.size(), loc); + mlir::Block *wsloopEntryBlock = firOpBuilder.createBlock( + &wsloopOp.getRegion(), {}, reductionTypes, reductionLocs); + firOpBuilder.setInsertionPoint( + Fortran::lower::genOpenMPTerminator(firOpBuilder, wsloopOp, loc)); + + // Create nested omp.loop_nest and fill body with loop contents. + auto loopOp = firOpBuilder.create(loc, loopClauseOps); auto *nestedEval = getCollapsedLoopEval(eval, getCollapseValue(clauses)); auto ivCallback = [&](mlir::Operation *op) { - return genLoopAndReductionVars(op, converter, loc, iv, reductionSyms, - reductionTypes); + genLoopVars(op, converter, loc, iv, reductionSyms, + wsloopEntryBlock->getArguments()); + return iv; }; - return genOpWithBody( - OpWithBodyGenInfo(converter, semaCtx, loc, *nestedEval, - llvm::omp::Directive::OMPD_do) - .setClauses(&clauses) - .setDataSharingProcessor(&dsp) - .setReductions(&reductionSyms, &reductionTypes) - .setGenRegionEntryCb(ivCallback), - clauseOps); + createBodyOfOp(*loopOp, + OpWithBodyGenInfo(converter, semaCtx, loc, *nestedEval, + llvm::omp::Directive::OMPD_do) + .setClauses(&clauses) + .setDataSharingProcessor(&dsp) + .setReductions(&reductionSyms, &reductionTypes) + .setGenRegionEntryCb(ivCallback)); + return wsloopOp; } //===----------------------------------------------------------------------===// @@ -2482,8 +2467,8 @@ static void genOMP(Fortran::lower::AbstractConverter &converter, mlir::Operation *Fortran::lower::genOpenMPTerminator(fir::FirOpBuilder &builder, mlir::Operation *op, mlir::Location loc) { - if (mlir::isa(op)) + if (mlir::isa(op)) return builder.create(loc); return builder.create(loc); } diff --git a/flang/lib/Lower/OpenMP/ReductionProcessor.cpp b/flang/lib/Lower/OpenMP/ReductionProcessor.cpp index 23fabaf34abac1d43cbe6ab13ad65bb2f66503de..895340549f7c67d33a1a093b235c3ec079f06d88 100644 --- a/flang/lib/Lower/OpenMP/ReductionProcessor.cpp +++ b/flang/lib/Lower/OpenMP/ReductionProcessor.cpp @@ -295,6 +295,33 @@ mlir::Value ReductionProcessor::createScalarCombiner( return reductionOp; } +/// Generate a fir::ShapeShift op describing the provided boxed array. +static fir::ShapeShiftOp getShapeShift(fir::FirOpBuilder &builder, + mlir::Location loc, mlir::Value box) { + fir::SequenceType sequenceType = mlir::cast( + hlfir::getFortranElementOrSequenceType(box.getType())); + const unsigned rank = sequenceType.getDimension(); + llvm::SmallVector lbAndExtents; + lbAndExtents.reserve(rank * 2); + + mlir::Type idxTy = builder.getIndexType(); + for (unsigned i = 0; i < rank; ++i) { + // TODO: ideally we want to hoist box reads out of the critical section. + // We could do this by having box dimensions in block arguments like + // OpenACC does + mlir::Value dim = builder.createIntegerConstant(loc, idxTy, i); + auto dimInfo = + builder.create(loc, idxTy, idxTy, idxTy, box, dim); + lbAndExtents.push_back(dimInfo.getLowerBound()); + lbAndExtents.push_back(dimInfo.getExtent()); + } + + auto shapeShiftTy = fir::ShapeShiftType::get(builder.getContext(), rank); + auto shapeShift = + builder.create(loc, shapeShiftTy, lbAndExtents); + return shapeShift; +} + /// Create reduction combiner region for reduction variables which are boxed /// arrays static void genBoxCombiner(fir::FirOpBuilder &builder, mlir::Location loc, @@ -330,29 +357,7 @@ static void genBoxCombiner(fir::FirOpBuilder &builder, mlir::Location loc, return; } - const unsigned rank = seqTy.getDimension(); - llvm::SmallVector extents; - extents.reserve(rank); - llvm::SmallVector lbAndExtents; - lbAndExtents.reserve(rank * 2); - - // Get box lowerbounds and extents: - mlir::Type idxTy = builder.getIndexType(); - for (unsigned i = 0; i < rank; ++i) { - // TODO: ideally we want to hoist box reads out of the critical section. - // We could do this by having box dimensions in block arguments like - // OpenACC does - mlir::Value dim = builder.createIntegerConstant(loc, idxTy, i); - auto dimInfo = - builder.create(loc, idxTy, idxTy, idxTy, lhs, dim); - extents.push_back(dimInfo.getExtent()); - lbAndExtents.push_back(dimInfo.getLowerBound()); - lbAndExtents.push_back(dimInfo.getExtent()); - } - - auto shapeShiftTy = fir::ShapeShiftType::get(builder.getContext(), rank); - auto shapeShift = - builder.create(loc, shapeShiftTy, lbAndExtents); + fir::ShapeShiftOp shapeShift = getShapeShift(builder, loc, lhs); // Iterate over array elements, applying the equivalent scalar reduction: @@ -364,8 +369,8 @@ static void genBoxCombiner(fir::FirOpBuilder &builder, mlir::Location loc, // loop nest directly. // This function already controls all of the code in this region so we // know this won't miss any opportuinties for clever elemental inlining - hlfir::LoopNest nest = - hlfir::genLoopNest(loc, builder, extents, /*isUnordered=*/true); + hlfir::LoopNest nest = hlfir::genLoopNest( + loc, builder, shapeShift.getExtents(), /*isUnordered=*/true); builder.setInsertionPointToStart(nest.innerLoop.getBody()); mlir::Type refTy = fir::ReferenceType::get(seqTy.getEleTy()); auto lhsEleAddr = builder.create( @@ -561,7 +566,8 @@ createReductionInitRegion(fir::FirOpBuilder &builder, mlir::Location loc, } // Create the private copy from the initial fir.box: - hlfir::Entity source = hlfir::Entity{blockArg}; + mlir::Value loadedBox = builder.loadIfRef(loc, blockArg); + hlfir::Entity source = hlfir::Entity{loadedBox}; // Allocating on the heap in case the whole reduction is nested inside of a // loop @@ -585,11 +591,23 @@ createReductionInitRegion(fir::FirOpBuilder &builder, mlir::Location loc, } // Put the temporary inside of a box: - hlfir::Entity box = hlfir::genVariableBox(loc, builder, temp); - // hlfir::genVariableBox removes fir.heap<> around the element type - mlir::Value convertedBox = builder.createConvert(loc, ty, box.getBase()); - builder.create(loc, initValue, convertedBox); - builder.create(loc, convertedBox, boxAlloca); + // hlfir::genVariableBox doesn't handle non-default lower bounds + mlir::Value box; + fir::ShapeShiftOp shapeShift = getShapeShift(builder, loc, loadedBox); + mlir::Type boxType = loadedBox.getType(); + if (mlir::isa(temp.getType())) + // the box created by the declare form createTempFromMold is missing lower + // bounds info + box = builder.create(loc, boxType, temp, shapeShift, + /*shift=*/mlir::Value{}); + else + box = builder.create( + loc, boxType, temp, shapeShift, + /*slice=*/mlir::Value{}, + /*typeParams=*/llvm::ArrayRef{}); + + builder.create(loc, initValue, box); + builder.create(loc, box, boxAlloca); if (ifUnallocated) builder.setInsertionPointAfter(ifUnallocated); return boxAlloca; diff --git a/flang/lib/Optimizer/Builder/IntrinsicCall.cpp b/flang/lib/Optimizer/Builder/IntrinsicCall.cpp index 4ee7258004fa74d7a6be6d59437d0f85b9959cc0..e28d14cd318d368a90dcc933efa49c4eed5b4033 100644 --- a/flang/lib/Optimizer/Builder/IntrinsicCall.cpp +++ b/flang/lib/Optimizer/Builder/IntrinsicCall.cpp @@ -554,6 +554,10 @@ static constexpr IntrinsicHandler handlers[]{ {"radix", asAddr, handleDynamicOptional}}}, /*isElemental=*/false}, {"set_exponent", &I::genSetExponent}, + {"shape", + &I::genShape, + {{{"source", asBox}, {"kind", asValue}}}, + /*isElemental=*/false}, {"shifta", &I::genShiftA}, {"shiftl", &I::genShift}, {"shiftr", &I::genShift}, @@ -5821,6 +5825,35 @@ mlir::Value IntrinsicLibrary::genSetExponent(mlir::Type resultType, fir::getBase(args[1]))); } +// SHAPE +fir::ExtendedValue +IntrinsicLibrary::genShape(mlir::Type resultType, + llvm::ArrayRef args) { + assert(args.size() >= 1); + const fir::ExtendedValue &array = args[0]; + int rank = array.rank(); + if (rank == 0) + TODO(loc, "shape intrinsic lowering with assumed-rank source"); + mlir::Type indexType = builder.getIndexType(); + mlir::Type extentType = fir::unwrapSequenceType(resultType); + mlir::Type seqType = fir::SequenceType::get( + {static_cast(rank)}, extentType); + mlir::Value shapeArray = builder.createTemporary(loc, seqType); + mlir::Type shapeAddrType = builder.getRefType(extentType); + for (int dim = 0; dim < rank; ++dim) { + mlir::Value extent = fir::factory::readExtent(builder, loc, array, dim); + extent = builder.createConvert(loc, extentType, extent); + auto index = builder.createIntegerConstant(loc, indexType, dim); + auto shapeAddr = builder.create(loc, shapeAddrType, + shapeArray, index); + builder.create(loc, extent, shapeAddr); + } + mlir::Value shapeArrayExtent = + builder.createIntegerConstant(loc, indexType, rank); + llvm::SmallVector extents{shapeArrayExtent}; + return fir::ArrayBoxValue{shapeArray, extents}; +} + // SHIFTL, SHIFTR template mlir::Value IntrinsicLibrary::genShift(mlir::Type resultType, diff --git a/flang/lib/Optimizer/Transforms/AddDebugInfo.cpp b/flang/lib/Optimizer/Transforms/AddDebugInfo.cpp index 4ca338066128768b0f5b5532997dd2fb7e871171..68584bef055b61e2e4e23503c0225b893488dcd7 100644 --- a/flang/lib/Optimizer/Transforms/AddDebugInfo.cpp +++ b/flang/lib/Optimizer/Transforms/AddDebugInfo.cpp @@ -11,12 +11,14 @@ /// This pass populates some debug information for the module and functions. //===----------------------------------------------------------------------===// +#include "flang/Common/Version.h" #include "flang/Optimizer/Builder/FIRBuilder.h" #include "flang/Optimizer/Builder/Todo.h" #include "flang/Optimizer/Dialect/FIRDialect.h" #include "flang/Optimizer/Dialect/FIROps.h" #include "flang/Optimizer/Dialect/FIRType.h" #include "flang/Optimizer/Dialect/Support/FIRContext.h" +#include "flang/Optimizer/Support/InternalNames.h" #include "flang/Optimizer/Transforms/Passes.h" #include "mlir/Dialect/Func/IR/FuncOps.h" #include "mlir/Dialect/LLVMIR/LLVMDialect.h" @@ -28,12 +30,12 @@ #include "mlir/Transforms/RegionUtils.h" #include "llvm/BinaryFormat/Dwarf.h" #include "llvm/Support/Debug.h" +#include "llvm/Support/FileSystem.h" #include "llvm/Support/Path.h" #include "llvm/Support/raw_ostream.h" namespace fir { #define GEN_PASS_DEF_ADDDEBUGINFO -#define GEN_PASS_DECL_ADDDEBUGINFO #include "flang/Optimizer/Transforms/Passes.h.inc" } // namespace fir @@ -43,6 +45,7 @@ namespace { class AddDebugInfoPass : public fir::impl::AddDebugInfoBase { public: + AddDebugInfoPass(fir::AddDebugInfoOptions options) : Base(options) {} void runOnOperation() override; }; @@ -52,21 +55,40 @@ void AddDebugInfoPass::runOnOperation() { mlir::ModuleOp module = getOperation(); mlir::MLIRContext *context = &getContext(); mlir::OpBuilder builder(context); - std::string inputFilePath("-"); - if (auto fileLoc = module.getLoc().dyn_cast()) - inputFilePath = fileLoc.getFilename().getValue(); + llvm::StringRef fileName; + std::string filePath; + // We need 2 type of file paths here. + // 1. Name of the file as was presented to compiler. This can be absolute + // or relative to 2. + // 2. Current working directory + // + // We are also dealing with 2 different situations below. One is normal + // compilation where we will have a value in 'inputFilename' and we can + // obtain the current directory using 'current_path'. + // The 2nd case is when this pass is invoked directly from 'fir-opt' tool. + // In that case, 'inputFilename' may be empty. Location embedded in the + // module will be used to get file name and its directory. + if (inputFilename.empty()) { + if (auto fileLoc = module.getLoc().dyn_cast()) { + fileName = llvm::sys::path::filename(fileLoc.getFilename().getValue()); + filePath = llvm::sys::path::parent_path(fileLoc.getFilename().getValue()); + } else + fileName = "-"; + } else { + fileName = inputFilename; + llvm::SmallString<256> cwd; + if (!llvm::sys::fs::current_path(cwd)) + filePath = cwd.str(); + } - auto getFileAttr = [context](llvm::StringRef path) -> mlir::LLVM::DIFileAttr { - return mlir::LLVM::DIFileAttr::get(context, llvm::sys::path::filename(path), - llvm::sys::path::parent_path(path)); - }; - - mlir::LLVM::DIFileAttr fileAttr = getFileAttr(inputFilePath); - mlir::StringAttr producer = mlir::StringAttr::get(context, "Flang"); + mlir::LLVM::DIFileAttr fileAttr = + mlir::LLVM::DIFileAttr::get(context, fileName, filePath); + mlir::StringAttr producer = + mlir::StringAttr::get(context, Fortran::common::getFlangFullVersion()); mlir::LLVM::DICompileUnitAttr cuAttr = mlir::LLVM::DICompileUnitAttr::get( mlir::DistinctAttr::create(mlir::UnitAttr::get(context)), llvm::dwarf::getLanguage("DW_LANG_Fortran95"), fileAttr, producer, - /*isOptimized=*/false, mlir::LLVM::DIEmissionKind::LineTablesOnly); + isOptimized, debugLevel); module.walk([&](mlir::func::FuncOp funcOp) { mlir::Location l = funcOp->getLoc(); @@ -75,43 +97,49 @@ void AddDebugInfoPass::runOnOperation() { if (l.dyn_cast()) return; - llvm::StringRef funcFilePath; - if (l.dyn_cast()) - funcFilePath = - l.dyn_cast().getFilename().getValue(); - else - funcFilePath = inputFilePath; + unsigned int CC = (funcOp.getName() == fir::NameUniquer::doProgramEntry()) + ? llvm::dwarf::getCallingConvention("DW_CC_program") + : llvm::dwarf::getCallingConvention("DW_CC_normal"); + + if (auto funcLoc = l.dyn_cast()) { + fileName = llvm::sys::path::filename(funcLoc.getFilename().getValue()); + filePath = llvm::sys::path::parent_path(funcLoc.getFilename().getValue()); + } mlir::StringAttr funcName = mlir::StringAttr::get(context, funcOp.getName()); mlir::LLVM::DIBasicTypeAttr bT = mlir::LLVM::DIBasicTypeAttr::get( context, llvm::dwarf::DW_TAG_base_type, "void", /*sizeInBits=*/0, /*encoding=*/1); + // FIXME: Provide proper type for subroutine mlir::LLVM::DISubroutineTypeAttr subTypeAttr = - mlir::LLVM::DISubroutineTypeAttr::get( - context, llvm::dwarf::getCallingConvention("DW_CC_normal"), - {bT, bT}); - mlir::LLVM::DIFileAttr funcFileAttr = getFileAttr(funcFilePath); + mlir::LLVM::DISubroutineTypeAttr::get(context, CC, {bT, bT}); + mlir::LLVM::DIFileAttr funcFileAttr = + mlir::LLVM::DIFileAttr::get(context, fileName, filePath); // Only definitions need a distinct identifier and a compilation unit. mlir::DistinctAttr id; mlir::LLVM::DICompileUnitAttr compilationUnit; - auto subprogramFlags = mlir::LLVM::DISubprogramFlags::Optimized; + mlir::LLVM::DISubprogramFlags subprogramFlags = + mlir::LLVM::DISubprogramFlags{}; + if (isOptimized) + subprogramFlags = mlir::LLVM::DISubprogramFlags::Optimized; if (!funcOp.isExternal()) { id = mlir::DistinctAttr::create(mlir::UnitAttr::get(context)); compilationUnit = cuAttr; subprogramFlags = subprogramFlags | mlir::LLVM::DISubprogramFlags::Definition; } + // FIXME: Provide proper line and scopeline. auto spAttr = mlir::LLVM::DISubprogramAttr::get( context, id, compilationUnit, fileAttr, funcName, funcName, - funcFileAttr, - /*line=*/1, - /*scopeline=*/1, subprogramFlags, subTypeAttr); + funcFileAttr, /*line=*/1, /*scopeline=*/1, subprogramFlags, + subTypeAttr); funcOp->setLoc(builder.getFusedLoc({funcOp->getLoc()}, spAttr)); }); } -std::unique_ptr fir::createAddDebugInfoPass() { - return std::make_unique(); +std::unique_ptr +fir::createAddDebugInfoPass(fir::AddDebugInfoOptions options) { + return std::make_unique(options); } diff --git a/flang/lib/Optimizer/Transforms/CMakeLists.txt b/flang/lib/Optimizer/Transforms/CMakeLists.txt index d55655c53906e62c6d77a24b77781d423f0c242e..fc08d67540ceb0770bdf469b6203c792b437f7f6 100644 --- a/flang/lib/Optimizer/Transforms/CMakeLists.txt +++ b/flang/lib/Optimizer/Transforms/CMakeLists.txt @@ -35,6 +35,7 @@ add_flang_library(FIRTransforms FIRDialect FIRDialectSupport FIRSupport + FortranCommon HLFIRDialect MLIRAffineUtils MLIRFuncDialect diff --git a/flang/lib/Optimizer/Transforms/CharacterConversion.cpp b/flang/lib/Optimizer/Transforms/CharacterConversion.cpp index 2e8fc42487a5f6753425a2f0b31f7ad9d5c8496d..87ea72dbca9bbc7011732a3d8bb4736cfd3651fa 100644 --- a/flang/lib/Optimizer/Transforms/CharacterConversion.cpp +++ b/flang/lib/Optimizer/Transforms/CharacterConversion.cpp @@ -102,6 +102,9 @@ public: class CharacterConversion : public fir::impl::CharacterConversionBase { public: + using fir::impl::CharacterConversionBase< + CharacterConversion>::CharacterConversionBase; + void runOnOperation() override { CharacterConversionOptions clOpts{useRuntimeCalls.getValue()}; if (clOpts.runtimeName.empty()) { @@ -130,7 +133,3 @@ public: } }; } // end anonymous namespace - -std::unique_ptr fir::createCharacterConversionPass() { - return std::make_unique(); -} diff --git a/flang/lib/Optimizer/Transforms/ControlFlowConverter.cpp b/flang/lib/Optimizer/Transforms/ControlFlowConverter.cpp index 45609a99995d0a03ed65550cbc9a708388cb9dc8..a62f6cde0e09b8a30271e9ebc607bcd8258c5067 100644 --- a/flang/lib/Optimizer/Transforms/ControlFlowConverter.cpp +++ b/flang/lib/Optimizer/Transforms/ControlFlowConverter.cpp @@ -24,8 +24,7 @@ #include "llvm/Support/CommandLine.h" namespace fir { -#define GEN_PASS_DEF_CFGCONVERSIONONFUNC -#define GEN_PASS_DEF_CFGCONVERSIONONREDUCTION +#define GEN_PASS_DEF_CFGCONVERSION #include "flang/Optimizer/Transforms/Passes.h.inc" } // namespace fir @@ -309,9 +308,10 @@ public: }; /// Convert FIR structured control flow ops to CFG ops. -template class PassBase> -class CfgConversionTemplate : public PassBase { +class CfgConversion : public fir::impl::CFGConversionBase { public: + using CFGConversionBase::CFGConversionBase; + void runOnOperation() override { auto *context = &this->getContext(); mlir::RewritePatternSet patterns(context); @@ -333,14 +333,6 @@ public: } }; -class CfgConversionOnFunc - : public CfgConversionTemplate {}; - -class CfgConversionOnReduction - : public CfgConversionTemplate { -}; } // namespace /// Expose conversion rewriters to other passes @@ -349,13 +341,3 @@ void fir::populateCfgConversionRewrites(mlir::RewritePatternSet &patterns, patterns.insert( patterns.getContext(), forceLoopToExecuteOnce); } - -/// Convert FIR's structured control flow ops to CFG ops. This -/// conversion enables the `createLowerToCFGPass` to transform these to CFG -/// form. -std::unique_ptr fir::createFirToCfgOnFuncPass() { - return std::make_unique(); -} -std::unique_ptr fir::createFirToCfgOnReductionPass() { - return std::make_unique(); -} diff --git a/flang/lib/Optimizer/Transforms/LoopVersioning.cpp b/flang/lib/Optimizer/Transforms/LoopVersioning.cpp index 7cbd2dd1f897a5f7921de212cd2ed75df343d364..0afc9c24b45b0ff7f8f267e04f89517760a7efc4 100644 --- a/flang/lib/Optimizer/Transforms/LoopVersioning.cpp +++ b/flang/lib/Optimizer/Transforms/LoopVersioning.cpp @@ -556,7 +556,3 @@ void LoopVersioningPass::runOnOperation() { LLVM_DEBUG(llvm::dbgs() << "=== End " DEBUG_TYPE " ===\n"); } - -std::unique_ptr fir::createLoopVersioningPass() { - return std::make_unique(); -} diff --git a/flang/lib/Optimizer/Transforms/MemoryAllocation.cpp b/flang/lib/Optimizer/Transforms/MemoryAllocation.cpp index 166a6b10def29354cb1e8f1388d85f1818960166..40b452a6202b07287b8d0f7c5fbe431fe62c2251 100644 --- a/flang/lib/Optimizer/Transforms/MemoryAllocation.cpp +++ b/flang/lib/Optimizer/Transforms/MemoryAllocation.cpp @@ -28,17 +28,6 @@ namespace fir { static constexpr std::size_t unlimitedArraySize = ~static_cast(0); namespace { -struct MemoryAllocationOptions { - // Always move dynamic array allocations to the heap. This may result in more - // heap fragmentation, so may impact performance negatively. - bool dynamicArrayOnHeap = false; - - // Number of elements in array threshold for moving to heap. In environments - // with limited stack size, moving large arrays to the heap can avoid running - // out of stack space. - std::size_t maxStackArraySize = unlimitedArraySize; -}; - class ReturnAnalysis { public: MLIR_DEFINE_EXPLICIT_INTERNAL_INLINE_TYPE_ID(ReturnAnalysis) @@ -68,8 +57,9 @@ private: /// Return `true` if this allocation is to remain on the stack (`fir.alloca`). /// Otherwise the allocation should be moved to the heap (`fir.allocmem`). -static inline bool keepStackAllocation(fir::AllocaOp alloca, mlir::Block *entry, - const MemoryAllocationOptions &options) { +static inline bool +keepStackAllocation(fir::AllocaOp alloca, mlir::Block *entry, + const fir::MemoryAllocationOptOptions &options) { // Limitation: only arrays allocated on the stack in the entry block are // considered for now. // TODO: Generalize the algorithm and placement of the freemem nodes. @@ -168,6 +158,9 @@ public: options = {dynOnHeap, maxStackSize}; } + MemoryAllocationOpt(const fir::MemoryAllocationOptOptions &options) + : options{options} {} + /// Override `options` if command-line options have been set. inline void useCommandLineOptions() { if (dynamicArrayOnHeap) @@ -211,15 +204,6 @@ public: } private: - MemoryAllocationOptions options; + fir::MemoryAllocationOptOptions options; }; } // namespace - -std::unique_ptr fir::createMemoryAllocationPass() { - return std::make_unique(); -} - -std::unique_ptr -fir::createMemoryAllocationPass(bool dynOnHeap, std::size_t maxStackSize) { - return std::make_unique(dynOnHeap, maxStackSize); -} diff --git a/flang/lib/Optimizer/Transforms/OMPFunctionFiltering.cpp b/flang/lib/Optimizer/Transforms/OMPFunctionFiltering.cpp index 959099d039a5e60f4fbc76b160862355bc7449f0..005e84cb8e9f9a2a307094f4b54f58e62e04b422 100644 --- a/flang/lib/Optimizer/Transforms/OMPFunctionFiltering.cpp +++ b/flang/lib/Optimizer/Transforms/OMPFunctionFiltering.cpp @@ -12,6 +12,7 @@ //===----------------------------------------------------------------------===// #include "flang/Optimizer/Dialect/FIRDialect.h" +#include "flang/Optimizer/Dialect/FIROpsSupport.h" #include "flang/Optimizer/Transforms/Passes.h" #include "mlir/Dialect/Func/IR/FuncOps.h" @@ -66,6 +67,16 @@ public: SymbolTable::UseRange funcUses = *funcOp.getSymbolUses(op); for (SymbolTable::SymbolUse use : funcUses) { Operation *callOp = use.getUser(); + if (auto internalFunc = mlir::dyn_cast(callOp)) { + // Do not delete internal procedures holding the symbol of their + // Fortran host procedure as attribute. + internalFunc->removeAttr(fir::getHostSymbolAttrName()); + // Set public visibility so that the function is not deleted by MLIR + // because unused. Changing it is OK here because the function will + // be deleted anyway in the second filtering phase. + internalFunc.setVisibility(mlir::SymbolTable::Visibility::Public); + continue; + } // If the callOp has users then replace them with Undef values. if (!callOp->use_empty()) { SmallVector undefResults; diff --git a/flang/lib/Optimizer/Transforms/SimplifyIntrinsics.cpp b/flang/lib/Optimizer/Transforms/SimplifyIntrinsics.cpp index f7820b6b8170ba075bd15ed1af6a202ee3da466d..a4f2f5238e4038f8e5fd9027cc3e91b7030b49e2 100644 --- a/flang/lib/Optimizer/Transforms/SimplifyIntrinsics.cpp +++ b/flang/lib/Optimizer/Transforms/SimplifyIntrinsics.cpp @@ -72,6 +72,9 @@ class SimplifyIntrinsicsPass mlir::Type elementType)>; public: + using fir::impl::SimplifyIntrinsicsBase< + SimplifyIntrinsicsPass>::SimplifyIntrinsicsBase; + /// Generate a new function implementing a simplified version /// of a Fortran runtime function defined by \p basename name. /// \p typeGenerator is a callback that generates the new function's type. @@ -1387,6 +1390,3 @@ void SimplifyIntrinsicsPass::getDependentDialects( // LLVM::LinkageAttr creation requires that LLVM dialect is loaded. registry.insert(); } -std::unique_ptr fir::createSimplifyIntrinsicsPass() { - return std::make_unique(); -} diff --git a/flang/lib/Optimizer/Transforms/SimplifyRegionLite.cpp b/flang/lib/Optimizer/Transforms/SimplifyRegionLite.cpp index 3fe6bed12cf40c44dd6c6cd361bc5770a82a4283..7d1f86f8cee9443939af194bffcf3a8a87428293 100644 --- a/flang/lib/Optimizer/Transforms/SimplifyRegionLite.cpp +++ b/flang/lib/Optimizer/Transforms/SimplifyRegionLite.cpp @@ -45,7 +45,3 @@ void SimplifyRegionLitePass::runOnOperation() { (void)mlir::eraseUnreachableBlocks(rewriter, regions); (void)mlir::runRegionDCE(rewriter, regions); } - -std::unique_ptr fir::createSimplifyRegionLitePass() { - return std::make_unique(); -} diff --git a/flang/lib/Optimizer/Transforms/StackArrays.cpp b/flang/lib/Optimizer/Transforms/StackArrays.cpp index 1c213abefe6f5f87ca3fcff0195d49ca2fa5176f..c81524dd16a77e92497e16ddb7b19bf3ee03a248 100644 --- a/flang/lib/Optimizer/Transforms/StackArrays.cpp +++ b/flang/lib/Optimizer/Transforms/StackArrays.cpp @@ -776,7 +776,3 @@ void StackArraysPass::runOnFunc(mlir::Operation *func) { signalPassFailure(); } } - -std::unique_ptr fir::createStackArraysPass() { - return std::make_unique(); -} diff --git a/flang/lib/Parser/Fortran-parsers.cpp b/flang/lib/Parser/Fortran-parsers.cpp index 2bdb8e38db95da00dca0c50c0b7fd70d299f2c5d..ff01974b549a1ee9e3f9695f9de09eb1a3700799 100644 --- a/flang/lib/Parser/Fortran-parsers.cpp +++ b/flang/lib/Parser/Fortran-parsers.cpp @@ -123,7 +123,8 @@ TYPE_PARSER(first( TYPE_CONTEXT_PARSER("internal subprogram"_en_US, (construct(indirect(functionSubprogram)) || construct(indirect(subroutineSubprogram))) / - forceEndOfStmt) + forceEndOfStmt || + construct(indirect(compilerDirective))) // R511 internal-subprogram-part -> contains-stmt [internal-subprogram]... TYPE_CONTEXT_PARSER("internal subprogram part"_en_US, diff --git a/flang/lib/Parser/prescan.cpp b/flang/lib/Parser/prescan.cpp index 96db3955299f33d12c30ba4df4b6f297fb9f1d1d..2d46eae531b1861e1b4af62a5ca319b2edd28a29 100644 --- a/flang/lib/Parser/prescan.cpp +++ b/flang/lib/Parser/prescan.cpp @@ -29,15 +29,18 @@ Prescanner::Prescanner(Messages &messages, CookedSource &cooked, Preprocessor &preprocessor, common::LanguageFeatureControl lfc) : messages_{messages}, cooked_{cooked}, preprocessor_{preprocessor}, allSources_{preprocessor_.allSources()}, features_{lfc}, + backslashFreeFormContinuation_{preprocessor.AnyDefinitions()}, encoding_{allSources_.encoding()} {} Prescanner::Prescanner(const Prescanner &that) : messages_{that.messages_}, cooked_{that.cooked_}, preprocessor_{that.preprocessor_}, allSources_{that.allSources_}, - features_{that.features_}, inFixedForm_{that.inFixedForm_}, + features_{that.features_}, + backslashFreeFormContinuation_{that.backslashFreeFormContinuation_}, + inFixedForm_{that.inFixedForm_}, fixedFormColumnLimit_{that.fixedFormColumnLimit_}, - encoding_{that.encoding_}, prescannerNesting_{that.prescannerNesting_ + - 1}, + encoding_{that.encoding_}, + prescannerNesting_{that.prescannerNesting_ + 1}, skipLeadingAmpersand_{that.skipLeadingAmpersand_}, compilerDirectiveBloomFilter_{that.compilerDirectiveBloomFilter_}, compilerDirectiveSentinels_{that.compilerDirectiveSentinels_} {} @@ -1226,9 +1229,14 @@ bool Prescanner::Continuation(bool mightNeedFixedFormSpace) { } else { return FreeFormContinuation(); } - } else { - return false; + } else if (*at_ == '\\' && at_ + 2 == nextLine_ && + backslashFreeFormContinuation_ && !inFixedForm_ && nextLine_ < limit_) { + // cpp-like handling of \ at end of a free form source line + BeginSourceLine(nextLine_); + NextLine(); + return true; } + return false; } std::optional diff --git a/flang/lib/Parser/prescan.h b/flang/lib/Parser/prescan.h index 581980001bcc23dca1eb2a9fa387043797d2e026..3ee4c5a2c69eaaf29b59ea9dc5aa9f36f266e085 100644 --- a/flang/lib/Parser/prescan.h +++ b/flang/lib/Parser/prescan.h @@ -197,6 +197,7 @@ private: Preprocessor &preprocessor_; AllSources &allSources_; common::LanguageFeatureControl features_; + bool backslashFreeFormContinuation_{false}; bool inFixedForm_{false}; int fixedFormColumnLimit_{72}; Encoding encoding_{Encoding::UTF_8}; diff --git a/flang/lib/Semantics/check-call.cpp b/flang/lib/Semantics/check-call.cpp index ce82cccf26d54684f16e28df5aff561015806d70..db0949e905a658349111ced89b837a6afa737e82 100644 --- a/flang/lib/Semantics/check-call.cpp +++ b/flang/lib/Semantics/check-call.cpp @@ -1929,6 +1929,7 @@ bool CheckArguments(const characteristics::Procedure &proc, bool explicitInterface{proc.HasExplicitInterface()}; evaluate::FoldingContext foldingContext{context.foldingContext()}; parser::ContextualMessages &messages{foldingContext.messages()}; + bool allowArgumentConversions{true}; if (!explicitInterface || treatingExternalAsImplicit) { parser::Messages buffer; { @@ -1945,11 +1946,12 @@ bool CheckArguments(const characteristics::Procedure &proc, } return false; // don't pile on } + allowArgumentConversions = false; } if (explicitInterface) { auto buffer{CheckExplicitInterface(proc, actuals, context, &scope, - intrinsic, /*allowArgumentConversions=*/true, /*extentErrors=*/true, - ignoreImplicitVsExplicit)}; + intrinsic, allowArgumentConversions, + /*extentErrors=*/true, ignoreImplicitVsExplicit)}; if (!buffer.empty()) { if (treatingExternalAsImplicit) { if (auto *msg{messages.Say( diff --git a/flang/lib/Semantics/check-declarations.cpp b/flang/lib/Semantics/check-declarations.cpp index 6fcee96dd690594206e47de08f85eeaffa2533b0..901ac20f8aae9b2f77c1a814d15edfb9207144e1 100644 --- a/flang/lib/Semantics/check-declarations.cpp +++ b/flang/lib/Semantics/check-declarations.cpp @@ -1436,10 +1436,6 @@ void CheckHelper::CheckSubprogram( } if (cudaAttrs && *cudaAttrs != common::CUDASubprogramAttrs::Host) { // CUDA device subprogram checks - if (symbol.attrs().HasAny({Attr::RECURSIVE, Attr::PURE, Attr::ELEMENTAL})) { - messages_.Say(symbol.name(), - "A device subprogram may not be RECURSIVE, PURE, or ELEMENTAL"_err_en_US); - } if (ClassifyProcedure(symbol) == ProcedureDefinitionClass::Internal) { messages_.Say(symbol.name(), "A device subprogram may not be an internal subprogram"_err_en_US); diff --git a/flang/lib/Semantics/expression.cpp b/flang/lib/Semantics/expression.cpp index a270e4b385e8dbe8b1f7e02350929d801930051f..b8396209fc68549f7b807b78709cd0589992400a 100644 --- a/flang/lib/Semantics/expression.cpp +++ b/flang/lib/Semantics/expression.cpp @@ -2989,8 +2989,8 @@ void ExpressionAnalyzer::Analyze(const parser::CallStmt &callStmt) { for (const auto &arg : actualArgList) { analyzer.Analyze(arg, true /* is subroutine call */); } - auto chevrons{AnalyzeChevrons(callStmt)}; - if (!analyzer.fatalErrors() && chevrons) { + if (auto chevrons{AnalyzeChevrons(callStmt)}; + chevrons && !analyzer.fatalErrors()) { if (std::optional callee{ GetCalleeAndArguments(std::get(call.t), analyzer.GetActuals(), true /* subroutine */)}) { diff --git a/flang/lib/Semantics/program-tree.cpp b/flang/lib/Semantics/program-tree.cpp index bf773f3810c847b129b49e6a68b18d8639c90c7d..13c85c17459e121a0baf5c58dff98114a8e51784 100644 --- a/flang/lib/Semantics/program-tree.cpp +++ b/flang/lib/Semantics/program-tree.cpp @@ -10,6 +10,7 @@ #include "flang/Common/idioms.h" #include "flang/Parser/char-block.h" #include "flang/Semantics/scope.h" +#include "flang/Semantics/semantics.h" namespace Fortran::semantics { @@ -76,7 +77,8 @@ static void GetGenerics( } template -static ProgramTree BuildSubprogramTree(const parser::Name &name, const T &x) { +static ProgramTree BuildSubprogramTree( + const parser::Name &name, SemanticsContext &context, const T &x) { const auto &spec{std::get(x.t)}; const auto &exec{std::get(x.t)}; const auto &subps{ @@ -89,7 +91,11 @@ static ProgramTree BuildSubprogramTree(const parser::Name &name, const T &x) { for (const auto &subp : std::get>(subps->t)) { common::visit( - [&](const auto &y) { node.AddChild(ProgramTree::Build(y.value())); }, + [&](const auto &y) { + if (auto child{ProgramTree::Build(y.value(), context)}) { + node.AddChild(std::move(*child)); + } + }, subp.u); } } @@ -97,13 +103,14 @@ static ProgramTree BuildSubprogramTree(const parser::Name &name, const T &x) { } static ProgramTree BuildSubprogramTree( - const parser::Name &name, const parser::BlockData &x) { + const parser::Name &name, SemanticsContext &, const parser::BlockData &x) { const auto &spec{std::get(x.t)}; return ProgramTree{name, spec}; } template -static ProgramTree BuildModuleTree(const parser::Name &name, const T &x) { +static ProgramTree BuildModuleTree( + const parser::Name &name, SemanticsContext &context, const T &x) { const auto &spec{std::get(x.t)}; const auto &subps{std::get>(x.t)}; ProgramTree node{name, spec}; @@ -112,28 +119,42 @@ static ProgramTree BuildModuleTree(const parser::Name &name, const T &x) { for (const auto &subp : std::get>(subps->t)) { common::visit( - [&](const auto &y) { node.AddChild(ProgramTree::Build(y.value())); }, + [&](const auto &y) { + if (auto child{ProgramTree::Build(y.value(), context)}) { + node.AddChild(std::move(*child)); + } + }, subp.u); } } return node; } -ProgramTree ProgramTree::Build(const parser::ProgramUnit &x) { - return common::visit([](const auto &y) { return Build(y.value()); }, x.u); +ProgramTree ProgramTree::Build( + const parser::ProgramUnit &x, SemanticsContext &context) { + return common::visit( + [&](const auto &y) { + auto node{Build(y.value(), context)}; + CHECK(node.has_value()); + return std::move(*node); + }, + x.u); } -ProgramTree ProgramTree::Build(const parser::MainProgram &x) { +std::optional ProgramTree::Build( + const parser::MainProgram &x, SemanticsContext &context) { const auto &stmt{ std::get>>(x.t)}; const auto &end{std::get>(x.t)}; static parser::Name emptyName; - auto result{stmt ? BuildSubprogramTree(stmt->statement.v, x).set_stmt(*stmt) - : BuildSubprogramTree(emptyName, x)}; - return result.set_endStmt(end); + auto result{stmt + ? BuildSubprogramTree(stmt->statement.v, context, x).set_stmt(*stmt) + : BuildSubprogramTree(emptyName, context, x)}; + return std::move(result.set_endStmt(end)); } -ProgramTree ProgramTree::Build(const parser::FunctionSubprogram &x) { +std::optional ProgramTree::Build( + const parser::FunctionSubprogram &x, SemanticsContext &context) { const auto &stmt{std::get>(x.t)}; const auto &end{std::get>(x.t)}; const auto &name{std::get(stmt.statement.t)}; @@ -144,13 +165,14 @@ ProgramTree ProgramTree::Build(const parser::FunctionSubprogram &x) { bindingSpec = &*suffix->binding; } } - return BuildSubprogramTree(name, x) + return BuildSubprogramTree(name, context, x) .set_stmt(stmt) .set_endStmt(end) .set_bindingSpec(bindingSpec); } -ProgramTree ProgramTree::Build(const parser::SubroutineSubprogram &x) { +std::optional ProgramTree::Build( + const parser::SubroutineSubprogram &x, SemanticsContext &context) { const auto &stmt{std::get>(x.t)}; const auto &end{std::get>(x.t)}; const auto &name{std::get(stmt.statement.t)}; @@ -159,48 +181,56 @@ ProgramTree ProgramTree::Build(const parser::SubroutineSubprogram &x) { stmt.statement.t)}) { bindingSpec = &*binding; } - return BuildSubprogramTree(name, x) + return BuildSubprogramTree(name, context, x) .set_stmt(stmt) .set_endStmt(end) .set_bindingSpec(bindingSpec); } -ProgramTree ProgramTree::Build(const parser::SeparateModuleSubprogram &x) { +std::optional ProgramTree::Build( + const parser::SeparateModuleSubprogram &x, SemanticsContext &context) { const auto &stmt{std::get>(x.t)}; const auto &end{ std::get>(x.t)}; const auto &name{stmt.statement.v}; - return BuildSubprogramTree(name, x).set_stmt(stmt).set_endStmt(end); + return BuildSubprogramTree(name, context, x).set_stmt(stmt).set_endStmt(end); } -ProgramTree ProgramTree::Build(const parser::Module &x) { +std::optional ProgramTree::Build( + const parser::Module &x, SemanticsContext &context) { const auto &stmt{std::get>(x.t)}; const auto &end{std::get>(x.t)}; const auto &name{stmt.statement.v}; - return BuildModuleTree(name, x).set_stmt(stmt).set_endStmt(end); + return BuildModuleTree(name, context, x).set_stmt(stmt).set_endStmt(end); } -ProgramTree ProgramTree::Build(const parser::Submodule &x) { +std::optional ProgramTree::Build( + const parser::Submodule &x, SemanticsContext &context) { const auto &stmt{std::get>(x.t)}; const auto &end{std::get>(x.t)}; const auto &name{std::get(stmt.statement.t)}; - return BuildModuleTree(name, x).set_stmt(stmt).set_endStmt(end); + return BuildModuleTree(name, context, x).set_stmt(stmt).set_endStmt(end); } -ProgramTree ProgramTree::Build(const parser::BlockData &x) { +std::optional ProgramTree::Build( + const parser::BlockData &x, SemanticsContext &context) { const auto &stmt{std::get>(x.t)}; const auto &end{std::get>(x.t)}; static parser::Name emptyName; - auto result{stmt.statement.v ? BuildSubprogramTree(*stmt.statement.v, x) - : BuildSubprogramTree(emptyName, x)}; - return result.set_stmt(stmt).set_endStmt(end); + auto result{stmt.statement.v + ? BuildSubprogramTree(*stmt.statement.v, context, x) + : BuildSubprogramTree(emptyName, context, x)}; + return std::move(result.set_stmt(stmt).set_endStmt(end)); } -ProgramTree ProgramTree::Build(const parser::CompilerDirective &) { - DIE("ProgramTree::Build() called for CompilerDirective"); +std::optional ProgramTree::Build( + const parser::CompilerDirective &x, SemanticsContext &context) { + context.Say(x.source, "Compiler directive ignored here"_warn_en_US); + return std::nullopt; } -ProgramTree ProgramTree::Build(const parser::OpenACCRoutineConstruct &) { +std::optional ProgramTree::Build( + const parser::OpenACCRoutineConstruct &, SemanticsContext &) { DIE("ProgramTree::Build() called for OpenACCRoutineConstruct"); } diff --git a/flang/lib/Semantics/program-tree.h b/flang/lib/Semantics/program-tree.h index d49b0405d8b122de9d88ba5e2c28f14451d595a1..ab00261a964a13c3e604b132528bc27be5be81fb 100644 --- a/flang/lib/Semantics/program-tree.h +++ b/flang/lib/Semantics/program-tree.h @@ -26,6 +26,7 @@ namespace Fortran::semantics { class Scope; +class SemanticsContext; class ProgramTree { public: @@ -34,16 +35,25 @@ public: std::list>; // Build the ProgramTree rooted at one of these program units. - static ProgramTree Build(const parser::ProgramUnit &); - static ProgramTree Build(const parser::MainProgram &); - static ProgramTree Build(const parser::FunctionSubprogram &); - static ProgramTree Build(const parser::SubroutineSubprogram &); - static ProgramTree Build(const parser::SeparateModuleSubprogram &); - static ProgramTree Build(const parser::Module &); - static ProgramTree Build(const parser::Submodule &); - static ProgramTree Build(const parser::BlockData &); - static ProgramTree Build(const parser::CompilerDirective &); - static ProgramTree Build(const parser::OpenACCRoutineConstruct &); + static ProgramTree Build(const parser::ProgramUnit &, SemanticsContext &); + static std::optional Build( + const parser::MainProgram &, SemanticsContext &); + static std::optional Build( + const parser::FunctionSubprogram &, SemanticsContext &); + static std::optional Build( + const parser::SubroutineSubprogram &, SemanticsContext &); + static std::optional Build( + const parser::SeparateModuleSubprogram &, SemanticsContext &); + static std::optional Build( + const parser::Module &, SemanticsContext &); + static std::optional Build( + const parser::Submodule &, SemanticsContext &); + static std::optional Build( + const parser::BlockData &, SemanticsContext &); + static std::optional Build( + const parser::CompilerDirective &, SemanticsContext &); + static std::optional Build( + const parser::OpenACCRoutineConstruct &, SemanticsContext &); ENUM_CLASS(Kind, // kind of node Program, Function, Subroutine, MpSubprogram, Module, Submodule, BlockData) diff --git a/flang/lib/Semantics/resolve-names.cpp b/flang/lib/Semantics/resolve-names.cpp index b941f257a95ea3d8f4903d5bfef37107231d175f..7bd1f4e4e9618566e4f889fe39142edd6f3a7fb7 100644 --- a/flang/lib/Semantics/resolve-names.cpp +++ b/flang/lib/Semantics/resolve-names.cpp @@ -1779,7 +1779,6 @@ void AttrsVisitor::SetBindNameOn(Symbol &symbol) { !symbol.attrs().test(Attr::BIND_C)) { return; } - std::optional label{ evaluate::GetScalarConstantValue(bindName_)}; // 18.9.2(2): discard leading and trailing blanks @@ -1798,16 +1797,18 @@ void AttrsVisitor::SetBindNameOn(Symbol &symbol) { } else { label = symbol.name().ToString(); } - // Check if a symbol has two Bind names. + // Checks whether a symbol has two Bind names. std::string oldBindName; - if (symbol.GetBindName()) { - oldBindName = *symbol.GetBindName(); + if (const auto *bindName{symbol.GetBindName()}) { + oldBindName = *bindName; } symbol.SetBindName(std::move(*label)); if (!oldBindName.empty()) { if (const std::string * newBindName{symbol.GetBindName()}) { if (oldBindName != *newBindName) { - Say(symbol.name(), "The entity '%s' has multiple BIND names"_err_en_US); + Say(symbol.name(), + "The entity '%s' has multiple BIND names ('%s' and '%s')"_err_en_US, + symbol.name(), oldBindName, *newBindName); } } } @@ -4986,7 +4987,9 @@ Symbol &DeclarationVisitor::DeclareUnknownEntity( if (symbol.attrs().test(Attr::EXTERNAL)) { ConvertToProcEntity(symbol); } - SetBindNameOn(symbol); + if (attrs.test(Attr::BIND_C)) { + SetBindNameOn(symbol); + } return symbol; } } @@ -8886,7 +8889,7 @@ void ResolveNamesVisitor::Post(const parser::CompilerDirective &x) { } } } else { - Say(x.source, "Compiler directive was ignored"_warn_en_US); + Say(x.source, "Unrecognized compiler directive was ignored"_warn_en_US); } } @@ -8901,7 +8904,7 @@ bool ResolveNamesVisitor::Pre(const parser::ProgramUnit &x) { ResolveAccParts(context(), x, &topScope_); return false; } - auto root{ProgramTree::Build(x)}; + auto root{ProgramTree::Build(x, context())}; SetScope(topScope_); ResolveSpecificationParts(root); FinishSpecificationParts(root); diff --git a/flang/runtime/edit-output.cpp b/flang/runtime/edit-output.cpp index a06ed258f0f1d2751f31f3d319f81944b15cda31..13ab91fc56eade41609ad11e6825cf031f3a9ccf 100644 --- a/flang/runtime/edit-output.cpp +++ b/flang/runtime/edit-output.cpp @@ -446,6 +446,7 @@ RT_API_ATTRS bool RealOutputEditing::EditFOutput(const DataEdit &edit) { fracDigits = sizeof buffer_ - 2; // sign & NUL } } + bool emitTrailingZeroes{!(flags & decimal::Minimize)}; // Multiple conversions may be needed to get the right number of // effective rounded fractional digits. bool canIncrease{true}; @@ -526,11 +527,18 @@ RT_API_ATTRS bool RealOutputEditing::EditFOutput(const DataEdit &edit) { } int digitsBeforePoint{std::max(0, std::min(expo, convertedDigits))}; int zeroesBeforePoint{std::max(0, expo - digitsBeforePoint)}; + if (zeroesBeforePoint > 0 && (flags & decimal::Minimize)) { + // If a minimized result looks like an integer, emit all of + // its digits rather than clipping some to zeroes. + // This can happen with HUGE(0._2) == 65504._2. + flags &= ~decimal::Minimize; + continue; + } int zeroesAfterPoint{std::min(fracDigits, std::max(0, -expo))}; int digitsAfterPoint{convertedDigits - digitsBeforePoint}; - int trailingZeroes{flags & decimal::Minimize - ? 0 - : std::max(0, fracDigits - (zeroesAfterPoint + digitsAfterPoint))}; + int trailingZeroes{emitTrailingZeroes + ? std::max(0, fracDigits - (zeroesAfterPoint + digitsAfterPoint)) + : 0}; if (digitsBeforePoint + zeroesBeforePoint + zeroesAfterPoint + digitsAfterPoint + trailingZeroes == 0) { @@ -822,6 +830,11 @@ RT_API_ATTRS bool EditLogicalOutput( case 'Z': return EditBOZOutput<4>(io, edit, reinterpret_cast(&truth), sizeof truth); + case 'A': { // legacy extension + int truthBits{truth}; + return EditCharacterOutput( + io, edit, reinterpret_cast(&truthBits), sizeof truthBits); + } default: io.GetIoErrorHandler().SignalError(IostatErrorInFormat, "Data edit descriptor '%c' may not be used with a LOGICAL data item", diff --git a/flang/runtime/numeric.cpp b/flang/runtime/numeric.cpp index abd3e500029fe49ab915b17e93f99d73f769ac0a..52b5a56894d8846587e40f3222298bda717f777f 100644 --- a/flang/runtime/numeric.cpp +++ b/flang/runtime/numeric.cpp @@ -9,6 +9,7 @@ #include "flang/Runtime/numeric.h" #include "numeric-templates.h" #include "terminator.h" +#include "tools.h" #include "flang/Common/float128.h" #include #include @@ -18,30 +19,30 @@ namespace Fortran::runtime { template -inline RT_API_ATTRS RES getIntArgValue(const char *source, int line, void *arg, - int kind, std::int64_t defaultValue, int resKind) { +inline RT_API_ATTRS RES GetIntArgValue(const char *source, int line, + const void *arg, int kind, std::int64_t defaultValue, int resKind) { RES res; if (!arg) { res = static_cast(defaultValue); } else if (kind == 1) { res = static_cast( - *static_cast *>(arg)); + *static_cast *>(arg)); } else if (kind == 2) { res = static_cast( - *static_cast *>(arg)); + *static_cast *>(arg)); } else if (kind == 4) { res = static_cast( - *static_cast *>(arg)); + *static_cast *>(arg)); } else if (kind == 8) { res = static_cast( - *static_cast *>(arg)); + *static_cast *>(arg)); #ifdef __SIZEOF_INT128__ } else if (kind == 16) { if (resKind != 16) { Terminator{source, line}.Crash("Unexpected integer kind in runtime"); } res = static_cast( - *static_cast *>(arg)); + *static_cast *>(arg)); #endif } else { Terminator{source, line}.Crash("Unexpected integer kind in runtime"); @@ -112,6 +113,22 @@ inline RT_API_ATTRS CppTypeFor SelectedIntKind(T x) { return -1; } +// SELECTED_LOGICAL_KIND (F'2023 16.9.182) +template +inline RT_API_ATTRS CppTypeFor SelectedLogicalKind( + T x) { + if (x <= 2) { + return 1; + } else if (x <= 4) { + return 2; + } else if (x <= 9) { + return 4; + } else if (x <= 18) { + return 8; + } + return -1; +} + // SELECTED_REAL_KIND (16.9.170) template inline RT_API_ATTRS CppTypeFor SelectedRealKind( @@ -717,40 +734,72 @@ CppTypeFor RTDEF(Scale10)( } #endif +// SELECTED_CHAR_KIND +CppTypeFor RTDEF(SelectedCharKind)( + const char *source, int line, const char *x, std::size_t length) { + static const char *keywords[]{ + "ASCII", "DEFAULT", "UCS-2", "ISO_10646", "UCS-4", nullptr}; + switch (IdentifyValue(x, length, keywords)) { + case 0: // ASCII + case 1: // DEFAULT + return 1; + case 2: // UCS-2 + return 2; + case 3: // ISO_10646 + case 4: // UCS-4 + return 4; + default: + return -1; + } +} // SELECTED_INT_KIND CppTypeFor RTDEF(SelectedIntKind)( const char *source, int line, void *x, int xKind) { #ifdef __SIZEOF_INT128__ CppTypeFor r = - getIntArgValue>( + GetIntArgValue>( source, line, x, xKind, /*defaultValue*/ 0, /*resKind*/ 16); #else - std::int64_t r = getIntArgValue( + std::int64_t r = GetIntArgValue( source, line, x, xKind, /*defaultValue*/ 0, /*resKind*/ 8); #endif return SelectedIntKind(r); } +// SELECTED_LOGICAL_KIND +CppTypeFor RTDEF(SelectedLogicalKind)( + const char *source, int line, void *x, int xKind) { +#ifdef __SIZEOF_INT128__ + CppTypeFor r = + GetIntArgValue>( + source, line, x, xKind, /*defaultValue*/ 0, /*resKind*/ 16); +#else + std::int64_t r = GetIntArgValue( + source, line, x, xKind, /*defaultValue*/ 0, /*resKind*/ 8); +#endif + return SelectedLogicalKind(r); +} + // SELECTED_REAL_KIND CppTypeFor RTDEF(SelectedRealKind)(const char *source, int line, void *precision, int pKind, void *range, int rKind, void *radix, int dKind) { #ifdef __SIZEOF_INT128__ CppTypeFor p = - getIntArgValue>( + GetIntArgValue>( source, line, precision, pKind, /*defaultValue*/ 0, /*resKind*/ 16); CppTypeFor r = - getIntArgValue>( + GetIntArgValue>( source, line, range, rKind, /*defaultValue*/ 0, /*resKind*/ 16); CppTypeFor d = - getIntArgValue>( + GetIntArgValue>( source, line, radix, dKind, /*defaultValue*/ 2, /*resKind*/ 16); #else - std::int64_t p = getIntArgValue( + std::int64_t p = GetIntArgValue( source, line, precision, pKind, /*defaultValue*/ 0, /*resKind*/ 8); - std::int64_t r = getIntArgValue( + std::int64_t r = GetIntArgValue( source, line, range, rKind, /*defaultValue*/ 0, /*resKind*/ 8); - std::int64_t d = getIntArgValue( + std::int64_t d = GetIntArgValue( source, line, radix, dKind, /*defaultValue*/ 2, /*resKind*/ 8); #endif return SelectedRealKind(p, r, d); diff --git a/flang/test/Driver/bbc-mlir-pass-pipeline.f90 b/flang/test/Driver/bbc-mlir-pass-pipeline.f90 index bd7facad1ce12fe6d00ca4f3db94894750981459..7a35e26dc478c8cb6c75d64a63e9616f46cb1f55 100644 --- a/flang/test/Driver/bbc-mlir-pass-pipeline.f90 +++ b/flang/test/Driver/bbc-mlir-pass-pipeline.f90 @@ -17,9 +17,14 @@ end program ! CHECK-NEXT: (S) 0 num-cse'd - Number of operations CSE'd ! CHECK-NEXT: (S) 0 num-dce'd - Number of operations DCE'd +! CHECK-NEXT: Pipeline Collection : ['fir.global', 'func.func', 'omp.declare_reduction'] +! CHECK-NEXT: 'fir.global' Pipeline +! CHECK-NEXT: CharacterConversion ! CHECK-NEXT: 'func.func' Pipeline ! CHECK-NEXT: ArrayValueCopy ! CHECK-NEXT: CharacterConversion +! CHECK-NEXT: 'omp.declare_reduction' Pipeline +! CHECK-NEXT: CharacterConversion ! CHECK-NEXT: Canonicalizer ! CHECK-NEXT: SimplifyRegionLite @@ -38,12 +43,14 @@ end program ! CHECK-NEXT: (S) 0 num-cse'd - Number of operations CSE'd ! CHECK-NEXT: (S) 0 num-dce'd - Number of operations DCE'd -! CHECK-NEXT: Pipeline Collection : ['func.func', 'omp.declare_reduction'] +! CHECK-NEXT: Pipeline Collection : ['fir.global', 'func.func', 'omp.declare_reduction'] +! CHECK-NEXT: 'fir.global' Pipeline +! CHECK-NEXT: CFGConversion ! CHECK-NEXT: 'func.func' Pipeline ! CHECK-NEXT: PolymorphicOpConversion -! CHECK-NEXT: CFGConversionOnFunc +! CHECK-NEXT: CFGConversion ! CHECK-NEXT: 'omp.declare_reduction' Pipeline -! CHECK-NEXT: CFGConversionOnReduction +! CHECK-NEXT: CFGConversion ! CHECK-NEXT: SCFToControlFlow ! CHECK-NEXT: Canonicalizer diff --git a/flang/test/Driver/driver-help-hidden.f90 b/flang/test/Driver/driver-help-hidden.f90 deleted file mode 100644 index b5bb0f1c1b25604180097d7d44ddf4299c64257b..0000000000000000000000000000000000000000 --- a/flang/test/Driver/driver-help-hidden.f90 +++ /dev/null @@ -1,173 +0,0 @@ - -!-------------------------- -! FLANG DRIVER (flang-new) -!-------------------------- -! RUN: %flang --help-hidden 2>&1 | FileCheck %s -! RUN: not %flang -help-hidden 2>&1 | FileCheck %s --check-prefix=ERROR-FLANG - -!---------------------------------------- -! FLANG FRONTEND DRIVER (flang-new -fc1) -!---------------------------------------- -! RUN: not %flang_fc1 --help-hidden 2>&1 | FileCheck %s --check-prefix=ERROR-FLANG-FC1 -! RUN: not %flang_fc1 -help-hidden 2>&1 | FileCheck %s --check-prefix=ERROR-FLANG-FC1 - -! CHECK:USAGE: flang-new -! CHECK-EMPTY: -! CHECK-NEXT: DRIVER OPTIONS: -! CHECK-NEXT: --driver-mode= Set the driver mode to either 'gcc', 'g++', 'cpp', 'cl' or 'flang' -! CHECK-EMPTY: -! CHECK-NEXT:OPTIONS: -! CHECK-NEXT: -### Print (but do not run) the commands to run for this compilation -! CHECK-NEXT: -ccc-print-phases Dump list of actions to perform -! CHECK-NEXT: -cpp Enable predefined and command line preprocessor macros -! CHECK-NEXT: -c Only run preprocess, compile, and assemble steps -! CHECK-NEXT: -dM Print macro definitions in -E mode instead of normal output -! CHECK-NEXT: -dumpmachine Display the compiler's target processor -! CHECK-NEXT: -dumpversion Display the version of the compiler -! CHECK-NEXT: -D = Define to (or 1 if omitted) -! CHECK-NEXT: -emit-llvm Use the LLVM representation for assembler and object files -! CHECK-NEXT: -E Only run the preprocessor -! CHECK-NEXT: -falternative-parameter-statement -! CHECK-NEXT: Enable the old style PARAMETER statement -! CHECK-NEXT: -fapprox-func Allow certain math function calls to be replaced with an approximately equivalent calculation -! CHECK-NEXT: -fbackslash Specify that backslash in string introduces an escape character -! CHECK-NEXT: -fcolor-diagnostics Enable colors in diagnostics -! CHECK-NEXT: -fconvert= Set endian conversion of data for unformatted files -! CHECK-NEXT: -fdefault-double-8 Set the default double precision kind to an 8 byte wide type -! CHECK-NEXT: -fdefault-integer-8 Set the default integer and logical kind to an 8 byte wide type -! CHECK-NEXT: -fdefault-real-8 Set the default real kind to an 8 byte wide type -! CHECK-NEXT: -ffast-math Allow aggressive, lossy floating-point optimizations -! CHECK-NEXT: -ffixed-form Process source files in fixed form -! CHECK-NEXT: -ffixed-line-length= -! CHECK-NEXT: Use as character line width in fixed mode -! CHECK-NEXT: -ffp-contract= Form fused FP ops (e.g. FMAs) -! CHECK-NEXT: -ffree-form Process source files in free form -! CHECK-NEXT: -fhonor-infinities Specify that floating-point optimizations are not allowed that assume arguments and results are not +-inf. -! CHECK-NEXT: -fhonor-nans Specify that floating-point optimizations are not allowed that assume arguments and results are not NANs. -! CHECK-NEXT: -fimplicit-none No implicit typing allowed unless overridden by IMPLICIT statements -! CHECK-NEXT: -finput-charset= Specify the default character set for source files -! CHECK-NEXT: -fintegrated-as Enable the integrated assembler -! CHECK-NEXT: -fintrinsic-modules-path -! CHECK-NEXT: Specify where to find the compiled intrinsic modules -! CHECK-NEXT: -flang-deprecated-no-hlfir -! CHECK-NEXT: Do not use HLFIR lowering (deprecated) -! CHECK-NEXT: -flang-experimental-hlfir -! CHECK-NEXT: Use HLFIR lowering (experimental) -! CHECK-NEXT: -flarge-sizes Use INTEGER(KIND=8) for the result type in size-related intrinsics -! CHECK-NEXT: -flogical-abbreviations Enable logical abbreviations -! CHECK-NEXT: -flto=auto Enable LTO in 'full' mode -! CHECK-NEXT: -flto=jobserver Enable LTO in 'full' mode -! CHECK-NEXT: -flto= Set LTO mode -! CHECK-NEXT: -flto Enable LTO in 'full' mode -! CHECK-NEXT: -fms-runtime-lib= -! CHECK-NEXT: Select Windows run-time library -! CHECK-NEXT: -fno-automatic Implies the SAVE attribute for non-automatic local objects in subprograms unless RECURSIVE -! CHECK-NEXT: -fno-color-diagnostics Disable colors in diagnostics -! CHECK-NEXT: -fno-fortran-main Do not include Fortran_main.a (provided by Flang) when linking -! CHECK-NEXT: -fno-integrated-as Disable the integrated assembler -! CHECK-NEXT: -fno-lto Disable LTO mode (default) -! CHECK-NEXT: -fno-ppc-native-vector-element-order -! CHECK-NEXT: Specifies PowerPC non-native vector element order -! CHECK-NEXT: -fno-rtlib-add-rpath Do not add -rpath with architecture-specific resource directory to the linker flags. When --hip-link is specified, do not add -rpath with HIP runtime library directory to the linker flags -! CHECK-NEXT: -fno-signed-zeros Allow optimizations that ignore the sign of floating point zeros -! CHECK-NEXT: -fno-stack-arrays Allocate array temporaries on the heap (default) -! CHECK-NEXT: -fno-version-loops-for-stride -! CHECK-NEXT: Do not create unit-strided loops (default) -! CHECK-NEXT: -fomit-frame-pointer Omit the frame pointer from functions that don't need it. Some stack unwinding cases, such as profilers and sanitizers, may prefer specifying -fno-omit-frame-pointer. On many targets, -O1 and higher omit the frame pointer by default. -m[no-]omit-leaf-frame-pointer takes precedence for leaf functions -! CHECK-NEXT: -fopenacc Enable OpenACC -! CHECK-NEXT: -fopenmp-assume-no-nested-parallelism -! CHECK-NEXT: Assert no nested parallel regions in the GPU -! CHECK-NEXT: -fopenmp-assume-no-thread-state -! CHECK-NEXT: Assert no thread in a parallel region modifies an ICV -! CHECK-NEXT: -fopenmp-target-debug Enable debugging in the OpenMP offloading device RTL -! CHECK-NEXT: -fopenmp-targets= -! CHECK-NEXT: Specify comma-separated list of triples OpenMP offloading targets to be supported -! CHECK-NEXT: -fopenmp-version= -! CHECK-NEXT: Set OpenMP version (e.g. 45 for OpenMP 4.5, 51 for OpenMP 5.1). Default value is 11 for Flang -! CHECK-NEXT: -fopenmp Parse OpenMP pragmas and generate parallel code. -! CHECK-NEXT: -foptimization-record-file= -! CHECK-NEXT: Specify the output name of the file containing the optimization remarks. Implies -fsave-optimization-record. On Darwin platforms, this cannot be used with multiple -arch options. -! CHECK-NEXT: -foptimization-record-passes= -! CHECK-NEXT: Only include passes which match a specified regular expression in the generated optimization record (by default, include all passes) -! CHECK-NEXT: -fpass-plugin= Load pass plugin from a dynamic shared object file (only with new pass manager). -! CHECK-NEXT: -fppc-native-vector-element-order -! CHECK-NEXT: Specifies PowerPC native vector element order (default) -! CHECK-NEXT: -freciprocal-math Allow division operations to be reassociated -! CHECK-NEXT: -fropi Generate read-only position independent code (ARM only) -! CHECK-NEXT: -frtlib-add-rpath Add -rpath with architecture-specific resource directory to the linker flags. When --hip-link is specified, also add -rpath with HIP runtime library directory to the linker flags -! CHECK-NEXT: -frwpi Generate read-write position independent code (ARM only) -! CHECK-NEXT: -fsave-optimization-record= -! CHECK-NEXT: Generate an optimization record file in a specific format -! CHECK-NEXT: -fsave-optimization-record -! CHECK-NEXT: Generate a YAML optimization record file -! CHECK-NEXT: -fstack-arrays Attempt to allocate array temporaries on the stack, no matter their size -! CHECK-NEXT: -fsyntax-only Run the preprocessor, parser and semantic analysis stages -! CHECK-NEXT: -funderscoring Appends one trailing underscore to external names -! CHECK-NEXT: -fveclib= Use the given vector functions library -! CHECK-NEXT: -fversion-loops-for-stride -! CHECK-NEXT: Create unit-strided versions of loops -! CHECK-NEXT: -fxor-operator Enable .XOR. as a synonym of .NEQV. -! CHECK-NEXT: --gcc-install-dir= -! CHECK-NEXT: Use GCC installation in the specified directory. The directory ends with path components like 'lib{,32,64}/gcc{,-cross}/$triple/$version'. Note: executables (e.g. ld) used by the compiler are not overridden by the selected GCC installation -! CHECK-NEXT: --gcc-toolchain= Specify a directory where Flang can find 'lib{,32,64}/gcc{,-cross}/$triple/$version'. Flang will use the GCC installation with the largest version -! CHECK-NEXT: -gline-directives-only Emit debug line info directives only -! CHECK-NEXT: -gline-tables-only Emit debug line number tables only -! CHECK-NEXT: -gpulibc Link the LLVM C Library for GPUs -! CHECK-NEXT: -g Generate source-level debug information -! CHECK-NEXT: --help-hidden Display help for hidden options -! CHECK-NEXT: -help Display available options -! CHECK-NEXT: -isysroot Set the system root directory (usually /) -! CHECK-NEXT: -I Add directory to the end of the list of include search paths -! CHECK-NEXT: -L Add directory to library search path -! CHECK-NEXT: -march= For a list of available architectures for the target use '-mcpu=help' -! CHECK-NEXT: -mcode-object-version= -! CHECK-NEXT: Specify code object ABI version. Defaults to 5. (AMDGPU only) -! CHECK-NEXT: -mcpu= For a list of available CPUs for the target use '-mcpu=help' -! CHECK-NEXT: -mllvm= Alias for -mllvm -! CHECK-NEXT: -mllvm Additional arguments to forward to LLVM's option processing -! CHECK-NEXT: -mmlir Additional arguments to forward to MLIR's option processing -! CHECK-NEXT: -mno-outline-atomics Don't generate local calls to out-of-line atomic operations -! CHECK-NEXT: -module-dir Put MODULE files in -! CHECK-NEXT: -moutline-atomics Generate local calls to out-of-line atomic operations -! CHECK-NEXT: -mrvv-vector-bits= -! CHECK-NEXT: Specify the size in bits of an RVV vector register -! CHECK-NEXT: -msve-vector-bits= -! CHECK-NEXT: Specify the size in bits of an SVE vector register. Defaults to the vector length agnostic value of "scalable". (AArch64 only) -! CHECK-NEXT: --no-offload-arch= -! CHECK-NEXT: Remove CUDA/HIP offloading device architecture (e.g. sm_35, gfx906) from the list of devices to compile for. 'all' resets the list to its default value. -! CHECK-NEXT: -nocpp Disable predefined and command line preprocessor macros -! CHECK-NEXT: -nogpulib Do not link device library for CUDA/HIP device compilation -! CHECK-NEXT: --offload-arch= Specify an offloading device architecture for CUDA, HIP, or OpenMP. (e.g. sm_35). If 'native' is used the compiler will detect locally installed architectures. For HIP offloading, the device architecture can be followed by target ID features delimited by a colon (e.g. gfx908:xnack+:sramecc-). May be specified more than once. -! CHECK-NEXT: --offload-device-only Only compile for the offloading device. -! CHECK-NEXT: --offload-host-device Compile for both the offloading host and device (default). -! CHECK-NEXT: --offload-host-only Only compile for the offloading host. -! CHECK-NEXT: -o Write output to -! CHECK-NEXT: -pedantic Warn on language extensions -! CHECK-NEXT: -print-effective-triple Print the effective target triple -! CHECK-NEXT: -print-target-triple Print the normalized target triple -! CHECK-NEXT: -pthread Support POSIX threads in generated code -! CHECK-NEXT: -P Disable linemarker output in -E mode -! CHECK-NEXT: -resource-dir The directory which holds the compiler resource files -! CHECK-NEXT: --rocm-path= ROCm installation path, used for finding and automatically linking required bitcode libraries. -! CHECK-NEXT: -Rpass-analysis= Report transformation analysis from optimization passes whose name matches the given POSIX regular expression -! CHECK-NEXT: -Rpass-missed= Report missed transformations by optimization passes whose name matches the given POSIX regular expression -! CHECK-NEXT: -Rpass= Report transformations performed by optimization passes whose name matches the given POSIX regular expression -! CHECK-NEXT: -R Enable the specified remark -! CHECK-NEXT: -save-temps= Save intermediate compilation results. -! CHECK-NEXT: -save-temps Alias for --save-temps=cwd -! CHECK-NEXT: -std= Language standard to compile for -! CHECK-NEXT: -S Only run preprocess and compilation steps -! CHECK-NEXT: --target= Generate code for the given target -! CHECK-NEXT: -U Undefine macro -! CHECK-NEXT: --version Print version information -! CHECK-NEXT: -v Show commands to run and use verbose output -! CHECK-NEXT: -Wl, Pass the comma separated arguments in to the linker -! CHECK-NEXT: -W Enable the specified warning -! CHECK-NEXT: -Xflang Pass to the flang compiler -! CHECK-NEXT: -x Treat subsequent input files as having type - - -! ERROR-FLANG: error: unknown argument '-help-hidden'; did you mean '--help-hidden'? - -! Frontend driver -help-hidden is not supported -! ERROR-FLANG-FC1: error: unknown argument: '{{.*}}' diff --git a/flang/test/Driver/driver-help.f90 b/flang/test/Driver/driver-help.f90 index 0b0a493baf07f7e63f291f97ee979c63fd365dbc..4c3609db80b9acc15720d1a4bcd1c3f751f1e387 100644 --- a/flang/test/Driver/driver-help.f90 +++ b/flang/test/Driver/driver-help.f90 @@ -1,298 +1,15 @@ - -!-------------------------- -! FLANG DRIVER (flang) -!-------------------------- ! RUN: %flang -help 2>&1 | FileCheck %s --check-prefix=HELP ! RUN: not %flang -helps 2>&1 | FileCheck %s --check-prefix=ERROR -!---------------------------------------- -! FLANG FRONTEND DRIVER (flang -fc1) -!---------------------------------------- ! RUN: %flang_fc1 -help 2>&1 | FileCheck %s --check-prefix=HELP-FC1 ! RUN: not %flang_fc1 -helps 2>&1 | FileCheck %s --check-prefix=ERROR ! HELP:USAGE: flang ! HELP-EMPTY: ! HELP-NEXT:OPTIONS: -! HELP-NEXT: -### Print (but do not run) the commands to run for this compilation -! HELP-NEXT: -cpp Enable predefined and command line preprocessor macros -! HELP-NEXT: -c Only run preprocess, compile, and assemble steps -! HELP-NEXT: -dM Print macro definitions in -E mode instead of normal output -! HELP-NEXT: -dumpmachine Display the compiler's target processor -! HELP-NEXT: -dumpversion Display the version of the compiler -! HELP-NEXT: -D = Define to (or 1 if omitted) -! HELP-NEXT: -emit-llvm Use the LLVM representation for assembler and object files -! HELP-NEXT: -E Only run the preprocessor -! HELP-NEXT: -falternative-parameter-statement -! HELP-NEXT: Enable the old style PARAMETER statement -! HELP-NEXT: -fapprox-func Allow certain math function calls to be replaced with an approximately equivalent calculation -! HELP-NEXT: -fbackslash Specify that backslash in string introduces an escape character -! HELP-NEXT: -fcolor-diagnostics Enable colors in diagnostics -! HELP-NEXT: -fconvert= Set endian conversion of data for unformatted files -! HELP-NEXT: -fdefault-double-8 Set the default double precision kind to an 8 byte wide type -! HELP-NEXT: -fdefault-integer-8 Set the default integer and logical kind to an 8 byte wide type -! HELP-NEXT: -fdefault-real-8 Set the default real kind to an 8 byte wide type -! HELP-NEXT: -ffast-math Allow aggressive, lossy floating-point optimizations -! HELP-NEXT: -ffixed-form Process source files in fixed form -! HELP-NEXT: -ffixed-line-length= -! HELP-NEXT: Use as character line width in fixed mode -! HELP-NEXT: -ffp-contract= Form fused FP ops (e.g. FMAs) -! HELP-NEXT: -ffree-form Process source files in free form -! HELP-NEXT: -fhonor-infinities Specify that floating-point optimizations are not allowed that assume arguments and results are not +-inf. -! HELP-NEXT: -fhonor-nans Specify that floating-point optimizations are not allowed that assume arguments and results are not NANs. -! HELP-NEXT: -fimplicit-none No implicit typing allowed unless overridden by IMPLICIT statements -! HELP-NEXT: -finput-charset= Specify the default character set for source files -! HELP-NEXT: -fintegrated-as Enable the integrated assembler -! HELP-NEXT: -fintrinsic-modules-path -! HELP-NEXT: Specify where to find the compiled intrinsic modules -! HELP-NEXT: -flarge-sizes Use INTEGER(KIND=8) for the result type in size-related intrinsics -! HELP-NEXT: -flogical-abbreviations Enable logical abbreviations -! HELP-NEXT: -flto=auto Enable LTO in 'full' mode -! HELP-NEXT: -flto=jobserver Enable LTO in 'full' mode -! HELP-NEXT: -flto= Set LTO mode -! HELP-NEXT: -flto Enable LTO in 'full' mode -! HELP-NEXT: -fms-runtime-lib= -! HELP-NEXT: Select Windows run-time library -! HELP-NEXT: -fno-automatic Implies the SAVE attribute for non-automatic local objects in subprograms unless RECURSIVE -! HELP-NEXT: -fno-color-diagnostics Disable colors in diagnostics -! HELP-NEXT: -fno-fortran-main Do not include Fortran_main.a (provided by Flang) when linking -! HELP-NEXT: -fno-integrated-as Disable the integrated assembler -! HELP-NEXT: -fno-lto Disable LTO mode (default) -! HELP-NEXT: -fno-ppc-native-vector-element-order -! HELP-NEXT: Specifies PowerPC non-native vector element order -! HELP-NEXT: -fno-rtlib-add-rpath Do not add -rpath with architecture-specific resource directory to the linker flags. When --hip-link is specified, do not add -rpath with HIP runtime library directory to the linker flags -! HELP-NEXT: -fno-signed-zeros Allow optimizations that ignore the sign of floating point zeros -! HELP-NEXT: -fno-stack-arrays Allocate array temporaries on the heap (default) -! HELP-NEXT: -fno-version-loops-for-stride -! HELP-NEXT: Do not create unit-strided loops (default) -! HELP-NEXT: -fomit-frame-pointer Omit the frame pointer from functions that don't need it. Some stack unwinding cases, such as profilers and sanitizers, may prefer specifying -fno-omit-frame-pointer. On many targets, -O1 and higher omit the frame pointer by default. -m[no-]omit-leaf-frame-pointer takes precedence for leaf functions -! HELP-NEXT: -fopenacc Enable OpenACC -! HELP-NEXT: -fopenmp-target-debug Enable debugging in the OpenMP offloading device RTL -! HELP-NEXT: -fopenmp-targets= -! HELP-NEXT: Specify comma-separated list of triples OpenMP offloading targets to be supported -! HELP-NEXT: -fopenmp-version= -! HELP-NEXT: Set OpenMP version (e.g. 45 for OpenMP 4.5, 51 for OpenMP 5.1). Default value is 11 for Flang -! HELP-NEXT: -fopenmp Parse OpenMP pragmas and generate parallel code. -! HELP-NEXT: -foptimization-record-file= -! HELP-NEXT: Specify the output name of the file containing the optimization remarks. Implies -fsave-optimization-record. On Darwin platforms, this cannot be used with multiple -arch options. -! HELP-NEXT: -foptimization-record-passes= -! HELP-NEXT: Only include passes which match a specified regular expression in the generated optimization record (by default, include all passes) -! HELP-NEXT: -fpass-plugin= Load pass plugin from a dynamic shared object file (only with new pass manager). -! HELP-NEXT: -fppc-native-vector-element-order -! HELP-NEXT: Specifies PowerPC native vector element order (default) -! HELP-NEXT: -freciprocal-math Allow division operations to be reassociated -! HELP-NEXT: -fropi Generate read-only position independent code (ARM only) -! HELP-NEXT: -frtlib-add-rpath Add -rpath with architecture-specific resource directory to the linker flags. When --hip-link is specified, also add -rpath with HIP runtime library directory to the linker flags -! HELP-NEXT: -frwpi Generate read-write position independent code (ARM only) -! HELP-NEXT: -fsave-optimization-record= -! HELP-NEXT: Generate an optimization record file in a specific format -! HELP-NEXT: -fsave-optimization-record -! HELP-NEXT: Generate a YAML optimization record file -! HELP-NEXT: -fstack-arrays Attempt to allocate array temporaries on the stack, no matter their size -! HELP-NEXT: -fsyntax-only Run the preprocessor, parser and semantic analysis stages -! HELP-NEXT: -funderscoring Appends one trailing underscore to external names -! HELP-NEXT: -fveclib= Use the given vector functions library -! HELP-NEXT: -fversion-loops-for-stride -! HELP-NEXT: Create unit-strided versions of loops -! HELP-NEXT: -fxor-operator Enable .XOR. as a synonym of .NEQV. -! HELP-NEXT: --gcc-install-dir= -! HELP-NEXT: Use GCC installation in the specified directory. The directory ends with path components like 'lib{,32,64}/gcc{,-cross}/$triple/$version'. Note: executables (e.g. ld) used by the compiler are not overridden by the selected GCC installation -! HELP-NEXT: --gcc-toolchain= Specify a directory where Flang can find 'lib{,32,64}/gcc{,-cross}/$triple/$version'. Flang will use the GCC installation with the largest version -! HELP-NEXT: -gline-directives-only Emit debug line info directives only -! HELP-NEXT: -gline-tables-only Emit debug line number tables only -! HELP-NEXT: -gpulibc Link the LLVM C Library for GPUs -! HELP-NEXT: -g Generate source-level debug information -! HELP-NEXT: --help-hidden Display help for hidden options -! HELP-NEXT: -help Display available options -! HELP-NEXT: -isysroot Set the system root directory (usually /) -! HELP-NEXT: -I Add directory to the end of the list of include search paths -! HELP-NEXT: -L Add directory to library search path -! HELP-NEXT: -march= For a list of available architectures for the target use '-mcpu=help' -! HELP-NEXT: -mcode-object-version= -! HELP-NEXT: Specify code object ABI version. Defaults to 5. (AMDGPU only) -! HELP-NEXT: -mcpu= For a list of available CPUs for the target use '-mcpu=help' -! HELP-NEXT: -mllvm= Alias for -mllvm -! HELP-NEXT: -mllvm Additional arguments to forward to LLVM's option processing -! HELP-NEXT: -mmlir Additional arguments to forward to MLIR's option processing -! HELP-NEXT: -mno-outline-atomics Don't generate local calls to out-of-line atomic operations -! HELP-NEXT: -module-dir Put MODULE files in -! HELP-NEXT: -moutline-atomics Generate local calls to out-of-line atomic operations -! HELP-NEXT: -mrvv-vector-bits= -! HELP-NEXT: Specify the size in bits of an RVV vector register -! HELP-NEXT: -msve-vector-bits= -! HELP-NEXT: Specify the size in bits of an SVE vector register. Defaults to the vector length agnostic value of "scalable". (AArch64 only) -! HELP-NEXT: --no-offload-arch= -! HELP-NEXT: Remove CUDA/HIP offloading device architecture (e.g. sm_35, gfx906) from the list of devices to compile for. 'all' resets the list to its default value. -! HELP-NEXT: -nocpp Disable predefined and command line preprocessor macros -! HELP-NEXT: -nogpulib Do not link device library for CUDA/HIP device compilation -! HELP-NEXT: --offload-arch= Specify an offloading device architecture for CUDA, HIP, or OpenMP. (e.g. sm_35). If 'native' is used the compiler will detect locally installed architectures. For HIP offloading, the device architecture can be followed by target ID features delimited by a colon (e.g. gfx908:xnack+:sramecc-). May be specified more than once. -! HELP-NEXT: --offload-device-only Only compile for the offloading device. -! HELP-NEXT: --offload-host-device Compile for both the offloading host and device (default). -! HELP-NEXT: --offload-host-only Only compile for the offloading host. -! HELP-NEXT: -o Write output to -! HELP-NEXT: -pedantic Warn on language extensions -! HELP-NEXT: -print-effective-triple Print the effective target triple -! HELP-NEXT: -print-target-triple Print the normalized target triple -! HELP-NEXT: -pthread Support POSIX threads in generated code -! HELP-NEXT: -P Disable linemarker output in -E mode -! HELP-NEXT: --rocm-path= ROCm installation path, used for finding and automatically linking required bitcode libraries. -! HELP-NEXT: -Rpass-analysis= Report transformation analysis from optimization passes whose name matches the given POSIX regular expression -! HELP-NEXT: -Rpass-missed= Report missed transformations by optimization passes whose name matches the given POSIX regular expression -! HELP-NEXT: -Rpass= Report transformations performed by optimization passes whose name matches the given POSIX regular expression -! HELP-NEXT: -R Enable the specified remark -! HELP-NEXT: -save-temps= Save intermediate compilation results. -! HELP-NEXT: -save-temps Alias for --save-temps=cwd -! HELP-NEXT: -std= Language standard to compile for -! HELP-NEXT: -S Only run preprocess and compilation steps -! HELP-NEXT: --target= Generate code for the given target -! HELP-NEXT: -U Undefine macro -! HELP-NEXT: --version Print version information -! HELP-NEXT: -v Show commands to run and use verbose output -! HELP-NEXT: -Wl, Pass the comma separated arguments in to the linker -! HELP-NEXT: -W Enable the specified warning -! HELP-NEXT: -Xflang Pass to the flang compiler -! HELP-NEXT: -x Treat subsequent input files as having type - ! HELP-FC1:USAGE: flang ! HELP-FC1-EMPTY: ! HELP-FC1-NEXT:OPTIONS: -! HELP-FC1-NEXT: -cpp Enable predefined and command line preprocessor macros -! HELP-FC1-NEXT: --dependent-lib= Add dependent library -! HELP-FC1-NEXT: -dM Print macro definitions in -E mode instead of normal output -! HELP-FC1-NEXT: -D = Define to (or 1 if omitted) -! HELP-FC1-NEXT: -emit-fir Build the parse tree, then lower it to FIR -! HELP-FC1-NEXT: -emit-hlfir Build the parse tree, then lower it to HLFIR -! HELP-FC1-NEXT: -emit-llvm-bc Build ASTs then convert to LLVM, emit .bc file -! HELP-FC1-NEXT: -emit-llvm Use the LLVM representation for assembler and object files -! HELP-FC1-NEXT: -emit-obj Emit native object files -! HELP-FC1-NEXT: -E Only run the preprocessor -! HELP-FC1-NEXT: -falternative-parameter-statement -! HELP-FC1-NEXT: Enable the old style PARAMETER statement -! HELP-FC1-NEXT: -fapprox-func Allow certain math function calls to be replaced with an approximately equivalent calculation -! HELP-FC1-NEXT: -fbackslash Specify that backslash in string introduces an escape character -! HELP-FC1-NEXT: -fcolor-diagnostics Enable colors in diagnostics -! HELP-FC1-NEXT: -fconvert= Set endian conversion of data for unformatted files -! HELP-FC1-NEXT: -fdebug-dump-all Dump symbols and the parse tree after the semantic checks -! HELP-FC1-NEXT: -fdebug-dump-parse-tree-no-sema -! HELP-FC1-NEXT: Dump the parse tree (skips the semantic checks) -! HELP-FC1-NEXT: -fdebug-dump-parse-tree Dump the parse tree -! HELP-FC1-NEXT: -fdebug-dump-parsing-log -! HELP-FC1-NEXT: Run instrumented parse and dump the parsing log -! HELP-FC1-NEXT: -fdebug-dump-pft Dump the pre-fir parse tree -! HELP-FC1-NEXT: -fdebug-dump-provenance Dump provenance -! HELP-FC1-NEXT: -fdebug-dump-symbols Dump symbols after the semantic analysis -! HELP-FC1-NEXT: -fdebug-measure-parse-tree -! HELP-FC1-NEXT: Measure the parse tree -! HELP-FC1-NEXT: -fdebug-module-writer Enable debug messages while writing module files -! HELP-FC1-NEXT: -fdebug-pass-manager Prints debug information for the new pass manager -! HELP-FC1-NEXT: -fdebug-pre-fir-tree Dump the pre-FIR tree -! HELP-FC1-NEXT: -fdebug-unparse-no-sema Unparse and stop (skips the semantic checks) -! HELP-FC1-NEXT: -fdebug-unparse-with-symbols -! HELP-FC1-NEXT: Unparse and stop. -! HELP-FC1-NEXT: -fdebug-unparse Unparse and stop. -! HELP-FC1-NEXT: -fdefault-double-8 Set the default double precision kind to an 8 byte wide type -! HELP-FC1-NEXT: -fdefault-integer-8 Set the default integer and logical kind to an 8 byte wide type -! HELP-FC1-NEXT: -fdefault-real-8 Set the default real kind to an 8 byte wide type -! HELP-FC1-NEXT: -fembed-offload-object= -! HELP-FC1-NEXT: Embed Offloading device-side binary into host object file as a section. -! HELP-FC1-NEXT: -ffast-math Allow aggressive, lossy floating-point optimizations -! HELP-FC1-NEXT: -ffixed-form Process source files in fixed form -! HELP-FC1-NEXT: -ffixed-line-length= -! HELP-FC1-NEXT: Use as character line width in fixed mode -! HELP-FC1-NEXT: -ffp-contract= Form fused FP ops (e.g. FMAs) -! HELP-FC1-NEXT: -ffree-form Process source files in free form -! HELP-FC1-NEXT: -fget-definition -! HELP-FC1-NEXT: Get the symbol definition from -! HELP-FC1-NEXT: -fget-symbols-sources Dump symbols and their source code locations -! HELP-FC1-NEXT: -fimplicit-none No implicit typing allowed unless overridden by IMPLICIT statements -! HELP-FC1-NEXT: -finput-charset= Specify the default character set for source files -! HELP-FC1-NEXT: -fintrinsic-modules-path -! HELP-FC1-NEXT: Specify where to find the compiled intrinsic modules -! HELP-FC1-NEXT: -flarge-sizes Use INTEGER(KIND=8) for the result type in size-related intrinsics -! HELP-FC1-NEXT: -flogical-abbreviations Enable logical abbreviations -! HELP-FC1-NEXT: -flto= Set LTO mode -! HELP-FC1-NEXT: -flto Enable LTO in 'full' mode -! HELP-FC1-NEXT: -fno-analyzed-objects-for-unparse -! HELP-FC1-NEXT: Do not use the analyzed objects when unparsing -! HELP-FC1-NEXT: -fno-automatic Implies the SAVE attribute for non-automatic local objects in subprograms unless RECURSIVE -! HELP-FC1-NEXT: -fno-debug-pass-manager Disables debug printing for the new pass manager -! HELP-FC1-NEXT: -fno-ppc-native-vector-element-order -! HELP-FC1-NEXT: Specifies PowerPC non-native vector element order -! HELP-FC1-NEXT: -fno-reformat Dump the cooked character stream in -E mode -! HELP-FC1-NEXT: -fno-signed-zeros Allow optimizations that ignore the sign of floating point zeros -! HELP-FC1-NEXT: -fno-stack-arrays Allocate array temporaries on the heap (default) -! HELP-FC1-NEXT: -fno-version-loops-for-stride -! HELP-FC1-NEXT: Do not create unit-strided loops (default) -! HELP-FC1-NEXT: -fopenacc Enable OpenACC -! HELP-FC1-NEXT: -fopenmp-host-ir-file-path -! HELP-FC1-NEXT: Path to the IR file produced by the frontend for the host. -! HELP-FC1-NEXT: -fopenmp-is-target-device -! HELP-FC1-NEXT: Generate code only for an OpenMP target device. -! HELP-FC1-NEXT: -fopenmp-target-debug Enable debugging in the OpenMP offloading device RTL -! HELP-FC1-NEXT: -fopenmp-version= -! HELP-FC1-NEXT: Set OpenMP version (e.g. 45 for OpenMP 4.5, 51 for OpenMP 5.1). Default value is 11 for Flang -! HELP-FC1-NEXT: -fopenmp Parse OpenMP pragmas and generate parallel code. -! HELP-FC1-NEXT: -fpass-plugin= Load pass plugin from a dynamic shared object file (only with new pass manager). -! HELP-FC1-NEXT: -fppc-native-vector-element-order -! HELP-FC1-NEXT: Specifies PowerPC native vector element order (default) -! HELP-FC1-NEXT: -freciprocal-math Allow division operations to be reassociated -! HELP-FC1-NEXT: -fstack-arrays Attempt to allocate array temporaries on the stack, no matter their size -! HELP-FC1-NEXT: -fsyntax-only Run the preprocessor, parser and semantic analysis stages -! HELP-FC1-NEXT: -funderscoring Appends one trailing underscore to external names -! HELP-FC1-NEXT: -fveclib= Use the given vector functions library -! HELP-FC1-NEXT: -fversion-loops-for-stride -! HELP-FC1-NEXT: Create unit-strided versions of loops -! HELP-FC1-NEXT: -fxor-operator Enable .XOR. as a synonym of .NEQV. -! HELP-FC1-NEXT: -gpulibc Link the LLVM C Library for GPUs -! HELP-FC1-NEXT: -help Display available options -! HELP-FC1-NEXT: -init-only Only execute frontend initialization -! HELP-FC1-NEXT: -I Add directory to the end of the list of include search paths -! HELP-FC1-NEXT: -load Load the named plugin (dynamic shared object) -! HELP-FC1-NEXT: -mcode-object-version= -! HELP-FC1-NEXT: Specify code object ABI version. Defaults to 5. (AMDGPU only) -! HELP-FC1-NEXT: -menable-no-infs Allow optimization to assume there are no infinities. -! HELP-FC1-NEXT: -menable-no-nans Allow optimization to assume there are no NaNs. -! HELP-FC1-NEXT: -mframe-pointer= Specify which frame pointers to retain. -! HELP-FC1-NEXT: -mllvm Additional arguments to forward to LLVM's option processing -! HELP-FC1-NEXT: -mmlir Additional arguments to forward to MLIR's option processing -! HELP-FC1-NEXT: -module-dir Put MODULE files in -! HELP-FC1-NEXT: -module-suffix Use as the suffix for module files (the default value is `.mod`) -! HELP-FC1-NEXT: -mreassociate Allow reassociation transformations for floating-point instructions -! HELP-FC1-NEXT: -mrelocation-model -! HELP-FC1-NEXT: The relocation model to use -! HELP-FC1-NEXT: -mvscale-max= Specify the vscale maximum. Defaults to the vector length agnostic value of "0". (AArch64/RISC-V only) -! HELP-FC1-NEXT: -mvscale-min= Specify the vscale minimum. Defaults to "1". (AArch64/RISC-V only) -! HELP-FC1-NEXT: -nocpp Disable predefined and command line preprocessor macros -! HELP-FC1-NEXT: -nogpulib Do not link device library for CUDA/HIP device compilation -! HELP-FC1-NEXT: -opt-record-file -! HELP-FC1-NEXT: File name to use for YAML optimization record output -! HELP-FC1-NEXT: -opt-record-format -! HELP-FC1-NEXT: The format used for serializing remarks (default: YAML) -! HELP-FC1-NEXT: -opt-record-passes -! HELP-FC1-NEXT: Only record remark information for passes whose names match the given regular expression -! HELP-FC1-NEXT: -o Write output to -! HELP-FC1-NEXT: -pedantic Warn on language extensions -! HELP-FC1-NEXT: -pic-is-pie File is for a position independent executable -! HELP-FC1-NEXT: -pic-level Value for __PIC__ -! HELP-FC1-NEXT: -plugin Use the named plugin action instead of the default action (use "help" to list available options) -! HELP-FC1-NEXT: -pthread Support POSIX threads in generated code -! HELP-FC1-NEXT: -P Disable linemarker output in -E mode -! HELP-FC1-NEXT: -Rpass-analysis= Report transformation analysis from optimization passes whose name matches the given POSIX regular expression -! HELP-FC1-NEXT: -Rpass-missed= Report missed transformations by optimization passes whose name matches the given POSIX regular expression -! HELP-FC1-NEXT: -Rpass= Report transformations performed by optimization passes whose name matches the given POSIX regular expression -! HELP-FC1-NEXT: -R Enable the specified remark -! HELP-FC1-NEXT: -save-temps= Save intermediate compilation results. -! HELP-FC1-NEXT: -save-temps Alias for --save-temps=cwd -! HELP-FC1-NEXT: -std= Language standard to compile for -! HELP-FC1-NEXT: -S Only run preprocess and compilation steps -! HELP-FC1-NEXT: -target-cpu Target a specific cpu type -! HELP-FC1-NEXT: -target-feature Target specific attributes -! HELP-FC1-NEXT: -test-io Run the InputOuputTest action. Use for development and testing only. -! HELP-FC1-NEXT: -triple Specify target triple (e.g. i686-apple-darwin9) -! HELP-FC1-NEXT: -U Undefine macro -! HELP-FC1-NEXT: -version Print the compiler version -! HELP-FC1-NEXT: -W Enable the specified warning -! HELP-FC1-NEXT: -x Treat subsequent input files as having type ! ERROR: error: unknown argument '-helps'; did you mean '-help' diff --git a/flang/test/Driver/mlir-debug-pass-pipeline.f90 b/flang/test/Driver/mlir-debug-pass-pipeline.f90 index ef84cb80ecf1db05d3daae41414ad4bc0f00c640..28d70bc15264297b82129c739230942f2281c8f2 100644 --- a/flang/test/Driver/mlir-debug-pass-pipeline.f90 +++ b/flang/test/Driver/mlir-debug-pass-pipeline.f90 @@ -39,9 +39,14 @@ end program ! ALL-NEXT: (S) 0 num-cse'd - Number of operations CSE'd ! ALL-NEXT: (S) 0 num-dce'd - Number of operations DCE'd +! ALL-NEXT: Pipeline Collection : ['fir.global', 'func.func', 'omp.declare_reduction'] +! ALL-NEXT: 'fir.global' Pipeline +! ALL-NEXT: CharacterConversion ! ALL-NEXT: 'func.func' Pipeline ! ALL-NEXT: ArrayValueCopy ! ALL-NEXT: CharacterConversion +! ALL-NEXT: 'omp.declare_reduction' Pipeline +! ALL-NEXT: CharacterConversion ! ALL-NEXT: Canonicalizer ! ALL-NEXT: SimplifyRegionLite @@ -58,12 +63,14 @@ end program ! ALL-NEXT: (S) 0 num-cse'd - Number of operations CSE'd ! ALL-NEXT: (S) 0 num-dce'd - Number of operations DCE'd -! ALL-NEXT: Pipeline Collection : ['func.func', 'omp.declare_reduction'] +! ALL-NEXT: Pipeline Collection : ['fir.global', 'func.func', 'omp.declare_reduction'] +! ALL-NEXT: 'fir.global' Pipeline +! ALL-NEXT: CFGConversion ! ALL-NEXT: 'func.func' Pipeline ! ALL-NEXT: PolymorphicOpConversion -! ALL-NEXT: CFGConversionOnFunc +! ALL-NEXT: CFGConversion ! ALL-NEXT: 'omp.declare_reduction' Pipeline -! ALL-NEXT: CFGConversionOnReduction +! ALL-NEXT: CFGConversion ! ALL-NEXT: SCFToControlFlow ! ALL-NEXT: Canonicalizer ! ALL-NEXT: SimplifyRegionLite diff --git a/flang/test/Driver/mlir-pass-pipeline.f90 b/flang/test/Driver/mlir-pass-pipeline.f90 index d1ff2869b0a6a94d79ab88276197dc7306ae23ff..41f3c203e4355418de473a22da8ec7ae3a71b47e 100644 --- a/flang/test/Driver/mlir-pass-pipeline.f90 +++ b/flang/test/Driver/mlir-pass-pipeline.f90 @@ -28,9 +28,14 @@ end program ! ALL-NEXT: (S) 0 num-cse'd - Number of operations CSE'd ! ALL-NEXT: (S) 0 num-dce'd - Number of operations DCE'd +! ALL-NEXT: Pipeline Collection : ['fir.global', 'func.func', 'omp.declare_reduction'] +! ALL-NEXT: 'fir.global' Pipeline +! ALL-NEXT: CharacterConversion ! ALL-NEXT: 'func.func' Pipeline ! ALL-NEXT: ArrayValueCopy ! ALL-NEXT: CharacterConversion +! ALL-NEXT: 'omp.declare_reduction' Pipeline +! ALL-NEXT: CharacterConversion ! ALL-NEXT: Canonicalizer ! ALL-NEXT: SimplifyRegionLite @@ -52,12 +57,14 @@ end program ! O2-NEXT: 'func.func' Pipeline ! O2-NEXT: PolymorphicOpConversion ! O2-NEXT: AddAliasTags -! ALL-NEXT: Pipeline Collection : ['func.func', 'omp.declare_reduction'] +! ALL-NEXT: Pipeline Collection : ['fir.global', 'func.func', 'omp.declare_reduction'] +! ALL-NEXT: 'fir.global' Pipeline +! ALL-NEXT: CFGConversion ! ALL-NEXT: 'func.func' Pipeline ! NOTO2-NEXT: PolymorphicOpConversion -! ALL-NEXT: CFGConversionOnFunc +! ALL-NEXT: CFGConversion ! ALL-NEXT: 'omp.declare_reduction' Pipeline -! ALL-NEXT: CFGConversionOnReduction +! ALL-NEXT: CFGConversion ! ALL-NEXT: SCFToControlFlow ! ALL-NEXT: Canonicalizer diff --git a/flang/test/Fir/array-value-copy-2.fir b/flang/test/Fir/array-value-copy-2.fir index cb8d6ca2b05540ca49bd20c027f6b44a5570152e..21b340af10c6b818ae82bb3b41a5ef7281aaf9f4 100644 --- a/flang/test/Fir/array-value-copy-2.fir +++ b/flang/test/Fir/array-value-copy-2.fir @@ -1,5 +1,5 @@ -// RUN: fir-opt --array-value-copy --cfg-conversion-on-func-opt %s | FileCheck %s -// RUN: fir-opt --array-value-copy="optimize-conflicts=true" --cfg-conversion-on-func-opt %s | FileCheck %s +// RUN: fir-opt --array-value-copy --cfg-conversion %s | FileCheck %s +// RUN: fir-opt --array-value-copy="optimize-conflicts=true" --cfg-conversion %s | FileCheck %s // CHECK-LABEL: func @_QPslice1( // CHECK-NOT: fir.allocmem diff --git a/flang/test/Fir/basic-program.fir b/flang/test/Fir/basic-program.fir index 28c597fc918cd7a2c5ea05e04f9dc9917d1dea6e..7508963a3d5157a7d45b69bc0d9f5ead4424c976 100644 --- a/flang/test/Fir/basic-program.fir +++ b/flang/test/Fir/basic-program.fir @@ -34,9 +34,14 @@ func.func @_QQmain() { // PASSES-NEXT: (S) 0 num-cse'd - Number of operations CSE'd // PASSES-NEXT: (S) 0 num-dce'd - Number of operations DCE'd +// PASSES-NEXT: Pipeline Collection : ['fir.global', 'func.func', 'omp.declare_reduction'] +// PASSES-NEXT: 'fir.global' Pipeline +// PASSES-NEXT: CharacterConversion // PASSES-NEXT: 'func.func' Pipeline // PASSES-NEXT: ArrayValueCopy // PASSES-NEXT: CharacterConversion +// PASSES-NEXT: 'omp.declare_reduction' Pipeline +// PASSES-NEXT: CharacterConversion // PASSES-NEXT: Canonicalizer // PASSES-NEXT: SimplifyRegionLite @@ -60,11 +65,13 @@ func.func @_QQmain() { // PASSES-NEXT: AddAliasTags -// PASSES-NEXT: Pipeline Collection : ['func.func', 'omp.declare_reduction'] +// PASSES-NEXT: Pipeline Collection : ['fir.global', 'func.func', 'omp.declare_reduction'] +// PASSES-NEXT: 'fir.global' Pipeline +// PASSES-NEXT: CFGConversion // PASSES-NEXT: 'func.func' Pipeline -// PASSES-NEXT: CFGConversionOnFunc +// PASSES-NEXT: CFGConversion // PASSES-NEXT: 'omp.declare_reduction' Pipeline -// PASSES-NEXT: CFGConversionOnReduction +// PASSES-NEXT: CFGConversion // PASSES-NEXT: SCFToControlFlow // PASSES-NEXT: Canonicalizer diff --git a/flang/test/Fir/convert-to-llvm-openmp-and-fir.fir b/flang/test/Fir/convert-to-llvm-openmp-and-fir.fir index fa7979e8875afcd2da56d95618b0262016a65084..8cf4f566964f9169702ee431fdca2725e41c4c63 100644 --- a/flang/test/Fir/convert-to-llvm-openmp-and-fir.fir +++ b/flang/test/Fir/convert-to-llvm-openmp-and-fir.fir @@ -1,4 +1,4 @@ -// RUN: fir-opt --split-input-file --cfg-conversion-on-func-opt --fir-to-llvm-ir="target=aarch64-unknown-linux-gnu" %s | FileCheck %s +// RUN: fir-opt --split-input-file --cfg-conversion --fir-to-llvm-ir="target=aarch64-unknown-linux-gnu" %s | FileCheck %s func.func @_QPsb1(%arg0: !fir.ref {fir.bindc_name = "n"}, %arg1: !fir.ref> {fir.bindc_name = "arr"}) { %c1_i64 = arith.constant 1 : i64 @@ -7,15 +7,17 @@ func.func @_QPsb1(%arg0: !fir.ref {fir.bindc_name = "n"}, %arg1: !fir.ref - omp.wsloop nowait - for (%arg2) : i32 = (%c1_i32) to (%2) inclusive step (%c1_i32) { - fir.store %arg2 to %1 : !fir.ref - %3 = fir.load %1 : !fir.ref - %4 = fir.convert %3 : (i32) -> i64 - %5 = arith.subi %4, %c1_i64 : i64 - %6 = fir.coordinate_of %arg1, %5 : (!fir.ref>, i64) -> !fir.ref - fir.store %3 to %6 : !fir.ref - omp.yield + omp.wsloop nowait { + omp.loop_nest (%arg2) : i32 = (%c1_i32) to (%2) inclusive step (%c1_i32) { + fir.store %arg2 to %1 : !fir.ref + %3 = fir.load %1 : !fir.ref + %4 = fir.convert %3 : (i32) -> i64 + %5 = arith.subi %4, %c1_i64 : i64 + %6 = fir.coordinate_of %arg1, %5 : (!fir.ref>, i64) -> !fir.ref + fir.store %3 to %6 : !fir.ref + omp.yield + } + omp.terminator } omp.terminator } @@ -31,7 +33,7 @@ func.func @_QPsb1(%arg0: !fir.ref {fir.bindc_name = "n"}, %arg1: !fir.ref !llvm.ptr // CHECK: %[[N:.*]] = llvm.load %[[N_REF]] : !llvm.ptr -> i32 // CHECK: omp.wsloop nowait -// CHECK-SAME: for (%[[I:.*]]) : i32 = (%[[ONE_2]]) to (%[[N]]) inclusive step (%[[ONE_2]]) { +// CHECK-NEXT: omp.loop_nest (%[[I:.*]]) : i32 = (%[[ONE_2]]) to (%[[N]]) inclusive step (%[[ONE_2]]) { // CHECK: llvm.store %[[I]], %[[I_VAR]] : i32, !llvm.ptr // CHECK: %[[I1:.*]] = llvm.load %[[I_VAR]] : !llvm.ptr -> i32 // CHECK: %[[I1_EXT:.*]] = llvm.sext %[[I1]] : i32 to i64 @@ -42,6 +44,8 @@ func.func @_QPsb1(%arg0: !fir.ref {fir.bindc_name = "n"}, %arg1: !fir.ref> {fir.bindc_name = "arr"}) { omp.parallel { %c1 = arith.constant 1 : i32 %c50 = arith.constant 50 : i32 - omp.wsloop for (%indx) : i32 = (%c1) to (%c50) inclusive step (%c1) { - %1 = fir.convert %indx : (i32) -> i64 - %c1_i64 = arith.constant 1 : i64 - %2 = arith.subi %1, %c1_i64 : i64 - %3 = fir.coordinate_of %arr, %2 : (!fir.box>, i64) -> !fir.ref - fir.store %indx to %3 : !fir.ref - omp.yield + omp.wsloop { + omp.loop_nest (%indx) : i32 = (%c1) to (%c50) inclusive step (%c1) { + %1 = fir.convert %indx : (i32) -> i64 + %c1_i64 = arith.constant 1 : i64 + %2 = arith.subi %1, %c1_i64 : i64 + %3 = fir.coordinate_of %arr, %2 : (!fir.box>, i64) -> !fir.ref + fir.store %indx to %3 : !fir.ref + omp.yield + } + omp.terminator } omp.terminator } @@ -98,9 +105,11 @@ func.func @_QPsb(%arr: !fir.box> {fir.bindc_name = "arr"}) { // CHECK: omp.parallel { // CHECK: %[[C1:.*]] = llvm.mlir.constant(1 : i32) : i32 // CHECK: %[[C50:.*]] = llvm.mlir.constant(50 : i32) : i32 -// CHECK: omp.wsloop for (%[[INDX:.*]]) : i32 = (%[[C1]]) to (%[[C50]]) inclusive step (%[[C1]]) { -// CHECK: llvm.store %[[INDX]], %{{.*}} : i32, !llvm.ptr -// CHECK: omp.yield +// CHECK: omp.wsloop { +// CHECK-NEXT: omp.loop_nest (%[[INDX:.*]]) : i32 = (%[[C1]]) to (%[[C50]]) inclusive step (%[[C1]]) { +// CHECK: llvm.store %[[INDX]], %{{.*}} : i32, !llvm.ptr +// CHECK: omp.yield +// CHECK: omp.terminator // CHECK: omp.terminator // CHECK: llvm.return @@ -708,18 +717,20 @@ func.func @_QPsb() { // CHECK-SAME: %[[ARRAY_REF:.*]]: !llvm.ptr // CHECK: %[[RED_ACCUMULATOR:.*]] = llvm.alloca %2 x i32 {bindc_name = "x"} : (i64) -> !llvm.ptr // CHECK: omp.parallel { -// CHECK: omp.wsloop reduction(@[[EQV_REDUCTION]] %[[RED_ACCUMULATOR]] -> %[[PRV:.+]] : !llvm.ptr) for -// CHECK: %[[ARRAY_ELEM_REF:.*]] = llvm.getelementptr %[[ARRAY_REF]][0, %{{.*}}] : (!llvm.ptr, i64) -> !llvm.ptr -// CHECK: %[[ARRAY_ELEM:.*]] = llvm.load %[[ARRAY_ELEM_REF]] : !llvm.ptr -> i32 -// CHECK: %[[LPRV:.+]] = llvm.load %[[PRV]] : !llvm.ptr -> i32 -// CHECK: %[[ZERO_1:.*]] = llvm.mlir.constant(0 : i64) : i32 -// CHECK: %[[ARGVAL_1:.*]] = llvm.icmp "ne" %[[LPRV]], %[[ZERO_1]] : i32 -// CHECK: %[[ZERO_2:.*]] = llvm.mlir.constant(0 : i64) : i32 -// CHECK: %[[ARGVAL_2:.*]] = llvm.icmp "ne" %[[ARRAY_ELEM]], %[[ZERO_2]] : i32 -// CHECK: %[[RES:.*]] = llvm.icmp "eq" %[[ARGVAL_2]], %[[ARGVAL_1]] : i1 -// CHECK: %[[RES_EXT:.*]] = llvm.zext %[[RES]] : i1 to i32 -// CHECK: llvm.store %[[RES_EXT]], %[[PRV]] : i32, !llvm.ptr -// CHECK: omp.yield +// CHECK: omp.wsloop reduction(@[[EQV_REDUCTION]] %[[RED_ACCUMULATOR]] -> %[[PRV:.+]] : !llvm.ptr) { +// CHECK-NEXT: omp.loop_nest +// CHECK: %[[ARRAY_ELEM_REF:.*]] = llvm.getelementptr %[[ARRAY_REF]][0, %{{.*}}] : (!llvm.ptr, i64) -> !llvm.ptr +// CHECK: %[[ARRAY_ELEM:.*]] = llvm.load %[[ARRAY_ELEM_REF]] : !llvm.ptr -> i32 +// CHECK: %[[LPRV:.+]] = llvm.load %[[PRV]] : !llvm.ptr -> i32 +// CHECK: %[[ZERO_1:.*]] = llvm.mlir.constant(0 : i64) : i32 +// CHECK: %[[ARGVAL_1:.*]] = llvm.icmp "ne" %[[LPRV]], %[[ZERO_1]] : i32 +// CHECK: %[[ZERO_2:.*]] = llvm.mlir.constant(0 : i64) : i32 +// CHECK: %[[ARGVAL_2:.*]] = llvm.icmp "ne" %[[ARRAY_ELEM]], %[[ZERO_2]] : i32 +// CHECK: %[[RES:.*]] = llvm.icmp "eq" %[[ARGVAL_2]], %[[ARGVAL_1]] : i1 +// CHECK: %[[RES_EXT:.*]] = llvm.zext %[[RES]] : i1 to i32 +// CHECK: llvm.store %[[RES_EXT]], %[[PRV]] : i32, !llvm.ptr +// CHECK: omp.yield +// CHECK: omp.terminator // CHECK: omp.terminator // CHECK: llvm.return @@ -747,21 +758,24 @@ func.func @_QPsimple_reduction(%arg0: !fir.ref>> %c1_i32 = arith.constant 1 : i32 %c100_i32 = arith.constant 100 : i32 %c1_i32_0 = arith.constant 1 : i32 - omp.wsloop reduction(@eqv_reduction %1 -> %prv : !fir.ref>) for (%arg1) : i32 = (%c1_i32) to (%c100_i32) inclusive step (%c1_i32_0) { - fir.store %arg1 to %3 : !fir.ref - %4 = fir.load %3 : !fir.ref - %5 = fir.convert %4 : (i32) -> i64 - %c1_i64 = arith.constant 1 : i64 - %6 = arith.subi %5, %c1_i64 : i64 - %7 = fir.coordinate_of %arg0, %6 : (!fir.ref>>, i64) -> !fir.ref> - %8 = fir.load %7 : !fir.ref> - %lprv = fir.load %prv : !fir.ref> - %lprv1 = fir.convert %lprv : (!fir.logical<4>) -> i1 - %9 = fir.convert %8 : (!fir.logical<4>) -> i1 - %10 = arith.cmpi eq, %9, %lprv1 : i1 - %11 = fir.convert %10 : (i1) -> !fir.logical<4> - fir.store %11 to %prv : !fir.ref> - omp.yield + omp.wsloop reduction(@eqv_reduction %1 -> %prv : !fir.ref>) { + omp.loop_nest (%arg1) : i32 = (%c1_i32) to (%c100_i32) inclusive step (%c1_i32_0) { + fir.store %arg1 to %3 : !fir.ref + %4 = fir.load %3 : !fir.ref + %5 = fir.convert %4 : (i32) -> i64 + %c1_i64 = arith.constant 1 : i64 + %6 = arith.subi %5, %c1_i64 : i64 + %7 = fir.coordinate_of %arg0, %6 : (!fir.ref>>, i64) -> !fir.ref> + %8 = fir.load %7 : !fir.ref> + %lprv = fir.load %prv : !fir.ref> + %lprv1 = fir.convert %lprv : (!fir.logical<4>) -> i1 + %9 = fir.convert %8 : (!fir.logical<4>) -> i1 + %10 = arith.cmpi eq, %9, %lprv1 : i1 + %11 = fir.convert %10 : (i1) -> !fir.logical<4> + fir.store %11 to %prv : !fir.ref> + omp.yield + } + omp.terminator } omp.terminator } diff --git a/flang/test/Fir/loop01.fir b/flang/test/Fir/loop01.fir index c849797b969eba5bda1e38cce73b888c0c85efa4..72ca1c3989e453d41f3605c14cb48bc657f8e654 100644 --- a/flang/test/Fir/loop01.fir +++ b/flang/test/Fir/loop01.fir @@ -1,4 +1,4 @@ -// RUN: fir-opt --split-input-file --cfg-conversion-on-func-opt %s | FileCheck %s +// RUN: fir-opt --split-input-file --cfg-conversion %s | FileCheck %s func.func @x(%lb : index, %ub : index, %step : index, %b : i1, %addr : !fir.ref) { fir.do_loop %iv = %lb to %ub step %step unordered { diff --git a/flang/test/Fir/loop02.fir b/flang/test/Fir/loop02.fir index 8918666f0b3460d8b1982e83dd13de3b9f9cf557..50948e0e7aa6b53dcc40fafb74f112b401b29f89 100644 --- a/flang/test/Fir/loop02.fir +++ b/flang/test/Fir/loop02.fir @@ -1,5 +1,5 @@ -// RUN: fir-opt --cfg-conversion-on-func-opt="always-execute-loop-body=true" %s | FileCheck %s -// RUN: fir-opt --cfg-conversion-on-func-opt %s | FileCheck %s --check-prefix=NOOPT +// RUN: fir-opt --cfg-conversion="always-execute-loop-body=true" %s | FileCheck %s +// RUN: fir-opt --cfg-conversion %s | FileCheck %s --check-prefix=NOOPT func.func @x(%addr : !fir.ref) { %bound = arith.constant 452 : index diff --git a/flang/test/Lower/CUDA/cuda-allocatable.cuf b/flang/test/Lower/CUDA/cuda-allocatable.cuf index 251ff16a56c797cf02c38e29bdccc2ad62dfa79e..eff5f13669e904ce9eb80e8dbeb2f0795a27af6d 100644 --- a/flang/test/Lower/CUDA/cuda-allocatable.cuf +++ b/flang/test/Lower/CUDA/cuda-allocatable.cuf @@ -17,6 +17,15 @@ end subroutine ! CHECK: %{{.*}} = fir.cuda_deallocate %[[BOX_DECL]]#1 : !fir.ref>>> {cuda_attr = #fir.cuda} -> i32 +! CHECK: %[[BOX_LOAD:.*]] = fir.load %[[BOX_DECL]]#1 : !fir.ref>>> +! CHECK: %[[ADDR:.*]] = fir.box_addr %[[BOX_LOAD]] : (!fir.box>>) -> !fir.heap> +! CHECK: %[[ADDR_I64:.*]] = fir.convert %[[ADDR]] : (!fir.heap>) -> i64 +! CHECK: %[[C0:.*]] = arith.constant 0 : i64 +! CHECK: %[[NE_C0:.*]] = arith.cmpi ne, %[[ADDR_I64]], %[[C0]] : i64 +! CHECK: fir.if %[[NE_C0]] { +! CHECK: %{{.*}} = fir.cuda_deallocate %[[BOX_DECL]]#1 : !fir.ref>>> {cuda_attr = #fir.cuda} -> i32 +! CHECK: } + subroutine sub2() real, allocatable, managed :: a(:) integer :: istat @@ -37,6 +46,10 @@ end subroutine ! CHECK: %[[STAT:.*]] = fir.cuda_deallocate %[[BOX_DECL]]#1 : !fir.ref>>> {cuda_attr = #fir.cuda, hasStat} -> i32 ! CHECK: fir.store %[[STAT]] to %[[ISTAT_DECL]]#1 : !fir.ref +! CHECK: fir.if %{{.*}} { +! CHECK: %{{.*}} = fir.cuda_deallocate %[[BOX_DECL]]#1 : !fir.ref>>> {cuda_attr = #fir.cuda} -> i32 +! CHECK: } + subroutine sub3() integer, allocatable, pinned :: a(:,:) logical :: plog @@ -50,6 +63,9 @@ end subroutine ! CHECK: %[[PLOG_DECL:.*]]:2 = hlfir.declare %5 {uniq_name = "_QFsub3Eplog"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) ! CHECK-2: fir.call @_FortranAAllocatableSetBounds ! CHECK: %{{.*}} = fir.cuda_allocate %[[BOX_DECL]]#1 : !fir.ref>>> pinned(%[[PLOG_DECL]]#1 : !fir.ref>) {cuda_attr = #fir.cuda} -> i32 +! CHECK: fir.if %{{.*}} { +! CHECK: %{{.*}} = fir.cuda_deallocate %[[BOX_DECL]]#1 : !fir.ref>>> {cuda_attr = #fir.cuda} -> i32 +! CHECK: } subroutine sub4() real, allocatable, device :: a(:) @@ -65,6 +81,9 @@ end subroutine ! CHECK: fir.call @_FortranAAllocatableSetBounds ! CHECK: %[[STREAM:.*]] = fir.load %[[ISTREAM_DECL]]#0 : !fir.ref ! CHECK: %{{.*}} = fir.cuda_allocate %[[BOX_DECL]]#1 : !fir.ref>>> stream(%[[STREAM]] : i32) {cuda_attr = #fir.cuda} -> i32 +! CHECK: fir.if %{{.*}} { +! CHECK: %{{.*}} = fir.cuda_deallocate %[[BOX_DECL]]#1 : !fir.ref>>> {cuda_attr = #fir.cuda} -> i32 +! CHECK: } subroutine sub5() real, allocatable, device :: a(:) @@ -80,6 +99,11 @@ end subroutine ! CHECK: %[[LOAD_B:.*]] = fir.load %[[BOX_B_DECL]]#1 : !fir.ref>>> ! CHECK: fir.call @_FortranAAllocatableSetBounds ! CHECK: %{{.*}} = fir.cuda_allocate %[[BOX_A_DECL]]#1 : !fir.ref>>> source(%[[LOAD_B]] : !fir.box>>) {cuda_attr = #fir.cuda} -> i32 +! CHECK: fir.if +! CHECK: fir.freemem +! CHECK: fir.if %{{.*}} { +! CHECK: %{{.*}} = fir.cuda_deallocate %[[BOX_A_DECL]]#1 : !fir.ref>>> {cuda_attr = #fir.cuda} -> i32 +! CHECK: } subroutine sub6() real, allocatable, device :: a(:) @@ -95,6 +119,9 @@ end subroutine ! CHECK: %[[LOAD_B:.*]] = fir.load %[[BOX_B_DECL]]#1 : !fir.ref>>> ! CHECK: fir.call @_FortranAAllocatableApplyMold ! CHECK: %{{.*}} = fir.cuda_allocate %[[BOX_A_DECL]]#1 : !fir.ref>>> {cuda_attr = #fir.cuda} -> i32 +! CHECK: fir.if %{{.*}} { +! CHECK: %{{.*}} = fir.cuda_deallocate %[[BOX_A_DECL]]#1 : !fir.ref>>> {cuda_attr = #fir.cuda} -> i32 +! CHECK: } subroutine sub7() real, allocatable, device :: a(:) @@ -120,3 +147,6 @@ end subroutine ! CHECK: %[[ERR_BOX:.*]] = fir.embox %[[ERR_DECL]]#1 : (!fir.ref>) -> !fir.box> ! CHECK: %[[STAT:.*]] = fir.cuda_deallocate %[[BOX_DECL]]#1 : !fir.ref>>> errmsg(%15 : !fir.box>) {cuda_attr = #fir.cuda, hasStat} -> i32 ! CHECK: fir.store %[[STAT]] to %[[ISTAT_DECL]]#1 : !fir.ref +! CHECK: fir.if %{{.*}} { +! CHECK: %{{.*}} = fir.cuda_deallocate %[[BOX_DECL]]#1 : !fir.ref>>> {cuda_attr = #fir.cuda} -> i32 +! CHECK: } diff --git a/flang/test/Lower/CUDA/cuda-data-transfer.cuf b/flang/test/Lower/CUDA/cuda-data-transfer.cuf index 4ebd736315bcbce0305ac5134c549366f9a5c828..70483685d20019c75009a9a33b9aafffc57ee500 100644 --- a/flang/test/Lower/CUDA/cuda-data-transfer.cuf +++ b/flang/test/Lower/CUDA/cuda-data-transfer.cuf @@ -98,7 +98,7 @@ end ! CHECK: %[[TEMP:.*]] = fir.allocmem !fir.array<10xi32> {bindc_name = ".tmp", uniq_name = ""} ! CHECK: %[[DECL_TEMP:.*]]:2 = hlfir.declare %[[TEMP]](%{{.*}}) {uniq_name = ".tmp"} : (!fir.heap>, !fir.shape<1>) -> (!fir.heap>, !fir.heap>) -! CHECK: %[[ADEV_TEMP:.*]]:2 = hlfir.declare %21#0 {cuda_attr = #fir.cuda, uniq_name = "_QFsub2Eadev"} : (!fir.heap>) -> (!fir.heap>, !fir.heap>) +! CHECK: %[[ADEV_TEMP:.*]]:2 = hlfir.declare %[[DECL_TEMP]]#1(%{{.*}}) {cuda_attr = #fir.cuda, uniq_name = "_QFsub2Eadev"} : (!fir.heap>, !fir.shape<1>) -> (!fir.heap>, !fir.heap>) ! CHECK: fir.cuda_data_transfer %[[ADEV]]#1 to %[[DECL_TEMP]]#0 {transfer_kind = #fir.cuda_transfer} : !fir.ref>, !fir.heap> ! CHECK: %[[ELEMENTAL:.*]] = hlfir.elemental %{{.*}} unordered : (!fir.shape<1>) -> !hlfir.expr<10xi32> ! CHECK: hlfir.assign %[[ELEMENTAL]] to %[[BHOST]]#0 : !hlfir.expr<10xi32>, !fir.ref> @@ -119,3 +119,25 @@ end ! CHECK: %[[T:.*]]:2 = hlfir.declare %7 {cuda_attr = #fir.cuda, uniq_name = "_QFsub3Et"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) ! CHECK: %[[TMP_DECL:.*]]:2 = hlfir.declare %0 {uniq_name = ".tmp"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) ! CHECK: fir.cuda_data_transfer %[[T]]#1 to %[[TMP_DECL]]#0 {transfer_kind = #fir.cuda_transfer} : !fir.ref>, !fir.ref> + + +! Check that fir.cuda_data_transfer are not generated within cuf kernel +subroutine sub4() + integer, parameter :: n = 10 + real, device :: adev(n) + real :: ahost(n) + real :: b + integer :: i + + adev = ahost + !$cuf kernel do <<<*,*>>> + do i = 1, n + adev(i) = adev(i) + b + enddo +end subroutine + +! CHECK-LABEL: func.func @_QPsub4() +! CHECK: fir.cuda_data_transfer +! CHECK: fir.cuda_kernel<<<*, *>>> +! CHECK-NOT: fir.cuda_data_transfer +! CHECK: hlfir.assign diff --git a/flang/test/Lower/HLFIR/internal-procedures.f90 b/flang/test/Lower/HLFIR/internal-procedures.f90 index fff7125897ddfed701cfea93adbd0110bc009f5c..3c443991180905b0c1131e95a2abeefaaf0ac2cc 100644 --- a/flang/test/Lower/HLFIR/internal-procedures.f90 +++ b/flang/test/Lower/HLFIR/internal-procedures.f90 @@ -52,3 +52,30 @@ end subroutine ! CHECK: %[[VAL_4:.*]]:2 = fir.unboxchar %[[VAL_3]] : (!fir.boxchar<1>) -> (!fir.ref>, index) ! CHECK: %[[VAL_5:.*]]:2 = hlfir.declare %[[VAL_4]]#0 typeparams %[[VAL_4]]#1 {fortran_attrs = #fir.var_attrs, uniq_name = "_QFtest_scalar_charEc"} : (!fir.ref>, index) -> (!fir.boxchar<1>, !fir.ref>) ! CHECK: fir.call @_QPbar(%[[VAL_5]]#0) {{.*}}: (!fir.boxchar<1>) -> () + +subroutine test_proc_pointer(p) + real, pointer, external :: p + call internal() +contains + subroutine internal() + real :: x + x = p() + end subroutine +end subroutine +! CHECK-LABEL: func.func @_QPtest_proc_pointer( +! CHECK-SAME: %[[VAL_0:.*]]: !fir.ref ()>>) { +! CHECK: %[[VAL_1:.*]]:2 = hlfir.declare %[[VAL_0]] {fortran_attrs = #fir.var_attrs, uniq_name = "_QFtest_proc_pointerEp"} : (!fir.ref ()>>) -> (!fir.ref ()>>, !fir.ref ()>>) +! CHECK: %[[VAL_2:.*]] = fir.alloca tuple ()>>> +! CHECK: %[[VAL_3:.*]] = arith.constant 0 : i32 +! CHECK: %[[VAL_4:.*]] = fir.coordinate_of %[[VAL_2]], %[[VAL_3]] : (!fir.ref ()>>>>, i32) -> !fir.llvm_ptr ()>>> +! CHECK: fir.store %[[VAL_1]]#1 to %[[VAL_4]] : !fir.llvm_ptr ()>>> +! CHECK: fir.call @_QFtest_proc_pointerPinternal(%[[VAL_2]]) {{.*}}: (!fir.ref ()>>>>) -> () +! CHECK: return +! CHECK: } + +! CHECK-LABEL: func.func private @_QFtest_proc_pointerPinternal( +! CHECK-SAME: %[[VAL_0:.*]]: !fir.ref ()>>>> {fir.host_assoc}) attributes {fir.host_symbol = @_QPtest_proc_pointer, llvm.linkage = #llvm.linkage} { +! CHECK: %[[VAL_1:.*]] = arith.constant 0 : i32 +! CHECK: %[[VAL_2:.*]] = fir.coordinate_of %[[VAL_0]], %[[VAL_1]] : (!fir.ref ()>>>>, i32) -> !fir.llvm_ptr ()>>> +! CHECK: %[[VAL_3:.*]] = fir.load %[[VAL_2]] : !fir.llvm_ptr ()>>> +! CHECK: %[[VAL_4:.*]]:2 = hlfir.declare %[[VAL_3]] {fortran_attrs = #fir.var_attrs, uniq_name = "_QFtest_proc_pointerEp"} : (!fir.ref ()>>) -> (!fir.ref ()>>, !fir.ref ()>>) diff --git a/flang/test/Lower/Intrinsics/shape.f90 b/flang/test/Lower/Intrinsics/shape.f90 new file mode 100644 index 0000000000000000000000000000000000000000..60f28a326e99516b5557804278397ecb2c568da7 --- /dev/null +++ b/flang/test/Lower/Intrinsics/shape.f90 @@ -0,0 +1,74 @@ +! Test SHAPE with function results +! RUN: bbc -emit-hlfir -o - %s | FileCheck %s + +subroutine test() + interface + function return_array() + real, pointer :: return_array(:, :, :) + end function + end interface + print *, shape(return_array()) +end subroutine +! CHECK-LABEL: func.func @_QPtest() { +! CHECK: %[[VAL_0:.*]] = fir.alloca !fir.array<3xi32> +! CHECK: %[[VAL_7:.*]] = fir.call @_QPreturn_array() {{.*}}: () -> !fir.box>> +! CHECK: fir.save_result %[[VAL_7]] to %[[VAL_1:.*]] : !fir.box>>, !fir.ref>>> +! CHECK: %[[VAL_8:.*]]:2 = hlfir.declare %[[VAL_1]] {uniq_name = ".tmp.func_result"} : (!fir.ref>>>) -> (!fir.ref>>>, !fir.ref>>>) +! CHECK: %[[VAL_9:.*]] = fir.load %[[VAL_8]]#1 : !fir.ref>>> +! CHECK: %[[VAL_10:.*]] = arith.constant 0 : index +! CHECK: %[[VAL_11:.*]]:3 = fir.box_dims %[[VAL_9]], %[[VAL_10]] : (!fir.box>>, index) -> (index, index, index) +! CHECK: %[[VAL_12:.*]] = fir.convert %[[VAL_11]]#1 : (index) -> i32 +! CHECK: %[[VAL_13:.*]] = arith.constant 0 : index +! CHECK: %[[VAL_14:.*]] = fir.coordinate_of %[[VAL_0]], %[[VAL_13]] : (!fir.ref>, index) -> !fir.ref +! CHECK: fir.store %[[VAL_12]] to %[[VAL_14]] : !fir.ref +! CHECK: %[[VAL_15:.*]] = arith.constant 1 : index +! CHECK: %[[VAL_16:.*]]:3 = fir.box_dims %[[VAL_9]], %[[VAL_15]] : (!fir.box>>, index) -> (index, index, index) +! CHECK: %[[VAL_17:.*]] = fir.convert %[[VAL_16]]#1 : (index) -> i32 +! CHECK: %[[VAL_18:.*]] = arith.constant 1 : index +! CHECK: %[[VAL_19:.*]] = fir.coordinate_of %[[VAL_0]], %[[VAL_18]] : (!fir.ref>, index) -> !fir.ref +! CHECK: fir.store %[[VAL_17]] to %[[VAL_19]] : !fir.ref +! CHECK: %[[VAL_20:.*]] = arith.constant 2 : index +! CHECK: %[[VAL_21:.*]]:3 = fir.box_dims %[[VAL_9]], %[[VAL_20]] : (!fir.box>>, index) -> (index, index, index) +! CHECK: %[[VAL_22:.*]] = fir.convert %[[VAL_21]]#1 : (index) -> i32 +! CHECK: %[[VAL_23:.*]] = arith.constant 2 : index +! CHECK: %[[VAL_24:.*]] = fir.coordinate_of %[[VAL_0]], %[[VAL_23]] : (!fir.ref>, index) -> !fir.ref +! CHECK: fir.store %[[VAL_22]] to %[[VAL_24]] : !fir.ref +! CHECK: %[[VAL_25:.*]] = arith.constant 3 : index +! CHECK: %[[VAL_26:.*]] = fir.shape %[[VAL_25]] : (index) -> !fir.shape<1> +! CHECK: %[[VAL_27:.*]]:2 = hlfir.declare %[[VAL_0]](%[[VAL_26]]) {uniq_name = ".tmp.intrinsic_result"} : (!fir.ref>, !fir.shape<1>) -> (!fir.ref>, !fir.ref>) + +subroutine test_kind() + interface + function return_array() + real, pointer :: return_array(:, :, :) + end function + end interface + print *, shape(return_array(), kind=8) +end subroutine +! CHECK-LABEL: func.func @_QPtest_kind() { +! CHECK: %[[VAL_0:.*]] = fir.alloca !fir.array<3xi64> +! CHECK: %[[VAL_7:.*]] = fir.call @_QPreturn_array() {{.*}}: () -> !fir.box>> +! CHECK: fir.save_result %[[VAL_7]] to %[[VAL_1:.*]] : !fir.box>>, !fir.ref>>> +! CHECK: %[[VAL_8:.*]]:2 = hlfir.declare %[[VAL_1]] {uniq_name = ".tmp.func_result"} : (!fir.ref>>>) -> (!fir.ref>>>, !fir.ref>>>) +! CHECK: %[[VAL_9:.*]] = fir.load %[[VAL_8]]#1 : !fir.ref>>> +! CHECK: %[[VAL_10:.*]] = arith.constant 0 : index +! CHECK: %[[VAL_11:.*]]:3 = fir.box_dims %[[VAL_9]], %[[VAL_10]] : (!fir.box>>, index) -> (index, index, index) +! CHECK: %[[VAL_12:.*]] = fir.convert %[[VAL_11]]#1 : (index) -> i64 +! CHECK: %[[VAL_13:.*]] = arith.constant 0 : index +! CHECK: %[[VAL_14:.*]] = fir.coordinate_of %[[VAL_0]], %[[VAL_13]] : (!fir.ref>, index) -> !fir.ref +! CHECK: fir.store %[[VAL_12]] to %[[VAL_14]] : !fir.ref +! CHECK: %[[VAL_15:.*]] = arith.constant 1 : index +! CHECK: %[[VAL_16:.*]]:3 = fir.box_dims %[[VAL_9]], %[[VAL_15]] : (!fir.box>>, index) -> (index, index, index) +! CHECK: %[[VAL_17:.*]] = fir.convert %[[VAL_16]]#1 : (index) -> i64 +! CHECK: %[[VAL_18:.*]] = arith.constant 1 : index +! CHECK: %[[VAL_19:.*]] = fir.coordinate_of %[[VAL_0]], %[[VAL_18]] : (!fir.ref>, index) -> !fir.ref +! CHECK: fir.store %[[VAL_17]] to %[[VAL_19]] : !fir.ref +! CHECK: %[[VAL_20:.*]] = arith.constant 2 : index +! CHECK: %[[VAL_21:.*]]:3 = fir.box_dims %[[VAL_9]], %[[VAL_20]] : (!fir.box>>, index) -> (index, index, index) +! CHECK: %[[VAL_22:.*]] = fir.convert %[[VAL_21]]#1 : (index) -> i64 +! CHECK: %[[VAL_23:.*]] = arith.constant 2 : index +! CHECK: %[[VAL_24:.*]] = fir.coordinate_of %[[VAL_0]], %[[VAL_23]] : (!fir.ref>, index) -> !fir.ref +! CHECK: fir.store %[[VAL_22]] to %[[VAL_24]] : !fir.ref +! CHECK: %[[VAL_25:.*]] = arith.constant 3 : index +! CHECK: %[[VAL_26:.*]] = fir.shape %[[VAL_25]] : (index) -> !fir.shape<1> +! CHECK: %[[VAL_27:.*]]:2 = hlfir.declare %[[VAL_0]](%[[VAL_26]]) {uniq_name = ".tmp.intrinsic_result"} : (!fir.ref>, !fir.shape<1>) -> (!fir.ref>, !fir.ref>) diff --git a/flang/test/Lower/OpenACC/acc-declare.f90 b/flang/test/Lower/OpenACC/acc-declare.f90 index 401b654adeb61b6d9b4f03416e2ed654ea8fbb0a..5d3f9e3fe97e4a1b076c594366502535dbed5021 100644 --- a/flang/test/Lower/OpenACC/acc-declare.f90 +++ b/flang/test/Lower/OpenACC/acc-declare.f90 @@ -245,6 +245,11 @@ module acc_declare ! CHECK: fir.freemem %{{.*}} : !fir.heap> ! CHECK: fir.store %{{.*}} to %{{.*}} {acc.declare_action = #acc.declare_action} : !fir.ref>>> +! CHECK: fir.if +! CHECK: fir.freemem %{{.*}} : !fir.heap> +! CHECK: fir.store %{{.*}} to %{{.*}}#1 {acc.declare_action = #acc.declare_action} : !fir.ref>>> +! CHECK: } + end subroutine ! CHECK-LABEL: func.func private @_QMacc_declareFacc_declare_allocateEa_acc_declare_update_desc_post_alloc( diff --git a/flang/test/Lower/OpenMP/FIR/copyin.f90 b/flang/test/Lower/OpenMP/FIR/copyin.f90 index 20023a81977aef18299a797ae640e06bdbf044a3..e256404d3d55ce6030c625b817250cbded8d885a 100644 --- a/flang/test/Lower/OpenMP/FIR/copyin.f90 +++ b/flang/test/Lower/OpenMP/FIR/copyin.f90 @@ -145,10 +145,13 @@ end ! CHECK: %[[VAL_6:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_7:.*]] = fir.load %[[VAL_4]] : !fir.ref ! CHECK: %[[VAL_8:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop for (%[[VAL_9:.*]]) : i32 = (%[[VAL_6]]) to (%[[VAL_7]]) inclusive step (%[[VAL_8]]) { -! CHECK: fir.store %[[VAL_9]] to %[[VAL_3]] : !fir.ref -! CHECK: fir.call @_QPsub4(%[[VAL_4]]) {{.*}}: (!fir.ref) -> () -! CHECK: omp.yield +! CHECK: omp.wsloop { +! CHECK-NEXT: omp.loop_nest (%[[VAL_9:.*]]) : i32 = (%[[VAL_6]]) to (%[[VAL_7]]) inclusive step (%[[VAL_8]]) { +! CHECK: fir.store %[[VAL_9]] to %[[VAL_3]] : !fir.ref +! CHECK: fir.call @_QPsub4(%[[VAL_4]]) {{.*}}: (!fir.ref) -> () +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } @@ -286,7 +289,8 @@ end subroutine !CHECK: %[[val_c1_i32:.*]] = arith.constant 1 : i32 !CHECK: %[[val_19:.*]] = fir.load %[[val_13]] : !fir.ref !CHECK: %[[val_c1_i32_2:.*]] = arith.constant 1 : i32 -!CHECK: omp.wsloop for (%[[arg:.*]]) : i32 = (%[[val_c1_i32]]) to (%[[val_19]]) inclusive step (%[[val_c1_i32_2]]) { +!CHECK: omp.wsloop { +!CHECK-NEXT: omp.loop_nest (%[[arg:.*]]) : i32 = (%[[val_c1_i32]]) to (%[[val_19]]) inclusive step (%[[val_c1_i32_2]]) { !CHECK: fir.store %[[arg]] to %[[val_9]] : !fir.ref !CHECK: %[[val_20:.*]] = fir.load %[[val_16]] : !fir.ref !CHECK: %[[val_21:.*]] = fir.load %[[val_9]] : !fir.ref @@ -296,6 +300,8 @@ end subroutine !CHECK: } !CHECK: omp.terminator !CHECK: } +!CHECK: omp.terminator +!CHECK: } !CHECK: return !CHECK: } subroutine common_2() diff --git a/flang/test/Lower/OpenMP/FIR/flush.f90 b/flang/test/Lower/OpenMP/FIR/flush.f90 index 2868367fbdba64176257b1623cbb539c69b2090a..2c281632b85cb0460bf43436858cbe7f174d4021 100644 --- a/flang/test/Lower/OpenMP/FIR/flush.f90 +++ b/flang/test/Lower/OpenMP/FIR/flush.f90 @@ -1,7 +1,7 @@ ! This test checks lowering of OpenMP Flush Directive. !RUN: %flang_fc1 -emit-fir -flang-deprecated-no-hlfir -fopenmp %s -o - | FileCheck %s --check-prefixes="FIRDialect,OMPDialect" -!RUN: %flang_fc1 -emit-fir -flang-deprecated-no-hlfir -fopenmp %s -o - | fir-opt --cfg-conversion-on-func-opt | fir-opt --fir-to-llvm-ir | FileCheck %s --check-prefixes="LLVMIRDialect,OMPDialect" +!RUN: %flang_fc1 -emit-fir -flang-deprecated-no-hlfir -fopenmp %s -o - | fir-opt --cfg-conversion | fir-opt --fir-to-llvm-ir | FileCheck %s --check-prefixes="LLVMIRDialect,OMPDialect" subroutine flush_standalone(a, b, c) integer, intent(inout) :: a, b, c diff --git a/flang/test/Lower/OpenMP/FIR/if-clause.f90 b/flang/test/Lower/OpenMP/FIR/if-clause.f90 index f686b9708fc54a9461be183f6c7dead0b745256b..683d9f7ef97267a470e7f730735de968885ffd70 100644 --- a/flang/test/Lower/OpenMP/FIR/if-clause.f90 +++ b/flang/test/Lower/OpenMP/FIR/if-clause.f90 @@ -1,7 +1,9 @@ ! This test checks lowering of OpenMP IF clauses. -! RUN: bbc -fopenmp -emit-fir %s -o - | FileCheck %s -! RUN: %flang_fc1 -fopenmp -emit-fir %s -o - | FileCheck %s +! The "if" clause was added to the "simd" directive in OpenMP 5.0, and +! to the "teams" directive in OpenMP 5.2. +! RUN: bbc -fopenmp -fopenmp-version=52 -emit-fir %s -o - | FileCheck %s +! RUN: %flang_fc1 -fopenmp -fopenmp-version=52 -emit-fir %s -o - | FileCheck %s program main integer :: i diff --git a/flang/test/Lower/OpenMP/FIR/lastprivate-commonblock.f90 b/flang/test/Lower/OpenMP/FIR/lastprivate-commonblock.f90 index 389bcba35f77f5e17296a75c9b8a68ad5684831b..86c4d917fa51eefd3b1b667f83395fe4e1a39368 100644 --- a/flang/test/Lower/OpenMP/FIR/lastprivate-commonblock.f90 +++ b/flang/test/Lower/OpenMP/FIR/lastprivate-commonblock.f90 @@ -17,7 +17,8 @@ !CHECK: %[[val_c1_i32:.*]] = arith.constant 1 : i32 !CHECK: %[[val_c100_i32:.*]] = arith.constant 100 : i32 !CHECK: %[[val_c1_i32_0:.*]] = arith.constant 1 : i32 -!CHECK: omp.wsloop for (%[[arg:.*]]) : i32 = (%[[val_c1_i32]]) to (%[[val_c100_i32]]) inclusive step (%[[val_c1_i32_0]]) { +!CHECK: omp.wsloop { +!CHECK-NEXT: omp.loop_nest (%[[arg:.*]]) : i32 = (%[[val_c1_i32]]) to (%[[val_c100_i32]]) inclusive step (%[[val_c1_i32_0]]) { !CHECK: fir.store %[[arg]] to %[[val_0]] : !fir.ref !CHECK: %[[val_11:.*]] = arith.addi %[[arg]], %[[val_c1_i32_0]] : i32 !CHECK: %[[val_c0_i32:.*]] = arith.constant 0 : i32 @@ -34,6 +35,8 @@ !CHECK: } !CHECK: omp.yield !CHECK: } +!CHECK: omp.terminator +!CHECK: } !CHECK: return !CHECK: } subroutine lastprivate_common diff --git a/flang/test/Lower/OpenMP/FIR/location.f90 b/flang/test/Lower/OpenMP/FIR/location.f90 index 648377837670329e860e3d58cb967e0a6ff6aa50..6a7fb3c035846eeb68ab4684df2d13d86ef52afd 100644 --- a/flang/test/Lower/OpenMP/FIR/location.f90 +++ b/flang/test/Lower/OpenMP/FIR/location.f90 @@ -28,11 +28,14 @@ end !CHECK-LABEL: sub_loop subroutine sub_loop() -!CHECK: omp.wsloop {{.*}} { +!CHECK: omp.wsloop { +!CHECK-NEXT: omp.loop_nest {{.*}} { !$omp do do i=1,10 print *, i !CHECK: omp.yield loc(#[[LOOP_LOC:.*]]) +!CHECK: } loc(#[[LOOP_LOC]]) +!CHECK: omp.terminator loc(#[[LOOP_LOC]]) !CHECK: } loc(#[[LOOP_LOC]]) end do !$omp end do @@ -60,9 +63,9 @@ end subroutine !CHECK: #[[PAR_LOC]] = loc("{{.*}}location.f90":9:9) !CHECK: #[[TAR_LOC]] = loc("{{.*}}location.f90":21:9) -!CHECK: #[[LOOP_LOC]] = loc("{{.*}}location.f90":32:9) -!CHECK: #[[BAR_LOC]] = loc("{{.*}}location.f90":44:9) -!CHECK: #[[TW_LOC]] = loc("{{.*}}location.f90":46:9) -!CHECK: #[[TY_LOC]] = loc("{{.*}}location.f90":48:9) -!CHECK: #[[IF_LOC]] = loc("{{.*}}location.f90":55:14) -!CHECK: #[[TASK_LOC]] = loc("{{.*}}location.f90":55:9) +!CHECK: #[[LOOP_LOC]] = loc("{{.*}}location.f90":33:9) +!CHECK: #[[BAR_LOC]] = loc("{{.*}}location.f90":47:9) +!CHECK: #[[TW_LOC]] = loc("{{.*}}location.f90":49:9) +!CHECK: #[[TY_LOC]] = loc("{{.*}}location.f90":51:9) +!CHECK: #[[IF_LOC]] = loc("{{.*}}location.f90":58:14) +!CHECK: #[[TASK_LOC]] = loc("{{.*}}location.f90":58:9) diff --git a/flang/test/Lower/OpenMP/FIR/master.f90 b/flang/test/Lower/OpenMP/FIR/master.f90 index 3bac582c7725a889ae053102e0f8ca29d39fc623..dd9910da2f419034749611f205e256e9b67db16e 100644 --- a/flang/test/Lower/OpenMP/FIR/master.f90 +++ b/flang/test/Lower/OpenMP/FIR/master.f90 @@ -1,5 +1,5 @@ !RUN: %flang_fc1 -emit-fir -flang-deprecated-no-hlfir -fopenmp %s -o - | FileCheck %s --check-prefixes="FIRDialect,OMPDialect" -!RUN: %flang_fc1 -emit-fir -flang-deprecated-no-hlfir -fopenmp %s -o - | fir-opt --cfg-conversion-on-func-opt | fir-opt --fir-to-llvm-ir | FileCheck %s --check-prefixes="OMPDialect" +!RUN: %flang_fc1 -emit-fir -flang-deprecated-no-hlfir -fopenmp %s -o - | fir-opt --cfg-conversion | fir-opt --fir-to-llvm-ir | FileCheck %s --check-prefixes="OMPDialect" !=============================================================================== ! parallel construct with function call which has master construct internally diff --git a/flang/test/Lower/OpenMP/FIR/parallel-lastprivate-clause-scalar.f90 b/flang/test/Lower/OpenMP/FIR/parallel-lastprivate-clause-scalar.f90 index 2060e2062c1a34db57223bfeb1bed46b748f8931..16832355f5d1bcc29510b44acd6f4f8a16acfaf7 100644 --- a/flang/test/Lower/OpenMP/FIR/parallel-lastprivate-clause-scalar.f90 +++ b/flang/test/Lower/OpenMP/FIR/parallel-lastprivate-clause-scalar.f90 @@ -12,8 +12,9 @@ !CHECK-DAG: %[[ARG1_PVT:.*]] = fir.alloca !fir.char<1,5> {bindc_name = "arg1", ! Check that we are accessing the clone inside the loop -!CHECK-DAG: omp.wsloop for (%[[INDX_WS:.*]]) : {{.*}} { -!CHECK-DAG: %[[UNIT:.*]] = arith.constant 6 : i32 +!CHECK: omp.wsloop { +!CHECK-NEXT: omp.loop_nest (%[[INDX_WS:.*]]) : {{.*}} { +!CHECK: %[[UNIT:.*]] = arith.constant 6 : i32 !CHECK-NEXT: %[[ADDR:.*]] = fir.address_of(@_QQclX !CHECK-NEXT: %[[CVT0:.*]] = fir.convert %[[ADDR]] !CHECK-NEXT: %[[CNST:.*]] = arith.constant @@ -36,9 +37,12 @@ ! Testing lastprivate val update !CHECK-DAG: %[[CVT:.*]] = fir.convert %[[ARG1_REF]] : (!fir.ref>) -> !fir.ref !CHECK-DAG: %[[CVT1:.*]] = fir.convert %[[ARG1_PVT]] : (!fir.ref>) -> !fir.ref -!CHECK-DAG: fir.call @llvm.memmove.p0.p0.i64(%[[CVT]], %[[CVT1]]{{.*}}) -!CHECK-DAG: } -!CHECK-DAG: omp.yield +!CHECK: fir.call @llvm.memmove.p0.p0.i64(%[[CVT]], %[[CVT1]]{{.*}}) +!CHECK: } +!CHECK: omp.yield +!CHECK: } +!CHECK: omp.terminator +!CHECK: } subroutine lastprivate_character(arg1) character(5) :: arg1 @@ -55,7 +59,8 @@ end subroutine !CHECK: func @_QPlastprivate_int(%[[ARG1:.*]]: !fir.ref {fir.bindc_name = "arg1"}) { !CHECK-DAG: omp.parallel { !CHECK-DAG: %[[CLONE:.*]] = fir.alloca i32 {bindc_name = "arg1" -!CHECK: omp.wsloop for (%[[INDX_WS:.*]]) : {{.*}} { +!CHECK: omp.wsloop { +!CHECK-NEXT: omp.loop_nest (%[[INDX_WS:.*]]) : {{.*}} { ! Testing last iteration check !CHECK: %[[V:.*]] = arith.addi %[[INDX_WS]], %{{.*}} : i32 @@ -70,8 +75,11 @@ end subroutine ! Testing lastprivate val update !CHECK-NEXT: %[[CLONE_LD:.*]] = fir.load %[[CLONE]] : !fir.ref !CHECK-NEXT: fir.store %[[CLONE_LD]] to %[[ARG1]] : !fir.ref -!CHECK-DAG: } -!CHECK-DAG: omp.yield +!CHECK: } +!CHECK: omp.yield +!CHECK: } +!CHECK: omp.terminator +!CHECK: } subroutine lastprivate_int(arg1) integer :: arg1 @@ -90,7 +98,8 @@ end subroutine !CHECK: omp.parallel { !CHECK-DAG: %[[CLONE1:.*]] = fir.alloca i32 {bindc_name = "arg1" !CHECK-DAG: %[[CLONE2:.*]] = fir.alloca i32 {bindc_name = "arg2" -!CHECK: omp.wsloop for (%[[INDX_WS:.*]]) : {{.*}} { +!CHECK: omp.wsloop { +!CHECK-NEXT: omp.loop_nest (%[[INDX_WS:.*]]) : {{.*}} { ! Testing last iteration check !CHECK: %[[V:.*]] = arith.addi %[[INDX_WS]], %{{.*}} : i32 @@ -108,6 +117,9 @@ end subroutine !CHECK-DAG: fir.store %[[CLONE_LD2]] to %[[ARG2]] : !fir.ref !CHECK: } !CHECK: omp.yield +!CHECK: } +!CHECK: omp.terminator +!CHECK: } subroutine mult_lastprivate_int(arg1, arg2) integer :: arg1, arg2 @@ -127,7 +139,8 @@ end subroutine !CHECK: omp.parallel { !CHECK-DAG: %[[CLONE1:.*]] = fir.alloca i32 {bindc_name = "arg1" !CHECK-DAG: %[[CLONE2:.*]] = fir.alloca i32 {bindc_name = "arg2" -!CHECK: omp.wsloop for (%[[INDX_WS:.*]]) : {{.*}} { +!CHECK: omp.wsloop { +!CHECK-NEXT: omp.loop_nest (%[[INDX_WS:.*]]) : {{.*}} { !Testing last iteration check !CHECK: %[[V:.*]] = arith.addi %[[INDX_WS]], %{{.*}} : i32 @@ -145,6 +158,9 @@ end subroutine !CHECK-DAG: fir.store %[[CLONE_LD1]] to %[[ARG1]] : !fir.ref !CHECK: } !CHECK: omp.yield +!CHECK: } +!CHECK: omp.terminator +!CHECK: } subroutine mult_lastprivate_int2(arg1, arg2) integer :: arg1, arg2 @@ -169,7 +185,8 @@ end subroutine ! Lastprivate Allocation !CHECK-DAG: %[[CLONE2:.*]] = fir.alloca i32 {bindc_name = "arg2" !CHECK-NOT: omp.barrier -!CHECK: omp.wsloop for (%[[INDX_WS:.*]]) : {{.*}} { +!CHECK: omp.wsloop { +!CHECK-NEXT: omp.loop_nest (%[[INDX_WS:.*]]) : {{.*}} { ! Testing last iteration check !CHECK: %[[V:.*]] = arith.addi %[[INDX_WS]], %{{.*}} : i32 @@ -185,6 +202,9 @@ end subroutine !CHECK-NEXT: fir.store %[[CLONE_LD]] to %[[ARG2]] : !fir.ref !CHECK-NEXT: } !CHECK-NEXT: omp.yield +!CHECK-NEXT: } +!CHECK-NEXT: omp.terminator +!CHECK-NEXT: } subroutine firstpriv_lastpriv_int(arg1, arg2) integer :: arg1, arg2 @@ -207,7 +227,8 @@ end subroutine !CHECK-NEXT: %[[FPV_LD:.*]] = fir.load %[[ARG1]] : !fir.ref !CHECK-NEXT: fir.store %[[FPV_LD]] to %[[CLONE1]] : !fir.ref !CHECK-NEXT: omp.barrier -!CHECK: omp.wsloop for (%[[INDX_WS:.*]]) : {{.*}} { +!CHECK: omp.wsloop { +!CHECK-NEXT: omp.loop_nest (%[[INDX_WS:.*]]) : {{.*}} { ! Testing last iteration check !CHECK: %[[V:.*]] = arith.addi %[[INDX_WS]], %{{.*}} : i32 !CHECK: %[[C0:.*]] = arith.constant 0 : i32 @@ -222,6 +243,9 @@ end subroutine !CHECK-NEXT: fir.store %[[CLONE_LD]] to %[[ARG1]] : !fir.ref !CHECK-NEXT: } !CHECK-NEXT: omp.yield +!CHECK-NEXT: } +!CHECK-NEXT: omp.terminator +!CHECK-NEXT: } subroutine firstpriv_lastpriv_int2(arg1) integer :: arg1 diff --git a/flang/test/Lower/OpenMP/FIR/parallel-private-clause-fixes.f90 b/flang/test/Lower/OpenMP/FIR/parallel-private-clause-fixes.f90 index c99bf761333b8150201cdeda28c2dd3f743957d4..fb0fb9594c350e21957b462382cc021899fc2f2e 100644 --- a/flang/test/Lower/OpenMP/FIR/parallel-private-clause-fixes.f90 +++ b/flang/test/Lower/OpenMP/FIR/parallel-private-clause-fixes.f90 @@ -13,30 +13,33 @@ ! CHECK: %[[ONE:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_3:.*]] = fir.load %[[VAL_4:.*]] : !fir.ref ! CHECK: %[[VAL_5:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop for (%[[VAL_6:.*]]) : i32 = (%[[ONE]]) to (%[[VAL_3]]) inclusive step (%[[VAL_5]]) { -! CHECK: fir.store %[[VAL_6]] to %[[PRIV_I]] : !fir.ref -! CHECK: %[[VAL_7:.*]] = arith.constant 1 : i32 -! CHECK: %[[VAL_8:.*]] = fir.convert %[[VAL_7]] : (i32) -> index -! CHECK: %[[VAL_9:.*]] = fir.load %[[VAL_4]] : !fir.ref -! CHECK: %[[VAL_10:.*]] = fir.convert %[[VAL_9]] : (i32) -> index -! CHECK: %[[VAL_11:.*]] = arith.constant 1 : index -! CHECK: %[[LB:.*]] = fir.convert %[[VAL_8]] : (index) -> i32 -! CHECK: %[[VAL_12:.*]]:2 = fir.do_loop %[[VAL_13:[^ ]*]] = -! CHECK-SAME: %[[VAL_8]] to %[[VAL_10]] step %[[VAL_11]] -! CHECK-SAME: iter_args(%[[IV:.*]] = %[[LB]]) -> (index, i32) { -! CHECK: fir.store %[[IV]] to %[[PRIV_J]] : !fir.ref -! CHECK: %[[LOAD:.*]] = fir.load %[[PRIV_I]] : !fir.ref -! CHECK: %[[VAL_15:.*]] = fir.load %[[PRIV_J]] : !fir.ref -! CHECK: %[[VAL_16:.*]] = arith.addi %[[LOAD]], %[[VAL_15]] : i32 -! CHECK: fir.store %[[VAL_16]] to %[[PRIV_X]] : !fir.ref -! CHECK: %[[VAL_17:.*]] = arith.addi %[[VAL_13]], %[[VAL_11]] : index -! CHECK: %[[STEPCAST:.*]] = fir.convert %[[VAL_11]] : (index) -> i32 -! CHECK: %[[IVLOAD:.*]] = fir.load %[[PRIV_J]] : !fir.ref -! CHECK: %[[IVINC:.*]] = arith.addi %[[IVLOAD]], %[[STEPCAST]] -! CHECK: fir.result %[[VAL_17]], %[[IVINC]] : index, i32 +! CHECK: omp.wsloop { +! CHECK-NEXT: omp.loop_nest (%[[VAL_6:.*]]) : i32 = (%[[ONE]]) to (%[[VAL_3]]) inclusive step (%[[VAL_5]]) { +! CHECK: fir.store %[[VAL_6]] to %[[PRIV_I]] : !fir.ref +! CHECK: %[[VAL_7:.*]] = arith.constant 1 : i32 +! CHECK: %[[VAL_8:.*]] = fir.convert %[[VAL_7]] : (i32) -> index +! CHECK: %[[VAL_9:.*]] = fir.load %[[VAL_4]] : !fir.ref +! CHECK: %[[VAL_10:.*]] = fir.convert %[[VAL_9]] : (i32) -> index +! CHECK: %[[VAL_11:.*]] = arith.constant 1 : index +! CHECK: %[[LB:.*]] = fir.convert %[[VAL_8]] : (index) -> i32 +! CHECK: %[[VAL_12:.*]]:2 = fir.do_loop %[[VAL_13:[^ ]*]] = +! CHECK-SAME: %[[VAL_8]] to %[[VAL_10]] step %[[VAL_11]] +! CHECK-SAME: iter_args(%[[IV:.*]] = %[[LB]]) -> (index, i32) { +! CHECK: fir.store %[[IV]] to %[[PRIV_J]] : !fir.ref +! CHECK: %[[LOAD:.*]] = fir.load %[[PRIV_I]] : !fir.ref +! CHECK: %[[VAL_15:.*]] = fir.load %[[PRIV_J]] : !fir.ref +! CHECK: %[[VAL_16:.*]] = arith.addi %[[LOAD]], %[[VAL_15]] : i32 +! CHECK: fir.store %[[VAL_16]] to %[[PRIV_X]] : !fir.ref +! CHECK: %[[VAL_17:.*]] = arith.addi %[[VAL_13]], %[[VAL_11]] : index +! CHECK: %[[STEPCAST:.*]] = fir.convert %[[VAL_11]] : (index) -> i32 +! CHECK: %[[IVLOAD:.*]] = fir.load %[[PRIV_J]] : !fir.ref +! CHECK: %[[IVINC:.*]] = arith.addi %[[IVLOAD]], %[[STEPCAST]] +! CHECK: fir.result %[[VAL_17]], %[[IVINC]] : index, i32 +! CHECK: } +! CHECK: fir.store %[[VAL_12]]#1 to %[[PRIV_J]] : !fir.ref +! CHECK: omp.yield ! CHECK: } -! CHECK: fir.store %[[VAL_12]]#1 to %[[PRIV_J]] : !fir.ref -! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } diff --git a/flang/test/Lower/OpenMP/FIR/parallel-private-clause.f90 b/flang/test/Lower/OpenMP/FIR/parallel-private-clause.f90 index 8b75ecbaae8c73c9741dad7b9e465df452dfb371..2e68d25a15edc118a3ad5b6c96f7240735188019 100644 --- a/flang/test/Lower/OpenMP/FIR/parallel-private-clause.f90 +++ b/flang/test/Lower/OpenMP/FIR/parallel-private-clause.f90 @@ -249,31 +249,33 @@ subroutine simple_loop_1 real, allocatable :: r; ! FIRDialect: omp.parallel !$OMP PARALLEL PRIVATE(r) - ! FIRDialect: %[[ALLOCA_IV:.*]] = fir.alloca i32 {{{.*}}, pinned} + ! FIRDialect: %[[ALLOCA_IV:.*]] = fir.alloca i32 {{{.*}}, pinned} - ! FIRDialect: [[R:%.*]] = fir.alloca !fir.box> {bindc_name = "r", pinned, uniq_name = "{{.*}}Er"} - ! FIRDialect: fir.store {{%.*}} to [[R]] : !fir.ref>> - ! FIRDialect: fir.store {{%.*}} to [[R]] : !fir.ref>> + ! FIRDialect: [[R:%.*]] = fir.alloca !fir.box> {bindc_name = "r", pinned, uniq_name = "{{.*}}Er"} + ! FIRDialect: fir.store {{%.*}} to [[R]] : !fir.ref>> + ! FIRDialect: fir.store {{%.*}} to [[R]] : !fir.ref>> - ! FIRDialect: %[[WS_LB:.*]] = arith.constant 1 : i32 - ! FIRDialect: %[[WS_UB:.*]] = arith.constant 9 : i32 - ! FIRDialect: %[[WS_STEP:.*]] = arith.constant 1 : i32 + ! FIRDialect: %[[WS_LB:.*]] = arith.constant 1 : i32 + ! FIRDialect: %[[WS_UB:.*]] = arith.constant 9 : i32 + ! FIRDialect: %[[WS_STEP:.*]] = arith.constant 1 : i32 - ! FIRDialect: omp.wsloop for (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) + ! FIRDialect: omp.wsloop { + ! FIRDialect-NEXT: omp.loop_nest (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) { !$OMP DO do i=1, 9 - ! FIRDialect: fir.store %[[I]] to %[[ALLOCA_IV:.*]] : !fir.ref - ! FIRDialect: %[[LOAD_IV:.*]] = fir.load %[[ALLOCA_IV]] : !fir.ref - ! FIRDialect: fir.call @_FortranAioOutputInteger32({{.*}}, %[[LOAD_IV]]) {{.*}}: (!fir.ref, i32) -> i1 + ! FIRDialect: fir.store %[[I]] to %[[ALLOCA_IV:.*]] : !fir.ref + ! FIRDialect: %[[LOAD_IV:.*]] = fir.load %[[ALLOCA_IV]] : !fir.ref + ! FIRDialect: fir.call @_FortranAioOutputInteger32({{.*}}, %[[LOAD_IV]]) {{.*}}: (!fir.ref, i32) -> i1 print*, i end do - ! FIRDialect: omp.yield - ! FIRDialect: {{%.*}} = fir.load [[R]] : !fir.ref>> - ! FIRDialect: fir.if {{%.*}} { - ! FIRDialect: [[LD:%.*]] = fir.load [[R]] : !fir.ref>> - ! FIRDialect: [[AD:%.*]] = fir.box_addr [[LD]] : (!fir.box>) -> !fir.heap - ! FIRDialect: fir.freemem [[AD]] : !fir.heap - ! FIRDialect: fir.store {{%.*}} to [[R]] : !fir.ref>> + ! FIRDialect: omp.yield + ! FIRDialect: omp.terminator + ! FIRDialect: {{%.*}} = fir.load [[R]] : !fir.ref>> + ! FIRDialect: fir.if {{%.*}} { + ! FIRDialect: [[LD:%.*]] = fir.load [[R]] : !fir.ref>> + ! FIRDialect: [[AD:%.*]] = fir.box_addr [[LD]] : (!fir.box>) -> !fir.heap + ! FIRDialect: fir.freemem [[AD]] : !fir.heap + ! FIRDialect: fir.store {{%.*}} to [[R]] : !fir.ref>> !$OMP END DO ! FIRDialect: omp.terminator !$OMP END PARALLEL @@ -285,31 +287,33 @@ subroutine simple_loop_2 real, allocatable :: r; ! FIRDialect: omp.parallel !$OMP PARALLEL - ! FIRDialect: %[[ALLOCA_IV:.*]] = fir.alloca i32 {{{.*}}, pinned} + ! FIRDialect: %[[ALLOCA_IV:.*]] = fir.alloca i32 {{{.*}}, pinned} - ! FIRDialect: [[R:%.*]] = fir.alloca !fir.box> {bindc_name = "r", pinned, uniq_name = "{{.*}}Er"} - ! FIRDialect: fir.store {{%.*}} to [[R]] : !fir.ref>> - ! FIRDialect: fir.store {{%.*}} to [[R]] : !fir.ref>> + ! FIRDialect: [[R:%.*]] = fir.alloca !fir.box> {bindc_name = "r", pinned, uniq_name = "{{.*}}Er"} + ! FIRDialect: fir.store {{%.*}} to [[R]] : !fir.ref>> + ! FIRDialect: fir.store {{%.*}} to [[R]] : !fir.ref>> - ! FIRDialect: %[[WS_LB:.*]] = arith.constant 1 : i32 - ! FIRDialect: %[[WS_UB:.*]] = arith.constant 9 : i32 - ! FIRDialect: %[[WS_STEP:.*]] = arith.constant 1 : i32 + ! FIRDialect: %[[WS_LB:.*]] = arith.constant 1 : i32 + ! FIRDialect: %[[WS_UB:.*]] = arith.constant 9 : i32 + ! FIRDialect: %[[WS_STEP:.*]] = arith.constant 1 : i32 - ! FIRDialect: omp.wsloop for (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) + ! FIRDialect: omp.wsloop { + ! FIRDialect-NEXT: omp.loop_nest (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) { !$OMP DO PRIVATE(r) do i=1, 9 - ! FIRDialect: fir.store %[[I]] to %[[ALLOCA_IV:.*]] : !fir.ref - ! FIRDialect: %[[LOAD_IV:.*]] = fir.load %[[ALLOCA_IV]] : !fir.ref - ! FIRDialect: fir.call @_FortranAioOutputInteger32({{.*}}, %[[LOAD_IV]]) {{.*}}: (!fir.ref, i32) -> i1 + ! FIRDialect: fir.store %[[I]] to %[[ALLOCA_IV:.*]] : !fir.ref + ! FIRDialect: %[[LOAD_IV:.*]] = fir.load %[[ALLOCA_IV]] : !fir.ref + ! FIRDialect: fir.call @_FortranAioOutputInteger32({{.*}}, %[[LOAD_IV]]) {{.*}}: (!fir.ref, i32) -> i1 print*, i end do - ! FIRDialect: omp.yield - ! FIRDialect: {{%.*}} = fir.load [[R]] : !fir.ref>> - ! FIRDialect: fir.if {{%.*}} { - ! FIRDialect: [[LD:%.*]] = fir.load [[R]] : !fir.ref>> - ! FIRDialect: [[AD:%.*]] = fir.box_addr [[LD]] : (!fir.box>) -> !fir.heap - ! FIRDialect: fir.freemem [[AD]] : !fir.heap - ! FIRDialect: fir.store {{%.*}} to [[R]] : !fir.ref>> + ! FIRDialect: omp.yield + ! FIRDialect: omp.terminator + ! FIRDialect: {{%.*}} = fir.load [[R]] : !fir.ref>> + ! FIRDialect: fir.if {{%.*}} { + ! FIRDialect: [[LD:%.*]] = fir.load [[R]] : !fir.ref>> + ! FIRDialect: [[AD:%.*]] = fir.box_addr [[LD]] : (!fir.box>) -> !fir.heap + ! FIRDialect: fir.freemem [[AD]] : !fir.heap + ! FIRDialect: fir.store {{%.*}} to [[R]] : !fir.ref>> !$OMP END DO ! FIRDialect: omp.terminator !$OMP END PARALLEL @@ -320,31 +324,33 @@ subroutine simple_loop_3 integer :: i real, allocatable :: r; ! FIRDialect: omp.parallel - ! FIRDialect: %[[ALLOCA_IV:.*]] = fir.alloca i32 {{{.*}}, pinned} + ! FIRDialect: %[[ALLOCA_IV:.*]] = fir.alloca i32 {{{.*}}, pinned} - ! FIRDialect: [[R:%.*]] = fir.alloca !fir.box> {bindc_name = "r", pinned, uniq_name = "{{.*}}Er"} - ! FIRDialect: fir.store {{%.*}} to [[R]] : !fir.ref>> - ! FIRDialect: fir.store {{%.*}} to [[R]] : !fir.ref>> + ! FIRDialect: [[R:%.*]] = fir.alloca !fir.box> {bindc_name = "r", pinned, uniq_name = "{{.*}}Er"} + ! FIRDialect: fir.store {{%.*}} to [[R]] : !fir.ref>> + ! FIRDialect: fir.store {{%.*}} to [[R]] : !fir.ref>> - ! FIRDialect: %[[WS_LB:.*]] = arith.constant 1 : i32 - ! FIRDialect: %[[WS_UB:.*]] = arith.constant 9 : i32 - ! FIRDialect: %[[WS_STEP:.*]] = arith.constant 1 : i32 + ! FIRDialect: %[[WS_LB:.*]] = arith.constant 1 : i32 + ! FIRDialect: %[[WS_UB:.*]] = arith.constant 9 : i32 + ! FIRDialect: %[[WS_STEP:.*]] = arith.constant 1 : i32 - ! FIRDialect: omp.wsloop for (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) + ! FIRDialect: omp.wsloop { + ! FIRDialect-NEXT: omp.loop_nest (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) { !$OMP PARALLEL DO PRIVATE(r) do i=1, 9 - ! FIRDialect: fir.store %[[I]] to %[[ALLOCA_IV:.*]] : !fir.ref - ! FIRDialect: %[[LOAD_IV:.*]] = fir.load %[[ALLOCA_IV]] : !fir.ref - ! FIRDialect: fir.call @_FortranAioOutputInteger32({{.*}}, %[[LOAD_IV]]) {{.*}}: (!fir.ref, i32) -> i1 + ! FIRDialect: fir.store %[[I]] to %[[ALLOCA_IV:.*]] : !fir.ref + ! FIRDialect: %[[LOAD_IV:.*]] = fir.load %[[ALLOCA_IV]] : !fir.ref + ! FIRDialect: fir.call @_FortranAioOutputInteger32({{.*}}, %[[LOAD_IV]]) {{.*}}: (!fir.ref, i32) -> i1 print*, i end do - ! FIRDialect: omp.yield - ! FIRDialect: {{%.*}} = fir.load [[R]] : !fir.ref>> - ! FIRDialect: fir.if {{%.*}} { - ! FIRDialect: [[LD:%.*]] = fir.load [[R]] : !fir.ref>> - ! FIRDialect: [[AD:%.*]] = fir.box_addr [[LD]] : (!fir.box>) -> !fir.heap - ! FIRDialect: fir.freemem [[AD]] : !fir.heap - ! FIRDialect: fir.store {{%.*}} to [[R]] : !fir.ref>> + ! FIRDialect: omp.yield + ! FIRDialect: omp.terminator + ! FIRDialect: {{%.*}} = fir.load [[R]] : !fir.ref>> + ! FIRDialect: fir.if {{%.*}} { + ! FIRDialect: [[LD:%.*]] = fir.load [[R]] : !fir.ref>> + ! FIRDialect: [[AD:%.*]] = fir.box_addr [[LD]] : (!fir.box>) -> !fir.heap + ! FIRDialect: fir.freemem [[AD]] : !fir.heap + ! FIRDialect: fir.store {{%.*}} to [[R]] : !fir.ref>> !$OMP END PARALLEL DO ! FIRDialect: omp.terminator end subroutine diff --git a/flang/test/Lower/OpenMP/FIR/parallel-sections.f90 b/flang/test/Lower/OpenMP/FIR/parallel-sections.f90 index 0c0834cfafe9c3d8123f195f2064e7e57b7ea422..7730ab87a719af248a8bf2da56b2dba8cd45dbb3 100644 --- a/flang/test/Lower/OpenMP/FIR/parallel-sections.f90 +++ b/flang/test/Lower/OpenMP/FIR/parallel-sections.f90 @@ -1,7 +1,7 @@ ! REQUIRES: openmp_runtime !RUN: %flang_fc1 -emit-fir -flang-deprecated-no-hlfir -fopenmp %s -o - | FileCheck %s --check-prefixes="FIRDialect,OMPDialect" -!RUN: %flang_fc1 -emit-fir -flang-deprecated-no-hlfir -fopenmp %s -o - | fir-opt --cfg-conversion-on-func-opt | fir-opt --fir-to-llvm-ir | FileCheck %s --check-prefixes="OMPDialect,LLVMDialect" +!RUN: %flang_fc1 -emit-fir -flang-deprecated-no-hlfir -fopenmp %s -o - | fir-opt --cfg-conversion | fir-opt --fir-to-llvm-ir | FileCheck %s --check-prefixes="OMPDialect,LLVMDialect" !=============================================================================== ! Parallel sections construct diff --git a/flang/test/Lower/OpenMP/FIR/parallel-wsloop-firstpriv.f90 b/flang/test/Lower/OpenMP/FIR/parallel-wsloop-firstpriv.f90 index 6eb39a2f63725f343ae5a31b89c8c7d847564977..490f6d0cf7bcabc5ca649790fc7ce0cca65b29ef 100644 --- a/flang/test/Lower/OpenMP/FIR/parallel-wsloop-firstpriv.f90 +++ b/flang/test/Lower/OpenMP/FIR/parallel-wsloop-firstpriv.f90 @@ -17,10 +17,14 @@ subroutine omp_do_firstprivate(a) ! CHECK: %[[LB:.*]] = arith.constant 1 : i32 ! CHECK-NEXT: %[[UB:.*]] = fir.load %[[CLONE]] : !fir.ref ! CHECK-NEXT: %[[STEP:.*]] = arith.constant 1 : i32 - ! CHECK-NEXT: omp.wsloop for (%[[ARG1:.*]]) : i32 = (%[[LB]]) to (%[[UB]]) inclusive step (%[[STEP]]) + ! CHECK-NEXT: omp.wsloop { + ! CHECK-NEXT: omp.loop_nest (%[[ARG1:.*]]) : i32 = (%[[LB]]) to (%[[UB]]) inclusive step (%[[STEP]]) { ! CHECK-NEXT: fir.store %[[ARG1]] to %[[REF]] : !fir.ref ! CHECK-NEXT: fir.call @_QPfoo(%[[REF]], %[[CLONE]]) {{.*}}: (!fir.ref, !fir.ref) -> () ! CHECK-NEXT: omp.yield + ! CHECK-NEXT: } + ! CHECK-NEXT: omp.terminator + ! CHECK-NEXT: } do i=1, a call foo(i, a) end do @@ -48,10 +52,14 @@ subroutine omp_do_firstprivate2(a, n) ! CHECK: %[[LB:.*]] = fir.load %[[CLONE]] : !fir.ref ! CHECK-NEXT: %[[UB:.*]] = fir.load %[[CLONE1]] : !fir.ref ! CHECK-NEXT: %[[STEP:.*]] = arith.constant 1 : i32 - ! CHECK-NEXT: omp.wsloop for (%[[ARG2:.*]]) : i32 = (%[[LB]]) to (%[[UB]]) inclusive step (%[[STEP]]) + ! CHECK-NEXT: omp.wsloop { + ! CHECK-NEXT: omp.loop_nest (%[[ARG2:.*]]) : i32 = (%[[LB]]) to (%[[UB]]) inclusive step (%[[STEP]]) { ! CHECK-NEXT: fir.store %[[ARG2]] to %[[REF]] : !fir.ref ! CHECK-NEXT: fir.call @_QPfoo(%[[REF]], %[[CLONE]]) {{.*}}: (!fir.ref, !fir.ref) -> () ! CHECK-NEXT: omp.yield + ! CHECK-NEXT: } + ! CHECK-NEXT: omp.terminator + ! CHECK-NEXT: } do i= a, n call foo(i, a) end do diff --git a/flang/test/Lower/OpenMP/FIR/parallel-wsloop.f90 b/flang/test/Lower/OpenMP/FIR/parallel-wsloop.f90 index 8649cf284ffd9d070540b7852ec41476e0f72ddc..630d647bc64b60ff070da462e61c10079a81fc79 100644 --- a/flang/test/Lower/OpenMP/FIR/parallel-wsloop.f90 +++ b/flang/test/Lower/OpenMP/FIR/parallel-wsloop.f90 @@ -6,19 +6,21 @@ subroutine simple_parallel_do integer :: i ! CHECK: omp.parallel - ! CHECK: %[[WS_LB:.*]] = arith.constant 1 : i32 - ! CHECK: %[[WS_UB:.*]] = arith.constant 9 : i32 - ! CHECK: %[[WS_STEP:.*]] = arith.constant 1 : i32 - ! CHECK: omp.wsloop for (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) + ! CHECK: %[[WS_LB:.*]] = arith.constant 1 : i32 + ! CHECK: %[[WS_UB:.*]] = arith.constant 9 : i32 + ! CHECK: %[[WS_STEP:.*]] = arith.constant 1 : i32 + ! CHECK: omp.wsloop { + ! CHECK-NEXT: omp.loop_nest (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) { !$OMP PARALLEL DO do i=1, 9 - ! CHECK: fir.store %[[I]] to %[[IV_ADDR:.*]] : !fir.ref - ! CHECK: %[[LOAD_IV:.*]] = fir.load %[[IV_ADDR]] : !fir.ref - ! CHECK: fir.call @_FortranAioOutputInteger32({{.*}}, %[[LOAD_IV]]) {{.*}}: (!fir.ref, i32) -> i1 + ! CHECK: fir.store %[[I]] to %[[IV_ADDR:.*]] : !fir.ref + ! CHECK: %[[LOAD_IV:.*]] = fir.load %[[IV_ADDR]] : !fir.ref + ! CHECK: fir.call @_FortranAioOutputInteger32({{.*}}, %[[LOAD_IV]]) {{.*}}: (!fir.ref, i32) -> i1 print*, i end do - ! CHECK: omp.yield - ! CHECK: omp.terminator + ! CHECK: omp.yield + ! CHECK: omp.terminator + ! CHECK: omp.terminator !$OMP END PARALLEL DO end subroutine @@ -32,19 +34,21 @@ subroutine parallel_do_with_parallel_clauses(cond, nt) ! CHECK: %[[COND_CVT:.*]] = fir.convert %[[COND]] : (!fir.logical<4>) -> i1 ! CHECK: %[[NT:.*]] = fir.load %[[NT_REF]] : !fir.ref ! CHECK: omp.parallel if(%[[COND_CVT]] : i1) num_threads(%[[NT]] : i32) proc_bind(close) - ! CHECK: %[[WS_LB:.*]] = arith.constant 1 : i32 - ! CHECK: %[[WS_UB:.*]] = arith.constant 9 : i32 - ! CHECK: %[[WS_STEP:.*]] = arith.constant 1 : i32 - ! CHECK: omp.wsloop for (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) + ! CHECK: %[[WS_LB:.*]] = arith.constant 1 : i32 + ! CHECK: %[[WS_UB:.*]] = arith.constant 9 : i32 + ! CHECK: %[[WS_STEP:.*]] = arith.constant 1 : i32 + ! CHECK: omp.wsloop { + ! CHECK-NEXT: omp.loop_nest (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) { !$OMP PARALLEL DO IF(cond) NUM_THREADS(nt) PROC_BIND(close) do i=1, 9 - ! CHECK: fir.store %[[I]] to %[[IV_ADDR:.*]] : !fir.ref - ! CHECK: %[[LOAD_IV:.*]] = fir.load %[[IV_ADDR]] : !fir.ref - ! CHECK: fir.call @_FortranAioOutputInteger32({{.*}}, %[[LOAD_IV]]) {{.*}}: (!fir.ref, i32) -> i1 + ! CHECK: fir.store %[[I]] to %[[IV_ADDR:.*]] : !fir.ref + ! CHECK: %[[LOAD_IV:.*]] = fir.load %[[IV_ADDR]] : !fir.ref + ! CHECK: fir.call @_FortranAioOutputInteger32({{.*}}, %[[LOAD_IV]]) {{.*}}: (!fir.ref, i32) -> i1 print*, i end do - ! CHECK: omp.yield - ! CHECK: omp.terminator + ! CHECK: omp.yield + ! CHECK: omp.terminator + ! CHECK: omp.terminator !$OMP END PARALLEL DO end subroutine @@ -55,19 +59,21 @@ subroutine parallel_do_with_clauses(nt) integer :: i ! CHECK: %[[NT:.*]] = fir.load %[[NT_REF]] : !fir.ref ! CHECK: omp.parallel num_threads(%[[NT]] : i32) - ! CHECK: %[[WS_LB:.*]] = arith.constant 1 : i32 - ! CHECK: %[[WS_UB:.*]] = arith.constant 9 : i32 - ! CHECK: %[[WS_STEP:.*]] = arith.constant 1 : i32 - ! CHECK: omp.wsloop schedule(dynamic) for (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) + ! CHECK: %[[WS_LB:.*]] = arith.constant 1 : i32 + ! CHECK: %[[WS_UB:.*]] = arith.constant 9 : i32 + ! CHECK: %[[WS_STEP:.*]] = arith.constant 1 : i32 + ! CHECK: omp.wsloop schedule(dynamic) { + ! CHECK-NEXT: omp.loop_nest (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) !$OMP PARALLEL DO NUM_THREADS(nt) SCHEDULE(dynamic) do i=1, 9 - ! CHECK: fir.store %[[I]] to %[[IV_ADDR:.*]] : !fir.ref - ! CHECK: %[[LOAD_IV:.*]] = fir.load %[[IV_ADDR]] : !fir.ref - ! CHECK: fir.call @_FortranAioOutputInteger32({{.*}}, %[[LOAD_IV]]) {{.*}}: (!fir.ref, i32) -> i1 + ! CHECK: fir.store %[[I]] to %[[IV_ADDR:.*]] : !fir.ref + ! CHECK: %[[LOAD_IV:.*]] = fir.load %[[IV_ADDR]] : !fir.ref + ! CHECK: fir.call @_FortranAioOutputInteger32({{.*}}, %[[LOAD_IV]]) {{.*}}: (!fir.ref, i32) -> i1 print*, i end do - ! CHECK: omp.yield - ! CHECK: omp.terminator + ! CHECK: omp.yield + ! CHECK: omp.terminator + ! CHECK: omp.terminator !$OMP END PARALLEL DO end subroutine @@ -83,18 +89,19 @@ subroutine parallel_do_with_privatisation_clauses(cond,nt) integer :: nt integer :: i ! CHECK: omp.parallel - ! CHECK: %[[PRIVATE_COND_REF:.*]] = fir.alloca !fir.logical<4> {bindc_name = "cond", pinned, uniq_name = "_QFparallel_do_with_privatisation_clausesEcond"} - ! CHECK: %[[PRIVATE_NT_REF:.*]] = fir.alloca i32 {bindc_name = "nt", pinned, uniq_name = "_QFparallel_do_with_privatisation_clausesEnt"} - ! CHECK: %[[NT_VAL:.*]] = fir.load %[[NT_REF]] : !fir.ref - ! CHECK: fir.store %[[NT_VAL]] to %[[PRIVATE_NT_REF]] : !fir.ref - ! CHECK: %[[WS_LB:.*]] = arith.constant 1 : i32 - ! CHECK: %[[WS_UB:.*]] = arith.constant 9 : i32 - ! CHECK: %[[WS_STEP:.*]] = arith.constant 1 : i32 - ! CHECK: omp.wsloop for (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) + ! CHECK: %[[PRIVATE_COND_REF:.*]] = fir.alloca !fir.logical<4> {bindc_name = "cond", pinned, uniq_name = "_QFparallel_do_with_privatisation_clausesEcond"} + ! CHECK: %[[PRIVATE_NT_REF:.*]] = fir.alloca i32 {bindc_name = "nt", pinned, uniq_name = "_QFparallel_do_with_privatisation_clausesEnt"} + ! CHECK: %[[NT_VAL:.*]] = fir.load %[[NT_REF]] : !fir.ref + ! CHECK: fir.store %[[NT_VAL]] to %[[PRIVATE_NT_REF]] : !fir.ref + ! CHECK: %[[WS_LB:.*]] = arith.constant 1 : i32 + ! CHECK: %[[WS_UB:.*]] = arith.constant 9 : i32 + ! CHECK: %[[WS_STEP:.*]] = arith.constant 1 : i32 + ! CHECK: omp.wsloop { + ! CHECK-NEXT: omp.loop_nest (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) { !$OMP PARALLEL DO PRIVATE(cond) FIRSTPRIVATE(nt) do i=1, 9 - ! CHECK: fir.store %[[I]] to %[[IV_ADDR:.*]] : !fir.ref - ! CHECK: %[[LOAD_IV:.*]] = fir.load %[[IV_ADDR]] : !fir.ref + ! CHECK: fir.store %[[I]] to %[[IV_ADDR:.*]] : !fir.ref + ! CHECK: %[[LOAD_IV:.*]] = fir.load %[[IV_ADDR]] : !fir.ref ! CHECK: fir.call @_FortranAioOutputInteger32({{.*}}, %[[LOAD_IV]]) {{.*}}: (!fir.ref, i32) -> i1 ! CHECK: %[[PRIVATE_COND_VAL:.*]] = fir.load %[[PRIVATE_COND_REF]] : !fir.ref> ! CHECK: %[[PRIVATE_COND_VAL_CVT:.*]] = fir.convert %[[PRIVATE_COND_VAL]] : (!fir.logical<4>) -> i1 @@ -104,7 +111,8 @@ subroutine parallel_do_with_privatisation_clauses(cond,nt) print*, i, cond, nt end do ! CHECK: omp.yield - ! CHECK: omp.terminator + ! CHECK: omp.terminator + ! CHECK: omp.terminator !$OMP END PARALLEL DO end subroutine @@ -140,10 +148,13 @@ end subroutine parallel_private_do ! CHECK: %[[VAL_7:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_8:.*]] = arith.constant 9 : i32 ! CHECK: %[[VAL_9:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop for (%[[I:.*]]) : i32 = (%[[VAL_7]]) to (%[[VAL_8]]) inclusive step (%[[VAL_9]]) { -! CHECK: fir.store %[[I]] to %[[I_PRIV]] : !fir.ref -! CHECK: fir.call @_QPfoo(%[[I_PRIV]], %[[COND_ADDR]], %[[NT_ADDR]]) {{.*}}: (!fir.ref, !fir.ref>, !fir.ref) -> () -! CHECK: omp.yield +! CHECK: omp.wsloop { +! CHECK-NEXT: omp.loop_nest (%[[I:.*]]) : i32 = (%[[VAL_7]]) to (%[[VAL_8]]) inclusive step (%[[VAL_9]]) { +! CHECK: fir.store %[[I]] to %[[I_PRIV]] : !fir.ref +! CHECK: fir.call @_QPfoo(%[[I_PRIV]], %[[COND_ADDR]], %[[NT_ADDR]]) {{.*}}: (!fir.ref, !fir.ref>, !fir.ref) -> () +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } @@ -182,10 +193,13 @@ end subroutine omp_parallel_multiple_firstprivate_do ! CHECK: %[[VAL_8:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_9:.*]] = arith.constant 10 : i32 ! CHECK: %[[VAL_10:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop for (%[[I:.*]]) : i32 = (%[[VAL_8]]) to (%[[VAL_9]]) inclusive step (%[[VAL_10]]) { -! CHECK: fir.store %[[I]] to %[[I_PRIV_ADDR]] : !fir.ref -! CHECK: fir.call @_QPbar(%[[I_PRIV_ADDR]], %[[A_PRIV_ADDR]]) {{.*}}: (!fir.ref, !fir.ref) -> () -! CHECK: omp.yield +! CHECK: omp.wsloop { +! CHECK-NEXT: omp.loop_nest (%[[I:.*]]) : i32 = (%[[VAL_8]]) to (%[[VAL_9]]) inclusive step (%[[VAL_10]]) { +! CHECK: fir.store %[[I]] to %[[I_PRIV_ADDR]] : !fir.ref +! CHECK: fir.call @_QPbar(%[[I_PRIV_ADDR]], %[[A_PRIV_ADDR]]) {{.*}}: (!fir.ref, !fir.ref) -> () +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } @@ -224,10 +238,13 @@ end subroutine parallel_do_private ! CHECK: %[[VAL_7:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_8:.*]] = arith.constant 9 : i32 ! CHECK: %[[VAL_9:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop for (%[[I:.*]]) : i32 = (%[[VAL_7]]) to (%[[VAL_8]]) inclusive step (%[[VAL_9]]) { -! CHECK: fir.store %[[I]] to %[[I_PRIV_ADDR]] : !fir.ref -! CHECK: fir.call @_QPfoo(%[[I_PRIV_ADDR]], %[[COND_ADDR]], %[[NT_ADDR]]) {{.*}}: (!fir.ref, !fir.ref>, !fir.ref) -> () -! CHECK: omp.yield +! CHECK: omp.wsloop { +! CHECK-NEXT: omp.loop_nest (%[[I:.*]]) : i32 = (%[[VAL_7]]) to (%[[VAL_8]]) inclusive step (%[[VAL_9]]) { +! CHECK: fir.store %[[I]] to %[[I_PRIV_ADDR]] : !fir.ref +! CHECK: fir.call @_QPfoo(%[[I_PRIV_ADDR]], %[[COND_ADDR]], %[[NT_ADDR]]) {{.*}}: (!fir.ref, !fir.ref>, !fir.ref) -> () +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } @@ -266,10 +283,13 @@ end subroutine omp_parallel_do_multiple_firstprivate ! CHECK: %[[VAL_8:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_9:.*]] = arith.constant 10 : i32 ! CHECK: %[[VAL_10:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop for (%[[I:.*]]) : i32 = (%[[VAL_8]]) to (%[[VAL_9]]) inclusive step (%[[VAL_10]]) { -! CHECK: fir.store %[[I]] to %[[I_PRIV_ADDR]] : !fir.ref -! CHECK: fir.call @_QPbar(%[[I_PRIV_ADDR]], %[[A_PRIV_ADDR]]) {{.*}}: (!fir.ref, !fir.ref) -> () -! CHECK: omp.yield +! CHECK: omp.wsloop { +! CHECK-NEXT: omp.loop_nest (%[[I:.*]]) : i32 = (%[[VAL_8]]) to (%[[VAL_9]]) inclusive step (%[[VAL_10]]) { +! CHECK: fir.store %[[I]] to %[[I_PRIV_ADDR]] : !fir.ref +! CHECK: fir.call @_QPbar(%[[I_PRIV_ADDR]], %[[A_PRIV_ADDR]]) {{.*}}: (!fir.ref, !fir.ref) -> () +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } diff --git a/flang/test/Lower/OpenMP/FIR/simd.f90 b/flang/test/Lower/OpenMP/FIR/simd.f90 index db7d30295c45d9fdffa5b32a9b4c05ae9a57d107..91e8750578bfb444fecf35ce10217d47a8a9af84 100644 --- a/flang/test/Lower/OpenMP/FIR/simd.f90 +++ b/flang/test/Lower/OpenMP/FIR/simd.f90 @@ -1,6 +1,7 @@ ! Tests for 2.9.3.1 Simd -! RUN: bbc -fopenmp -emit-fir -hlfir=false %s -o - | FileCheck %s +! The "if" clause was added to the "simd" directive in OpenMP 5.0. +! RUN: bbc -fopenmp -fopenmp-version=50 -emit-fir -hlfir=false %s -o - | FileCheck %s !CHECK-LABEL: func @_QPsimd() subroutine simd diff --git a/flang/test/Lower/OpenMP/FIR/stop-stmt-in-region.f90 b/flang/test/Lower/OpenMP/FIR/stop-stmt-in-region.f90 index d6c10bdee88d54977d684bc88ef4657ff833b18c..32cc6d17c420be00db13ae059abaf6dd42cd8a37 100644 --- a/flang/test/Lower/OpenMP/FIR/stop-stmt-in-region.f90 +++ b/flang/test/Lower/OpenMP/FIR/stop-stmt-in-region.f90 @@ -77,24 +77,27 @@ end ! CHECK: %[[VAL_3:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_4:.*]] = arith.constant 10 : i32 ! CHECK: %[[VAL_5:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop for (%[[VAL_6:.*]]) : i32 = (%[[VAL_3]]) to (%[[VAL_4]]) inclusive step (%[[VAL_5]]) { -! CHECK: fir.store %[[VAL_6]] to %[[VAL_0]] : !fir.ref -! CHECK: cf.br ^bb1 -! CHECK: ^bb1: -! CHECK: %[[VAL_7:.*]] = arith.constant 3 : i32 -! CHECK: fir.store %[[VAL_7]] to %[[VAL_2]] : !fir.ref -! CHECK: %[[VAL_8:.*]] = fir.load %[[VAL_2]] : !fir.ref -! CHECK: %[[VAL_9:.*]] = arith.constant 1 : i32 -! CHECK: %[[VAL_10:.*]] = arith.cmpi sgt, %[[VAL_8]], %[[VAL_9]] : i32 -! CHECK: cf.cond_br %[[VAL_10]], ^bb2, ^bb3 -! CHECK: ^bb2: -! CHECK: %[[VAL_11:.*]] = fir.load %[[VAL_2]] : !fir.ref -! CHECK: %[[VAL_12:.*]] = arith.constant false -! CHECK: %[[VAL_13:.*]] = arith.constant false -! CHECK: %[[VAL_14:.*]] = fir.call @_FortranAStopStatement(%[[VAL_11]], %[[VAL_12]], %[[VAL_13]]) {{.*}} : (i32, i1, i1) -> none -! CHECK: omp.yield -! CHECK: ^bb3: -! CHECK: omp.yield +! CHECK: omp.wsloop { +! CHECK-NEXT: omp.loop_nest (%[[VAL_6:.*]]) : i32 = (%[[VAL_3]]) to (%[[VAL_4]]) inclusive step (%[[VAL_5]]) { +! CHECK: fir.store %[[VAL_6]] to %[[VAL_0]] : !fir.ref +! CHECK: cf.br ^bb1 +! CHECK: ^bb1: +! CHECK: %[[VAL_7:.*]] = arith.constant 3 : i32 +! CHECK: fir.store %[[VAL_7]] to %[[VAL_2]] : !fir.ref +! CHECK: %[[VAL_8:.*]] = fir.load %[[VAL_2]] : !fir.ref +! CHECK: %[[VAL_9:.*]] = arith.constant 1 : i32 +! CHECK: %[[VAL_10:.*]] = arith.cmpi sgt, %[[VAL_8]], %[[VAL_9]] : i32 +! CHECK: cf.cond_br %[[VAL_10]], ^bb2, ^bb3 +! CHECK: ^bb2: +! CHECK: %[[VAL_11:.*]] = fir.load %[[VAL_2]] : !fir.ref +! CHECK: %[[VAL_12:.*]] = arith.constant false +! CHECK: %[[VAL_13:.*]] = arith.constant false +! CHECK: %[[VAL_14:.*]] = fir.call @_FortranAStopStatement(%[[VAL_11]], %[[VAL_12]], %[[VAL_13]]) {{.*}} : (i32, i1, i1) -> none +! CHECK: omp.yield +! CHECK: ^bb3: +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: cf.br ^bb1 ! CHECK: ^bb1: diff --git a/flang/test/Lower/OpenMP/FIR/target.f90 b/flang/test/Lower/OpenMP/FIR/target.f90 index ca3162340d7846261bbac7479a88c79aeafc066a..ea4b9240e9e514b75f9fb1e5c46305a72984de22 100644 --- a/flang/test/Lower/OpenMP/FIR/target.f90 +++ b/flang/test/Lower/OpenMP/FIR/target.f90 @@ -1,4 +1,5 @@ -!RUN: %flang_fc1 -emit-fir -flang-deprecated-no-hlfir -fopenmp %s -o - | FileCheck %s +! The "thread_limit" clause was added to the "target" construct in OpenMP 5.1. +! RUN: %flang_fc1 -emit-fir -flang-deprecated-no-hlfir -fopenmp -fopenmp-version=51 %s -o - | FileCheck %s !=============================================================================== ! Target_Enter Simple @@ -487,7 +488,8 @@ subroutine omp_target_parallel_do !CHECK: %[[VAL_5:.*]] = arith.constant 1 : i32 !CHECK: %[[VAL_6:.*]] = arith.constant 1024 : i32 !CHECK: %[[VAL_7:.*]] = arith.constant 1 : i32 - !CHECK: omp.wsloop for (%[[VAL_8:.*]]) : i32 = (%[[VAL_5]]) to (%[[VAL_6]]) inclusive step (%[[VAL_7]]) { + !CHECK: omp.wsloop { + !CHECK: omp.loop_nest (%[[VAL_8:.*]]) : i32 = (%[[VAL_5]]) to (%[[VAL_6]]) inclusive step (%[[VAL_7]]) { !CHECK: fir.store %[[VAL_8]] to %[[VAL_4]] : !fir.ref !CHECK: %[[VAL_9:.*]] = arith.constant 10 : i32 !CHECK: %[[VAL_10:.*]] = fir.load %[[VAL_4]] : !fir.ref @@ -501,6 +503,8 @@ subroutine omp_target_parallel_do end do !CHECK: omp.yield !CHECK: } + !CHECK: omp.terminator + !CHECK: } !CHECK: omp.terminator !CHECK: } !CHECK: omp.terminator diff --git a/flang/test/Lower/OpenMP/FIR/unstructured.f90 b/flang/test/Lower/OpenMP/FIR/unstructured.f90 index bfaf38b7ef1afc5f4620dd2d2add5e9988551d9a..6d1c9aab146401e6b8107ab4b890f138d4f06f26 100644 --- a/flang/test/Lower/OpenMP/FIR/unstructured.f90 +++ b/flang/test/Lower/OpenMP/FIR/unstructured.f90 @@ -67,27 +67,33 @@ end ! CHECK: ^bb1: // 2 preds: ^bb0, ^bb3 ! CHECK: cond_br %{{[0-9]*}}, ^bb2, ^bb4 ! CHECK: ^bb2: // pred: ^bb1 -! CHECK: omp.wsloop for (%[[ARG1:.*]]) : {{.*}} { -! CHECK: fir.store %[[ARG1]] to %[[ALLOCA_2]] : !fir.ref -! CHECK: @_FortranAioBeginExternalListOutput -! CHECK: %[[LOAD_1:.*]] = fir.load %[[ALLOCA_2]] : !fir.ref -! CHECK: @_FortranAioOutputInteger32(%{{.*}}, %[[LOAD_1]]) -! CHECK: omp.yield +! CHECK: omp.wsloop { +! CHECK: omp.loop_nest (%[[ARG1:.*]]) : {{.*}} { +! CHECK: fir.store %[[ARG1]] to %[[ALLOCA_2]] : !fir.ref +! CHECK: @_FortranAioBeginExternalListOutput +! CHECK: %[[LOAD_1:.*]] = fir.load %[[ALLOCA_2]] : !fir.ref +! CHECK: @_FortranAioOutputInteger32(%{{.*}}, %[[LOAD_1]]) +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } -! CHECK: omp.wsloop for (%[[ARG2:.*]]) : {{.*}} { -! CHECK: fir.store %[[ARG2]] to %[[ALLOCA_1]] : !fir.ref -! CHECK: br ^bb1 -! CHECK: ^bb2: // 2 preds: ^bb1, ^bb5 -! CHECK: cond_br %{{[0-9]*}}, ^bb3, ^bb6 -! CHECK: ^bb3: // pred: ^bb2 -! CHECK: cond_br %{{[0-9]*}}, ^bb4, ^bb5 -! CHECK: ^bb4: // pred: ^bb3 -! CHECK: @_FortranAioBeginExternalListOutput -! CHECK: %[[LOAD_2:.*]] = fir.load %[[ALLOCA_K]] : !fir.ref -! CHECK: @_FortranAioOutputInteger32(%{{.*}}, %[[LOAD_2]]) -! CHECK: br ^bb2 -! CHECK: ^bb6: // 2 preds: ^bb2, ^bb4 -! CHECK: omp.yield +! CHECK: omp.wsloop { +! CHECK: omp.loop_nest (%[[ARG2:.*]]) : {{.*}} { +! CHECK: fir.store %[[ARG2]] to %[[ALLOCA_1]] : !fir.ref +! CHECK: br ^bb1 +! CHECK: ^bb2: // 2 preds: ^bb1, ^bb5 +! CHECK: cond_br %{{[0-9]*}}, ^bb3, ^bb6 +! CHECK: ^bb3: // pred: ^bb2 +! CHECK: cond_br %{{[0-9]*}}, ^bb4, ^bb5 +! CHECK: ^bb4: // pred: ^bb3 +! CHECK: @_FortranAioBeginExternalListOutput +! CHECK: %[[LOAD_2:.*]] = fir.load %[[ALLOCA_K]] : !fir.ref +! CHECK: @_FortranAioOutputInteger32(%{{.*}}, %[[LOAD_2]]) +! CHECK: br ^bb2 +! CHECK: ^bb6: // 2 preds: ^bb2, ^bb4 +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: br ^bb1 ! CHECK: ^bb4: // pred: ^bb1 @@ -117,20 +123,23 @@ end ! CHECK-LABEL: func @_QPss4{{.*}} { ! CHECK: omp.parallel { ! CHECK: %[[ALLOCA:.*]] = fir.alloca i32 {{{.*}}, pinned} -! CHECK: omp.wsloop for (%[[ARG:.*]]) : {{.*}} { -! CHECK: fir.store %[[ARG]] to %[[ALLOCA]] : !fir.ref -! CHECK: %[[COND:.*]] = arith.cmpi eq, %{{.*}}, %{{.*}} -! CHECK: %[[COND_XOR:.*]] = arith.xori %[[COND]], %{{.*}} -! CHECK: fir.if %[[COND_XOR]] { -! CHECK: @_FortranAioBeginExternalListOutput -! CHECK: %[[LOAD:.*]] = fir.load %[[ALLOCA]] : !fir.ref -! CHECK: @_FortranAioOutputInteger32(%{{.*}}, %[[LOAD]]) -! CHECK: } else { -! CHECK: } -! CHECK-NEXT: omp.yield +! CHECK: omp.wsloop { +! CHECK: omp.loop_nest (%[[ARG:.*]]) : {{.*}} { +! CHECK: fir.store %[[ARG]] to %[[ALLOCA]] : !fir.ref +! CHECK: %[[COND:.*]] = arith.cmpi eq, %{{.*}}, %{{.*}} +! CHECK: %[[COND_XOR:.*]] = arith.xori %[[COND]], %{{.*}} +! CHECK: fir.if %[[COND_XOR]] { +! CHECK: @_FortranAioBeginExternalListOutput +! CHECK: %[[LOAD:.*]] = fir.load %[[ALLOCA]] : !fir.ref +! CHECK: @_FortranAioOutputInteger32(%{{.*}}, %[[LOAD]]) +! CHECK: } else { +! CHECK: } +! CHECK-NEXT: omp.yield +! CHECK-NEXT: } +! CHECK-NEXT: omp.terminator +! CHECK-NEXT: } +! CHECK: omp.terminator ! CHECK-NEXT: } -! CHECK: omp.terminator -! CHECK-NEXT:} subroutine ss4(n) ! CYCLE in OpenMP wsloop constructs !$omp parallel do i = 1, 3 @@ -146,20 +155,23 @@ end ! CHECK-LABEL: func @_QPss5() { ! CHECK: omp.parallel { -! CHECK: omp.wsloop {{.*}} { -! CHECK: br ^[[BB1:.*]] -! CHECK: ^[[BB1]]: -! CHECK: br ^[[BB2:.*]] -! CHECK: ^[[BB2]]: -! CHECK: cond_br %{{.*}}, ^[[BB3:.*]], ^[[BB6:.*]] -! CHECK: ^[[BB3]]: -! CHECK: cond_br %{{.*}}, ^[[BB4:.*]], ^[[BB3:.*]] -! CHECK: ^[[BB4]]: -! CHECK: br ^[[BB6]] -! CHECK: ^[[BB3]]: -! CHECK: br ^[[BB2]] -! CHECK: ^[[BB6]]: -! CHECK: omp.yield +! CHECK: omp.wsloop { +! CHECK: omp.loop_nest {{.*}} { +! CHECK: br ^[[BB1:.*]] +! CHECK: ^[[BB1]]: +! CHECK: br ^[[BB2:.*]] +! CHECK: ^[[BB2]]: +! CHECK: cond_br %{{.*}}, ^[[BB3:.*]], ^[[BB6:.*]] +! CHECK: ^[[BB3]]: +! CHECK: cond_br %{{.*}}, ^[[BB4:.*]], ^[[BB3:.*]] +! CHECK: ^[[BB4]]: +! CHECK: br ^[[BB6]] +! CHECK: ^[[BB3]]: +! CHECK: br ^[[BB2]] +! CHECK: ^[[BB6]]: +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } @@ -186,20 +198,23 @@ end ! CHECK: ^[[BB1_OUTER]]: ! CHECK: cond_br %{{.*}}, ^[[BB2_OUTER:.*]], ^[[BB3_OUTER:.*]] ! CHECK: ^[[BB2_OUTER]]: -! CHECK: omp.wsloop {{.*}} { -! CHECK: br ^[[BB1:.*]] -! CHECK: ^[[BB1]]: -! CHECK: br ^[[BB2:.*]] -! CHECK: ^[[BB2]]: -! CHECK: cond_br %{{.*}}, ^[[BB3:.*]], ^[[BB6:.*]] -! CHECK: ^[[BB3]]: -! CHECK: cond_br %{{.*}}, ^[[BB4:.*]], ^[[BB5:.*]] -! CHECK: ^[[BB4]]: -! CHECK: br ^[[BB6]] -! CHECK: ^[[BB5]] -! CHECK: br ^[[BB2]] -! CHECK: ^[[BB6]]: -! CHECK: omp.yield +! CHECK: omp.wsloop { +! CHECK: omp.loop_nest {{.*}} { +! CHECK: br ^[[BB1:.*]] +! CHECK: ^[[BB1]]: +! CHECK: br ^[[BB2:.*]] +! CHECK: ^[[BB2]]: +! CHECK: cond_br %{{.*}}, ^[[BB3:.*]], ^[[BB6:.*]] +! CHECK: ^[[BB3]]: +! CHECK: cond_br %{{.*}}, ^[[BB4:.*]], ^[[BB5:.*]] +! CHECK: ^[[BB4]]: +! CHECK: br ^[[BB6]] +! CHECK: ^[[BB5]] +! CHECK: br ^[[BB2]] +! CHECK: ^[[BB6]]: +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: br ^[[BB1_OUTER]] ! CHECK: ^[[BB3_OUTER]]: @@ -230,20 +245,23 @@ end ! CHECK: cond_br %{{.*}}, ^[[BB2_OUTER:.*]], ^[[BB3_OUTER:.*]] ! CHECK-NEXT: ^[[BB2_OUTER:.*]]: ! CHECK: omp.parallel { -! CHECK: omp.wsloop {{.*}} { -! CHECK: br ^[[BB1:.*]] -! CHECK-NEXT: ^[[BB1]]: -! CHECK: br ^[[BB2:.*]] -! CHECK-NEXT: ^[[BB2]]: -! CHECK: cond_br %{{.*}}, ^[[BB3:.*]], ^[[BB6:.*]] -! CHECK-NEXT: ^[[BB3]]: -! CHECK: cond_br %{{.*}}, ^[[BB4:.*]], ^[[BB5:.*]] -! CHECK-NEXT: ^[[BB4]]: -! CHECK: br ^[[BB6]] -! CHECK-NEXT: ^[[BB5]]: -! CHECK: br ^[[BB2]] -! CHECK-NEXT: ^[[BB6]]: -! CHECK: omp.yield +! CHECK: omp.wsloop { +! CHECK: omp.loop_nest {{.*}} { +! CHECK: br ^[[BB1:.*]] +! CHECK-NEXT: ^[[BB1]]: +! CHECK: br ^[[BB2:.*]] +! CHECK-NEXT: ^[[BB2]]: +! CHECK: cond_br %{{.*}}, ^[[BB3:.*]], ^[[BB6:.*]] +! CHECK-NEXT: ^[[BB3]]: +! CHECK: cond_br %{{.*}}, ^[[BB4:.*]], ^[[BB5:.*]] +! CHECK-NEXT: ^[[BB4]]: +! CHECK: br ^[[BB6]] +! CHECK-NEXT: ^[[BB5]]: +! CHECK: br ^[[BB2]] +! CHECK-NEXT: ^[[BB6]]: +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } @@ -268,20 +286,23 @@ end ! CHECK-LABEL: func @_QPss8() { ! CHECK: omp.parallel { -! CHECK: omp.wsloop {{.*}} { -! CHECK: br ^[[BB1:.*]] -! CHECK-NEXT: ^[[BB1]]: -! CHECK: br ^[[BB2:.*]] -! CHECK: ^[[BB2]]: -! CHECK: cond_br %{{.*}}, ^[[BB3:.*]], ^[[BB6:.*]] -! CHECK: ^[[BB3]]: -! CHECK: cond_br %{{.*}}, ^[[BB4:.*]], ^[[BB5:.*]] -! CHECK: ^[[BB4]]: -! CHECK-NEXT: br ^[[BB6]] -! CHECK: ^[[BB5]]: -! CHECK: br ^[[BB2]] -! CHECK-NEXT: ^[[BB6]]: -! CHECK: omp.yield +! CHECK: omp.wsloop { +! CHECK: omp.loop_nest {{.*}} { +! CHECK: br ^[[BB1:.*]] +! CHECK-NEXT: ^[[BB1]]: +! CHECK: br ^[[BB2:.*]] +! CHECK: ^[[BB2]]: +! CHECK: cond_br %{{.*}}, ^[[BB3:.*]], ^[[BB6:.*]] +! CHECK: ^[[BB3]]: +! CHECK: cond_br %{{.*}}, ^[[BB4:.*]], ^[[BB5:.*]] +! CHECK: ^[[BB4]]: +! CHECK-NEXT: br ^[[BB6]] +! CHECK: ^[[BB5]]: +! CHECK: br ^[[BB2]] +! CHECK-NEXT: ^[[BB6]]: +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } diff --git a/flang/test/Lower/OpenMP/FIR/wsloop-chunks.f90 b/flang/test/Lower/OpenMP/FIR/wsloop-chunks.f90 index 4030f46299d0b0b55bd3bfbb3c2fab140f8f7953..e4b85fb447767f4778a7be6b39de69eaf448d80c 100644 --- a/flang/test/Lower/OpenMP/FIR/wsloop-chunks.f90 +++ b/flang/test/Lower/OpenMP/FIR/wsloop-chunks.f90 @@ -19,11 +19,14 @@ do i=1, 9 ! CHECK: %[[VAL_3:.*]] = arith.constant 9 : i32 ! CHECK: %[[VAL_4:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_5:.*]] = arith.constant 4 : i32 -! CHECK: omp.wsloop schedule(static = %[[VAL_5]] : i32) nowait for (%[[ARG0:.*]]) : i32 = (%[[VAL_2]]) to (%[[VAL_3]]) inclusive step (%[[VAL_4]]) { -! CHECK: fir.store %[[ARG0]] to %[[STORE_IV:.*]] : !fir.ref -! CHECK: %[[LOAD_IV:.*]] = fir.load %[[STORE_IV]] : !fir.ref -! CHECK: {{.*}} = fir.call @_FortranAioOutputInteger32({{.*}}, %[[LOAD_IV]]) {{.*}}: (!fir.ref, i32) -> i1 -! CHECK: omp.yield +! CHECK: omp.wsloop schedule(static = %[[VAL_5]] : i32) nowait { +! CHECK-NEXT: omp.loop_nest (%[[ARG0:.*]]) : i32 = (%[[VAL_2]]) to (%[[VAL_3]]) inclusive step (%[[VAL_4]]) { +! CHECK: fir.store %[[ARG0]] to %[[STORE_IV:.*]] : !fir.ref +! CHECK: %[[LOAD_IV:.*]] = fir.load %[[STORE_IV]] : !fir.ref +! CHECK: {{.*}} = fir.call @_FortranAioOutputInteger32({{.*}}, %[[LOAD_IV]]) {{.*}}: (!fir.ref, i32) -> i1 +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } end do @@ -37,13 +40,16 @@ do i=1, 9 ! CHECK: %[[VAL_15:.*]] = arith.constant 9 : i32 ! CHECK: %[[VAL_16:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_17:.*]] = arith.constant 4 : i32 -! CHECK: omp.wsloop schedule(static = %[[VAL_17]] : i32) nowait for (%[[ARG1:.*]]) : i32 = (%[[VAL_14]]) to (%[[VAL_15]]) inclusive step (%[[VAL_16]]) { -! CHECK: fir.store %[[ARG1]] to %[[STORE_IV1:.*]] : !fir.ref -! CHECK: %[[VAL_24:.*]] = arith.constant 2 : i32 -! CHECK: %[[LOAD_IV1:.*]] = fir.load %[[STORE_IV1]] : !fir.ref -! CHECK: %[[VAL_25:.*]] = arith.muli %[[VAL_24]], %[[LOAD_IV1]] : i32 -! CHECK: {{.*}} = fir.call @_FortranAioOutputInteger32({{.*}}, %[[VAL_25]]) {{.*}}: (!fir.ref, i32) -> i1 -! CHECK: omp.yield +! CHECK: omp.wsloop schedule(static = %[[VAL_17]] : i32) nowait { +! CHECK-NEXT: omp.loop_nest (%[[ARG1:.*]]) : i32 = (%[[VAL_14]]) to (%[[VAL_15]]) inclusive step (%[[VAL_16]]) { +! CHECK: fir.store %[[ARG1]] to %[[STORE_IV1:.*]] : !fir.ref +! CHECK: %[[VAL_24:.*]] = arith.constant 2 : i32 +! CHECK: %[[LOAD_IV1:.*]] = fir.load %[[STORE_IV1]] : !fir.ref +! CHECK: %[[VAL_25:.*]] = arith.muli %[[VAL_24]], %[[LOAD_IV1]] : i32 +! CHECK: {{.*}} = fir.call @_FortranAioOutputInteger32({{.*}}, %[[VAL_25]]) {{.*}}: (!fir.ref, i32) -> i1 +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } end do @@ -61,13 +67,16 @@ end do ! CHECK: %[[VAL_30:.*]] = arith.constant 9 : i32 ! CHECK: %[[VAL_31:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_32:.*]] = fir.load %[[VAL_0]] : !fir.ref -! CHECK: omp.wsloop schedule(static = %[[VAL_32]] : i32) nowait for (%[[ARG2:.*]]) : i32 = (%[[VAL_29]]) to (%[[VAL_30]]) inclusive step (%[[VAL_31]]) { -! CHECK: fir.store %[[ARG2]] to %[[STORE_IV2:.*]] : !fir.ref -! CHECK: %[[VAL_39:.*]] = arith.constant 3 : i32 -! CHECK: %[[LOAD_IV2:.*]] = fir.load %[[STORE_IV2]] : !fir.ref -! CHECK: %[[VAL_40:.*]] = arith.muli %[[VAL_39]], %[[LOAD_IV2]] : i32 -! CHECK: {{.*}} = fir.call @_FortranAioOutputInteger32({{.*}}, %[[VAL_40]]) {{.*}}: (!fir.ref, i32) -> i1 -! CHECK: omp.yield +! CHECK: omp.wsloop schedule(static = %[[VAL_32]] : i32) nowait { +! CHECK-NEXT: omp.loop_nest (%[[ARG2:.*]]) : i32 = (%[[VAL_29]]) to (%[[VAL_30]]) inclusive step (%[[VAL_31]]) { +! CHECK: fir.store %[[ARG2]] to %[[STORE_IV2:.*]] : !fir.ref +! CHECK: %[[VAL_39:.*]] = arith.constant 3 : i32 +! CHECK: %[[LOAD_IV2:.*]] = fir.load %[[STORE_IV2]] : !fir.ref +! CHECK: %[[VAL_40:.*]] = arith.muli %[[VAL_39]], %[[LOAD_IV2]] : i32 +! CHECK: {{.*}} = fir.call @_FortranAioOutputInteger32({{.*}}, %[[VAL_40]]) {{.*}}: (!fir.ref, i32) -> i1 +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: return ! CHECK: } diff --git a/flang/test/Lower/OpenMP/FIR/wsloop-collapse.f90 b/flang/test/Lower/OpenMP/FIR/wsloop-collapse.f90 index 933fc0910e3382c323d0e77f540255099e565ca1..a2ba3ebfe1967d86c4d6ce95e1287d9dce24ee01 100644 --- a/flang/test/Lower/OpenMP/FIR/wsloop-collapse.f90 +++ b/flang/test/Lower/OpenMP/FIR/wsloop-collapse.f90 @@ -39,19 +39,22 @@ program wsloop_collapse do i = 1, a do j= 1, b do k = 1, c -! CHECK: omp.wsloop for (%[[ARG0:.*]], %[[ARG1:.*]], %[[ARG2:.*]]) : i32 = (%[[VAL_20]], %[[VAL_23]], %[[VAL_26]]) to (%[[VAL_21]], %[[VAL_24]], %[[VAL_27]]) inclusive step (%[[VAL_22]], %[[VAL_25]], %[[VAL_28]]) { -! CHECK: fir.store %[[ARG0]] to %[[STORE_IV0:.*]] : !fir.ref -! CHECK: fir.store %[[ARG1]] to %[[STORE_IV1:.*]] : !fir.ref -! CHECK: fir.store %[[ARG2]] to %[[STORE_IV2:.*]] : !fir.ref -! CHECK: %[[VAL_12:.*]] = fir.load %[[VAL_6]] : !fir.ref -! CHECK: %[[LOAD_IV0:.*]] = fir.load %[[STORE_IV0]] : !fir.ref -! CHECK: %[[VAL_13:.*]] = arith.addi %[[VAL_12]], %[[LOAD_IV0]] : i32 -! CHECK: %[[LOAD_IV1:.*]] = fir.load %[[STORE_IV1]] : !fir.ref -! CHECK: %[[VAL_14:.*]] = arith.addi %[[VAL_13]], %[[LOAD_IV1]] : i32 -! CHECK: %[[LOAD_IV2:.*]] = fir.load %[[STORE_IV2]] : !fir.ref -! CHECK: %[[VAL_15:.*]] = arith.addi %[[VAL_14]], %[[LOAD_IV2]] : i32 -! CHECK: fir.store %[[VAL_15]] to %[[VAL_6]] : !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop { +! CHECK-NEXT: omp.loop_nest (%[[ARG0:.*]], %[[ARG1:.*]], %[[ARG2:.*]]) : i32 = (%[[VAL_20]], %[[VAL_23]], %[[VAL_26]]) to (%[[VAL_21]], %[[VAL_24]], %[[VAL_27]]) inclusive step (%[[VAL_22]], %[[VAL_25]], %[[VAL_28]]) { +! CHECK: fir.store %[[ARG0]] to %[[STORE_IV0:.*]] : !fir.ref +! CHECK: fir.store %[[ARG1]] to %[[STORE_IV1:.*]] : !fir.ref +! CHECK: fir.store %[[ARG2]] to %[[STORE_IV2:.*]] : !fir.ref +! CHECK: %[[VAL_12:.*]] = fir.load %[[VAL_6]] : !fir.ref +! CHECK: %[[LOAD_IV0:.*]] = fir.load %[[STORE_IV0]] : !fir.ref +! CHECK: %[[VAL_13:.*]] = arith.addi %[[VAL_12]], %[[LOAD_IV0]] : i32 +! CHECK: %[[LOAD_IV1:.*]] = fir.load %[[STORE_IV1]] : !fir.ref +! CHECK: %[[VAL_14:.*]] = arith.addi %[[VAL_13]], %[[LOAD_IV1]] : i32 +! CHECK: %[[LOAD_IV2:.*]] = fir.load %[[STORE_IV2]] : !fir.ref +! CHECK: %[[VAL_15:.*]] = arith.addi %[[VAL_14]], %[[LOAD_IV2]] : i32 +! CHECK: fir.store %[[VAL_15]] to %[[VAL_6]] : !fir.ref +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } x = x + i + j + k end do diff --git a/flang/test/Lower/OpenMP/FIR/wsloop-monotonic.f90 b/flang/test/Lower/OpenMP/FIR/wsloop-monotonic.f90 index 1c381475f6cbb12a0a8bf6173393993811fa262f..941885bdb1e384f7864fd628e43db21703b6c5eb 100644 --- a/flang/test/Lower/OpenMP/FIR/wsloop-monotonic.f90 +++ b/flang/test/Lower/OpenMP/FIR/wsloop-monotonic.f90 @@ -11,23 +11,27 @@ program wsloop_dynamic !CHECK: omp.parallel { !$OMP DO SCHEDULE(monotonic:dynamic) -!CHECK: %[[ALLOCA_IV:.*]] = fir.alloca i32 {{{.*}}, pinned} -!CHECK: %[[WS_LB:.*]] = arith.constant 1 : i32 -!CHECK: %[[WS_UB:.*]] = arith.constant 9 : i32 -!CHECK: %[[WS_STEP:.*]] = arith.constant 1 : i32 -!CHECK: omp.wsloop schedule(dynamic, monotonic) nowait for (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) -!CHECK: fir.store %[[I]] to %[[ALLOCA_IV:.*]] : !fir.ref +!CHECK: %[[ALLOCA_IV:.*]] = fir.alloca i32 {{{.*}}, pinned} +!CHECK: %[[WS_LB:.*]] = arith.constant 1 : i32 +!CHECK: %[[WS_UB:.*]] = arith.constant 9 : i32 +!CHECK: %[[WS_STEP:.*]] = arith.constant 1 : i32 +!CHECK: omp.wsloop schedule(dynamic, monotonic) nowait { +!CHECK-NEXT: omp.loop_nest (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) { +!CHECK: fir.store %[[I]] to %[[ALLOCA_IV:.*]] : !fir.ref do i=1, 9 print*, i -!CHECK: %[[RTBEGIN:.*]] = fir.call @_FortranAioBeginExternalListOutput -!CHECK: %[[LOAD:.*]] = fir.load %[[ALLOCA_IV]] : !fir.ref -!CHECK: fir.call @_FortranAioOutputInteger32(%[[RTBEGIN]], %[[LOAD]]) {{.*}}: (!fir.ref, i32) -> i1 -!CHECK: fir.call @_FortranAioEndIoStatement(%[[RTBEGIN]]) {{.*}}: (!fir.ref) -> i32 +!CHECK: %[[RTBEGIN:.*]] = fir.call @_FortranAioBeginExternalListOutput +!CHECK: %[[LOAD:.*]] = fir.load %[[ALLOCA_IV]] : !fir.ref +!CHECK: fir.call @_FortranAioOutputInteger32(%[[RTBEGIN]], %[[LOAD]]) {{.*}}: (!fir.ref, i32) -> i1 +!CHECK: fir.call @_FortranAioEndIoStatement(%[[RTBEGIN]]) {{.*}}: (!fir.ref) -> i32 end do -!CHECK: omp.yield -!CHECK: omp.terminator -!CHECK: } +!CHECK: omp.yield +!CHECK: } +!CHECK: omp.terminator +!CHECK: } +!CHECK: omp.terminator +!CHECK: } !$OMP END DO NOWAIT !$OMP END PARALLEL diff --git a/flang/test/Lower/OpenMP/FIR/wsloop-nonmonotonic.f90 b/flang/test/Lower/OpenMP/FIR/wsloop-nonmonotonic.f90 index 3f425200b8fa48d83f2cab708d1832940b2999ff..96a3e71f34b1eaba442d6d562c880df0da168e5d 100644 --- a/flang/test/Lower/OpenMP/FIR/wsloop-nonmonotonic.f90 +++ b/flang/test/Lower/OpenMP/FIR/wsloop-nonmonotonic.f90 @@ -12,24 +12,27 @@ program wsloop_dynamic !CHECK: omp.parallel { !$OMP DO SCHEDULE(nonmonotonic:dynamic) -!CHECK: %[[ALLOCA_IV:.*]] = fir.alloca i32 {{{.*}}, pinned} -!CHECK: %[[WS_LB:.*]] = arith.constant 1 : i32 -!CHECK: %[[WS_UB:.*]] = arith.constant 9 : i32 -!CHECK: %[[WS_STEP:.*]] = arith.constant 1 : i32 -!CHECK: omp.wsloop schedule(dynamic, nonmonotonic) nowait for (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) -!CHECK: fir.store %[[I]] to %[[ALLOCA_IV]] : !fir.ref +!CHECK: %[[ALLOCA_IV:.*]] = fir.alloca i32 {{{.*}}, pinned} +!CHECK: %[[WS_LB:.*]] = arith.constant 1 : i32 +!CHECK: %[[WS_UB:.*]] = arith.constant 9 : i32 +!CHECK: %[[WS_STEP:.*]] = arith.constant 1 : i32 +!CHECK: omp.wsloop schedule(dynamic, nonmonotonic) nowait { +!CHECK-NEXT: omp.loop_nest (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) +!CHECK: fir.store %[[I]] to %[[ALLOCA_IV]] : !fir.ref do i=1, 9 print*, i -!CHECK: %[[RTBEGIN:.*]] = fir.call @_FortranAioBeginExternalListOutput -!CHECK: %[[LOAD:.*]] = fir.load %[[ALLOCA_IV]] : !fir.ref -!CHECK: fir.call @_FortranAioOutputInteger32(%[[RTBEGIN]], %[[LOAD]]) {{.*}}: (!fir.ref, i32) -> i1 -!CHECK: fir.call @_FortranAioEndIoStatement(%[[RTBEGIN]]) {{.*}}: (!fir.ref) -> i32 +!CHECK: %[[RTBEGIN:.*]] = fir.call @_FortranAioBeginExternalListOutput +!CHECK: %[[LOAD:.*]] = fir.load %[[ALLOCA_IV]] : !fir.ref +!CHECK: fir.call @_FortranAioOutputInteger32(%[[RTBEGIN]], %[[LOAD]]) {{.*}}: (!fir.ref, i32) -> i1 +!CHECK: fir.call @_FortranAioEndIoStatement(%[[RTBEGIN]]) {{.*}}: (!fir.ref) -> i32 end do -!CHECK: omp.yield -!CHECK: } -!CHECK: omp.terminator -!CHECK: } +!CHECK: omp.yield +!CHECK: } +!CHECK: omp.terminator +!CHECK: } +!CHECK: omp.terminator +!CHECK: } !$OMP END DO NOWAIT !$OMP END PARALLEL diff --git a/flang/test/Lower/OpenMP/FIR/wsloop-ordered.f90 b/flang/test/Lower/OpenMP/FIR/wsloop-ordered.f90 index 7548d7a597228a29ab2a2cdd719ab6a8debde72e..fec027608d991365d1eb921e84fa00cc06ee08f7 100644 --- a/flang/test/Lower/OpenMP/FIR/wsloop-ordered.f90 +++ b/flang/test/Lower/OpenMP/FIR/wsloop-ordered.f90 @@ -6,9 +6,12 @@ subroutine wsloop_ordered_no_para() integer :: a(10), i -! CHECK: omp.wsloop ordered(0) for (%{{.*}}) : i32 = (%{{.*}}) to (%{{.*}}) inclusive step (%{{.*}}) { -! CHECK: omp.yield -! CHECK: } +! CHECK: omp.wsloop ordered(0) { +! CHECK-NEXT: omp.loop_nest (%{{.*}}) : i32 = (%{{.*}}) to (%{{.*}}) inclusive step (%{{.*}}) { +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator +! CHECK: } !$omp do ordered do i = 2, 10 @@ -25,9 +28,12 @@ subroutine wsloop_ordered_with_para() integer :: a(10), i ! CHECK: func @_QPwsloop_ordered_with_para() { -! CHECK: omp.wsloop ordered(1) for (%{{.*}}) : i32 = (%{{.*}}) to (%{{.*}}) inclusive step (%{{.*}}) { -! CHECK: omp.yield -! CHECK: } +! CHECK: omp.wsloop ordered(1) { +! CHECK-NEXT: omp.loop_nest (%{{.*}}) : i32 = (%{{.*}}) to (%{{.*}}) inclusive step (%{{.*}}) { +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator +! CHECK: } !$omp do ordered(1) do i = 2, 10 diff --git a/flang/test/Lower/OpenMP/FIR/wsloop-reduction-add-byref.f90 b/flang/test/Lower/OpenMP/FIR/wsloop-reduction-add-byref.f90 index 08f5a0fcdbae67068cdab5adba9c5ee178b91ad7..b6dfec09007e54a82cbd8d6a9bad9eebd2a2db10 100644 --- a/flang/test/Lower/OpenMP/FIR/wsloop-reduction-add-byref.f90 +++ b/flang/test/Lower/OpenMP/FIR/wsloop-reduction-add-byref.f90 @@ -80,13 +80,16 @@ ! CHECK: %[[VAL_4:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_5:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_6:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@add_reduction_byref_i32 %[[VAL_1]] -> %[[VAL_7:.*]] : !fir.ref) for (%[[VAL_8:.*]]) : i32 = (%[[VAL_4]]) to (%[[VAL_5]]) inclusive step (%[[VAL_6]]) { -! CHECK: fir.store %[[VAL_8]] to %[[VAL_3]] : !fir.ref -! CHECK: %[[VAL_9:.*]] = fir.load %[[VAL_7]] : !fir.ref -! CHECK: %[[VAL_10:.*]] = fir.load %[[VAL_3]] : !fir.ref -! CHECK: %[[VAL_11:.*]] = arith.addi %[[VAL_9]], %[[VAL_10]] : i32 -! CHECK: fir.store %[[VAL_11]] to %[[VAL_7]] : !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@add_reduction_byref_i32 %[[VAL_1]] -> %[[VAL_7:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_8:.*]]) : i32 = (%[[VAL_4]]) to (%[[VAL_5]]) inclusive step (%[[VAL_6]]) { +! CHECK: fir.store %[[VAL_8]] to %[[VAL_3]] : !fir.ref +! CHECK: %[[VAL_9:.*]] = fir.load %[[VAL_7]] : !fir.ref +! CHECK: %[[VAL_10:.*]] = fir.load %[[VAL_3]] : !fir.ref +! CHECK: %[[VAL_11:.*]] = arith.addi %[[VAL_9]], %[[VAL_10]] : i32 +! CHECK: fir.store %[[VAL_11]] to %[[VAL_7]] : !fir.ref +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } @@ -116,14 +119,17 @@ end subroutine ! CHECK: %[[VAL_4:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_5:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_6:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@add_reduction_byref_f32 %[[VAL_1]] -> %[[VAL_7:.*]] : !fir.ref) for (%[[VAL_8:.*]]) : i32 = (%[[VAL_4]]) to (%[[VAL_5]]) inclusive step (%[[VAL_6]]) { -! CHECK: fir.store %[[VAL_8]] to %[[VAL_3]] : !fir.ref -! CHECK: %[[VAL_9:.*]] = fir.load %[[VAL_7]] : !fir.ref -! CHECK: %[[VAL_10:.*]] = fir.load %[[VAL_3]] : !fir.ref -! CHECK: %[[VAL_11:.*]] = fir.convert %[[VAL_10]] : (i32) -> f32 -! CHECK: %[[VAL_12:.*]] = arith.addf %[[VAL_9]], %[[VAL_11]] fastmath : f32 -! CHECK: fir.store %[[VAL_12]] to %[[VAL_7]] : !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@add_reduction_byref_f32 %[[VAL_1]] -> %[[VAL_7:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_8:.*]]) : i32 = (%[[VAL_4]]) to (%[[VAL_5]]) inclusive step (%[[VAL_6]]) { +! CHECK: fir.store %[[VAL_8]] to %[[VAL_3]] : !fir.ref +! CHECK: %[[VAL_9:.*]] = fir.load %[[VAL_7]] : !fir.ref +! CHECK: %[[VAL_10:.*]] = fir.load %[[VAL_3]] : !fir.ref +! CHECK: %[[VAL_11:.*]] = fir.convert %[[VAL_10]] : (i32) -> f32 +! CHECK: %[[VAL_12:.*]] = arith.addf %[[VAL_9]], %[[VAL_11]] fastmath : f32 +! CHECK: fir.store %[[VAL_12]] to %[[VAL_7]] : !fir.ref +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } @@ -152,13 +158,16 @@ end subroutine ! CHECK: %[[VAL_4:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_5:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_6:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@add_reduction_byref_i32 %[[VAL_1]] -> %[[VAL_7:.*]] : !fir.ref) for (%[[VAL_8:.*]]) : i32 = (%[[VAL_4]]) to (%[[VAL_5]]) inclusive step (%[[VAL_6]]) { -! CHECK: fir.store %[[VAL_8]] to %[[VAL_3]] : !fir.ref -! CHECK: %[[VAL_9:.*]] = fir.load %[[VAL_3]] : !fir.ref -! CHECK: %[[VAL_10:.*]] = fir.load %[[VAL_7]] : !fir.ref -! CHECK: %[[VAL_11:.*]] = arith.addi %[[VAL_9]], %[[VAL_10]] : i32 -! CHECK: fir.store %[[VAL_11]] to %[[VAL_7]] : !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@add_reduction_byref_i32 %[[VAL_1]] -> %[[VAL_7:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_8:.*]]) : i32 = (%[[VAL_4]]) to (%[[VAL_5]]) inclusive step (%[[VAL_6]]) { +! CHECK: fir.store %[[VAL_8]] to %[[VAL_3]] : !fir.ref +! CHECK: %[[VAL_9:.*]] = fir.load %[[VAL_3]] : !fir.ref +! CHECK: %[[VAL_10:.*]] = fir.load %[[VAL_7]] : !fir.ref +! CHECK: %[[VAL_11:.*]] = arith.addi %[[VAL_9]], %[[VAL_10]] : i32 +! CHECK: fir.store %[[VAL_11]] to %[[VAL_7]] : !fir.ref +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } @@ -187,14 +196,17 @@ end subroutine ! CHECK: %[[VAL_4:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_5:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_6:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@add_reduction_byref_f32 %[[VAL_1]] -> %[[VAL_7:.*]] : !fir.ref) for (%[[VAL_8:.*]]) : i32 = (%[[VAL_4]]) to (%[[VAL_5]]) inclusive step (%[[VAL_6]]) { -! CHECK: fir.store %[[VAL_8]] to %[[VAL_3]] : !fir.ref -! CHECK: %[[VAL_9:.*]] = fir.load %[[VAL_3]] : !fir.ref -! CHECK: %[[VAL_10:.*]] = fir.convert %[[VAL_9]] : (i32) -> f32 -! CHECK: %[[VAL_11:.*]] = fir.load %[[VAL_7]] : !fir.ref -! CHECK: %[[VAL_12:.*]] = arith.addf %[[VAL_10]], %[[VAL_11]] fastmath : f32 -! CHECK: fir.store %[[VAL_12]] to %[[VAL_7]] : !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@add_reduction_byref_f32 %[[VAL_1]] -> %[[VAL_7:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_8:.*]]) : i32 = (%[[VAL_4]]) to (%[[VAL_5]]) inclusive step (%[[VAL_6]]) { +! CHECK: fir.store %[[VAL_8]] to %[[VAL_3]] : !fir.ref +! CHECK: %[[VAL_9:.*]] = fir.load %[[VAL_3]] : !fir.ref +! CHECK: %[[VAL_10:.*]] = fir.convert %[[VAL_9]] : (i32) -> f32 +! CHECK: %[[VAL_11:.*]] = fir.load %[[VAL_7]] : !fir.ref +! CHECK: %[[VAL_12:.*]] = arith.addf %[[VAL_10]], %[[VAL_11]] fastmath : f32 +! CHECK: fir.store %[[VAL_12]] to %[[VAL_7]] : !fir.ref +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } @@ -229,21 +241,24 @@ end subroutine ! CHECK: %[[VAL_8:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_9:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_10:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@add_reduction_byref_i32 %[[VAL_1]] -> %[[VAL_11:.*]] : !fir.ref, @add_reduction_byref_i32 %[[VAL_2]] -> %[[VAL_12:.*]] : !fir.ref, @add_reduction_byref_i32 %[[VAL_3]] -> %[[VAL_13:.*]] : !fir.ref) for (%[[VAL_14:.*]]) : i32 = (%[[VAL_8]]) to (%[[VAL_9]]) inclusive step (%[[VAL_10]]) { -! CHECK: fir.store %[[VAL_14]] to %[[VAL_7]] : !fir.ref -! CHECK: %[[VAL_15:.*]] = fir.load %[[VAL_11]] : !fir.ref -! CHECK: %[[VAL_16:.*]] = fir.load %[[VAL_7]] : !fir.ref -! CHECK: %[[VAL_17:.*]] = arith.addi %[[VAL_15]], %[[VAL_16]] : i32 -! CHECK: fir.store %[[VAL_17]] to %[[VAL_11]] : !fir.ref -! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_12]] : !fir.ref -! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_7]] : !fir.ref -! CHECK: %[[VAL_20:.*]] = arith.addi %[[VAL_18]], %[[VAL_19]] : i32 -! CHECK: fir.store %[[VAL_20]] to %[[VAL_12]] : !fir.ref -! CHECK: %[[VAL_21:.*]] = fir.load %[[VAL_13]] : !fir.ref -! CHECK: %[[VAL_22:.*]] = fir.load %[[VAL_7]] : !fir.ref -! CHECK: %[[VAL_23:.*]] = arith.addi %[[VAL_21]], %[[VAL_22]] : i32 -! CHECK: fir.store %[[VAL_23]] to %[[VAL_13]] : !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@add_reduction_byref_i32 %[[VAL_1]] -> %[[VAL_11:.*]] : !fir.ref, @add_reduction_byref_i32 %[[VAL_2]] -> %[[VAL_12:.*]] : !fir.ref, @add_reduction_byref_i32 %[[VAL_3]] -> %[[VAL_13:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_14:.*]]) : i32 = (%[[VAL_8]]) to (%[[VAL_9]]) inclusive step (%[[VAL_10]]) { +! CHECK: fir.store %[[VAL_14]] to %[[VAL_7]] : !fir.ref +! CHECK: %[[VAL_15:.*]] = fir.load %[[VAL_11]] : !fir.ref +! CHECK: %[[VAL_16:.*]] = fir.load %[[VAL_7]] : !fir.ref +! CHECK: %[[VAL_17:.*]] = arith.addi %[[VAL_15]], %[[VAL_16]] : i32 +! CHECK: fir.store %[[VAL_17]] to %[[VAL_11]] : !fir.ref +! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_12]] : !fir.ref +! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_7]] : !fir.ref +! CHECK: %[[VAL_20:.*]] = arith.addi %[[VAL_18]], %[[VAL_19]] : i32 +! CHECK: fir.store %[[VAL_20]] to %[[VAL_12]] : !fir.ref +! CHECK: %[[VAL_21:.*]] = fir.load %[[VAL_13]] : !fir.ref +! CHECK: %[[VAL_22:.*]] = fir.load %[[VAL_7]] : !fir.ref +! CHECK: %[[VAL_23:.*]] = arith.addi %[[VAL_21]], %[[VAL_22]] : i32 +! CHECK: fir.store %[[VAL_23]] to %[[VAL_13]] : !fir.ref +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } @@ -282,24 +297,27 @@ end subroutine ! CHECK: %[[VAL_8:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_9:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_10:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@add_reduction_byref_f32 %[[VAL_1]] -> %[[VAL_11:.*]] : !fir.ref, @add_reduction_byref_f32 %[[VAL_2]] -> %[[VAL_12:.*]] : !fir.ref, @add_reduction_byref_f32 %[[VAL_3]] -> %[[VAL_13:.*]] : !fir.ref) for (%[[VAL_14:.*]]) : i32 = (%[[VAL_8]]) to (%[[VAL_9]]) inclusive step (%[[VAL_10]]) { -! CHECK: fir.store %[[VAL_14]] to %[[VAL_7]] : !fir.ref -! CHECK: %[[VAL_15:.*]] = fir.load %[[VAL_11]] : !fir.ref -! CHECK: %[[VAL_16:.*]] = fir.load %[[VAL_7]] : !fir.ref -! CHECK: %[[VAL_17:.*]] = fir.convert %[[VAL_16]] : (i32) -> f32 -! CHECK: %[[VAL_18:.*]] = arith.addf %[[VAL_15]], %[[VAL_17]] fastmath : f32 -! CHECK: fir.store %[[VAL_18]] to %[[VAL_11]] : !fir.ref -! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_12]] : !fir.ref -! CHECK: %[[VAL_20:.*]] = fir.load %[[VAL_7]] : !fir.ref -! CHECK: %[[VAL_21:.*]] = fir.convert %[[VAL_20]] : (i32) -> f32 -! CHECK: %[[VAL_22:.*]] = arith.addf %[[VAL_19]], %[[VAL_21]] fastmath : f32 -! CHECK: fir.store %[[VAL_22]] to %[[VAL_12]] : !fir.ref -! CHECK: %[[VAL_23:.*]] = fir.load %[[VAL_13]] : !fir.ref -! CHECK: %[[VAL_24:.*]] = fir.load %[[VAL_7]] : !fir.ref -! CHECK: %[[VAL_25:.*]] = fir.convert %[[VAL_24]] : (i32) -> f32 -! CHECK: %[[VAL_26:.*]] = arith.addf %[[VAL_23]], %[[VAL_25]] fastmath : f32 -! CHECK: fir.store %[[VAL_26]] to %[[VAL_13]] : !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@add_reduction_byref_f32 %[[VAL_1]] -> %[[VAL_11:.*]] : !fir.ref, @add_reduction_byref_f32 %[[VAL_2]] -> %[[VAL_12:.*]] : !fir.ref, @add_reduction_byref_f32 %[[VAL_3]] -> %[[VAL_13:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_14:.*]]) : i32 = (%[[VAL_8]]) to (%[[VAL_9]]) inclusive step (%[[VAL_10]]) { +! CHECK: fir.store %[[VAL_14]] to %[[VAL_7]] : !fir.ref +! CHECK: %[[VAL_15:.*]] = fir.load %[[VAL_11]] : !fir.ref +! CHECK: %[[VAL_16:.*]] = fir.load %[[VAL_7]] : !fir.ref +! CHECK: %[[VAL_17:.*]] = fir.convert %[[VAL_16]] : (i32) -> f32 +! CHECK: %[[VAL_18:.*]] = arith.addf %[[VAL_15]], %[[VAL_17]] fastmath : f32 +! CHECK: fir.store %[[VAL_18]] to %[[VAL_11]] : !fir.ref +! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_12]] : !fir.ref +! CHECK: %[[VAL_20:.*]] = fir.load %[[VAL_7]] : !fir.ref +! CHECK: %[[VAL_21:.*]] = fir.convert %[[VAL_20]] : (i32) -> f32 +! CHECK: %[[VAL_22:.*]] = arith.addf %[[VAL_19]], %[[VAL_21]] fastmath : f32 +! CHECK: fir.store %[[VAL_22]] to %[[VAL_12]] : !fir.ref +! CHECK: %[[VAL_23:.*]] = fir.load %[[VAL_13]] : !fir.ref +! CHECK: %[[VAL_24:.*]] = fir.load %[[VAL_7]] : !fir.ref +! CHECK: %[[VAL_25:.*]] = fir.convert %[[VAL_24]] : (i32) -> f32 +! CHECK: %[[VAL_26:.*]] = arith.addf %[[VAL_23]], %[[VAL_25]] fastmath : f32 +! CHECK: fir.store %[[VAL_26]] to %[[VAL_13]] : !fir.ref +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } @@ -341,28 +359,31 @@ end subroutine ! CHECK: %[[VAL_10:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_11:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_12:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@add_reduction_byref_i32 %[[VAL_2]] -> %[[VAL_13:.*]] : !fir.ref, @add_reduction_byref_i64 %[[VAL_3]] -> %[[VAL_14:.*]] : !fir.ref, @add_reduction_byref_f32 %[[VAL_4]] -> %[[VAL_15:.*]] : !fir.ref, @add_reduction_byref_f64 %[[VAL_1]] -> %[[VAL_16:.*]] : !fir.ref) for (%[[VAL_17:.*]]) : i32 = (%[[VAL_10]]) to (%[[VAL_11]]) inclusive step (%[[VAL_12]]) { -! CHECK: fir.store %[[VAL_17]] to %[[VAL_9]] : !fir.ref -! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_13]] : !fir.ref -! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_9]] : !fir.ref -! CHECK: %[[VAL_20:.*]] = arith.addi %[[VAL_18]], %[[VAL_19]] : i32 -! CHECK: fir.store %[[VAL_20]] to %[[VAL_13]] : !fir.ref -! CHECK: %[[VAL_21:.*]] = fir.load %[[VAL_14]] : !fir.ref -! CHECK: %[[VAL_22:.*]] = fir.load %[[VAL_9]] : !fir.ref -! CHECK: %[[VAL_23:.*]] = fir.convert %[[VAL_22]] : (i32) -> i64 -! CHECK: %[[VAL_24:.*]] = arith.addi %[[VAL_21]], %[[VAL_23]] : i64 -! CHECK: fir.store %[[VAL_24]] to %[[VAL_14]] : !fir.ref -! CHECK: %[[VAL_25:.*]] = fir.load %[[VAL_15]] : !fir.ref -! CHECK: %[[VAL_26:.*]] = fir.load %[[VAL_9]] : !fir.ref -! CHECK: %[[VAL_27:.*]] = fir.convert %[[VAL_26]] : (i32) -> f32 -! CHECK: %[[VAL_28:.*]] = arith.addf %[[VAL_25]], %[[VAL_27]] fastmath : f32 -! CHECK: fir.store %[[VAL_28]] to %[[VAL_15]] : !fir.ref -! CHECK: %[[VAL_29:.*]] = fir.load %[[VAL_16]] : !fir.ref -! CHECK: %[[VAL_30:.*]] = fir.load %[[VAL_9]] : !fir.ref -! CHECK: %[[VAL_31:.*]] = fir.convert %[[VAL_30]] : (i32) -> f64 -! CHECK: %[[VAL_32:.*]] = arith.addf %[[VAL_29]], %[[VAL_31]] fastmath : f64 -! CHECK: fir.store %[[VAL_32]] to %[[VAL_16]] : !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@add_reduction_byref_i32 %[[VAL_2]] -> %[[VAL_13:.*]] : !fir.ref, @add_reduction_byref_i64 %[[VAL_3]] -> %[[VAL_14:.*]] : !fir.ref, @add_reduction_byref_f32 %[[VAL_4]] -> %[[VAL_15:.*]] : !fir.ref, @add_reduction_byref_f64 %[[VAL_1]] -> %[[VAL_16:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_17:.*]]) : i32 = (%[[VAL_10]]) to (%[[VAL_11]]) inclusive step (%[[VAL_12]]) { +! CHECK: fir.store %[[VAL_17]] to %[[VAL_9]] : !fir.ref +! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_13]] : !fir.ref +! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_9]] : !fir.ref +! CHECK: %[[VAL_20:.*]] = arith.addi %[[VAL_18]], %[[VAL_19]] : i32 +! CHECK: fir.store %[[VAL_20]] to %[[VAL_13]] : !fir.ref +! CHECK: %[[VAL_21:.*]] = fir.load %[[VAL_14]] : !fir.ref +! CHECK: %[[VAL_22:.*]] = fir.load %[[VAL_9]] : !fir.ref +! CHECK: %[[VAL_23:.*]] = fir.convert %[[VAL_22]] : (i32) -> i64 +! CHECK: %[[VAL_24:.*]] = arith.addi %[[VAL_21]], %[[VAL_23]] : i64 +! CHECK: fir.store %[[VAL_24]] to %[[VAL_14]] : !fir.ref +! CHECK: %[[VAL_25:.*]] = fir.load %[[VAL_15]] : !fir.ref +! CHECK: %[[VAL_26:.*]] = fir.load %[[VAL_9]] : !fir.ref +! CHECK: %[[VAL_27:.*]] = fir.convert %[[VAL_26]] : (i32) -> f32 +! CHECK: %[[VAL_28:.*]] = arith.addf %[[VAL_25]], %[[VAL_27]] fastmath : f32 +! CHECK: fir.store %[[VAL_28]] to %[[VAL_15]] : !fir.ref +! CHECK: %[[VAL_29:.*]] = fir.load %[[VAL_16]] : !fir.ref +! CHECK: %[[VAL_30:.*]] = fir.load %[[VAL_9]] : !fir.ref +! CHECK: %[[VAL_31:.*]] = fir.convert %[[VAL_30]] : (i32) -> f64 +! CHECK: %[[VAL_32:.*]] = arith.addf %[[VAL_29]], %[[VAL_31]] fastmath : f64 +! CHECK: fir.store %[[VAL_32]] to %[[VAL_16]] : !fir.ref +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } diff --git a/flang/test/Lower/OpenMP/FIR/wsloop-reduction-add.f90 b/flang/test/Lower/OpenMP/FIR/wsloop-reduction-add.f90 index dc96b875f745f2d953e3f0fca22f326b9af42b2a..e0b9330b1a6d5cf8240a40674dcd13a693ebe822 100644 --- a/flang/test/Lower/OpenMP/FIR/wsloop-reduction-add.f90 +++ b/flang/test/Lower/OpenMP/FIR/wsloop-reduction-add.f90 @@ -55,13 +55,16 @@ ! CHECK: %[[VAL_4:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_5:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_6:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@add_reduction_i32 %[[VAL_1]] -> %[[VAL_7:.*]] : !fir.ref) for (%[[VAL_8:.*]]) : i32 = (%[[VAL_4]]) to (%[[VAL_5]]) inclusive step (%[[VAL_6]]) { -! CHECK: fir.store %[[VAL_8]] to %[[VAL_3]] : !fir.ref -! CHECK: %[[VAL_9:.*]] = fir.load %[[VAL_7]] : !fir.ref -! CHECK: %[[VAL_10:.*]] = fir.load %[[VAL_3]] : !fir.ref -! CHECK: %[[VAL_11:.*]] = arith.addi %[[VAL_9]], %[[VAL_10]] : i32 -! CHECK: fir.store %[[VAL_11]] to %[[VAL_7]] : !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop reduction(@add_reduction_i32 %[[VAL_1]] -> %[[VAL_7:.*]] : !fir.ref) +! CHECK-NEXT: omp.loop_nest (%[[VAL_8:.*]]) : i32 = (%[[VAL_4]]) to (%[[VAL_5]]) inclusive step (%[[VAL_6]]) { +! CHECK: fir.store %[[VAL_8]] to %[[VAL_3]] : !fir.ref +! CHECK: %[[VAL_9:.*]] = fir.load %[[VAL_7]] : !fir.ref +! CHECK: %[[VAL_10:.*]] = fir.load %[[VAL_3]] : !fir.ref +! CHECK: %[[VAL_11:.*]] = arith.addi %[[VAL_9]], %[[VAL_10]] : i32 +! CHECK: fir.store %[[VAL_11]] to %[[VAL_7]] : !fir.ref +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } @@ -91,14 +94,17 @@ end subroutine ! CHECK: %[[VAL_4:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_5:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_6:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@add_reduction_f32 %[[VAL_1]] -> %[[VAL_7:.*]] : !fir.ref) for (%[[VAL_8:.*]]) : i32 = (%[[VAL_4]]) to (%[[VAL_5]]) inclusive step (%[[VAL_6]]) { -! CHECK: fir.store %[[VAL_8]] to %[[VAL_3]] : !fir.ref -! CHECK: %[[VAL_9:.*]] = fir.load %[[VAL_7]] : !fir.ref -! CHECK: %[[VAL_10:.*]] = fir.load %[[VAL_3]] : !fir.ref -! CHECK: %[[VAL_11:.*]] = fir.convert %[[VAL_10]] : (i32) -> f32 -! CHECK: %[[VAL_12:.*]] = arith.addf %[[VAL_9]], %[[VAL_11]] fastmath : f32 -! CHECK: fir.store %[[VAL_12]] to %[[VAL_7]] : !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop reduction(@add_reduction_f32 %[[VAL_1]] -> %[[VAL_7:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_8:.*]]) : i32 = (%[[VAL_4]]) to (%[[VAL_5]]) inclusive step (%[[VAL_6]]) { +! CHECK: fir.store %[[VAL_8]] to %[[VAL_3]] : !fir.ref +! CHECK: %[[VAL_9:.*]] = fir.load %[[VAL_7]] : !fir.ref +! CHECK: %[[VAL_10:.*]] = fir.load %[[VAL_3]] : !fir.ref +! CHECK: %[[VAL_11:.*]] = fir.convert %[[VAL_10]] : (i32) -> f32 +! CHECK: %[[VAL_12:.*]] = arith.addf %[[VAL_9]], %[[VAL_11]] fastmath : f32 +! CHECK: fir.store %[[VAL_12]] to %[[VAL_7]] : !fir.ref +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } @@ -127,13 +133,16 @@ end subroutine ! CHECK: %[[VAL_4:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_5:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_6:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@add_reduction_i32 %[[VAL_1]] -> %[[VAL_7:.*]] : !fir.ref) for (%[[VAL_8:.*]]) : i32 = (%[[VAL_4]]) to (%[[VAL_5]]) inclusive step (%[[VAL_6]]) { -! CHECK: fir.store %[[VAL_8]] to %[[VAL_3]] : !fir.ref -! CHECK: %[[VAL_9:.*]] = fir.load %[[VAL_3]] : !fir.ref -! CHECK: %[[VAL_10:.*]] = fir.load %[[VAL_7]] : !fir.ref -! CHECK: %[[VAL_11:.*]] = arith.addi %[[VAL_9]], %[[VAL_10]] : i32 -! CHECK: fir.store %[[VAL_11]] to %[[VAL_7]] : !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop reduction(@add_reduction_i32 %[[VAL_1]] -> %[[VAL_7:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_8:.*]]) : i32 = (%[[VAL_4]]) to (%[[VAL_5]]) inclusive step (%[[VAL_6]]) { +! CHECK: fir.store %[[VAL_8]] to %[[VAL_3]] : !fir.ref +! CHECK: %[[VAL_9:.*]] = fir.load %[[VAL_3]] : !fir.ref +! CHECK: %[[VAL_10:.*]] = fir.load %[[VAL_7]] : !fir.ref +! CHECK: %[[VAL_11:.*]] = arith.addi %[[VAL_9]], %[[VAL_10]] : i32 +! CHECK: fir.store %[[VAL_11]] to %[[VAL_7]] : !fir.ref +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } @@ -162,14 +171,17 @@ end subroutine ! CHECK: %[[VAL_4:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_5:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_6:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@add_reduction_f32 %[[VAL_1]] -> %[[VAL_7:.*]] : !fir.ref) for (%[[VAL_8:.*]]) : i32 = (%[[VAL_4]]) to (%[[VAL_5]]) inclusive step (%[[VAL_6]]) { -! CHECK: fir.store %[[VAL_8]] to %[[VAL_3]] : !fir.ref -! CHECK: %[[VAL_9:.*]] = fir.load %[[VAL_3]] : !fir.ref -! CHECK: %[[VAL_10:.*]] = fir.convert %[[VAL_9]] : (i32) -> f32 -! CHECK: %[[VAL_11:.*]] = fir.load %[[VAL_7]] : !fir.ref -! CHECK: %[[VAL_12:.*]] = arith.addf %[[VAL_10]], %[[VAL_11]] fastmath : f32 -! CHECK: fir.store %[[VAL_12]] to %[[VAL_7]] : !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop reduction(@add_reduction_f32 %[[VAL_1]] -> %[[VAL_7:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_8:.*]]) : i32 = (%[[VAL_4]]) to (%[[VAL_5]]) inclusive step (%[[VAL_6]]) { +! CHECK: fir.store %[[VAL_8]] to %[[VAL_3]] : !fir.ref +! CHECK: %[[VAL_9:.*]] = fir.load %[[VAL_3]] : !fir.ref +! CHECK: %[[VAL_10:.*]] = fir.convert %[[VAL_9]] : (i32) -> f32 +! CHECK: %[[VAL_11:.*]] = fir.load %[[VAL_7]] : !fir.ref +! CHECK: %[[VAL_12:.*]] = arith.addf %[[VAL_10]], %[[VAL_11]] fastmath : f32 +! CHECK: fir.store %[[VAL_12]] to %[[VAL_7]] : !fir.ref +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } @@ -204,21 +216,24 @@ end subroutine ! CHECK: %[[VAL_8:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_9:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_10:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@add_reduction_i32 %[[VAL_1]] -> %[[VAL_11:.*]] : !fir.ref, @add_reduction_i32 %[[VAL_2]] -> %[[VAL_12:.*]] : !fir.ref, @add_reduction_i32 %[[VAL_3]] -> %[[VAL_13:.*]] : !fir.ref) for (%[[VAL_14:.*]]) : i32 = (%[[VAL_8]]) to (%[[VAL_9]]) inclusive step (%[[VAL_10]]) { -! CHECK: fir.store %[[VAL_14]] to %[[VAL_7]] : !fir.ref -! CHECK: %[[VAL_15:.*]] = fir.load %[[VAL_11]] : !fir.ref -! CHECK: %[[VAL_16:.*]] = fir.load %[[VAL_7]] : !fir.ref -! CHECK: %[[VAL_17:.*]] = arith.addi %[[VAL_15]], %[[VAL_16]] : i32 -! CHECK: fir.store %[[VAL_17]] to %[[VAL_11]] : !fir.ref -! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_12]] : !fir.ref -! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_7]] : !fir.ref -! CHECK: %[[VAL_20:.*]] = arith.addi %[[VAL_18]], %[[VAL_19]] : i32 -! CHECK: fir.store %[[VAL_20]] to %[[VAL_12]] : !fir.ref -! CHECK: %[[VAL_21:.*]] = fir.load %[[VAL_13]] : !fir.ref -! CHECK: %[[VAL_22:.*]] = fir.load %[[VAL_7]] : !fir.ref -! CHECK: %[[VAL_23:.*]] = arith.addi %[[VAL_21]], %[[VAL_22]] : i32 -! CHECK: fir.store %[[VAL_23]] to %[[VAL_13]] : !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop reduction(@add_reduction_i32 %[[VAL_1]] -> %[[VAL_11:.*]] : !fir.ref, @add_reduction_i32 %[[VAL_2]] -> %[[VAL_12:.*]] : !fir.ref, @add_reduction_i32 %[[VAL_3]] -> %[[VAL_13:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_14:.*]]) : i32 = (%[[VAL_8]]) to (%[[VAL_9]]) inclusive step (%[[VAL_10]]) { +! CHECK: fir.store %[[VAL_14]] to %[[VAL_7]] : !fir.ref +! CHECK: %[[VAL_15:.*]] = fir.load %[[VAL_11]] : !fir.ref +! CHECK: %[[VAL_16:.*]] = fir.load %[[VAL_7]] : !fir.ref +! CHECK: %[[VAL_17:.*]] = arith.addi %[[VAL_15]], %[[VAL_16]] : i32 +! CHECK: fir.store %[[VAL_17]] to %[[VAL_11]] : !fir.ref +! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_12]] : !fir.ref +! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_7]] : !fir.ref +! CHECK: %[[VAL_20:.*]] = arith.addi %[[VAL_18]], %[[VAL_19]] : i32 +! CHECK: fir.store %[[VAL_20]] to %[[VAL_12]] : !fir.ref +! CHECK: %[[VAL_21:.*]] = fir.load %[[VAL_13]] : !fir.ref +! CHECK: %[[VAL_22:.*]] = fir.load %[[VAL_7]] : !fir.ref +! CHECK: %[[VAL_23:.*]] = arith.addi %[[VAL_21]], %[[VAL_22]] : i32 +! CHECK: fir.store %[[VAL_23]] to %[[VAL_13]] : !fir.ref +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } @@ -257,24 +272,27 @@ end subroutine ! CHECK: %[[VAL_8:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_9:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_10:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@add_reduction_f32 %[[VAL_1]] -> %[[VAL_11:.*]] : !fir.ref, @add_reduction_f32 %[[VAL_2]] -> %[[VAL_12:.*]] : !fir.ref, @add_reduction_f32 %[[VAL_3]] -> %[[VAL_13:.*]] : !fir.ref) for (%[[VAL_14:.*]]) : i32 = (%[[VAL_8]]) to (%[[VAL_9]]) inclusive step (%[[VAL_10]]) { -! CHECK: fir.store %[[VAL_14]] to %[[VAL_7]] : !fir.ref -! CHECK: %[[VAL_15:.*]] = fir.load %[[VAL_11]] : !fir.ref -! CHECK: %[[VAL_16:.*]] = fir.load %[[VAL_7]] : !fir.ref -! CHECK: %[[VAL_17:.*]] = fir.convert %[[VAL_16]] : (i32) -> f32 -! CHECK: %[[VAL_18:.*]] = arith.addf %[[VAL_15]], %[[VAL_17]] fastmath : f32 -! CHECK: fir.store %[[VAL_18]] to %[[VAL_11]] : !fir.ref -! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_12]] : !fir.ref -! CHECK: %[[VAL_20:.*]] = fir.load %[[VAL_7]] : !fir.ref -! CHECK: %[[VAL_21:.*]] = fir.convert %[[VAL_20]] : (i32) -> f32 -! CHECK: %[[VAL_22:.*]] = arith.addf %[[VAL_19]], %[[VAL_21]] fastmath : f32 -! CHECK: fir.store %[[VAL_22]] to %[[VAL_12]] : !fir.ref -! CHECK: %[[VAL_23:.*]] = fir.load %[[VAL_13]] : !fir.ref -! CHECK: %[[VAL_24:.*]] = fir.load %[[VAL_7]] : !fir.ref -! CHECK: %[[VAL_25:.*]] = fir.convert %[[VAL_24]] : (i32) -> f32 -! CHECK: %[[VAL_26:.*]] = arith.addf %[[VAL_23]], %[[VAL_25]] fastmath : f32 -! CHECK: fir.store %[[VAL_26]] to %[[VAL_13]] : !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop reduction(@add_reduction_f32 %[[VAL_1]] -> %[[VAL_11:.*]] : !fir.ref, @add_reduction_f32 %[[VAL_2]] -> %[[VAL_12:.*]] : !fir.ref, @add_reduction_f32 %[[VAL_3]] -> %[[VAL_13:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_14:.*]]) : i32 = (%[[VAL_8]]) to (%[[VAL_9]]) inclusive step (%[[VAL_10]]) { +! CHECK: fir.store %[[VAL_14]] to %[[VAL_7]] : !fir.ref +! CHECK: %[[VAL_15:.*]] = fir.load %[[VAL_11]] : !fir.ref +! CHECK: %[[VAL_16:.*]] = fir.load %[[VAL_7]] : !fir.ref +! CHECK: %[[VAL_17:.*]] = fir.convert %[[VAL_16]] : (i32) -> f32 +! CHECK: %[[VAL_18:.*]] = arith.addf %[[VAL_15]], %[[VAL_17]] fastmath : f32 +! CHECK: fir.store %[[VAL_18]] to %[[VAL_11]] : !fir.ref +! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_12]] : !fir.ref +! CHECK: %[[VAL_20:.*]] = fir.load %[[VAL_7]] : !fir.ref +! CHECK: %[[VAL_21:.*]] = fir.convert %[[VAL_20]] : (i32) -> f32 +! CHECK: %[[VAL_22:.*]] = arith.addf %[[VAL_19]], %[[VAL_21]] fastmath : f32 +! CHECK: fir.store %[[VAL_22]] to %[[VAL_12]] : !fir.ref +! CHECK: %[[VAL_23:.*]] = fir.load %[[VAL_13]] : !fir.ref +! CHECK: %[[VAL_24:.*]] = fir.load %[[VAL_7]] : !fir.ref +! CHECK: %[[VAL_25:.*]] = fir.convert %[[VAL_24]] : (i32) -> f32 +! CHECK: %[[VAL_26:.*]] = arith.addf %[[VAL_23]], %[[VAL_25]] fastmath : f32 +! CHECK: fir.store %[[VAL_26]] to %[[VAL_13]] : !fir.ref +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } @@ -316,28 +334,31 @@ end subroutine ! CHECK: %[[VAL_10:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_11:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_12:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@add_reduction_i32 %[[VAL_2]] -> %[[VAL_13:.*]] : !fir.ref, @add_reduction_i64 %[[VAL_3]] -> %[[VAL_14:.*]] : !fir.ref, @add_reduction_f32 %[[VAL_4]] -> %[[VAL_15:.*]] : !fir.ref, @add_reduction_f64 %[[VAL_1]] -> %[[VAL_16:.*]] : !fir.ref) for (%[[VAL_17:.*]]) : i32 = (%[[VAL_10]]) to (%[[VAL_11]]) inclusive step (%[[VAL_12]]) { -! CHECK: fir.store %[[VAL_17]] to %[[VAL_9]] : !fir.ref -! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_13]] : !fir.ref -! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_9]] : !fir.ref -! CHECK: %[[VAL_20:.*]] = arith.addi %[[VAL_18]], %[[VAL_19]] : i32 -! CHECK: fir.store %[[VAL_20]] to %[[VAL_13]] : !fir.ref -! CHECK: %[[VAL_21:.*]] = fir.load %[[VAL_14]] : !fir.ref -! CHECK: %[[VAL_22:.*]] = fir.load %[[VAL_9]] : !fir.ref -! CHECK: %[[VAL_23:.*]] = fir.convert %[[VAL_22]] : (i32) -> i64 -! CHECK: %[[VAL_24:.*]] = arith.addi %[[VAL_21]], %[[VAL_23]] : i64 -! CHECK: fir.store %[[VAL_24]] to %[[VAL_14]] : !fir.ref -! CHECK: %[[VAL_25:.*]] = fir.load %[[VAL_15]] : !fir.ref -! CHECK: %[[VAL_26:.*]] = fir.load %[[VAL_9]] : !fir.ref -! CHECK: %[[VAL_27:.*]] = fir.convert %[[VAL_26]] : (i32) -> f32 -! CHECK: %[[VAL_28:.*]] = arith.addf %[[VAL_25]], %[[VAL_27]] fastmath : f32 -! CHECK: fir.store %[[VAL_28]] to %[[VAL_15]] : !fir.ref -! CHECK: %[[VAL_29:.*]] = fir.load %[[VAL_16]] : !fir.ref -! CHECK: %[[VAL_30:.*]] = fir.load %[[VAL_9]] : !fir.ref -! CHECK: %[[VAL_31:.*]] = fir.convert %[[VAL_30]] : (i32) -> f64 -! CHECK: %[[VAL_32:.*]] = arith.addf %[[VAL_29]], %[[VAL_31]] fastmath : f64 -! CHECK: fir.store %[[VAL_32]] to %[[VAL_16]] : !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop reduction(@add_reduction_i32 %[[VAL_2]] -> %[[VAL_13:.*]] : !fir.ref, @add_reduction_i64 %[[VAL_3]] -> %[[VAL_14:.*]] : !fir.ref, @add_reduction_f32 %[[VAL_4]] -> %[[VAL_15:.*]] : !fir.ref, @add_reduction_f64 %[[VAL_1]] -> %[[VAL_16:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_17:.*]]) : i32 = (%[[VAL_10]]) to (%[[VAL_11]]) inclusive step (%[[VAL_12]]) { +! CHECK: fir.store %[[VAL_17]] to %[[VAL_9]] : !fir.ref +! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_13]] : !fir.ref +! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_9]] : !fir.ref +! CHECK: %[[VAL_20:.*]] = arith.addi %[[VAL_18]], %[[VAL_19]] : i32 +! CHECK: fir.store %[[VAL_20]] to %[[VAL_13]] : !fir.ref +! CHECK: %[[VAL_21:.*]] = fir.load %[[VAL_14]] : !fir.ref +! CHECK: %[[VAL_22:.*]] = fir.load %[[VAL_9]] : !fir.ref +! CHECK: %[[VAL_23:.*]] = fir.convert %[[VAL_22]] : (i32) -> i64 +! CHECK: %[[VAL_24:.*]] = arith.addi %[[VAL_21]], %[[VAL_23]] : i64 +! CHECK: fir.store %[[VAL_24]] to %[[VAL_14]] : !fir.ref +! CHECK: %[[VAL_25:.*]] = fir.load %[[VAL_15]] : !fir.ref +! CHECK: %[[VAL_26:.*]] = fir.load %[[VAL_9]] : !fir.ref +! CHECK: %[[VAL_27:.*]] = fir.convert %[[VAL_26]] : (i32) -> f32 +! CHECK: %[[VAL_28:.*]] = arith.addf %[[VAL_25]], %[[VAL_27]] fastmath : f32 +! CHECK: fir.store %[[VAL_28]] to %[[VAL_15]] : !fir.ref +! CHECK: %[[VAL_29:.*]] = fir.load %[[VAL_16]] : !fir.ref +! CHECK: %[[VAL_30:.*]] = fir.load %[[VAL_9]] : !fir.ref +! CHECK: %[[VAL_31:.*]] = fir.convert %[[VAL_30]] : (i32) -> f64 +! CHECK: %[[VAL_32:.*]] = arith.addf %[[VAL_29]], %[[VAL_31]] fastmath : f64 +! CHECK: fir.store %[[VAL_32]] to %[[VAL_16]] : !fir.ref +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } diff --git a/flang/test/Lower/OpenMP/FIR/wsloop-reduction-iand-byref.f90 b/flang/test/Lower/OpenMP/FIR/wsloop-reduction-iand-byref.f90 index 6717597ff3b04d8f85c3b41b48d9145f848bb1fb..b25ab84f60fe916aefbf68fc93f168b858ad39bb 100644 --- a/flang/test/Lower/OpenMP/FIR/wsloop-reduction-iand-byref.f90 +++ b/flang/test/Lower/OpenMP/FIR/wsloop-reduction-iand-byref.f90 @@ -23,7 +23,8 @@ !CHECK-SAME: %[[Y_BOX:.*]]: !fir.box> !CHECK: %[[X_REF:.*]] = fir.alloca i32 {bindc_name = "x", uniq_name = "_QFreduction_iandEx"} !CHECK: omp.parallel -!CHECK: omp.wsloop byref reduction(@iand_byref_i32 %[[X_REF]] -> %[[PRV:.+]] : !fir.ref) for +!CHECK: omp.wsloop byref reduction(@iand_byref_i32 %[[X_REF]] -> %[[PRV:.+]] : !fir.ref) +!CHECK-NEXT: omp.loop_nest !CHECK: %[[LPRV:.+]] = fir.load %[[PRV]] : !fir.ref !CHECK: %[[Y_I_REF:.*]] = fir.coordinate_of %[[Y_BOX]] !CHECK: %[[Y_I:.*]] = fir.load %[[Y_I_REF]] : !fir.ref @@ -31,6 +32,7 @@ !CHECK: fir.store %[[RES]] to %[[PRV]] : !fir.ref !CHECK: omp.yield !CHECK: omp.terminator +!CHECK: omp.terminator subroutine reduction_iand(y) integer :: x, y(:) diff --git a/flang/test/Lower/OpenMP/FIR/wsloop-reduction-iand.f90 b/flang/test/Lower/OpenMP/FIR/wsloop-reduction-iand.f90 index 9bc45f9f3a0d870af97e7d72ddcdc6792f02cd89..dfc140d7d5f61925b8f1b1d0f493b56c3fd8119e 100644 --- a/flang/test/Lower/OpenMP/FIR/wsloop-reduction-iand.f90 +++ b/flang/test/Lower/OpenMP/FIR/wsloop-reduction-iand.f90 @@ -13,7 +13,8 @@ !CHECK-SAME: %[[Y_BOX:.*]]: !fir.box> !CHECK: %[[X_REF:.*]] = fir.alloca i32 {bindc_name = "x", uniq_name = "_QFreduction_iandEx"} !CHECK: omp.parallel -!CHECK: omp.wsloop reduction(@[[IAND_DECLARE_I]] %[[X_REF]] -> %[[PRV:.+]] : !fir.ref) for +!CHECK: omp.wsloop reduction(@[[IAND_DECLARE_I]] %[[X_REF]] -> %[[PRV:.+]] : !fir.ref) +!CHECK-NEXT: omp.loop_nest !CHECK: %[[LPRV:.+]] = fir.load %[[PRV]] : !fir.ref !CHECK: %[[Y_I_REF:.*]] = fir.coordinate_of %[[Y_BOX]] !CHECK: %[[Y_I:.*]] = fir.load %[[Y_I_REF]] : !fir.ref @@ -21,6 +22,7 @@ !CHECK: fir.store %[[RES]] to %[[PRV]] : !fir.ref !CHECK: omp.yield !CHECK: omp.terminator +!CHECK: omp.terminator subroutine reduction_iand(y) integer :: x, y(:) diff --git a/flang/test/Lower/OpenMP/FIR/wsloop-reduction-ieor-byref.f90 b/flang/test/Lower/OpenMP/FIR/wsloop-reduction-ieor-byref.f90 index 1baa59a510fa11cf3984a3617da30ba25f7ad075..56eb087bae5a0801b832b5f68bcfa5398e01af23 100644 --- a/flang/test/Lower/OpenMP/FIR/wsloop-reduction-ieor-byref.f90 +++ b/flang/test/Lower/OpenMP/FIR/wsloop-reduction-ieor-byref.f90 @@ -22,7 +22,8 @@ !CHECK-SAME: %[[Y_BOX:.*]]: !fir.box> !CHECK: %[[X_REF:.*]] = fir.alloca i32 {bindc_name = "x", uniq_name = "_QFreduction_ieorEx"} !CHECK: omp.parallel -!CHECK: omp.wsloop byref reduction(@ieor_byref_i32 %[[X_REF]] -> %[[PRV:.+]] : !fir.ref) for +!CHECK: omp.wsloop byref reduction(@ieor_byref_i32 %[[X_REF]] -> %[[PRV:.+]] : !fir.ref) +!CHECK-NEXT: omp.loop_nest !CHECK: %[[LPRV:.+]] = fir.load %[[PRV]] : !fir.ref !CHECK: %[[Y_I_REF:.*]] = fir.coordinate_of %[[Y_BOX]] !CHECK: %[[Y_I:.*]] = fir.load %[[Y_I_REF]] : !fir.ref @@ -30,6 +31,7 @@ !CHECK: fir.store %[[RES]] to %[[PRV]] : !fir.ref !CHECK: omp.yield !CHECK: omp.terminator +!CHECK: omp.terminator subroutine reduction_ieor(y) integer :: x, y(:) diff --git a/flang/test/Lower/OpenMP/FIR/wsloop-reduction-ieor.f90 b/flang/test/Lower/OpenMP/FIR/wsloop-reduction-ieor.f90 index 9c07d5ee20873b2a15f649f0d7854bc7cfeadfb1..1ddf82b828cb016d49aafb84dec5d03e8b88d937 100644 --- a/flang/test/Lower/OpenMP/FIR/wsloop-reduction-ieor.f90 +++ b/flang/test/Lower/OpenMP/FIR/wsloop-reduction-ieor.f90 @@ -13,7 +13,8 @@ !CHECK-SAME: %[[Y_BOX:.*]]: !fir.box> !CHECK: %[[X_REF:.*]] = fir.alloca i32 {bindc_name = "x", uniq_name = "_QFreduction_ieorEx"} !CHECK: omp.parallel -!CHECK: omp.wsloop reduction(@[[IEOR_DECLARE_I]] %[[X_REF]] -> %[[PRV:.+]] : !fir.ref) for +!CHECK: omp.wsloop reduction(@[[IEOR_DECLARE_I]] %[[X_REF]] -> %[[PRV:.+]] : !fir.ref) +!CHECK-NEXT: omp.loop_nest !CHECK: %[[LPRV:.+]] = fir.load %[[PRV]] : !fir.ref !CHECK: %[[Y_I_REF:.*]] = fir.coordinate_of %[[Y_BOX]] !CHECK: %[[Y_I:.*]] = fir.load %[[Y_I_REF]] : !fir.ref @@ -21,6 +22,7 @@ !CHECK: fir.store %[[RES]] to %[[PRV]] : !fir.ref !CHECK: omp.yield !CHECK: omp.terminator +!CHECK: omp.terminator subroutine reduction_ieor(y) integer :: x, y(:) diff --git a/flang/test/Lower/OpenMP/FIR/wsloop-reduction-ior-byref.f90 b/flang/test/Lower/OpenMP/FIR/wsloop-reduction-ior-byref.f90 index 5482ef33fc8aa926c37e9c21bf11a58a00559b01..e761d24cd303b6ade2f5cbb7806918f130ebabc6 100644 --- a/flang/test/Lower/OpenMP/FIR/wsloop-reduction-ior-byref.f90 +++ b/flang/test/Lower/OpenMP/FIR/wsloop-reduction-ior-byref.f90 @@ -22,7 +22,8 @@ !CHECK-SAME: %[[Y_BOX:.*]]: !fir.box> !CHECK: %[[X_REF:.*]] = fir.alloca i32 {bindc_name = "x", uniq_name = "_QFreduction_iorEx"} !CHECK: omp.parallel -!CHECK: omp.wsloop byref reduction(@ior_byref_i32 %[[X_REF]] -> %[[PRV:.+]] : !fir.ref) for +!CHECK: omp.wsloop byref reduction(@ior_byref_i32 %[[X_REF]] -> %[[PRV:.+]] : !fir.ref) +!CHECK-NEXT: omp.loop_nest !CHECK: %[[LPRV:.+]] = fir.load %[[PRV]] : !fir.ref !CHECK: %[[Y_I_REF:.*]] = fir.coordinate_of %[[Y_BOX]] !CHECK: %[[Y_I:.*]] = fir.load %[[Y_I_REF]] : !fir.ref @@ -30,6 +31,7 @@ !CHECK: fir.store %[[RES]] to %[[PRV]] : !fir.ref !CHECK: omp.yield !CHECK: omp.terminator +!CHECK: omp.terminator subroutine reduction_ior(y) integer :: x, y(:) diff --git a/flang/test/Lower/OpenMP/FIR/wsloop-reduction-ior.f90 b/flang/test/Lower/OpenMP/FIR/wsloop-reduction-ior.f90 index 79cc8b2d892275dac4c813eae8996c3fd270e732..148dbc909babe921d4791f2eb91eda6dffc22f78 100644 --- a/flang/test/Lower/OpenMP/FIR/wsloop-reduction-ior.f90 +++ b/flang/test/Lower/OpenMP/FIR/wsloop-reduction-ior.f90 @@ -13,7 +13,8 @@ !CHECK-SAME: %[[Y_BOX:.*]]: !fir.box> !CHECK: %[[X_REF:.*]] = fir.alloca i32 {bindc_name = "x", uniq_name = "_QFreduction_iorEx"} !CHECK: omp.parallel -!CHECK: omp.wsloop reduction(@[[IOR_DECLARE_I]] %[[X_REF]] -> %[[PRV:.+]] : !fir.ref) for +!CHECK: omp.wsloop reduction(@[[IOR_DECLARE_I]] %[[X_REF]] -> %[[PRV:.+]] : !fir.ref) +!CHECK-NEXT: omp.loop_nest !CHECK: %[[LPRV:.+]] = fir.load %[[PRV]] : !fir.ref !CHECK: %[[Y_I_REF:.*]] = fir.coordinate_of %[[Y_BOX]] !CHECK: %[[Y_I:.*]] = fir.load %[[Y_I_REF]] : !fir.ref @@ -21,6 +22,7 @@ !CHECK: fir.store %[[RES]] to %[[PRV]] : !fir.ref !CHECK: omp.yield !CHECK: omp.terminator +!CHECK: omp.terminator subroutine reduction_ior(y) integer :: x, y(:) diff --git a/flang/test/Lower/OpenMP/FIR/wsloop-reduction-logical-eqv-byref.f90 b/flang/test/Lower/OpenMP/FIR/wsloop-reduction-logical-eqv-byref.f90 index 696ff68b2059cd1b00d7e69657ecf9bf5368b848..17cd02a0ca7ff7bbae85fc96d83b8212b17353c0 100644 --- a/flang/test/Lower/OpenMP/FIR/wsloop-reduction-logical-eqv-byref.f90 +++ b/flang/test/Lower/OpenMP/FIR/wsloop-reduction-logical-eqv-byref.f90 @@ -36,21 +36,23 @@ ! CHECK: %[[VAL_6:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_7:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_8:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@eqv_reduction %[[VAL_2]] -> %[[VAL_9:.*]] : !fir.ref>) for (%[[VAL_10:.*]]) : i32 = (%[[VAL_6]]) to (%[[VAL_7]]) inclusive step (%[[VAL_8]]) { -! CHECK: fir.store %[[VAL_10]] to %[[VAL_5]] : !fir.ref -! CHECK: %[[VAL_11:.*]] = fir.load %[[VAL_9]] : !fir.ref> -! CHECK: %[[VAL_12:.*]] = fir.load %[[VAL_5]] : !fir.ref -! CHECK: %[[VAL_13:.*]] = fir.convert %[[VAL_12]] : (i32) -> i64 -! CHECK: %[[VAL_14:.*]] = arith.constant 1 : i64 -! CHECK: %[[VAL_15:.*]] = arith.subi %[[VAL_13]], %[[VAL_14]] : i64 -! CHECK: %[[VAL_16:.*]] = fir.coordinate_of %[[VAL_0]], %[[VAL_15]] : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_17:.*]] = fir.load %[[VAL_16]] : !fir.ref> -! CHECK: %[[VAL_18:.*]] = fir.convert %[[VAL_11]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_19:.*]] = fir.convert %[[VAL_17]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_20:.*]] = arith.cmpi eq, %[[VAL_18]], %[[VAL_19]] : i1 -! CHECK: %[[VAL_21:.*]] = fir.convert %[[VAL_20]] : (i1) -> !fir.logical<4> -! CHECK: fir.store %[[VAL_21]] to %[[VAL_9]] : !fir.ref> -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@eqv_reduction %[[VAL_2]] -> %[[VAL_9:.*]] : !fir.ref>) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_10:.*]]) : i32 = (%[[VAL_6]]) to (%[[VAL_7]]) inclusive step (%[[VAL_8]]) { +! CHECK: fir.store %[[VAL_10]] to %[[VAL_5]] : !fir.ref +! CHECK: %[[VAL_11:.*]] = fir.load %[[VAL_9]] : !fir.ref> +! CHECK: %[[VAL_12:.*]] = fir.load %[[VAL_5]] : !fir.ref +! CHECK: %[[VAL_13:.*]] = fir.convert %[[VAL_12]] : (i32) -> i64 +! CHECK: %[[VAL_14:.*]] = arith.constant 1 : i64 +! CHECK: %[[VAL_15:.*]] = arith.subi %[[VAL_13]], %[[VAL_14]] : i64 +! CHECK: %[[VAL_16:.*]] = fir.coordinate_of %[[VAL_0]], %[[VAL_15]] : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_17:.*]] = fir.load %[[VAL_16]] : !fir.ref> +! CHECK: %[[VAL_18:.*]] = fir.convert %[[VAL_11]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_19:.*]] = fir.convert %[[VAL_17]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_20:.*]] = arith.cmpi eq, %[[VAL_18]], %[[VAL_19]] : i1 +! CHECK: %[[VAL_21:.*]] = fir.convert %[[VAL_20]] : (i1) -> !fir.logical<4> +! CHECK: fir.store %[[VAL_21]] to %[[VAL_9]] : !fir.ref> +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return @@ -78,21 +80,23 @@ end subroutine ! CHECK: %[[VAL_6:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_7:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_8:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@eqv_reduction %[[VAL_2]] -> %[[VAL_9:.*]] : !fir.ref>) for (%[[VAL_10:.*]]) : i32 = (%[[VAL_6]]) to (%[[VAL_7]]) inclusive step (%[[VAL_8]]) { -! CHECK: fir.store %[[VAL_10]] to %[[VAL_5]] : !fir.ref -! CHECK: %[[VAL_11:.*]] = fir.load %[[VAL_5]] : !fir.ref -! CHECK: %[[VAL_12:.*]] = fir.convert %[[VAL_11]] : (i32) -> i64 -! CHECK: %[[VAL_13:.*]] = arith.constant 1 : i64 -! CHECK: %[[VAL_14:.*]] = arith.subi %[[VAL_12]], %[[VAL_13]] : i64 -! CHECK: %[[VAL_15:.*]] = fir.coordinate_of %[[VAL_0]], %[[VAL_14]] : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_16:.*]] = fir.load %[[VAL_15]] : !fir.ref> -! CHECK: %[[VAL_17:.*]] = fir.load %[[VAL_9]] : !fir.ref> -! CHECK: %[[VAL_18:.*]] = fir.convert %[[VAL_16]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_19:.*]] = fir.convert %[[VAL_17]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_20:.*]] = arith.cmpi eq, %[[VAL_18]], %[[VAL_19]] : i1 -! CHECK: %[[VAL_21:.*]] = fir.convert %[[VAL_20]] : (i1) -> !fir.logical<4> -! CHECK: fir.store %[[VAL_21]] to %[[VAL_9]] : !fir.ref> -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@eqv_reduction %[[VAL_2]] -> %[[VAL_9:.*]] : !fir.ref>) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_10:.*]]) : i32 = (%[[VAL_6]]) to (%[[VAL_7]]) inclusive step (%[[VAL_8]]) { +! CHECK: fir.store %[[VAL_10]] to %[[VAL_5]] : !fir.ref +! CHECK: %[[VAL_11:.*]] = fir.load %[[VAL_5]] : !fir.ref +! CHECK: %[[VAL_12:.*]] = fir.convert %[[VAL_11]] : (i32) -> i64 +! CHECK: %[[VAL_13:.*]] = arith.constant 1 : i64 +! CHECK: %[[VAL_14:.*]] = arith.subi %[[VAL_12]], %[[VAL_13]] : i64 +! CHECK: %[[VAL_15:.*]] = fir.coordinate_of %[[VAL_0]], %[[VAL_14]] : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_16:.*]] = fir.load %[[VAL_15]] : !fir.ref> +! CHECK: %[[VAL_17:.*]] = fir.load %[[VAL_9]] : !fir.ref> +! CHECK: %[[VAL_18:.*]] = fir.convert %[[VAL_16]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_19:.*]] = fir.convert %[[VAL_17]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_20:.*]] = arith.cmpi eq, %[[VAL_18]], %[[VAL_19]] : i1 +! CHECK: %[[VAL_21:.*]] = fir.convert %[[VAL_20]] : (i1) -> !fir.logical<4> +! CHECK: fir.store %[[VAL_21]] to %[[VAL_9]] : !fir.ref> +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return @@ -128,45 +132,47 @@ end subroutine ! CHECK: %[[VAL_12:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_13:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_14:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@eqv_reduction %[[VAL_2]] -> %[[VAL_15:.*]] : !fir.ref>, @eqv_reduction %[[VAL_3]] -> %[[VAL_16:.*]] : !fir.ref>, @eqv_reduction %[[VAL_4]] -> %[[VAL_17:.*]] : !fir.ref>) for (%[[VAL_18:.*]]) : i32 = (%[[VAL_12]]) to (%[[VAL_13]]) inclusive step (%[[VAL_14]]) { -! CHECK: fir.store %[[VAL_18]] to %[[VAL_11]] : !fir.ref -! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_15]] : !fir.ref> -! CHECK: %[[VAL_20:.*]] = fir.load %[[VAL_11]] : !fir.ref -! CHECK: %[[VAL_21:.*]] = fir.convert %[[VAL_20]] : (i32) -> i64 -! CHECK: %[[VAL_22:.*]] = arith.constant 1 : i64 -! CHECK: %[[VAL_23:.*]] = arith.subi %[[VAL_21]], %[[VAL_22]] : i64 -! CHECK: %[[VAL_24:.*]] = fir.coordinate_of %[[VAL_0]], %[[VAL_23]] : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_25:.*]] = fir.load %[[VAL_24]] : !fir.ref> -! CHECK: %[[VAL_26:.*]] = fir.convert %[[VAL_19]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_27:.*]] = fir.convert %[[VAL_25]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_28:.*]] = arith.cmpi eq, %[[VAL_26]], %[[VAL_27]] : i1 -! CHECK: %[[VAL_29:.*]] = fir.convert %[[VAL_28]] : (i1) -> !fir.logical<4> -! CHECK: fir.store %[[VAL_29]] to %[[VAL_15]] : !fir.ref> -! CHECK: %[[VAL_30:.*]] = fir.load %[[VAL_16]] : !fir.ref> -! CHECK: %[[VAL_31:.*]] = fir.load %[[VAL_11]] : !fir.ref -! CHECK: %[[VAL_32:.*]] = fir.convert %[[VAL_31]] : (i32) -> i64 -! CHECK: %[[VAL_33:.*]] = arith.constant 1 : i64 -! CHECK: %[[VAL_34:.*]] = arith.subi %[[VAL_32]], %[[VAL_33]] : i64 -! CHECK: %[[VAL_35:.*]] = fir.coordinate_of %[[VAL_0]], %[[VAL_34]] : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_36:.*]] = fir.load %[[VAL_35]] : !fir.ref> -! CHECK: %[[VAL_37:.*]] = fir.convert %[[VAL_30]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_38:.*]] = fir.convert %[[VAL_36]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_39:.*]] = arith.cmpi eq, %[[VAL_37]], %[[VAL_38]] : i1 -! CHECK: %[[VAL_40:.*]] = fir.convert %[[VAL_39]] : (i1) -> !fir.logical<4> -! CHECK: fir.store %[[VAL_40]] to %[[VAL_16]] : !fir.ref> -! CHECK: %[[VAL_41:.*]] = fir.load %[[VAL_17]] : !fir.ref> -! CHECK: %[[VAL_42:.*]] = fir.load %[[VAL_11]] : !fir.ref -! CHECK: %[[VAL_43:.*]] = fir.convert %[[VAL_42]] : (i32) -> i64 -! CHECK: %[[VAL_44:.*]] = arith.constant 1 : i64 -! CHECK: %[[VAL_45:.*]] = arith.subi %[[VAL_43]], %[[VAL_44]] : i64 -! CHECK: %[[VAL_46:.*]] = fir.coordinate_of %[[VAL_0]], %[[VAL_45]] : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_47:.*]] = fir.load %[[VAL_46]] : !fir.ref> -! CHECK: %[[VAL_48:.*]] = fir.convert %[[VAL_41]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_49:.*]] = fir.convert %[[VAL_47]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_50:.*]] = arith.cmpi eq, %[[VAL_48]], %[[VAL_49]] : i1 -! CHECK: %[[VAL_51:.*]] = fir.convert %[[VAL_50]] : (i1) -> !fir.logical<4> -! CHECK: fir.store %[[VAL_51]] to %[[VAL_17]] : !fir.ref> -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@eqv_reduction %[[VAL_2]] -> %[[VAL_15:.*]] : !fir.ref>, @eqv_reduction %[[VAL_3]] -> %[[VAL_16:.*]] : !fir.ref>, @eqv_reduction %[[VAL_4]] -> %[[VAL_17:.*]] : !fir.ref>) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_18:.*]]) : i32 = (%[[VAL_12]]) to (%[[VAL_13]]) inclusive step (%[[VAL_14]]) { +! CHECK: fir.store %[[VAL_18]] to %[[VAL_11]] : !fir.ref +! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_15]] : !fir.ref> +! CHECK: %[[VAL_20:.*]] = fir.load %[[VAL_11]] : !fir.ref +! CHECK: %[[VAL_21:.*]] = fir.convert %[[VAL_20]] : (i32) -> i64 +! CHECK: %[[VAL_22:.*]] = arith.constant 1 : i64 +! CHECK: %[[VAL_23:.*]] = arith.subi %[[VAL_21]], %[[VAL_22]] : i64 +! CHECK: %[[VAL_24:.*]] = fir.coordinate_of %[[VAL_0]], %[[VAL_23]] : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_25:.*]] = fir.load %[[VAL_24]] : !fir.ref> +! CHECK: %[[VAL_26:.*]] = fir.convert %[[VAL_19]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_27:.*]] = fir.convert %[[VAL_25]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_28:.*]] = arith.cmpi eq, %[[VAL_26]], %[[VAL_27]] : i1 +! CHECK: %[[VAL_29:.*]] = fir.convert %[[VAL_28]] : (i1) -> !fir.logical<4> +! CHECK: fir.store %[[VAL_29]] to %[[VAL_15]] : !fir.ref> +! CHECK: %[[VAL_30:.*]] = fir.load %[[VAL_16]] : !fir.ref> +! CHECK: %[[VAL_31:.*]] = fir.load %[[VAL_11]] : !fir.ref +! CHECK: %[[VAL_32:.*]] = fir.convert %[[VAL_31]] : (i32) -> i64 +! CHECK: %[[VAL_33:.*]] = arith.constant 1 : i64 +! CHECK: %[[VAL_34:.*]] = arith.subi %[[VAL_32]], %[[VAL_33]] : i64 +! CHECK: %[[VAL_35:.*]] = fir.coordinate_of %[[VAL_0]], %[[VAL_34]] : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_36:.*]] = fir.load %[[VAL_35]] : !fir.ref> +! CHECK: %[[VAL_37:.*]] = fir.convert %[[VAL_30]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_38:.*]] = fir.convert %[[VAL_36]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_39:.*]] = arith.cmpi eq, %[[VAL_37]], %[[VAL_38]] : i1 +! CHECK: %[[VAL_40:.*]] = fir.convert %[[VAL_39]] : (i1) -> !fir.logical<4> +! CHECK: fir.store %[[VAL_40]] to %[[VAL_16]] : !fir.ref> +! CHECK: %[[VAL_41:.*]] = fir.load %[[VAL_17]] : !fir.ref> +! CHECK: %[[VAL_42:.*]] = fir.load %[[VAL_11]] : !fir.ref +! CHECK: %[[VAL_43:.*]] = fir.convert %[[VAL_42]] : (i32) -> i64 +! CHECK: %[[VAL_44:.*]] = arith.constant 1 : i64 +! CHECK: %[[VAL_45:.*]] = arith.subi %[[VAL_43]], %[[VAL_44]] : i64 +! CHECK: %[[VAL_46:.*]] = fir.coordinate_of %[[VAL_0]], %[[VAL_45]] : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_47:.*]] = fir.load %[[VAL_46]] : !fir.ref> +! CHECK: %[[VAL_48:.*]] = fir.convert %[[VAL_41]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_49:.*]] = fir.convert %[[VAL_47]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_50:.*]] = arith.cmpi eq, %[[VAL_48]], %[[VAL_49]] : i1 +! CHECK: %[[VAL_51:.*]] = fir.convert %[[VAL_50]] : (i1) -> !fir.logical<4> +! CHECK: fir.store %[[VAL_51]] to %[[VAL_17]] : !fir.ref> +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return diff --git a/flang/test/Lower/OpenMP/FIR/wsloop-reduction-logical-eqv.f90 b/flang/test/Lower/OpenMP/FIR/wsloop-reduction-logical-eqv.f90 index 6dcb3952655eabd2c3a5be7815abfe63715a31a5..e714e45540c393fb392608e9a97552264f37dcce 100644 --- a/flang/test/Lower/OpenMP/FIR/wsloop-reduction-logical-eqv.f90 +++ b/flang/test/Lower/OpenMP/FIR/wsloop-reduction-logical-eqv.f90 @@ -30,21 +30,23 @@ ! CHECK: %[[VAL_6:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_7:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_8:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@eqv_reduction %[[VAL_2]] -> %[[VAL_9:.*]] : !fir.ref>) for (%[[VAL_10:.*]]) : i32 = (%[[VAL_6]]) to (%[[VAL_7]]) inclusive step (%[[VAL_8]]) { -! CHECK: fir.store %[[VAL_10]] to %[[VAL_5]] : !fir.ref -! CHECK: %[[VAL_11:.*]] = fir.load %[[VAL_9]] : !fir.ref> -! CHECK: %[[VAL_12:.*]] = fir.load %[[VAL_5]] : !fir.ref -! CHECK: %[[VAL_13:.*]] = fir.convert %[[VAL_12]] : (i32) -> i64 -! CHECK: %[[VAL_14:.*]] = arith.constant 1 : i64 -! CHECK: %[[VAL_15:.*]] = arith.subi %[[VAL_13]], %[[VAL_14]] : i64 -! CHECK: %[[VAL_16:.*]] = fir.coordinate_of %[[VAL_0]], %[[VAL_15]] : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_17:.*]] = fir.load %[[VAL_16]] : !fir.ref> -! CHECK: %[[VAL_18:.*]] = fir.convert %[[VAL_11]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_19:.*]] = fir.convert %[[VAL_17]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_20:.*]] = arith.cmpi eq, %[[VAL_18]], %[[VAL_19]] : i1 -! CHECK: %[[VAL_21:.*]] = fir.convert %[[VAL_20]] : (i1) -> !fir.logical<4> -! CHECK: fir.store %[[VAL_21]] to %[[VAL_9]] : !fir.ref> -! CHECK: omp.yield +! CHECK: omp.wsloop reduction(@eqv_reduction %[[VAL_2]] -> %[[VAL_9:.*]] : !fir.ref>) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_10:.*]]) : i32 = (%[[VAL_6]]) to (%[[VAL_7]]) inclusive step (%[[VAL_8]]) { +! CHECK: fir.store %[[VAL_10]] to %[[VAL_5]] : !fir.ref +! CHECK: %[[VAL_11:.*]] = fir.load %[[VAL_9]] : !fir.ref> +! CHECK: %[[VAL_12:.*]] = fir.load %[[VAL_5]] : !fir.ref +! CHECK: %[[VAL_13:.*]] = fir.convert %[[VAL_12]] : (i32) -> i64 +! CHECK: %[[VAL_14:.*]] = arith.constant 1 : i64 +! CHECK: %[[VAL_15:.*]] = arith.subi %[[VAL_13]], %[[VAL_14]] : i64 +! CHECK: %[[VAL_16:.*]] = fir.coordinate_of %[[VAL_0]], %[[VAL_15]] : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_17:.*]] = fir.load %[[VAL_16]] : !fir.ref> +! CHECK: %[[VAL_18:.*]] = fir.convert %[[VAL_11]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_19:.*]] = fir.convert %[[VAL_17]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_20:.*]] = arith.cmpi eq, %[[VAL_18]], %[[VAL_19]] : i1 +! CHECK: %[[VAL_21:.*]] = fir.convert %[[VAL_20]] : (i1) -> !fir.logical<4> +! CHECK: fir.store %[[VAL_21]] to %[[VAL_9]] : !fir.ref> +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return @@ -72,21 +74,23 @@ end subroutine ! CHECK: %[[VAL_6:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_7:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_8:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@eqv_reduction %[[VAL_2]] -> %[[VAL_9:.*]] : !fir.ref>) for (%[[VAL_10:.*]]) : i32 = (%[[VAL_6]]) to (%[[VAL_7]]) inclusive step (%[[VAL_8]]) { -! CHECK: fir.store %[[VAL_10]] to %[[VAL_5]] : !fir.ref -! CHECK: %[[VAL_11:.*]] = fir.load %[[VAL_5]] : !fir.ref -! CHECK: %[[VAL_12:.*]] = fir.convert %[[VAL_11]] : (i32) -> i64 -! CHECK: %[[VAL_13:.*]] = arith.constant 1 : i64 -! CHECK: %[[VAL_14:.*]] = arith.subi %[[VAL_12]], %[[VAL_13]] : i64 -! CHECK: %[[VAL_15:.*]] = fir.coordinate_of %[[VAL_0]], %[[VAL_14]] : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_16:.*]] = fir.load %[[VAL_15]] : !fir.ref> -! CHECK: %[[VAL_17:.*]] = fir.load %[[VAL_9]] : !fir.ref> -! CHECK: %[[VAL_18:.*]] = fir.convert %[[VAL_16]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_19:.*]] = fir.convert %[[VAL_17]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_20:.*]] = arith.cmpi eq, %[[VAL_18]], %[[VAL_19]] : i1 -! CHECK: %[[VAL_21:.*]] = fir.convert %[[VAL_20]] : (i1) -> !fir.logical<4> -! CHECK: fir.store %[[VAL_21]] to %[[VAL_9]] : !fir.ref> -! CHECK: omp.yield +! CHECK: omp.wsloop reduction(@eqv_reduction %[[VAL_2]] -> %[[VAL_9:.*]] : !fir.ref>) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_10:.*]]) : i32 = (%[[VAL_6]]) to (%[[VAL_7]]) inclusive step (%[[VAL_8]]) { +! CHECK: fir.store %[[VAL_10]] to %[[VAL_5]] : !fir.ref +! CHECK: %[[VAL_11:.*]] = fir.load %[[VAL_5]] : !fir.ref +! CHECK: %[[VAL_12:.*]] = fir.convert %[[VAL_11]] : (i32) -> i64 +! CHECK: %[[VAL_13:.*]] = arith.constant 1 : i64 +! CHECK: %[[VAL_14:.*]] = arith.subi %[[VAL_12]], %[[VAL_13]] : i64 +! CHECK: %[[VAL_15:.*]] = fir.coordinate_of %[[VAL_0]], %[[VAL_14]] : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_16:.*]] = fir.load %[[VAL_15]] : !fir.ref> +! CHECK: %[[VAL_17:.*]] = fir.load %[[VAL_9]] : !fir.ref> +! CHECK: %[[VAL_18:.*]] = fir.convert %[[VAL_16]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_19:.*]] = fir.convert %[[VAL_17]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_20:.*]] = arith.cmpi eq, %[[VAL_18]], %[[VAL_19]] : i1 +! CHECK: %[[VAL_21:.*]] = fir.convert %[[VAL_20]] : (i1) -> !fir.logical<4> +! CHECK: fir.store %[[VAL_21]] to %[[VAL_9]] : !fir.ref> +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return @@ -122,45 +126,47 @@ end subroutine ! CHECK: %[[VAL_12:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_13:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_14:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@eqv_reduction %[[VAL_2]] -> %[[VAL_15:.*]] : !fir.ref>, @eqv_reduction %[[VAL_3]] -> %[[VAL_16:.*]] : !fir.ref>, @eqv_reduction %[[VAL_4]] -> %[[VAL_17:.*]] : !fir.ref>) for (%[[VAL_18:.*]]) : i32 = (%[[VAL_12]]) to (%[[VAL_13]]) inclusive step (%[[VAL_14]]) { -! CHECK: fir.store %[[VAL_18]] to %[[VAL_11]] : !fir.ref -! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_15]] : !fir.ref> -! CHECK: %[[VAL_20:.*]] = fir.load %[[VAL_11]] : !fir.ref -! CHECK: %[[VAL_21:.*]] = fir.convert %[[VAL_20]] : (i32) -> i64 -! CHECK: %[[VAL_22:.*]] = arith.constant 1 : i64 -! CHECK: %[[VAL_23:.*]] = arith.subi %[[VAL_21]], %[[VAL_22]] : i64 -! CHECK: %[[VAL_24:.*]] = fir.coordinate_of %[[VAL_0]], %[[VAL_23]] : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_25:.*]] = fir.load %[[VAL_24]] : !fir.ref> -! CHECK: %[[VAL_26:.*]] = fir.convert %[[VAL_19]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_27:.*]] = fir.convert %[[VAL_25]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_28:.*]] = arith.cmpi eq, %[[VAL_26]], %[[VAL_27]] : i1 -! CHECK: %[[VAL_29:.*]] = fir.convert %[[VAL_28]] : (i1) -> !fir.logical<4> -! CHECK: fir.store %[[VAL_29]] to %[[VAL_15]] : !fir.ref> -! CHECK: %[[VAL_30:.*]] = fir.load %[[VAL_16]] : !fir.ref> -! CHECK: %[[VAL_31:.*]] = fir.load %[[VAL_11]] : !fir.ref -! CHECK: %[[VAL_32:.*]] = fir.convert %[[VAL_31]] : (i32) -> i64 -! CHECK: %[[VAL_33:.*]] = arith.constant 1 : i64 -! CHECK: %[[VAL_34:.*]] = arith.subi %[[VAL_32]], %[[VAL_33]] : i64 -! CHECK: %[[VAL_35:.*]] = fir.coordinate_of %[[VAL_0]], %[[VAL_34]] : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_36:.*]] = fir.load %[[VAL_35]] : !fir.ref> -! CHECK: %[[VAL_37:.*]] = fir.convert %[[VAL_30]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_38:.*]] = fir.convert %[[VAL_36]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_39:.*]] = arith.cmpi eq, %[[VAL_37]], %[[VAL_38]] : i1 -! CHECK: %[[VAL_40:.*]] = fir.convert %[[VAL_39]] : (i1) -> !fir.logical<4> -! CHECK: fir.store %[[VAL_40]] to %[[VAL_16]] : !fir.ref> -! CHECK: %[[VAL_41:.*]] = fir.load %[[VAL_17]] : !fir.ref> -! CHECK: %[[VAL_42:.*]] = fir.load %[[VAL_11]] : !fir.ref -! CHECK: %[[VAL_43:.*]] = fir.convert %[[VAL_42]] : (i32) -> i64 -! CHECK: %[[VAL_44:.*]] = arith.constant 1 : i64 -! CHECK: %[[VAL_45:.*]] = arith.subi %[[VAL_43]], %[[VAL_44]] : i64 -! CHECK: %[[VAL_46:.*]] = fir.coordinate_of %[[VAL_0]], %[[VAL_45]] : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_47:.*]] = fir.load %[[VAL_46]] : !fir.ref> -! CHECK: %[[VAL_48:.*]] = fir.convert %[[VAL_41]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_49:.*]] = fir.convert %[[VAL_47]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_50:.*]] = arith.cmpi eq, %[[VAL_48]], %[[VAL_49]] : i1 -! CHECK: %[[VAL_51:.*]] = fir.convert %[[VAL_50]] : (i1) -> !fir.logical<4> -! CHECK: fir.store %[[VAL_51]] to %[[VAL_17]] : !fir.ref> -! CHECK: omp.yield +! CHECK: omp.wsloop reduction(@eqv_reduction %[[VAL_2]] -> %[[VAL_15:.*]] : !fir.ref>, @eqv_reduction %[[VAL_3]] -> %[[VAL_16:.*]] : !fir.ref>, @eqv_reduction %[[VAL_4]] -> %[[VAL_17:.*]] : !fir.ref>) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_18:.*]]) : i32 = (%[[VAL_12]]) to (%[[VAL_13]]) inclusive step (%[[VAL_14]]) { +! CHECK: fir.store %[[VAL_18]] to %[[VAL_11]] : !fir.ref +! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_15]] : !fir.ref> +! CHECK: %[[VAL_20:.*]] = fir.load %[[VAL_11]] : !fir.ref +! CHECK: %[[VAL_21:.*]] = fir.convert %[[VAL_20]] : (i32) -> i64 +! CHECK: %[[VAL_22:.*]] = arith.constant 1 : i64 +! CHECK: %[[VAL_23:.*]] = arith.subi %[[VAL_21]], %[[VAL_22]] : i64 +! CHECK: %[[VAL_24:.*]] = fir.coordinate_of %[[VAL_0]], %[[VAL_23]] : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_25:.*]] = fir.load %[[VAL_24]] : !fir.ref> +! CHECK: %[[VAL_26:.*]] = fir.convert %[[VAL_19]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_27:.*]] = fir.convert %[[VAL_25]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_28:.*]] = arith.cmpi eq, %[[VAL_26]], %[[VAL_27]] : i1 +! CHECK: %[[VAL_29:.*]] = fir.convert %[[VAL_28]] : (i1) -> !fir.logical<4> +! CHECK: fir.store %[[VAL_29]] to %[[VAL_15]] : !fir.ref> +! CHECK: %[[VAL_30:.*]] = fir.load %[[VAL_16]] : !fir.ref> +! CHECK: %[[VAL_31:.*]] = fir.load %[[VAL_11]] : !fir.ref +! CHECK: %[[VAL_32:.*]] = fir.convert %[[VAL_31]] : (i32) -> i64 +! CHECK: %[[VAL_33:.*]] = arith.constant 1 : i64 +! CHECK: %[[VAL_34:.*]] = arith.subi %[[VAL_32]], %[[VAL_33]] : i64 +! CHECK: %[[VAL_35:.*]] = fir.coordinate_of %[[VAL_0]], %[[VAL_34]] : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_36:.*]] = fir.load %[[VAL_35]] : !fir.ref> +! CHECK: %[[VAL_37:.*]] = fir.convert %[[VAL_30]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_38:.*]] = fir.convert %[[VAL_36]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_39:.*]] = arith.cmpi eq, %[[VAL_37]], %[[VAL_38]] : i1 +! CHECK: %[[VAL_40:.*]] = fir.convert %[[VAL_39]] : (i1) -> !fir.logical<4> +! CHECK: fir.store %[[VAL_40]] to %[[VAL_16]] : !fir.ref> +! CHECK: %[[VAL_41:.*]] = fir.load %[[VAL_17]] : !fir.ref> +! CHECK: %[[VAL_42:.*]] = fir.load %[[VAL_11]] : !fir.ref +! CHECK: %[[VAL_43:.*]] = fir.convert %[[VAL_42]] : (i32) -> i64 +! CHECK: %[[VAL_44:.*]] = arith.constant 1 : i64 +! CHECK: %[[VAL_45:.*]] = arith.subi %[[VAL_43]], %[[VAL_44]] : i64 +! CHECK: %[[VAL_46:.*]] = fir.coordinate_of %[[VAL_0]], %[[VAL_45]] : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_47:.*]] = fir.load %[[VAL_46]] : !fir.ref> +! CHECK: %[[VAL_48:.*]] = fir.convert %[[VAL_41]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_49:.*]] = fir.convert %[[VAL_47]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_50:.*]] = arith.cmpi eq, %[[VAL_48]], %[[VAL_49]] : i1 +! CHECK: %[[VAL_51:.*]] = fir.convert %[[VAL_50]] : (i1) -> !fir.logical<4> +! CHECK: fir.store %[[VAL_51]] to %[[VAL_17]] : !fir.ref> +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return diff --git a/flang/test/Lower/OpenMP/FIR/wsloop-reduction-logical-neqv-byref.f90 b/flang/test/Lower/OpenMP/FIR/wsloop-reduction-logical-neqv-byref.f90 index a31abd0def56e16da67efac729c9b6e985281ac2..89d16c3191b26e72501924f2c013421aea63104c 100644 --- a/flang/test/Lower/OpenMP/FIR/wsloop-reduction-logical-neqv-byref.f90 +++ b/flang/test/Lower/OpenMP/FIR/wsloop-reduction-logical-neqv-byref.f90 @@ -37,21 +37,23 @@ ! CHECK: %[[VAL_6:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_7:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_8:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@neqv_reduction %[[VAL_2]] -> %[[VAL_9:.*]] : !fir.ref>) for (%[[VAL_10:.*]]) : i32 = (%[[VAL_6]]) to (%[[VAL_7]]) inclusive step (%[[VAL_8]]) { -! CHECK: fir.store %[[VAL_10]] to %[[VAL_5]] : !fir.ref -! CHECK: %[[VAL_11:.*]] = fir.load %[[VAL_9]] : !fir.ref> -! CHECK: %[[VAL_12:.*]] = fir.load %[[VAL_5]] : !fir.ref -! CHECK: %[[VAL_13:.*]] = fir.convert %[[VAL_12]] : (i32) -> i64 -! CHECK: %[[VAL_14:.*]] = arith.constant 1 : i64 -! CHECK: %[[VAL_15:.*]] = arith.subi %[[VAL_13]], %[[VAL_14]] : i64 -! CHECK: %[[VAL_16:.*]] = fir.coordinate_of %[[VAL_0]], %[[VAL_15]] : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_17:.*]] = fir.load %[[VAL_16]] : !fir.ref> -! CHECK: %[[VAL_18:.*]] = fir.convert %[[VAL_11]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_19:.*]] = fir.convert %[[VAL_17]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_20:.*]] = arith.cmpi ne, %[[VAL_18]], %[[VAL_19]] : i1 -! CHECK: %[[VAL_21:.*]] = fir.convert %[[VAL_20]] : (i1) -> !fir.logical<4> -! CHECK: fir.store %[[VAL_21]] to %[[VAL_9]] : !fir.ref> -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@neqv_reduction %[[VAL_2]] -> %[[VAL_9:.*]] : !fir.ref>) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_10:.*]]) : i32 = (%[[VAL_6]]) to (%[[VAL_7]]) inclusive step (%[[VAL_8]]) { +! CHECK: fir.store %[[VAL_10]] to %[[VAL_5]] : !fir.ref +! CHECK: %[[VAL_11:.*]] = fir.load %[[VAL_9]] : !fir.ref> +! CHECK: %[[VAL_12:.*]] = fir.load %[[VAL_5]] : !fir.ref +! CHECK: %[[VAL_13:.*]] = fir.convert %[[VAL_12]] : (i32) -> i64 +! CHECK: %[[VAL_14:.*]] = arith.constant 1 : i64 +! CHECK: %[[VAL_15:.*]] = arith.subi %[[VAL_13]], %[[VAL_14]] : i64 +! CHECK: %[[VAL_16:.*]] = fir.coordinate_of %[[VAL_0]], %[[VAL_15]] : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_17:.*]] = fir.load %[[VAL_16]] : !fir.ref> +! CHECK: %[[VAL_18:.*]] = fir.convert %[[VAL_11]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_19:.*]] = fir.convert %[[VAL_17]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_20:.*]] = arith.cmpi ne, %[[VAL_18]], %[[VAL_19]] : i1 +! CHECK: %[[VAL_21:.*]] = fir.convert %[[VAL_20]] : (i1) -> !fir.logical<4> +! CHECK: fir.store %[[VAL_21]] to %[[VAL_9]] : !fir.ref> +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return @@ -79,21 +81,23 @@ end subroutine ! CHECK: %[[VAL_6:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_7:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_8:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@neqv_reduction %[[VAL_2]] -> %[[VAL_9:.*]] : !fir.ref>) for (%[[VAL_10:.*]]) : i32 = (%[[VAL_6]]) to (%[[VAL_7]]) inclusive step (%[[VAL_8]]) { -! CHECK: fir.store %[[VAL_10]] to %[[VAL_5]] : !fir.ref -! CHECK: %[[VAL_11:.*]] = fir.load %[[VAL_5]] : !fir.ref -! CHECK: %[[VAL_12:.*]] = fir.convert %[[VAL_11]] : (i32) -> i64 -! CHECK: %[[VAL_13:.*]] = arith.constant 1 : i64 -! CHECK: %[[VAL_14:.*]] = arith.subi %[[VAL_12]], %[[VAL_13]] : i64 -! CHECK: %[[VAL_15:.*]] = fir.coordinate_of %[[VAL_0]], %[[VAL_14]] : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_16:.*]] = fir.load %[[VAL_15]] : !fir.ref> -! CHECK: %[[VAL_17:.*]] = fir.load %[[VAL_9]] : !fir.ref> -! CHECK: %[[VAL_18:.*]] = fir.convert %[[VAL_16]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_19:.*]] = fir.convert %[[VAL_17]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_20:.*]] = arith.cmpi ne, %[[VAL_18]], %[[VAL_19]] : i1 -! CHECK: %[[VAL_21:.*]] = fir.convert %[[VAL_20]] : (i1) -> !fir.logical<4> -! CHECK: fir.store %[[VAL_21]] to %[[VAL_9]] : !fir.ref> -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@neqv_reduction %[[VAL_2]] -> %[[VAL_9:.*]] : !fir.ref>) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_10:.*]]) : i32 = (%[[VAL_6]]) to (%[[VAL_7]]) inclusive step (%[[VAL_8]]) { +! CHECK: fir.store %[[VAL_10]] to %[[VAL_5]] : !fir.ref +! CHECK: %[[VAL_11:.*]] = fir.load %[[VAL_5]] : !fir.ref +! CHECK: %[[VAL_12:.*]] = fir.convert %[[VAL_11]] : (i32) -> i64 +! CHECK: %[[VAL_13:.*]] = arith.constant 1 : i64 +! CHECK: %[[VAL_14:.*]] = arith.subi %[[VAL_12]], %[[VAL_13]] : i64 +! CHECK: %[[VAL_15:.*]] = fir.coordinate_of %[[VAL_0]], %[[VAL_14]] : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_16:.*]] = fir.load %[[VAL_15]] : !fir.ref> +! CHECK: %[[VAL_17:.*]] = fir.load %[[VAL_9]] : !fir.ref> +! CHECK: %[[VAL_18:.*]] = fir.convert %[[VAL_16]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_19:.*]] = fir.convert %[[VAL_17]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_20:.*]] = arith.cmpi ne, %[[VAL_18]], %[[VAL_19]] : i1 +! CHECK: %[[VAL_21:.*]] = fir.convert %[[VAL_20]] : (i1) -> !fir.logical<4> +! CHECK: fir.store %[[VAL_21]] to %[[VAL_9]] : !fir.ref> +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return @@ -129,45 +133,47 @@ end subroutine ! CHECK: %[[VAL_12:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_13:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_14:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@neqv_reduction %[[VAL_2]] -> %[[VAL_15:.*]] : !fir.ref>, @neqv_reduction %[[VAL_3]] -> %[[VAL_16:.*]] : !fir.ref>, @neqv_reduction %[[VAL_4]] -> %[[VAL_17:.*]] : !fir.ref>) for (%[[VAL_18:.*]]) : i32 = (%[[VAL_12]]) to (%[[VAL_13]]) inclusive step (%[[VAL_14]]) { -! CHECK: fir.store %[[VAL_18]] to %[[VAL_11]] : !fir.ref -! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_15]] : !fir.ref> -! CHECK: %[[VAL_20:.*]] = fir.load %[[VAL_11]] : !fir.ref -! CHECK: %[[VAL_21:.*]] = fir.convert %[[VAL_20]] : (i32) -> i64 -! CHECK: %[[VAL_22:.*]] = arith.constant 1 : i64 -! CHECK: %[[VAL_23:.*]] = arith.subi %[[VAL_21]], %[[VAL_22]] : i64 -! CHECK: %[[VAL_24:.*]] = fir.coordinate_of %[[VAL_0]], %[[VAL_23]] : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_25:.*]] = fir.load %[[VAL_24]] : !fir.ref> -! CHECK: %[[VAL_26:.*]] = fir.convert %[[VAL_19]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_27:.*]] = fir.convert %[[VAL_25]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_28:.*]] = arith.cmpi ne, %[[VAL_26]], %[[VAL_27]] : i1 -! CHECK: %[[VAL_29:.*]] = fir.convert %[[VAL_28]] : (i1) -> !fir.logical<4> -! CHECK: fir.store %[[VAL_29]] to %[[VAL_15]] : !fir.ref> -! CHECK: %[[VAL_30:.*]] = fir.load %[[VAL_16]] : !fir.ref> -! CHECK: %[[VAL_31:.*]] = fir.load %[[VAL_11]] : !fir.ref -! CHECK: %[[VAL_32:.*]] = fir.convert %[[VAL_31]] : (i32) -> i64 -! CHECK: %[[VAL_33:.*]] = arith.constant 1 : i64 -! CHECK: %[[VAL_34:.*]] = arith.subi %[[VAL_32]], %[[VAL_33]] : i64 -! CHECK: %[[VAL_35:.*]] = fir.coordinate_of %[[VAL_0]], %[[VAL_34]] : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_36:.*]] = fir.load %[[VAL_35]] : !fir.ref> -! CHECK: %[[VAL_37:.*]] = fir.convert %[[VAL_30]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_38:.*]] = fir.convert %[[VAL_36]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_39:.*]] = arith.cmpi ne, %[[VAL_37]], %[[VAL_38]] : i1 -! CHECK: %[[VAL_40:.*]] = fir.convert %[[VAL_39]] : (i1) -> !fir.logical<4> -! CHECK: fir.store %[[VAL_40]] to %[[VAL_16]] : !fir.ref> -! CHECK: %[[VAL_41:.*]] = fir.load %[[VAL_17]] : !fir.ref> -! CHECK: %[[VAL_42:.*]] = fir.load %[[VAL_11]] : !fir.ref -! CHECK: %[[VAL_43:.*]] = fir.convert %[[VAL_42]] : (i32) -> i64 -! CHECK: %[[VAL_44:.*]] = arith.constant 1 : i64 -! CHECK: %[[VAL_45:.*]] = arith.subi %[[VAL_43]], %[[VAL_44]] : i64 -! CHECK: %[[VAL_46:.*]] = fir.coordinate_of %[[VAL_0]], %[[VAL_45]] : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_47:.*]] = fir.load %[[VAL_46]] : !fir.ref> -! CHECK: %[[VAL_48:.*]] = fir.convert %[[VAL_41]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_49:.*]] = fir.convert %[[VAL_47]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_50:.*]] = arith.cmpi ne, %[[VAL_48]], %[[VAL_49]] : i1 -! CHECK: %[[VAL_51:.*]] = fir.convert %[[VAL_50]] : (i1) -> !fir.logical<4> -! CHECK: fir.store %[[VAL_51]] to %[[VAL_17]] : !fir.ref> -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@neqv_reduction %[[VAL_2]] -> %[[VAL_15:.*]] : !fir.ref>, @neqv_reduction %[[VAL_3]] -> %[[VAL_16:.*]] : !fir.ref>, @neqv_reduction %[[VAL_4]] -> %[[VAL_17:.*]] : !fir.ref>) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_18:.*]]) : i32 = (%[[VAL_12]]) to (%[[VAL_13]]) inclusive step (%[[VAL_14]]) { +! CHECK: fir.store %[[VAL_18]] to %[[VAL_11]] : !fir.ref +! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_15]] : !fir.ref> +! CHECK: %[[VAL_20:.*]] = fir.load %[[VAL_11]] : !fir.ref +! CHECK: %[[VAL_21:.*]] = fir.convert %[[VAL_20]] : (i32) -> i64 +! CHECK: %[[VAL_22:.*]] = arith.constant 1 : i64 +! CHECK: %[[VAL_23:.*]] = arith.subi %[[VAL_21]], %[[VAL_22]] : i64 +! CHECK: %[[VAL_24:.*]] = fir.coordinate_of %[[VAL_0]], %[[VAL_23]] : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_25:.*]] = fir.load %[[VAL_24]] : !fir.ref> +! CHECK: %[[VAL_26:.*]] = fir.convert %[[VAL_19]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_27:.*]] = fir.convert %[[VAL_25]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_28:.*]] = arith.cmpi ne, %[[VAL_26]], %[[VAL_27]] : i1 +! CHECK: %[[VAL_29:.*]] = fir.convert %[[VAL_28]] : (i1) -> !fir.logical<4> +! CHECK: fir.store %[[VAL_29]] to %[[VAL_15]] : !fir.ref> +! CHECK: %[[VAL_30:.*]] = fir.load %[[VAL_16]] : !fir.ref> +! CHECK: %[[VAL_31:.*]] = fir.load %[[VAL_11]] : !fir.ref +! CHECK: %[[VAL_32:.*]] = fir.convert %[[VAL_31]] : (i32) -> i64 +! CHECK: %[[VAL_33:.*]] = arith.constant 1 : i64 +! CHECK: %[[VAL_34:.*]] = arith.subi %[[VAL_32]], %[[VAL_33]] : i64 +! CHECK: %[[VAL_35:.*]] = fir.coordinate_of %[[VAL_0]], %[[VAL_34]] : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_36:.*]] = fir.load %[[VAL_35]] : !fir.ref> +! CHECK: %[[VAL_37:.*]] = fir.convert %[[VAL_30]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_38:.*]] = fir.convert %[[VAL_36]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_39:.*]] = arith.cmpi ne, %[[VAL_37]], %[[VAL_38]] : i1 +! CHECK: %[[VAL_40:.*]] = fir.convert %[[VAL_39]] : (i1) -> !fir.logical<4> +! CHECK: fir.store %[[VAL_40]] to %[[VAL_16]] : !fir.ref> +! CHECK: %[[VAL_41:.*]] = fir.load %[[VAL_17]] : !fir.ref> +! CHECK: %[[VAL_42:.*]] = fir.load %[[VAL_11]] : !fir.ref +! CHECK: %[[VAL_43:.*]] = fir.convert %[[VAL_42]] : (i32) -> i64 +! CHECK: %[[VAL_44:.*]] = arith.constant 1 : i64 +! CHECK: %[[VAL_45:.*]] = arith.subi %[[VAL_43]], %[[VAL_44]] : i64 +! CHECK: %[[VAL_46:.*]] = fir.coordinate_of %[[VAL_0]], %[[VAL_45]] : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_47:.*]] = fir.load %[[VAL_46]] : !fir.ref> +! CHECK: %[[VAL_48:.*]] = fir.convert %[[VAL_41]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_49:.*]] = fir.convert %[[VAL_47]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_50:.*]] = arith.cmpi ne, %[[VAL_48]], %[[VAL_49]] : i1 +! CHECK: %[[VAL_51:.*]] = fir.convert %[[VAL_50]] : (i1) -> !fir.logical<4> +! CHECK: fir.store %[[VAL_51]] to %[[VAL_17]] : !fir.ref> +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return diff --git a/flang/test/Lower/OpenMP/FIR/wsloop-reduction-logical-neqv.f90 b/flang/test/Lower/OpenMP/FIR/wsloop-reduction-logical-neqv.f90 index 702c185e25ee401c99f332448f7b0c80b00e9f86..106e867f367b7da8e8bb4560577926c704168199 100644 --- a/flang/test/Lower/OpenMP/FIR/wsloop-reduction-logical-neqv.f90 +++ b/flang/test/Lower/OpenMP/FIR/wsloop-reduction-logical-neqv.f90 @@ -31,21 +31,23 @@ ! CHECK: %[[VAL_6:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_7:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_8:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@neqv_reduction %[[VAL_2]] -> %[[VAL_9:.*]] : !fir.ref>) for (%[[VAL_10:.*]]) : i32 = (%[[VAL_6]]) to (%[[VAL_7]]) inclusive step (%[[VAL_8]]) { -! CHECK: fir.store %[[VAL_10]] to %[[VAL_5]] : !fir.ref -! CHECK: %[[VAL_11:.*]] = fir.load %[[VAL_9]] : !fir.ref> -! CHECK: %[[VAL_12:.*]] = fir.load %[[VAL_5]] : !fir.ref -! CHECK: %[[VAL_13:.*]] = fir.convert %[[VAL_12]] : (i32) -> i64 -! CHECK: %[[VAL_14:.*]] = arith.constant 1 : i64 -! CHECK: %[[VAL_15:.*]] = arith.subi %[[VAL_13]], %[[VAL_14]] : i64 -! CHECK: %[[VAL_16:.*]] = fir.coordinate_of %[[VAL_0]], %[[VAL_15]] : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_17:.*]] = fir.load %[[VAL_16]] : !fir.ref> -! CHECK: %[[VAL_18:.*]] = fir.convert %[[VAL_11]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_19:.*]] = fir.convert %[[VAL_17]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_20:.*]] = arith.cmpi ne, %[[VAL_18]], %[[VAL_19]] : i1 -! CHECK: %[[VAL_21:.*]] = fir.convert %[[VAL_20]] : (i1) -> !fir.logical<4> -! CHECK: fir.store %[[VAL_21]] to %[[VAL_9]] : !fir.ref> -! CHECK: omp.yield +! CHECK: omp.wsloop reduction(@neqv_reduction %[[VAL_2]] -> %[[VAL_9:.*]] : !fir.ref>) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_10:.*]]) : i32 = (%[[VAL_6]]) to (%[[VAL_7]]) inclusive step (%[[VAL_8]]) { +! CHECK: fir.store %[[VAL_10]] to %[[VAL_5]] : !fir.ref +! CHECK: %[[VAL_11:.*]] = fir.load %[[VAL_9]] : !fir.ref> +! CHECK: %[[VAL_12:.*]] = fir.load %[[VAL_5]] : !fir.ref +! CHECK: %[[VAL_13:.*]] = fir.convert %[[VAL_12]] : (i32) -> i64 +! CHECK: %[[VAL_14:.*]] = arith.constant 1 : i64 +! CHECK: %[[VAL_15:.*]] = arith.subi %[[VAL_13]], %[[VAL_14]] : i64 +! CHECK: %[[VAL_16:.*]] = fir.coordinate_of %[[VAL_0]], %[[VAL_15]] : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_17:.*]] = fir.load %[[VAL_16]] : !fir.ref> +! CHECK: %[[VAL_18:.*]] = fir.convert %[[VAL_11]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_19:.*]] = fir.convert %[[VAL_17]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_20:.*]] = arith.cmpi ne, %[[VAL_18]], %[[VAL_19]] : i1 +! CHECK: %[[VAL_21:.*]] = fir.convert %[[VAL_20]] : (i1) -> !fir.logical<4> +! CHECK: fir.store %[[VAL_21]] to %[[VAL_9]] : !fir.ref> +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return @@ -73,21 +75,23 @@ end subroutine ! CHECK: %[[VAL_6:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_7:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_8:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@neqv_reduction %[[VAL_2]] -> %[[VAL_9:.*]] : !fir.ref>) for (%[[VAL_10:.*]]) : i32 = (%[[VAL_6]]) to (%[[VAL_7]]) inclusive step (%[[VAL_8]]) { -! CHECK: fir.store %[[VAL_10]] to %[[VAL_5]] : !fir.ref -! CHECK: %[[VAL_11:.*]] = fir.load %[[VAL_5]] : !fir.ref -! CHECK: %[[VAL_12:.*]] = fir.convert %[[VAL_11]] : (i32) -> i64 -! CHECK: %[[VAL_13:.*]] = arith.constant 1 : i64 -! CHECK: %[[VAL_14:.*]] = arith.subi %[[VAL_12]], %[[VAL_13]] : i64 -! CHECK: %[[VAL_15:.*]] = fir.coordinate_of %[[VAL_0]], %[[VAL_14]] : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_16:.*]] = fir.load %[[VAL_15]] : !fir.ref> -! CHECK: %[[VAL_17:.*]] = fir.load %[[VAL_9]] : !fir.ref> -! CHECK: %[[VAL_18:.*]] = fir.convert %[[VAL_16]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_19:.*]] = fir.convert %[[VAL_17]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_20:.*]] = arith.cmpi ne, %[[VAL_18]], %[[VAL_19]] : i1 -! CHECK: %[[VAL_21:.*]] = fir.convert %[[VAL_20]] : (i1) -> !fir.logical<4> -! CHECK: fir.store %[[VAL_21]] to %[[VAL_9]] : !fir.ref> -! CHECK: omp.yield +! CHECK: omp.wsloop reduction(@neqv_reduction %[[VAL_2]] -> %[[VAL_9:.*]] : !fir.ref>) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_10:.*]]) : i32 = (%[[VAL_6]]) to (%[[VAL_7]]) inclusive step (%[[VAL_8]]) { +! CHECK: fir.store %[[VAL_10]] to %[[VAL_5]] : !fir.ref +! CHECK: %[[VAL_11:.*]] = fir.load %[[VAL_5]] : !fir.ref +! CHECK: %[[VAL_12:.*]] = fir.convert %[[VAL_11]] : (i32) -> i64 +! CHECK: %[[VAL_13:.*]] = arith.constant 1 : i64 +! CHECK: %[[VAL_14:.*]] = arith.subi %[[VAL_12]], %[[VAL_13]] : i64 +! CHECK: %[[VAL_15:.*]] = fir.coordinate_of %[[VAL_0]], %[[VAL_14]] : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_16:.*]] = fir.load %[[VAL_15]] : !fir.ref> +! CHECK: %[[VAL_17:.*]] = fir.load %[[VAL_9]] : !fir.ref> +! CHECK: %[[VAL_18:.*]] = fir.convert %[[VAL_16]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_19:.*]] = fir.convert %[[VAL_17]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_20:.*]] = arith.cmpi ne, %[[VAL_18]], %[[VAL_19]] : i1 +! CHECK: %[[VAL_21:.*]] = fir.convert %[[VAL_20]] : (i1) -> !fir.logical<4> +! CHECK: fir.store %[[VAL_21]] to %[[VAL_9]] : !fir.ref> +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return @@ -123,45 +127,47 @@ end subroutine ! CHECK: %[[VAL_12:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_13:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_14:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@neqv_reduction %[[VAL_2]] -> %[[VAL_15:.*]] : !fir.ref>, @neqv_reduction %[[VAL_3]] -> %[[VAL_16:.*]] : !fir.ref>, @neqv_reduction %[[VAL_4]] -> %[[VAL_17:.*]] : !fir.ref>) for (%[[VAL_18:.*]]) : i32 = (%[[VAL_12]]) to (%[[VAL_13]]) inclusive step (%[[VAL_14]]) { -! CHECK: fir.store %[[VAL_18]] to %[[VAL_11]] : !fir.ref -! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_15]] : !fir.ref> -! CHECK: %[[VAL_20:.*]] = fir.load %[[VAL_11]] : !fir.ref -! CHECK: %[[VAL_21:.*]] = fir.convert %[[VAL_20]] : (i32) -> i64 -! CHECK: %[[VAL_22:.*]] = arith.constant 1 : i64 -! CHECK: %[[VAL_23:.*]] = arith.subi %[[VAL_21]], %[[VAL_22]] : i64 -! CHECK: %[[VAL_24:.*]] = fir.coordinate_of %[[VAL_0]], %[[VAL_23]] : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_25:.*]] = fir.load %[[VAL_24]] : !fir.ref> -! CHECK: %[[VAL_26:.*]] = fir.convert %[[VAL_19]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_27:.*]] = fir.convert %[[VAL_25]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_28:.*]] = arith.cmpi ne, %[[VAL_26]], %[[VAL_27]] : i1 -! CHECK: %[[VAL_29:.*]] = fir.convert %[[VAL_28]] : (i1) -> !fir.logical<4> -! CHECK: fir.store %[[VAL_29]] to %[[VAL_15]] : !fir.ref> -! CHECK: %[[VAL_30:.*]] = fir.load %[[VAL_16]] : !fir.ref> -! CHECK: %[[VAL_31:.*]] = fir.load %[[VAL_11]] : !fir.ref -! CHECK: %[[VAL_32:.*]] = fir.convert %[[VAL_31]] : (i32) -> i64 -! CHECK: %[[VAL_33:.*]] = arith.constant 1 : i64 -! CHECK: %[[VAL_34:.*]] = arith.subi %[[VAL_32]], %[[VAL_33]] : i64 -! CHECK: %[[VAL_35:.*]] = fir.coordinate_of %[[VAL_0]], %[[VAL_34]] : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_36:.*]] = fir.load %[[VAL_35]] : !fir.ref> -! CHECK: %[[VAL_37:.*]] = fir.convert %[[VAL_30]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_38:.*]] = fir.convert %[[VAL_36]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_39:.*]] = arith.cmpi ne, %[[VAL_37]], %[[VAL_38]] : i1 -! CHECK: %[[VAL_40:.*]] = fir.convert %[[VAL_39]] : (i1) -> !fir.logical<4> -! CHECK: fir.store %[[VAL_40]] to %[[VAL_16]] : !fir.ref> -! CHECK: %[[VAL_41:.*]] = fir.load %[[VAL_17]] : !fir.ref> -! CHECK: %[[VAL_42:.*]] = fir.load %[[VAL_11]] : !fir.ref -! CHECK: %[[VAL_43:.*]] = fir.convert %[[VAL_42]] : (i32) -> i64 -! CHECK: %[[VAL_44:.*]] = arith.constant 1 : i64 -! CHECK: %[[VAL_45:.*]] = arith.subi %[[VAL_43]], %[[VAL_44]] : i64 -! CHECK: %[[VAL_46:.*]] = fir.coordinate_of %[[VAL_0]], %[[VAL_45]] : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_47:.*]] = fir.load %[[VAL_46]] : !fir.ref> -! CHECK: %[[VAL_48:.*]] = fir.convert %[[VAL_41]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_49:.*]] = fir.convert %[[VAL_47]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_50:.*]] = arith.cmpi ne, %[[VAL_48]], %[[VAL_49]] : i1 -! CHECK: %[[VAL_51:.*]] = fir.convert %[[VAL_50]] : (i1) -> !fir.logical<4> -! CHECK: fir.store %[[VAL_51]] to %[[VAL_17]] : !fir.ref> -! CHECK: omp.yield +! CHECK: omp.wsloop reduction(@neqv_reduction %[[VAL_2]] -> %[[VAL_15:.*]] : !fir.ref>, @neqv_reduction %[[VAL_3]] -> %[[VAL_16:.*]] : !fir.ref>, @neqv_reduction %[[VAL_4]] -> %[[VAL_17:.*]] : !fir.ref>) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_18:.*]]) : i32 = (%[[VAL_12]]) to (%[[VAL_13]]) inclusive step (%[[VAL_14]]) { +! CHECK: fir.store %[[VAL_18]] to %[[VAL_11]] : !fir.ref +! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_15]] : !fir.ref> +! CHECK: %[[VAL_20:.*]] = fir.load %[[VAL_11]] : !fir.ref +! CHECK: %[[VAL_21:.*]] = fir.convert %[[VAL_20]] : (i32) -> i64 +! CHECK: %[[VAL_22:.*]] = arith.constant 1 : i64 +! CHECK: %[[VAL_23:.*]] = arith.subi %[[VAL_21]], %[[VAL_22]] : i64 +! CHECK: %[[VAL_24:.*]] = fir.coordinate_of %[[VAL_0]], %[[VAL_23]] : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_25:.*]] = fir.load %[[VAL_24]] : !fir.ref> +! CHECK: %[[VAL_26:.*]] = fir.convert %[[VAL_19]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_27:.*]] = fir.convert %[[VAL_25]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_28:.*]] = arith.cmpi ne, %[[VAL_26]], %[[VAL_27]] : i1 +! CHECK: %[[VAL_29:.*]] = fir.convert %[[VAL_28]] : (i1) -> !fir.logical<4> +! CHECK: fir.store %[[VAL_29]] to %[[VAL_15]] : !fir.ref> +! CHECK: %[[VAL_30:.*]] = fir.load %[[VAL_16]] : !fir.ref> +! CHECK: %[[VAL_31:.*]] = fir.load %[[VAL_11]] : !fir.ref +! CHECK: %[[VAL_32:.*]] = fir.convert %[[VAL_31]] : (i32) -> i64 +! CHECK: %[[VAL_33:.*]] = arith.constant 1 : i64 +! CHECK: %[[VAL_34:.*]] = arith.subi %[[VAL_32]], %[[VAL_33]] : i64 +! CHECK: %[[VAL_35:.*]] = fir.coordinate_of %[[VAL_0]], %[[VAL_34]] : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_36:.*]] = fir.load %[[VAL_35]] : !fir.ref> +! CHECK: %[[VAL_37:.*]] = fir.convert %[[VAL_30]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_38:.*]] = fir.convert %[[VAL_36]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_39:.*]] = arith.cmpi ne, %[[VAL_37]], %[[VAL_38]] : i1 +! CHECK: %[[VAL_40:.*]] = fir.convert %[[VAL_39]] : (i1) -> !fir.logical<4> +! CHECK: fir.store %[[VAL_40]] to %[[VAL_16]] : !fir.ref> +! CHECK: %[[VAL_41:.*]] = fir.load %[[VAL_17]] : !fir.ref> +! CHECK: %[[VAL_42:.*]] = fir.load %[[VAL_11]] : !fir.ref +! CHECK: %[[VAL_43:.*]] = fir.convert %[[VAL_42]] : (i32) -> i64 +! CHECK: %[[VAL_44:.*]] = arith.constant 1 : i64 +! CHECK: %[[VAL_45:.*]] = arith.subi %[[VAL_43]], %[[VAL_44]] : i64 +! CHECK: %[[VAL_46:.*]] = fir.coordinate_of %[[VAL_0]], %[[VAL_45]] : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_47:.*]] = fir.load %[[VAL_46]] : !fir.ref> +! CHECK: %[[VAL_48:.*]] = fir.convert %[[VAL_41]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_49:.*]] = fir.convert %[[VAL_47]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_50:.*]] = arith.cmpi ne, %[[VAL_48]], %[[VAL_49]] : i1 +! CHECK: %[[VAL_51:.*]] = fir.convert %[[VAL_50]] : (i1) -> !fir.logical<4> +! CHECK: fir.store %[[VAL_51]] to %[[VAL_17]] : !fir.ref> +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return diff --git a/flang/test/Lower/OpenMP/FIR/wsloop-reduction-max-byref.f90 b/flang/test/Lower/OpenMP/FIR/wsloop-reduction-max-byref.f90 index 80b720e3aac1d10ffefedc61394561d4b14c9eb4..a4244d11a55867b3d1f1749c8e1d3dbaeb901473 100644 --- a/flang/test/Lower/OpenMP/FIR/wsloop-reduction-max-byref.f90 +++ b/flang/test/Lower/OpenMP/FIR/wsloop-reduction-max-byref.f90 @@ -32,25 +32,30 @@ !CHECK-SAME: %[[Y_BOX:.*]]: !fir.box> !CHECK: %[[X_REF:.*]] = fir.alloca i32 {bindc_name = "x", uniq_name = "_QFreduction_max_intEx"} !CHECK: omp.parallel -!CHECK: omp.wsloop byref reduction(@max_byref_i32 %[[X_REF]] -> %[[PRV:.+]] : !fir.ref) for -!CHECK: %[[LPRV:.+]] = fir.load %[[PRV]] : !fir.ref -!CHECK: %[[Y_I_REF:.*]] = fir.coordinate_of %[[Y_BOX]] -!CHECK: %[[Y_I:.*]] = fir.load %[[Y_I_REF]] : !fir.ref -!CHECK: %[[RES:.+]] = arith.cmpi sgt, %[[LPRV]], %[[Y_I]] : i32 -!CHECK: %[[SEL:.+]] = arith.select %[[RES]], %[[LPRV]], %[[Y_I]] -!CHECK: fir.store %[[SEL]] to %[[PRV]] : !fir.ref +!CHECK: omp.wsloop byref reduction(@max_byref_i32 %[[X_REF]] -> %[[PRV:.+]] : !fir.ref) +!CHECK-NEXT: omp.loop_nest +!CHECK: %[[LPRV:.+]] = fir.load %[[PRV]] : !fir.ref +!CHECK: %[[Y_I_REF:.*]] = fir.coordinate_of %[[Y_BOX]] +!CHECK: %[[Y_I:.*]] = fir.load %[[Y_I_REF]] : !fir.ref +!CHECK: %[[RES:.+]] = arith.cmpi sgt, %[[LPRV]], %[[Y_I]] : i32 +!CHECK: %[[SEL:.+]] = arith.select %[[RES]], %[[LPRV]], %[[Y_I]] +!CHECK: fir.store %[[SEL]] to %[[PRV]] : !fir.ref +!CHECK: omp.yield +!CHECK: omp.terminator !CHECK: omp.terminator !CHECK-LABEL: @_QPreduction_max_real !CHECK-SAME: %[[Y_BOX:.*]]: !fir.box> !CHECK: %[[X_REF:.*]] = fir.alloca f32 {bindc_name = "x", uniq_name = "_QFreduction_max_realEx"} !CHECK: omp.parallel -!CHECK: omp.wsloop byref reduction(@max_byref_f32 %[[X_REF]] -> %[[PRV:.+]] : !fir.ref) for -!CHECK: %[[LPRV:.+]] = fir.load %[[PRV]] : !fir.ref -!CHECK: %[[Y_I_REF:.*]] = fir.coordinate_of %[[Y_BOX]] -!CHECK: %[[Y_I:.*]] = fir.load %[[Y_I_REF]] : !fir.ref -!CHECK: %[[RES:.+]] = arith.cmpf ogt, %[[Y_I]], %[[LPRV]] {{.*}} : f32 -!CHECK: omp.yield +!CHECK: omp.wsloop byref reduction(@max_byref_f32 %[[X_REF]] -> %[[PRV:.+]] : !fir.ref) +!CHECK-NEXT: omp.loop_nest +!CHECK: %[[LPRV:.+]] = fir.load %[[PRV]] : !fir.ref +!CHECK: %[[Y_I_REF:.*]] = fir.coordinate_of %[[Y_BOX]] +!CHECK: %[[Y_I:.*]] = fir.load %[[Y_I_REF]] : !fir.ref +!CHECK: %[[RES:.+]] = arith.cmpf ogt, %[[Y_I]], %[[LPRV]] {{.*}} : f32 +!CHECK: omp.yield +!CHECK: omp.terminator !CHECK: omp.terminator subroutine reduction_max_int(y) diff --git a/flang/test/Lower/OpenMP/FIR/wsloop-reduction-max.f90 b/flang/test/Lower/OpenMP/FIR/wsloop-reduction-max.f90 index c3b821ea5912468c2c10767bca5e5dddf63e3bd2..e000bc36ca3fbb052ca79fc94d07dfa51100ea68 100644 --- a/flang/test/Lower/OpenMP/FIR/wsloop-reduction-max.f90 +++ b/flang/test/Lower/OpenMP/FIR/wsloop-reduction-max.f90 @@ -21,25 +21,30 @@ !CHECK-SAME: %[[Y_BOX:.*]]: !fir.box> !CHECK: %[[X_REF:.*]] = fir.alloca i32 {bindc_name = "x", uniq_name = "_QFreduction_max_intEx"} !CHECK: omp.parallel -!CHECK: omp.wsloop reduction(@[[MAX_DECLARE_I]] %[[X_REF]] -> %[[PRV:.+]] : !fir.ref) for -!CHECK: %[[LPRV:.+]] = fir.load %[[PRV]] : !fir.ref -!CHECK: %[[Y_I_REF:.*]] = fir.coordinate_of %[[Y_BOX]] -!CHECK: %[[Y_I:.*]] = fir.load %[[Y_I_REF]] : !fir.ref -!CHECK: %[[RES:.+]] = arith.cmpi sgt, %[[LPRV]], %[[Y_I]] : i32 -!CHECK: %[[SEL:.+]] = arith.select %[[RES]], %[[LPRV]], %[[Y_I]] -!CHECK: fir.store %[[SEL]] to %[[PRV]] : !fir.ref +!CHECK: omp.wsloop reduction(@[[MAX_DECLARE_I]] %[[X_REF]] -> %[[PRV:.+]] : !fir.ref) +!CHECK-NEXT: omp.loop_nest +!CHECK: %[[LPRV:.+]] = fir.load %[[PRV]] : !fir.ref +!CHECK: %[[Y_I_REF:.*]] = fir.coordinate_of %[[Y_BOX]] +!CHECK: %[[Y_I:.*]] = fir.load %[[Y_I_REF]] : !fir.ref +!CHECK: %[[RES:.+]] = arith.cmpi sgt, %[[LPRV]], %[[Y_I]] : i32 +!CHECK: %[[SEL:.+]] = arith.select %[[RES]], %[[LPRV]], %[[Y_I]] +!CHECK: fir.store %[[SEL]] to %[[PRV]] : !fir.ref +!CHECK: omp.yield +!CHECK: omp.terminator !CHECK: omp.terminator !CHECK-LABEL: @_QPreduction_max_real !CHECK-SAME: %[[Y_BOX:.*]]: !fir.box> !CHECK: %[[X_REF:.*]] = fir.alloca f32 {bindc_name = "x", uniq_name = "_QFreduction_max_realEx"} !CHECK: omp.parallel -!CHECK: omp.wsloop reduction(@[[MAX_DECLARE_F]] %[[X_REF]] -> %[[PRV:.+]] : !fir.ref) for -!CHECK: %[[LPRV:.+]] = fir.load %[[PRV]] : !fir.ref -!CHECK: %[[Y_I_REF:.*]] = fir.coordinate_of %[[Y_BOX]] -!CHECK: %[[Y_I:.*]] = fir.load %[[Y_I_REF]] : !fir.ref -!CHECK: %[[RES:.+]] = arith.cmpf ogt, %[[Y_I]], %[[LPRV]] {{.*}} : f32 -!CHECK: omp.yield +!CHECK: omp.wsloop reduction(@[[MAX_DECLARE_F]] %[[X_REF]] -> %[[PRV:.+]] : !fir.ref) +!CHECK-NEXT: omp.loop_nest +!CHECK: %[[LPRV:.+]] = fir.load %[[PRV]] : !fir.ref +!CHECK: %[[Y_I_REF:.*]] = fir.coordinate_of %[[Y_BOX]] +!CHECK: %[[Y_I:.*]] = fir.load %[[Y_I_REF]] : !fir.ref +!CHECK: %[[RES:.+]] = arith.cmpf ogt, %[[Y_I]], %[[LPRV]] {{.*}} : f32 +!CHECK: omp.yield +!CHECK: omp.terminator !CHECK: omp.terminator subroutine reduction_max_int(y) diff --git a/flang/test/Lower/OpenMP/FIR/wsloop-reduction-min-byref.f90 b/flang/test/Lower/OpenMP/FIR/wsloop-reduction-min-byref.f90 index b284f8e5d96721345b20349f869f7caa12947e29..17435e1a194ca4f94ea7269e72a7f2bad986f8ae 100644 --- a/flang/test/Lower/OpenMP/FIR/wsloop-reduction-min-byref.f90 +++ b/flang/test/Lower/OpenMP/FIR/wsloop-reduction-min-byref.f90 @@ -32,26 +32,30 @@ !CHECK-SAME: %[[Y_BOX:.*]]: !fir.box> !CHECK: %[[X_REF:.*]] = fir.alloca i32 {bindc_name = "x", uniq_name = "_QFreduction_min_intEx"} !CHECK: omp.parallel -!CHECK: omp.wsloop byref reduction(@min_byref_i32 %[[X_REF]] -> %[[PRV:.+]] : !fir.ref) for -!CHECK: %[[LPRV:.+]] = fir.load %[[PRV]] : !fir.ref -!CHECK: %[[Y_I_REF:.*]] = fir.coordinate_of %[[Y_BOX]] -!CHECK: %[[Y_I:.*]] = fir.load %[[Y_I_REF]] : !fir.ref -!CHECK: %[[RES:.+]] = arith.cmpi slt, %[[LPRV]], %[[Y_I]] : i32 -!CHECK: %[[SEL:.+]] = arith.select %[[RES]], %[[LPRV]], %[[Y_I]] -!CHECK: fir.store %[[SEL]] to %[[PRV]] : !fir.ref -!CHECK: omp.yield +!CHECK: omp.wsloop byref reduction(@min_byref_i32 %[[X_REF]] -> %[[PRV:.+]] : !fir.ref) +!CHECK-NEXT: omp.loop_nest +!CHECK: %[[LPRV:.+]] = fir.load %[[PRV]] : !fir.ref +!CHECK: %[[Y_I_REF:.*]] = fir.coordinate_of %[[Y_BOX]] +!CHECK: %[[Y_I:.*]] = fir.load %[[Y_I_REF]] : !fir.ref +!CHECK: %[[RES:.+]] = arith.cmpi slt, %[[LPRV]], %[[Y_I]] : i32 +!CHECK: %[[SEL:.+]] = arith.select %[[RES]], %[[LPRV]], %[[Y_I]] +!CHECK: fir.store %[[SEL]] to %[[PRV]] : !fir.ref +!CHECK: omp.yield +!CHECK: omp.terminator !CHECK: omp.terminator !CHECK-LABEL: @_QPreduction_min_real !CHECK-SAME: %[[Y_BOX:.*]]: !fir.box> !CHECK: %[[X_REF:.*]] = fir.alloca f32 {bindc_name = "x", uniq_name = "_QFreduction_min_realEx"} !CHECK: omp.parallel -!CHECK: omp.wsloop byref reduction(@min_byref_f32 %[[X_REF]] -> %[[PRV:.+]] : !fir.ref) for -!CHECK: %[[LPRV:.+]] = fir.load %[[PRV]] : !fir.ref -!CHECK: %[[Y_I_REF:.*]] = fir.coordinate_of %[[Y_BOX]] -!CHECK: %[[Y_I:.*]] = fir.load %[[Y_I_REF]] : !fir.ref -!CHECK: %[[RES:.+]] = arith.cmpf ogt, %[[Y_I]], %[[LPRV]] {{.*}} : f32 -!CHECK: omp.yield +!CHECK: omp.wsloop byref reduction(@min_byref_f32 %[[X_REF]] -> %[[PRV:.+]] : !fir.ref) +!CHECK-NEXT: omp.loop_nest +!CHECK: %[[LPRV:.+]] = fir.load %[[PRV]] : !fir.ref +!CHECK: %[[Y_I_REF:.*]] = fir.coordinate_of %[[Y_BOX]] +!CHECK: %[[Y_I:.*]] = fir.load %[[Y_I_REF]] : !fir.ref +!CHECK: %[[RES:.+]] = arith.cmpf ogt, %[[Y_I]], %[[LPRV]] {{.*}} : f32 +!CHECK: omp.yield +!CHECK: omp.terminator !CHECK: omp.terminator subroutine reduction_min_int(y) diff --git a/flang/test/Lower/OpenMP/FIR/wsloop-reduction-min.f90 b/flang/test/Lower/OpenMP/FIR/wsloop-reduction-min.f90 index ab33e180ed883dee446720b2175f3a9d40cb1f4e..1d18ece7297d4e0f15db599ae867e140819f169e 100644 --- a/flang/test/Lower/OpenMP/FIR/wsloop-reduction-min.f90 +++ b/flang/test/Lower/OpenMP/FIR/wsloop-reduction-min.f90 @@ -21,26 +21,30 @@ !CHECK-SAME: %[[Y_BOX:.*]]: !fir.box> !CHECK: %[[X_REF:.*]] = fir.alloca i32 {bindc_name = "x", uniq_name = "_QFreduction_min_intEx"} !CHECK: omp.parallel -!CHECK: omp.wsloop reduction(@[[MIN_DECLARE_I]] %[[X_REF]] -> %[[PRV:.+]] : !fir.ref) for -!CHECK: %[[LPRV:.+]] = fir.load %[[PRV]] : !fir.ref -!CHECK: %[[Y_I_REF:.*]] = fir.coordinate_of %[[Y_BOX]] -!CHECK: %[[Y_I:.*]] = fir.load %[[Y_I_REF]] : !fir.ref -!CHECK: %[[RES:.+]] = arith.cmpi slt, %[[LPRV]], %[[Y_I]] : i32 -!CHECK: %[[SEL:.+]] = arith.select %[[RES]], %[[LPRV]], %[[Y_I]] -!CHECK: fir.store %[[SEL]] to %[[PRV]] : !fir.ref -!CHECK: omp.yield +!CHECK: omp.wsloop reduction(@[[MIN_DECLARE_I]] %[[X_REF]] -> %[[PRV:.+]] : !fir.ref) +!CHECK-NEXT: omp.loop_nest +!CHECK: %[[LPRV:.+]] = fir.load %[[PRV]] : !fir.ref +!CHECK: %[[Y_I_REF:.*]] = fir.coordinate_of %[[Y_BOX]] +!CHECK: %[[Y_I:.*]] = fir.load %[[Y_I_REF]] : !fir.ref +!CHECK: %[[RES:.+]] = arith.cmpi slt, %[[LPRV]], %[[Y_I]] : i32 +!CHECK: %[[SEL:.+]] = arith.select %[[RES]], %[[LPRV]], %[[Y_I]] +!CHECK: fir.store %[[SEL]] to %[[PRV]] : !fir.ref +!CHECK: omp.yield +!CHECK: omp.terminator !CHECK: omp.terminator !CHECK-LABEL: @_QPreduction_min_real !CHECK-SAME: %[[Y_BOX:.*]]: !fir.box> !CHECK: %[[X_REF:.*]] = fir.alloca f32 {bindc_name = "x", uniq_name = "_QFreduction_min_realEx"} !CHECK: omp.parallel -!CHECK: omp.wsloop reduction(@[[MIN_DECLARE_F]] %[[X_REF]] -> %[[PRV:.+]] : !fir.ref) for -!CHECK: %[[LPRV:.+]] = fir.load %[[PRV]] : !fir.ref -!CHECK: %[[Y_I_REF:.*]] = fir.coordinate_of %[[Y_BOX]] -!CHECK: %[[Y_I:.*]] = fir.load %[[Y_I_REF]] : !fir.ref -!CHECK: %[[RES:.+]] = arith.cmpf ogt, %[[Y_I]], %[[LPRV]] {{.*}} : f32 -!CHECK: omp.yield +!CHECK: omp.wsloop reduction(@[[MIN_DECLARE_F]] %[[X_REF]] -> %[[PRV:.+]] : !fir.ref) +!CHECK-NEXT: omp.loop_nest +!CHECK: %[[LPRV:.+]] = fir.load %[[PRV]] : !fir.ref +!CHECK: %[[Y_I_REF:.*]] = fir.coordinate_of %[[Y_BOX]] +!CHECK: %[[Y_I:.*]] = fir.load %[[Y_I_REF]] : !fir.ref +!CHECK: %[[RES:.+]] = arith.cmpf ogt, %[[Y_I]], %[[LPRV]] {{.*}} : f32 +!CHECK: omp.yield +!CHECK: omp.terminator !CHECK: omp.terminator subroutine reduction_min_int(y) diff --git a/flang/test/Lower/OpenMP/FIR/wsloop-simd.f90 b/flang/test/Lower/OpenMP/FIR/wsloop-simd.f90 index 2e3f8ca3c207dd0b53529bbd922226158707cd84..751e4c8c57094cc87a512a3300f11f1408da4a15 100644 --- a/flang/test/Lower/OpenMP/FIR/wsloop-simd.f90 +++ b/flang/test/Lower/OpenMP/FIR/wsloop-simd.f90 @@ -11,23 +11,26 @@ program wsloop_dynamic !CHECK: omp.parallel { !$OMP DO SCHEDULE(simd: runtime) -!CHECK: %[[WS_LB:.*]] = arith.constant 1 : i32 -!CHECK: %[[WS_UB:.*]] = arith.constant 9 : i32 -!CHECK: %[[WS_STEP:.*]] = arith.constant 1 : i32 -!CHECK: omp.wsloop schedule(runtime, simd) nowait for (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) -!CHECK: fir.store %[[I]] to %[[STORE:.*]] : !fir.ref +!CHECK: %[[WS_LB:.*]] = arith.constant 1 : i32 +!CHECK: %[[WS_UB:.*]] = arith.constant 9 : i32 +!CHECK: %[[WS_STEP:.*]] = arith.constant 1 : i32 +!CHECK: omp.wsloop schedule(runtime, simd) nowait { +!CHECK-NEXT: omp.loop_nest (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) { +!CHECK: fir.store %[[I]] to %[[STORE:.*]] : !fir.ref do i=1, 9 print*, i -!CHECK: %[[RTBEGIN:.*]] = fir.call @_FortranAioBeginExternalListOutput -!CHECK: %[[LOAD:.*]] = fir.load %[[STORE]] : !fir.ref -!CHECK: fir.call @_FortranAioOutputInteger32(%[[RTBEGIN]], %[[LOAD]]) {{.*}}: (!fir.ref, i32) -> i1 -!CHECK: fir.call @_FortranAioEndIoStatement(%[[RTBEGIN]]) {{.*}}: (!fir.ref) -> i32 +!CHECK: %[[RTBEGIN:.*]] = fir.call @_FortranAioBeginExternalListOutput +!CHECK: %[[LOAD:.*]] = fir.load %[[STORE]] : !fir.ref +!CHECK: fir.call @_FortranAioOutputInteger32(%[[RTBEGIN]], %[[LOAD]]) {{.*}}: (!fir.ref, i32) -> i1 +!CHECK: fir.call @_FortranAioEndIoStatement(%[[RTBEGIN]]) {{.*}}: (!fir.ref) -> i32 end do -!CHECK: omp.yield -!CHECK: } -!CHECK: omp.terminator -!CHECK: } +!CHECK: omp.yield +!CHECK: } +!CHECK: omp.terminator +!CHECK: } +!CHECK: omp.terminator +!CHECK: } !$OMP END DO NOWAIT !$OMP END PARALLEL diff --git a/flang/test/Lower/OpenMP/FIR/wsloop-variable.f90 b/flang/test/Lower/OpenMP/FIR/wsloop-variable.f90 index 4f34f30f3e7c98189cb2a648821ea6cbe0d89a0a..4bd876012278924da02bad5e694d49ce4289df33 100644 --- a/flang/test/Lower/OpenMP/FIR/wsloop-variable.f90 +++ b/flang/test/Lower/OpenMP/FIR/wsloop-variable.f90 @@ -14,26 +14,29 @@ program wsloop_variable integer(kind=16) :: i16, i16_lb real :: x -!CHECK: %[[TMP0:.*]] = arith.constant 1 : i32 -!CHECK: %[[TMP1:.*]] = arith.constant 100 : i32 -!CHECK: %[[TMP2:.*]] = fir.convert %[[TMP0]] : (i32) -> i64 -!CHECK: %[[TMP3:.*]] = fir.convert %{{.*}} : (i8) -> i64 -!CHECK: %[[TMP4:.*]] = fir.convert %{{.*}} : (i16) -> i64 -!CHECK: %[[TMP5:.*]] = fir.convert %{{.*}} : (i128) -> i64 -!CHECK: %[[TMP6:.*]] = fir.convert %[[TMP1]] : (i32) -> i64 -!CHECK: %[[TMP7:.*]] = fir.convert %{{.*}} : (i32) -> i64 -!CHECK: omp.wsloop for (%[[ARG0:.*]], %[[ARG1:.*]]) : i64 = (%[[TMP2]], %[[TMP5]]) to (%[[TMP3]], %[[TMP6]]) inclusive step (%[[TMP4]], %[[TMP7]]) { -!CHECK: %[[ARG0_I16:.*]] = fir.convert %[[ARG0]] : (i64) -> i16 -!CHECK: fir.store %[[ARG0_I16]] to %[[STORE_IV0:.*]] : !fir.ref -!CHECK: fir.store %[[ARG1]] to %[[STORE_IV1:.*]] : !fir.ref -!CHECK: %[[LOAD_IV0:.*]] = fir.load %[[STORE_IV0]] : !fir.ref -!CHECK: %[[LOAD_IV0_I64:.*]] = fir.convert %[[LOAD_IV0]] : (i16) -> i64 -!CHECK: %[[LOAD_IV1:.*]] = fir.load %[[STORE_IV1]] : !fir.ref -!CHECK: %[[TMP10:.*]] = arith.addi %[[LOAD_IV0_I64]], %[[LOAD_IV1]] : i64 -!CHECK: %[[TMP11:.*]] = fir.convert %[[TMP10]] : (i64) -> f32 -!CHECK: fir.store %[[TMP11]] to %{{.*}} : !fir.ref -!CHECK: omp.yield -!CHECK: } +!CHECK: %[[TMP0:.*]] = arith.constant 1 : i32 +!CHECK: %[[TMP1:.*]] = arith.constant 100 : i32 +!CHECK: %[[TMP2:.*]] = fir.convert %[[TMP0]] : (i32) -> i64 +!CHECK: %[[TMP3:.*]] = fir.convert %{{.*}} : (i8) -> i64 +!CHECK: %[[TMP4:.*]] = fir.convert %{{.*}} : (i16) -> i64 +!CHECK: %[[TMP5:.*]] = fir.convert %{{.*}} : (i128) -> i64 +!CHECK: %[[TMP6:.*]] = fir.convert %[[TMP1]] : (i32) -> i64 +!CHECK: %[[TMP7:.*]] = fir.convert %{{.*}} : (i32) -> i64 +!CHECK: omp.wsloop { +!CHECK-NEXT: omp.loop_nest (%[[ARG0:.*]], %[[ARG1:.*]]) : i64 = (%[[TMP2]], %[[TMP5]]) to (%[[TMP3]], %[[TMP6]]) inclusive step (%[[TMP4]], %[[TMP7]]) { +!CHECK: %[[ARG0_I16:.*]] = fir.convert %[[ARG0]] : (i64) -> i16 +!CHECK: fir.store %[[ARG0_I16]] to %[[STORE_IV0:.*]] : !fir.ref +!CHECK: fir.store %[[ARG1]] to %[[STORE_IV1:.*]] : !fir.ref +!CHECK: %[[LOAD_IV0:.*]] = fir.load %[[STORE_IV0]] : !fir.ref +!CHECK: %[[LOAD_IV0_I64:.*]] = fir.convert %[[LOAD_IV0]] : (i16) -> i64 +!CHECK: %[[LOAD_IV1:.*]] = fir.load %[[STORE_IV1]] : !fir.ref +!CHECK: %[[TMP10:.*]] = arith.addi %[[LOAD_IV0_I64]], %[[LOAD_IV1]] : i64 +!CHECK: %[[TMP11:.*]] = fir.convert %[[TMP10]] : (i64) -> f32 +!CHECK: fir.store %[[TMP11]] to %{{.*}} : !fir.ref +!CHECK: omp.yield +!CHECK: } +!CHECK: omp.terminator +!CHECK: } !$omp do collapse(2) do i2 = 1, i1_ub, i2_s @@ -43,18 +46,20 @@ program wsloop_variable end do !$omp end do -!CHECK: %[[TMP12:.*]] = arith.constant 1 : i32 -!CHECK: %[[TMP13:.*]] = fir.convert %{{.*}} : (i8) -> i32 -!CHECK: %[[TMP14:.*]] = fir.convert %{{.*}} : (i64) -> i32 -!CHECK: omp.wsloop for (%[[ARG0:.*]]) : i32 = (%[[TMP12]]) to (%[[TMP13]]) inclusive step (%[[TMP14]]) { -!CHECK: %[[ARG0_I16:.*]] = fir.convert %[[ARG0]] : (i32) -> i16 -!CHECK: fir.store %[[ARG0_I16]] to %[[STORE3:.*]] : !fir.ref -!CHECK: %[[LOAD3:.*]] = fir.load %[[STORE3]] : !fir.ref -!CHECK: %[[TMP16:.*]] = fir.convert %[[LOAD3]] : (i16) -> f32 - -!CHECK: fir.store %[[TMP16]] to %{{.*}} : !fir.ref -!CHECK: omp.yield -!CHECK: } +!CHECK: %[[TMP12:.*]] = arith.constant 1 : i32 +!CHECK: %[[TMP13:.*]] = fir.convert %{{.*}} : (i8) -> i32 +!CHECK: %[[TMP14:.*]] = fir.convert %{{.*}} : (i64) -> i32 +!CHECK: omp.wsloop { +!CHECK-NEXT: omp.loop_nest (%[[ARG0:.*]]) : i32 = (%[[TMP12]]) to (%[[TMP13]]) inclusive step (%[[TMP14]]) { +!CHECK: %[[ARG0_I16:.*]] = fir.convert %[[ARG0]] : (i32) -> i16 +!CHECK: fir.store %[[ARG0_I16]] to %[[STORE3:.*]] : !fir.ref +!CHECK: %[[LOAD3:.*]] = fir.load %[[STORE3]] : !fir.ref +!CHECK: %[[TMP16:.*]] = fir.convert %[[LOAD3]] : (i16) -> f32 +!CHECK: fir.store %[[TMP16]] to %{{.*}} : !fir.ref +!CHECK: omp.yield +!CHECK: } +!CHECK: omp.terminator +!CHECK: } !$omp do do i2 = 1, i1_ub, i8_s @@ -62,17 +67,20 @@ program wsloop_variable end do !$omp end do -!CHECK: %[[TMP17:.*]] = fir.convert %{{.*}} : (i8) -> i64 -!CHECK: %[[TMP18:.*]] = fir.convert %{{.*}} : (i16) -> i64 -!CHECK: %[[TMP19:.*]] = fir.convert %{{.*}} : (i32) -> i64 -!CHECK: omp.wsloop for (%[[ARG1:.*]]) : i64 = (%[[TMP17]]) to (%[[TMP18]]) inclusive step (%[[TMP19]]) { -!CHECK: %[[ARG1_I128:.*]] = fir.convert %[[ARG1]] : (i64) -> i128 -!CHECK: fir.store %[[ARG1_I128]] to %[[STORE4:.*]] : !fir.ref -!CHECK: %[[LOAD4:.*]] = fir.load %[[STORE4]] : !fir.ref -!CHECK: %[[TMP21:.*]] = fir.convert %[[LOAD4]] : (i128) -> f32 -!CHECK: fir.store %[[TMP21]] to %{{.*}} : !fir.ref -!CHECK: omp.yield -!CHECK: } +!CHECK: %[[TMP17:.*]] = fir.convert %{{.*}} : (i8) -> i64 +!CHECK: %[[TMP18:.*]] = fir.convert %{{.*}} : (i16) -> i64 +!CHECK: %[[TMP19:.*]] = fir.convert %{{.*}} : (i32) -> i64 +!CHECK: omp.wsloop { +!CHECK-NEXT: omp.loop_nest (%[[ARG1:.*]]) : i64 = (%[[TMP17]]) to (%[[TMP18]]) inclusive step (%[[TMP19]]) { +!CHECK: %[[ARG1_I128:.*]] = fir.convert %[[ARG1]] : (i64) -> i128 +!CHECK: fir.store %[[ARG1_I128]] to %[[STORE4:.*]] : !fir.ref +!CHECK: %[[LOAD4:.*]] = fir.load %[[STORE4]] : !fir.ref +!CHECK: %[[TMP21:.*]] = fir.convert %[[LOAD4]] : (i128) -> f32 +!CHECK: fir.store %[[TMP21]] to %{{.*}} : !fir.ref +!CHECK: omp.yield +!CHECK: } +!CHECK: omp.terminator +!CHECK: } !$omp do do i16 = i1_lb, i2_ub, i4_s @@ -97,34 +105,37 @@ end program wsloop_variable !CHECK: %[[VAL_9:.*]] = fir.load %[[VAL_3]] : !fir.ref !CHECK: %[[VAL_10:.*]] = fir.convert %[[VAL_8]] : (i8) -> i32 !CHECK: %[[VAL_11:.*]] = fir.convert %[[VAL_9]] : (i16) -> i32 -!CHECK: omp.wsloop for (%[[ARG0:.*]]) : i32 = (%[[VAL_7]]) to (%[[VAL_10]]) inclusive step (%[[VAL_11]]) { -!CHECK: %[[ARG0_I16:.*]] = fir.convert %[[ARG0]] : (i32) -> i16 -!CHECK: fir.store %[[ARG0_I16]] to %[[STORE_IV:.*]] : !fir.ref -!CHECK: %[[VAL_13:.*]] = fir.load %[[VAL_0]] : !fir.ref -!CHECK: %[[VAL_14:.*]] = fir.convert %[[VAL_13]] : (i128) -> index -!CHECK: %[[VAL_15:.*]] = arith.constant 100 : i32 -!CHECK: %[[VAL_16:.*]] = fir.convert %[[VAL_15]] : (i32) -> index -!CHECK: %[[VAL_17:.*]] = fir.load %[[VAL_4]] : !fir.ref -!CHECK: %[[VAL_18:.*]] = fir.convert %[[VAL_17]] : (i32) -> index -!CHECK: %[[LB:.*]] = fir.convert %[[VAL_14]] : (index) -> i64 -!CHECK: %[[VAL_19:.*]]:2 = fir.do_loop %[[VAL_20:[^ ]*]] = -!CHECK-SAME: %[[VAL_14]] to %[[VAL_16]] step %[[VAL_18]] -!CHECK-SAME: iter_args(%[[IV:.*]] = %[[LB]]) -> (index, i64) { -!CHECK: fir.store %[[IV]] to %[[VAL_5]] : !fir.ref -!CHECK: %[[LOAD_IV:.*]] = fir.load %[[STORE_IV]] : !fir.ref -!CHECK: %[[VAL_22:.*]] = fir.convert %[[LOAD_IV]] : (i16) -> i64 -!CHECK: %[[VAL_23:.*]] = fir.load %[[VAL_5]] : !fir.ref -!CHECK: %[[VAL_24:.*]] = arith.addi %[[VAL_22]], %[[VAL_23]] : i64 -!CHECK: %[[VAL_25:.*]] = fir.convert %[[VAL_24]] : (i64) -> f32 -!CHECK: fir.store %[[VAL_25]] to %[[VAL_6]] : !fir.ref -!CHECK: %[[VAL_26:.*]] = arith.addi %[[VAL_20]], %[[VAL_18]] : index -!CHECK: %[[STEPCAST:.*]] = fir.convert %[[VAL_18]] : (index) -> i64 -!CHECK: %[[IVLOAD:.*]] = fir.load %[[VAL_5]] : !fir.ref -!CHECK: %[[IVINC:.*]] = arith.addi %[[IVLOAD]], %[[STEPCAST]] -!CHECK: fir.result %[[VAL_26]], %[[IVINC]] : index, i64 +!CHECK: omp.wsloop { +!CHECK-NEXT: omp.loop_nest (%[[ARG0:.*]]) : i32 = (%[[VAL_7]]) to (%[[VAL_10]]) inclusive step (%[[VAL_11]]) { +!CHECK: %[[ARG0_I16:.*]] = fir.convert %[[ARG0]] : (i32) -> i16 +!CHECK: fir.store %[[ARG0_I16]] to %[[STORE_IV:.*]] : !fir.ref +!CHECK: %[[VAL_13:.*]] = fir.load %[[VAL_0]] : !fir.ref +!CHECK: %[[VAL_14:.*]] = fir.convert %[[VAL_13]] : (i128) -> index +!CHECK: %[[VAL_15:.*]] = arith.constant 100 : i32 +!CHECK: %[[VAL_16:.*]] = fir.convert %[[VAL_15]] : (i32) -> index +!CHECK: %[[VAL_17:.*]] = fir.load %[[VAL_4]] : !fir.ref +!CHECK: %[[VAL_18:.*]] = fir.convert %[[VAL_17]] : (i32) -> index +!CHECK: %[[LB:.*]] = fir.convert %[[VAL_14]] : (index) -> i64 +!CHECK: %[[VAL_19:.*]]:2 = fir.do_loop %[[VAL_20:[^ ]*]] = +!CHECK-SAME: %[[VAL_14]] to %[[VAL_16]] step %[[VAL_18]] +!CHECK-SAME: iter_args(%[[IV:.*]] = %[[LB]]) -> (index, i64) { +!CHECK: fir.store %[[IV]] to %[[VAL_5]] : !fir.ref +!CHECK: %[[LOAD_IV:.*]] = fir.load %[[STORE_IV]] : !fir.ref +!CHECK: %[[VAL_22:.*]] = fir.convert %[[LOAD_IV]] : (i16) -> i64 +!CHECK: %[[VAL_23:.*]] = fir.load %[[VAL_5]] : !fir.ref +!CHECK: %[[VAL_24:.*]] = arith.addi %[[VAL_22]], %[[VAL_23]] : i64 +!CHECK: %[[VAL_25:.*]] = fir.convert %[[VAL_24]] : (i64) -> f32 +!CHECK: fir.store %[[VAL_25]] to %[[VAL_6]] : !fir.ref +!CHECK: %[[VAL_26:.*]] = arith.addi %[[VAL_20]], %[[VAL_18]] : index +!CHECK: %[[STEPCAST:.*]] = fir.convert %[[VAL_18]] : (index) -> i64 +!CHECK: %[[IVLOAD:.*]] = fir.load %[[VAL_5]] : !fir.ref +!CHECK: %[[IVINC:.*]] = arith.addi %[[IVLOAD]], %[[STEPCAST]] +!CHECK: fir.result %[[VAL_26]], %[[IVINC]] : index, i64 +!CHECK: } +!CHECK: fir.store %[[VAL_19]]#1 to %[[VAL_5]] : !fir.ref +!CHECK: omp.yield !CHECK: } -!CHECK: fir.store %[[VAL_19]]#1 to %[[VAL_5]] : !fir.ref -!CHECK: omp.yield +!CHECK: omp.terminator !CHECK: } subroutine wsloop_variable_sub @@ -146,16 +157,19 @@ subroutine wsloop_variable_sub !CHECK: %[[C1:.*]] = arith.constant 1 : i32 !CHECK: %[[C10:.*]] = arith.constant 10 : i32 !CHECK: %[[C1_2:.*]] = arith.constant 1 : i32 -!CHECK: omp.wsloop for (%[[ARG0:.*]]) : i32 = (%[[C1]]) to (%[[C10]]) inclusive step (%[[C1_2]]) { -!CHECK: %[[ARG0_I8:.*]] = fir.convert %[[ARG0]] : (i32) -> i8 -!CHECK: fir.store %[[ARG0_I8]] to %[[IV2]] : !fir.ref -!CHECK: %[[IV2LOAD:.*]] = fir.load %[[IV2]] : !fir.ref -!CHECK: %[[J1LOAD:.*]] = fir.load %[[J1]] : !fir.ref -!CHECK: %[[VAL_27:.*]] = arith.cmpi eq, %[[IV2LOAD]], %[[J1LOAD]] : i8 -!CHECK: fir.if %[[VAL_27]] { -!CHECK: } else { +!CHECK: omp.wsloop { +!CHECK-NEXT: omp.loop_nest (%[[ARG0:.*]]) : i32 = (%[[C1]]) to (%[[C10]]) inclusive step (%[[C1_2]]) { +!CHECK: %[[ARG0_I8:.*]] = fir.convert %[[ARG0]] : (i32) -> i8 +!CHECK: fir.store %[[ARG0_I8]] to %[[IV2]] : !fir.ref +!CHECK: %[[IV2LOAD:.*]] = fir.load %[[IV2]] : !fir.ref +!CHECK: %[[J1LOAD:.*]] = fir.load %[[J1]] : !fir.ref +!CHECK: %[[VAL_27:.*]] = arith.cmpi eq, %[[IV2LOAD]], %[[J1LOAD]] : i8 +!CHECK: fir.if %[[VAL_27]] { +!CHECK: } else { +!CHECK: } +!CHECK: omp.yield !CHECK: } -!CHECK: omp.yield +!CHECK: omp.terminator !CHECK: } j1 = 5 diff --git a/flang/test/Lower/OpenMP/FIR/wsloop.f90 b/flang/test/Lower/OpenMP/FIR/wsloop.f90 index abc0489b08ff5560ed6b3b30490ba37b0ff0148d..c9e428abdb440e6bf566506f9a6d4832abfc3268 100644 --- a/flang/test/Lower/OpenMP/FIR/wsloop.f90 +++ b/flang/test/Lower/OpenMP/FIR/wsloop.f90 @@ -7,21 +7,23 @@ subroutine simple_loop integer :: i ! CHECK: omp.parallel !$OMP PARALLEL - ! CHECK: %[[ALLOCA_IV:.*]] = fir.alloca i32 {{{.*}}, pinned} - ! CHECK: %[[WS_LB:.*]] = arith.constant 1 : i32 - ! CHECK: %[[WS_UB:.*]] = arith.constant 9 : i32 - ! CHECK: %[[WS_STEP:.*]] = arith.constant 1 : i32 - ! CHECK: omp.wsloop for (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) + ! CHECK: %[[ALLOCA_IV:.*]] = fir.alloca i32 {{{.*}}, pinned} + ! CHECK: %[[WS_LB:.*]] = arith.constant 1 : i32 + ! CHECK: %[[WS_UB:.*]] = arith.constant 9 : i32 + ! CHECK: %[[WS_STEP:.*]] = arith.constant 1 : i32 + ! CHECK: omp.wsloop { + ! CHECK-NEXT: omp.loop_nest (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) { !$OMP DO do i=1, 9 - ! CHECK: fir.store %[[I]] to %[[ALLOCA_IV:.*]] : !fir.ref - ! CHECK: %[[LOAD_IV:.*]] = fir.load %[[ALLOCA_IV]] : !fir.ref - ! CHECK: fir.call @_FortranAioOutputInteger32({{.*}}, %[[LOAD_IV]]) {{.*}}: (!fir.ref, i32) -> i1 + ! CHECK: fir.store %[[I]] to %[[ALLOCA_IV:.*]] : !fir.ref + ! CHECK: %[[LOAD_IV:.*]] = fir.load %[[ALLOCA_IV]] : !fir.ref + ! CHECK: fir.call @_FortranAioOutputInteger32({{.*}}, %[[LOAD_IV]]) {{.*}}: (!fir.ref, i32) -> i1 print*, i end do - ! CHECK: omp.yield + ! CHECK: omp.yield + ! CHECK: omp.terminator !$OMP END DO - ! CHECK: omp.terminator + ! CHECK: omp.terminator !$OMP END PARALLEL end subroutine @@ -30,21 +32,23 @@ subroutine simple_loop_with_step integer :: i ! CHECK: omp.parallel !$OMP PARALLEL - ! CHECK: %[[ALLOCA_IV:.*]] = fir.alloca i32 {{{.*}}, pinned} - ! CHECK: %[[WS_LB:.*]] = arith.constant 1 : i32 - ! CHECK: %[[WS_UB:.*]] = arith.constant 9 : i32 - ! CHECK: %[[WS_STEP:.*]] = arith.constant 2 : i32 - ! CHECK: omp.wsloop for (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) - ! CHECK: fir.store %[[I]] to %[[ALLOCA_IV]] : !fir.ref - ! CHECK: %[[LOAD_IV:.*]] = fir.load %[[ALLOCA_IV]] : !fir.ref + ! CHECK: %[[ALLOCA_IV:.*]] = fir.alloca i32 {{{.*}}, pinned} + ! CHECK: %[[WS_LB:.*]] = arith.constant 1 : i32 + ! CHECK: %[[WS_UB:.*]] = arith.constant 9 : i32 + ! CHECK: %[[WS_STEP:.*]] = arith.constant 2 : i32 + ! CHECK: omp.wsloop { + ! CHECK-NEXT: omp.loop_nest (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) { + ! CHECK: fir.store %[[I]] to %[[ALLOCA_IV]] : !fir.ref + ! CHECK: %[[LOAD_IV:.*]] = fir.load %[[ALLOCA_IV]] : !fir.ref !$OMP DO do i=1, 9, 2 - ! CHECK: fir.call @_FortranAioOutputInteger32({{.*}}, %[[LOAD_IV]]) {{.*}}: (!fir.ref, i32) -> i1 + ! CHECK: fir.call @_FortranAioOutputInteger32({{.*}}, %[[LOAD_IV]]) {{.*}}: (!fir.ref, i32) -> i1 print*, i end do - ! CHECK: omp.yield + ! CHECK: omp.yield + ! CHECK: omp.terminator !$OMP END DO - ! CHECK: omp.terminator + ! CHECK: omp.terminator !$OMP END PARALLEL end subroutine @@ -53,20 +57,22 @@ subroutine loop_with_schedule_nowait integer :: i ! CHECK: omp.parallel !$OMP PARALLEL - ! CHECK: %[[ALLOCA_IV:.*]] = fir.alloca i32 {{{.*}}, pinned} - ! CHECK: %[[WS_LB:.*]] = arith.constant 1 : i32 - ! CHECK: %[[WS_UB:.*]] = arith.constant 9 : i32 - ! CHECK: %[[WS_STEP:.*]] = arith.constant 1 : i32 - ! CHECK: omp.wsloop schedule(runtime) nowait for (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) + ! CHECK: %[[ALLOCA_IV:.*]] = fir.alloca i32 {{{.*}}, pinned} + ! CHECK: %[[WS_LB:.*]] = arith.constant 1 : i32 + ! CHECK: %[[WS_UB:.*]] = arith.constant 9 : i32 + ! CHECK: %[[WS_STEP:.*]] = arith.constant 1 : i32 + ! CHECK: omp.wsloop schedule(runtime) nowait { + ! CHECK-NEXT: omp.loop_nest (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) { !$OMP DO SCHEDULE(runtime) do i=1, 9 - ! CHECK: fir.store %[[I]] to %[[ALLOCA_IV]] : !fir.ref - ! CHECK: %[[LOAD_IV:.*]] = fir.load %[[ALLOCA_IV]] : !fir.ref - ! CHECK: fir.call @_FortranAioOutputInteger32({{.*}}, %[[LOAD_IV]]) {{.*}}: (!fir.ref, i32) -> i1 + ! CHECK: fir.store %[[I]] to %[[ALLOCA_IV]] : !fir.ref + ! CHECK: %[[LOAD_IV:.*]] = fir.load %[[ALLOCA_IV]] : !fir.ref + ! CHECK: fir.call @_FortranAioOutputInteger32({{.*}}, %[[LOAD_IV]]) {{.*}}: (!fir.ref, i32) -> i1 print*, i end do - ! CHECK: omp.yield + ! CHECK: omp.yield + ! CHECK: omp.terminator !$OMP END DO NOWAIT - ! CHECK: omp.terminator + ! CHECK: omp.terminator !$OMP END PARALLEL end subroutine diff --git a/flang/test/Lower/OpenMP/Todo/omp-default-clause-inner-loop.f90 b/flang/test/Lower/OpenMP/Todo/omp-default-clause-inner-loop.f90 index 5c624d31b5f36da27113d4ed98ab798a254c8099..c245137f16c7af0fcb5b8dca104c5ac2fbbf7e88 100644 --- a/flang/test/Lower/OpenMP/Todo/omp-default-clause-inner-loop.f90 +++ b/flang/test/Lower/OpenMP/Todo/omp-default-clause-inner-loop.f90 @@ -12,7 +12,8 @@ ! CHECK: %[[const_1:.*]] = arith.constant 1 : i32 ! CHECK: %[[const_2:.*]] = arith.constant 10 : i32 ! CHECK: %[[const_3:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop for (%[[ARG:.*]]) : i32 = (%[[const_1]]) to (%[[const_2]]) inclusive step (%[[const_3]]) { +! CHECK: omp.wsloop { +! CHECK-NEXT: omp.loop_nest (%[[ARG:.*]]) : i32 = (%[[const_1]]) to (%[[const_2]]) inclusive step (%[[const_3]]) { ! CHECK: fir.store %[[ARG]] to %[[TEMP]] : !fir.ref ! EXPECTED: %[[temp_1:.*]] = fir.load %[[PRIVATE_Z]] : !fir.ref ! CHECK: %[[temp_1:.*]] = fir.load %{{.*}} : !fir.ref @@ -24,6 +25,8 @@ ! CHECK: } ! CHECK: omp.terminator ! CHECK: } +! CHECK: omp.terminator +! CHECK: } subroutine nested_default_clause() integer x, y, z !$omp parallel do default(private) diff --git a/flang/test/Lower/OpenMP/copyin.f90 b/flang/test/Lower/OpenMP/copyin.f90 index 895e1abd274f30eeaae4156e884c948bd75fa21a..dda563303148bbb059c51dc9bfed8c288fa6c066 100644 --- a/flang/test/Lower/OpenMP/copyin.f90 +++ b/flang/test/Lower/OpenMP/copyin.f90 @@ -156,10 +156,13 @@ end ! CHECK: %[[VAL_11:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_12:.*]] = fir.load %[[VAL_9]]#0 : !fir.ref ! CHECK: %[[VAL_13:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop for (%[[VAL_14:.*]]) : i32 = (%[[VAL_11]]) to (%[[VAL_12]]) inclusive step (%[[VAL_13]]) { -! CHECK: fir.store %[[VAL_14]] to %[[VAL_7]]#1 : !fir.ref -! CHECK: fir.call @_QPsub4(%[[VAL_9]]#1) fastmath : (!fir.ref) -> () -! CHECK: omp.yield +! CHECK: omp.wsloop { +! CHECK-NEXT: omp.loop_nest (%[[VAL_14:.*]]) : i32 = (%[[VAL_11]]) to (%[[VAL_12]]) inclusive step (%[[VAL_13]]) { +! CHECK: fir.store %[[VAL_14]] to %[[VAL_7]]#1 : !fir.ref +! CHECK: fir.call @_QPsub4(%[[VAL_9]]#1) fastmath : (!fir.ref) -> () +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } @@ -320,13 +323,16 @@ end subroutine ! CHECK: %[[VAL_34:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_35:.*]] = fir.load %[[VAL_26]]#0 : !fir.ref ! CHECK: %[[VAL_36:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop for (%[[VAL_37:.*]]) : i32 = (%[[VAL_34]]) to (%[[VAL_35]]) inclusive step (%[[VAL_36]]) { -! CHECK: fir.store %[[VAL_37]] to %[[VAL_20]]#1 : !fir.ref -! CHECK: %[[VAL_38:.*]] = fir.load %[[VAL_31]]#0 : !fir.ref -! CHECK: %[[VAL_39:.*]] = fir.load %[[VAL_20]]#0 : !fir.ref -! CHECK: %[[VAL_40:.*]] = arith.addi %[[VAL_38]], %[[VAL_39]] : i32 -! CHECK: hlfir.assign %[[VAL_40]] to %[[VAL_31]]#0 : i32, !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop { +! CHECK-NEXT: omp.loop_nest (%[[VAL_37:.*]]) : i32 = (%[[VAL_34]]) to (%[[VAL_35]]) inclusive step (%[[VAL_36]]) { +! CHECK: fir.store %[[VAL_37]] to %[[VAL_20]]#1 : !fir.ref +! CHECK: %[[VAL_38:.*]] = fir.load %[[VAL_31]]#0 : !fir.ref +! CHECK: %[[VAL_39:.*]] = fir.load %[[VAL_20]]#0 : !fir.ref +! CHECK: %[[VAL_40:.*]] = arith.addi %[[VAL_38]], %[[VAL_39]] : i32 +! CHECK: hlfir.assign %[[VAL_40]] to %[[VAL_31]]#0 : i32, !fir.ref +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } diff --git a/flang/test/Lower/OpenMP/default-clause-byref.f90 b/flang/test/Lower/OpenMP/default-clause-byref.f90 index 1167ba7e6ae0d47c14a6b6bf68a4c5d3fcda70eb..6a91927ab02dba5ea3a4d2d422450b1b42826de7 100644 --- a/flang/test/Lower/OpenMP/default-clause-byref.f90 +++ b/flang/test/Lower/OpenMP/default-clause-byref.f90 @@ -352,10 +352,13 @@ subroutine skipped_default_clause_checks() type(it)::iii !CHECK: omp.parallel { -!CHECK: omp.wsloop byref reduction(@min_byref_i32 %[[VAL_Z_DECLARE]]#0 -> %[[PRV:.+]] : !fir.ref) for (%[[ARG:.*]]) {{.*}} { +!CHECK: omp.wsloop byref reduction(@min_byref_i32 %[[VAL_Z_DECLARE]]#0 -> %[[PRV:.+]] : !fir.ref) { +!CHECK-NEXT: omp.loop_nest (%[[ARG:.*]]) {{.*}} { !CHECK: omp.yield !CHECK: } !CHECK: omp.terminator +!CHECK: } +!CHECK: omp.terminator !CHECK: } !$omp parallel do default(private) REDUCTION(MIN:z) do i = 1, 10 diff --git a/flang/test/Lower/OpenMP/default-clause-implied-do-fix.f90 b/flang/test/Lower/OpenMP/default-clause-implied-do-fix.f90 new file mode 100644 index 0000000000000000000000000000000000000000..25579272a6e0bc4bde470b5efa2416b884c89abc --- /dev/null +++ b/flang/test/Lower/OpenMP/default-clause-implied-do-fix.f90 @@ -0,0 +1,11 @@ +!RUN: %flang_fc1 -emit-hlfir -fopenmp %s -o - | FileCheck %s + +!CHECK: @_QPsb +subroutine sb(a) + integer :: a(:) +!CHECK: omp.parallel + !$omp parallel default(private) +!CHECK: hlfir.elemental + if (any(a/=(/(100,i=1,5)/))) print *, "OK" + !$omp end parallel +end subroutine diff --git a/flang/test/Lower/OpenMP/default-clause.f90 b/flang/test/Lower/OpenMP/default-clause.f90 index 9a47e561338f1e49189845b0ff86ec72ff345e87..d3c6550821f0d47d4a94b51ed326690c15e12b85 100644 --- a/flang/test/Lower/OpenMP/default-clause.f90 +++ b/flang/test/Lower/OpenMP/default-clause.f90 @@ -352,10 +352,13 @@ subroutine skipped_default_clause_checks() type(it)::iii !CHECK: omp.parallel { -!CHECK: omp.wsloop reduction(@min_i32 %[[VAL_Z_DECLARE]]#0 -> %[[PRV:.+]] : !fir.ref) for (%[[ARG:.*]]) {{.*}} { +!CHECK: omp.wsloop reduction(@min_i32 %[[VAL_Z_DECLARE]]#0 -> %[[PRV:.+]] : !fir.ref) { +!CHECK-NEXT: omp.loop_nest (%[[ARG:.*]]) {{.*}} { !CHECK: omp.yield !CHECK: } !CHECK: omp.terminator +!CHECK: } +!CHECK: omp.terminator !CHECK: } !$omp parallel do default(private) REDUCTION(MIN:z) do i = 1, 10 diff --git a/flang/test/Lower/OpenMP/function-filtering-3.f90 b/flang/test/Lower/OpenMP/function-filtering-3.f90 new file mode 100644 index 0000000000000000000000000000000000000000..a277c06d620669b8a5eb66f14c715f1b567f5f9f --- /dev/null +++ b/flang/test/Lower/OpenMP/function-filtering-3.f90 @@ -0,0 +1,34 @@ +! RUN: %flang_fc1 -fopenmp -flang-experimental-hlfir -emit-llvm %s -o - | FileCheck --check-prefixes=LLVM-HOST,LLVM-ALL %s +! RUN: %flang_fc1 -fopenmp -emit-hlfir %s -o - | FileCheck --check-prefixes=MLIR-HOST,MLIR-ALL %s +! RUN: %flang_fc1 -fopenmp -fopenmp-is-target-device -flang-experimental-hlfir -emit-llvm %s -o - | FileCheck --check-prefixes=LLVM-DEVICE,LLVM-ALL %s +! RUN: %flang_fc1 -fopenmp -fopenmp-is-target-device -emit-hlfir %s -o - | FileCheck --check-prefixes=MLIR-DEVICE,MLIR-ALL %s +! RUN: bbc -fopenmp -emit-hlfir %s -o - | FileCheck --check-prefixes=MLIR-HOST,MLIR-ALL %s +! RUN: bbc -fopenmp -fopenmp-is-target-device -emit-hlfir %s -o - | FileCheck --check-prefixes=MLIR-DEVICE,MLIR-ALL %s + +! Check that the correct LLVM IR functions are kept for the host and device +! after running the whole set of translation and transformation passes from +! Fortran. + +! MLIR-HOST: func.func @{{.*}}host_parent_procedure( +! MLIR-HOST: return +! MLIR-DEVICE-NOT: func.func {{.*}}host_parent_procedure( + +! LLVM-HOST: define {{.*}} @host_parent_procedure{{.*}}( +! LLVM-DEVICE-NOT: {{.*}} @{{.*}}_host_parent_procedure{{.*}}( +subroutine host_parent_procedure(x) + integer, intent(out) :: x + call target_internal_proc(x) +contains +! MLIR-ALL: func.func {{.*}}@_QFhost_parent_procedurePtarget_internal_proc( + +! LLVM-HOST: define {{.*}} @_QFhost_parent_procedurePtarget_internal_proc( +! LLVM-DEVICE-NOT: define {{.*}} @_QFhost_parent_procedurePtarget_internal_proc( +! LLVM-ALL: define {{.*}} @__omp_offloading_{{.*}}QFhost_parent_procedurePtarget_internal_proc{{.*}}( + +subroutine target_internal_proc(x) + integer, intent(out) :: x + !$omp target map(from:x) + x = 10 + !$omp end target +end subroutine +end subroutine diff --git a/flang/test/Lower/OpenMP/hlfir-wsloop.f90 b/flang/test/Lower/OpenMP/hlfir-wsloop.f90 index b6be77fe3016d13f5253b6a4a394d4e82aa42159..fea05ae3d6bce34cac15d146f3cd91cbf597345f 100644 --- a/flang/test/Lower/OpenMP/hlfir-wsloop.f90 +++ b/flang/test/Lower/OpenMP/hlfir-wsloop.f90 @@ -11,17 +11,19 @@ subroutine simple_loop ! CHECK: omp.parallel !$OMP PARALLEL ! CHECK-DAG: %[[ALLOCA_IV:.*]] = fir.alloca i32 {{{.*}}, pinned} - ! CHECK: %[[IV:.*]] = fir.declare %[[ALLOCA_IV]] {uniq_name = "_QFsimple_loopEi"} : (!fir.ref) -> !fir.ref - ! CHECK: omp.wsloop for (%[[I:.*]]) : i32 = (%[[WS_ST]]) to (%[[WS_END]]) inclusive step (%[[WS_ST]]) + ! CHECK: %[[IV:.*]] = fir.declare %[[ALLOCA_IV]] {uniq_name = "_QFsimple_loopEi"} : (!fir.ref) -> !fir.ref + ! CHECK: omp.wsloop { + ! CHECK-NEXT: omp.loop_nest (%[[I:.*]]) : i32 = (%[[WS_ST]]) to (%[[WS_END]]) inclusive step (%[[WS_ST]]) { !$OMP DO do i=1, 9 ! CHECK: fir.store %[[I]] to %[[IV:.*]] : !fir.ref ! CHECK: %[[LOAD_IV:.*]] = fir.load %[[IV]] : !fir.ref - ! CHECK: fir.call @_FortranAioOutputInteger32({{.*}}, %[[LOAD_IV]]) {{.*}}: (!fir.ref, i32) -> i1 + ! CHECK: fir.call @_FortranAioOutputInteger32({{.*}}, %[[LOAD_IV]]) {{.*}}: (!fir.ref, i32) -> i1 print*, i end do - ! CHECK: omp.yield + ! CHECK: omp.yield + ! CHECK: omp.terminator !$OMP END DO - ! CHECK: omp.terminator + ! CHECK: omp.terminator !$OMP END PARALLEL end subroutine diff --git a/flang/test/Lower/OpenMP/if-clause.f90 b/flang/test/Lower/OpenMP/if-clause.f90 index ce4427a0c2cab2f68259042ed8903b7c4fbe404d..7c15c275d8cc9d44ee66697d9181aa0778a6af12 100644 --- a/flang/test/Lower/OpenMP/if-clause.f90 +++ b/flang/test/Lower/OpenMP/if-clause.f90 @@ -1,7 +1,9 @@ ! This test checks lowering of OpenMP IF clauses. -! RUN: bbc -fopenmp -emit-hlfir %s -o - | FileCheck %s -! RUN: %flang_fc1 -fopenmp -emit-hlfir %s -o - | FileCheck %s +! The "if" clause was added to the "simd" directive in OpenMP 5.0, and +! to the "teams" directive in OpenMP 5.2. +! RUN: bbc -fopenmp -fopenmp-version=52 -emit-hlfir %s -o - | FileCheck %s +! RUN: %flang_fc1 -fopenmp -fopenmp-version=52 -emit-hlfir %s -o - | FileCheck %s program main integer :: i diff --git a/flang/test/Lower/OpenMP/lastprivate-commonblock.f90 b/flang/test/Lower/OpenMP/lastprivate-commonblock.f90 index a11bdee156637b0db5b2c8cd298036f5beb99a95..78adf09c6fe34553149c00f65867bd1adc140b90 100644 --- a/flang/test/Lower/OpenMP/lastprivate-commonblock.f90 +++ b/flang/test/Lower/OpenMP/lastprivate-commonblock.f90 @@ -2,35 +2,38 @@ !CHECK: fir.global common @[[CB_C:.*]](dense<0> : vector<8xi8>) : !fir.array<8xi8> !CHECK-LABEL: func.func @_QPlastprivate_common -!CHECK: %[[CB_C_REF:.*]] = fir.address_of(@[[CB_C]]) : !fir.ref> -!CHECK: %[[CB_C_REF_CVT:.*]] = fir.convert %[[CB_C_REF]] : (!fir.ref>) -> !fir.ref> -!CHECK: %[[CB_C_X_COOR:.*]] = fir.coordinate_of %[[CB_C_REF_CVT]], %{{.*}} : (!fir.ref>, index) -> !fir.ref -!CHECK: %[[CB_C_X_ADDR:.*]] = fir.convert %[[CB_C_X_COOR]] : (!fir.ref) -> !fir.ref -!CHECK: %[[X_DECL:.*]]:2 = hlfir.declare %[[CB_C_X_ADDR]] {uniq_name = "_QFlastprivate_commonEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -!CHECK: %[[CB_C_REF_CVT:.*]] = fir.convert %[[CB_C_REF]] : (!fir.ref>) -> !fir.ref> -!CHECK: %[[CB_C_Y_COOR:.*]] = fir.coordinate_of %[[CB_C_REF_CVT]], %{{.*}} : (!fir.ref>, index) -> !fir.ref -!CHECK: %[[CB_C_Y_ADDR:.*]] = fir.convert %[[CB_C_Y_COOR]] : (!fir.ref) -> !fir.ref -!CHECK: %[[Y_DECL:.*]]:2 = hlfir.declare %[[CB_C_Y_ADDR]] {uniq_name = "_QFlastprivate_commonEy"} : (!fir.ref) -> (!fir.ref, !fir.ref) -!CHECK: %[[PRIVATE_X_REF:.*]] = fir.alloca f32 {bindc_name = "x", pinned, uniq_name = "_QFlastprivate_commonEx"} -!CHECK: %[[PRIVATE_X_DECL:.*]]:2 = hlfir.declare %[[PRIVATE_X_REF]] {uniq_name = "_QFlastprivate_commonEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -!CHECK: %[[PRIVATE_Y_REF:.*]] = fir.alloca f32 {bindc_name = "y", pinned, uniq_name = "_QFlastprivate_commonEy"} -!CHECK: %[[PRIVATE_Y_DECL:.*]]:2 = hlfir.declare %[[PRIVATE_Y_REF]] {uniq_name = "_QFlastprivate_commonEy"} : (!fir.ref) -> (!fir.ref, !fir.ref) -!CHECK: omp.wsloop for (%[[I:.*]]) : i32 = (%{{.*}}) to (%{{.*}}) inclusive step (%{{.*}}) { -!CHECK: %[[V:.*]] = arith.addi %[[I]], %{{.*}} : i32 -!CHECK: %[[C0:.*]] = arith.constant 0 : i32 -!CHECK: %[[NEG_STEP:.*]] = arith.cmpi slt, %{{.*}}, %[[C0]] : i32 -!CHECK: %[[V_LT:.*]] = arith.cmpi slt, %[[V]], %{{.*}} : i32 -!CHECK: %[[V_GT:.*]] = arith.cmpi sgt, %[[V]], %{{.*}} : i32 -!CHECK: %[[LAST_ITER:.*]] = arith.select %[[NEG_STEP]], %[[V_LT]], %[[V_GT]] : i1 -!CHECK: fir.if %[[LAST_ITER]] { -!CHECK: fir.store %[[V]] to %{{.*}} : !fir.ref -!CHECK: %[[PRIVATE_X_VAL:.*]] = fir.load %[[PRIVATE_X_DECL]]#0 : !fir.ref -!CHECK: hlfir.assign %[[PRIVATE_X_VAL]] to %[[X_DECL]]#0 temporary_lhs : f32, !fir.ref -!CHECK: %[[PRIVATE_Y_VAL:.*]] = fir.load %[[PRIVATE_Y_DECL]]#0 : !fir.ref -!CHECK: hlfir.assign %[[PRIVATE_Y_VAL]] to %[[Y_DECL]]#0 temporary_lhs : f32, !fir.ref +!CHECK: %[[CB_C_REF:.*]] = fir.address_of(@[[CB_C]]) : !fir.ref> +!CHECK: %[[CB_C_REF_CVT:.*]] = fir.convert %[[CB_C_REF]] : (!fir.ref>) -> !fir.ref> +!CHECK: %[[CB_C_X_COOR:.*]] = fir.coordinate_of %[[CB_C_REF_CVT]], %{{.*}} : (!fir.ref>, index) -> !fir.ref +!CHECK: %[[CB_C_X_ADDR:.*]] = fir.convert %[[CB_C_X_COOR]] : (!fir.ref) -> !fir.ref +!CHECK: %[[X_DECL:.*]]:2 = hlfir.declare %[[CB_C_X_ADDR]] {uniq_name = "_QFlastprivate_commonEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +!CHECK: %[[CB_C_REF_CVT:.*]] = fir.convert %[[CB_C_REF]] : (!fir.ref>) -> !fir.ref> +!CHECK: %[[CB_C_Y_COOR:.*]] = fir.coordinate_of %[[CB_C_REF_CVT]], %{{.*}} : (!fir.ref>, index) -> !fir.ref +!CHECK: %[[CB_C_Y_ADDR:.*]] = fir.convert %[[CB_C_Y_COOR]] : (!fir.ref) -> !fir.ref +!CHECK: %[[Y_DECL:.*]]:2 = hlfir.declare %[[CB_C_Y_ADDR]] {uniq_name = "_QFlastprivate_commonEy"} : (!fir.ref) -> (!fir.ref, !fir.ref) +!CHECK: %[[PRIVATE_X_REF:.*]] = fir.alloca f32 {bindc_name = "x", pinned, uniq_name = "_QFlastprivate_commonEx"} +!CHECK: %[[PRIVATE_X_DECL:.*]]:2 = hlfir.declare %[[PRIVATE_X_REF]] {uniq_name = "_QFlastprivate_commonEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +!CHECK: %[[PRIVATE_Y_REF:.*]] = fir.alloca f32 {bindc_name = "y", pinned, uniq_name = "_QFlastprivate_commonEy"} +!CHECK: %[[PRIVATE_Y_DECL:.*]]:2 = hlfir.declare %[[PRIVATE_Y_REF]] {uniq_name = "_QFlastprivate_commonEy"} : (!fir.ref) -> (!fir.ref, !fir.ref) +!CHECK: omp.wsloop { +!CHECK-NEXT: omp.loop_nest (%[[I:.*]]) : i32 = (%{{.*}}) to (%{{.*}}) inclusive step (%{{.*}}) { +!CHECK: %[[V:.*]] = arith.addi %[[I]], %{{.*}} : i32 +!CHECK: %[[C0:.*]] = arith.constant 0 : i32 +!CHECK: %[[NEG_STEP:.*]] = arith.cmpi slt, %{{.*}}, %[[C0]] : i32 +!CHECK: %[[V_LT:.*]] = arith.cmpi slt, %[[V]], %{{.*}} : i32 +!CHECK: %[[V_GT:.*]] = arith.cmpi sgt, %[[V]], %{{.*}} : i32 +!CHECK: %[[LAST_ITER:.*]] = arith.select %[[NEG_STEP]], %[[V_LT]], %[[V_GT]] : i1 +!CHECK: fir.if %[[LAST_ITER]] { +!CHECK: fir.store %[[V]] to %{{.*}} : !fir.ref +!CHECK: %[[PRIVATE_X_VAL:.*]] = fir.load %[[PRIVATE_X_DECL]]#0 : !fir.ref +!CHECK: hlfir.assign %[[PRIVATE_X_VAL]] to %[[X_DECL]]#0 temporary_lhs : f32, !fir.ref +!CHECK: %[[PRIVATE_Y_VAL:.*]] = fir.load %[[PRIVATE_Y_DECL]]#0 : !fir.ref +!CHECK: hlfir.assign %[[PRIVATE_Y_VAL]] to %[[Y_DECL]]#0 temporary_lhs : f32, !fir.ref +!CHECK: } +!CHECK: omp.yield +!CHECK: } +!CHECK: omp.terminator !CHECK: } -!CHECK: omp.yield -!CHECK: } subroutine lastprivate_common common /c/ x, y real x, y diff --git a/flang/test/Lower/OpenMP/lastprivate-iv.f90 b/flang/test/Lower/OpenMP/lastprivate-iv.f90 index 70fe500129d128fafd3b847283323f676331a579..24c20281b9c3897c58761586165d8f87ef5f9825 100644 --- a/flang/test/Lower/OpenMP/lastprivate-iv.f90 +++ b/flang/test/Lower/OpenMP/lastprivate-iv.f90 @@ -2,28 +2,31 @@ ! RUN: %flang_fc1 -emit-hlfir -fopenmp -o - %s 2>&1 | FileCheck %s !CHECK-LABEL: func @_QPlastprivate_iv_inc -!CHECK: %[[I_MEM:.*]] = fir.alloca i32 {adapt.valuebyref, pinned} -!CHECK: %[[I:.*]]:2 = hlfir.declare %[[I_MEM]] {uniq_name = "_QFlastprivate_iv_incEi"} : (!fir.ref) -> (!fir.ref, !fir.ref) -!CHECK: %[[I2_MEM:.*]] = fir.alloca i32 {bindc_name = "i", uniq_name = "_QFlastprivate_iv_incEi"} -!CHECK: %[[I2:.*]]:2 = hlfir.declare %[[I2_MEM]] {uniq_name = "_QFlastprivate_iv_incEi"} : (!fir.ref) -> (!fir.ref, !fir.ref) -!CHECK: %[[LB:.*]] = arith.constant 4 : i32 -!CHECK: %[[UB:.*]] = arith.constant 10 : i32 -!CHECK: %[[STEP:.*]] = arith.constant 3 : i32 -!CHECK: omp.wsloop for (%[[IV:.*]]) : i32 = (%[[LB]]) to (%[[UB]]) inclusive step (%[[STEP]]) { -!CHECK: fir.store %[[IV]] to %[[I]]#1 : !fir.ref -!CHECK: %[[V:.*]] = arith.addi %[[IV]], %[[STEP]] : i32 -!CHECK: %[[C0:.*]] = arith.constant 0 : i32 -!CHECK: %[[STEP_NEG:.*]] = arith.cmpi slt, %[[STEP]], %[[C0]] : i32 -!CHECK: %[[V_LT:.*]] = arith.cmpi slt, %[[V]], %[[UB]] : i32 -!CHECK: %[[V_GT:.*]] = arith.cmpi sgt, %[[V]], %[[UB]] : i32 -!CHECK: %[[CMP:.*]] = arith.select %[[STEP_NEG]], %[[V_LT]], %[[V_GT]] : i1 -!CHECK: fir.if %[[CMP]] { -!CHECK: fir.store %[[V]] to %[[I]]#1 : !fir.ref -!CHECK: %[[I_VAL:.*]] = fir.load %[[I]]#0 : !fir.ref -!CHECK: hlfir.assign %[[I_VAL]] to %[[I2]]#0 temporary_lhs : i32, !fir.ref +!CHECK: %[[I_MEM:.*]] = fir.alloca i32 {adapt.valuebyref, pinned} +!CHECK: %[[I:.*]]:2 = hlfir.declare %[[I_MEM]] {uniq_name = "_QFlastprivate_iv_incEi"} : (!fir.ref) -> (!fir.ref, !fir.ref) +!CHECK: %[[I2_MEM:.*]] = fir.alloca i32 {bindc_name = "i", uniq_name = "_QFlastprivate_iv_incEi"} +!CHECK: %[[I2:.*]]:2 = hlfir.declare %[[I2_MEM]] {uniq_name = "_QFlastprivate_iv_incEi"} : (!fir.ref) -> (!fir.ref, !fir.ref) +!CHECK: %[[LB:.*]] = arith.constant 4 : i32 +!CHECK: %[[UB:.*]] = arith.constant 10 : i32 +!CHECK: %[[STEP:.*]] = arith.constant 3 : i32 +!CHECK: omp.wsloop { +!CHECK-NEXT: omp.loop_nest (%[[IV:.*]]) : i32 = (%[[LB]]) to (%[[UB]]) inclusive step (%[[STEP]]) { +!CHECK: fir.store %[[IV]] to %[[I]]#1 : !fir.ref +!CHECK: %[[V:.*]] = arith.addi %[[IV]], %[[STEP]] : i32 +!CHECK: %[[C0:.*]] = arith.constant 0 : i32 +!CHECK: %[[STEP_NEG:.*]] = arith.cmpi slt, %[[STEP]], %[[C0]] : i32 +!CHECK: %[[V_LT:.*]] = arith.cmpi slt, %[[V]], %[[UB]] : i32 +!CHECK: %[[V_GT:.*]] = arith.cmpi sgt, %[[V]], %[[UB]] : i32 +!CHECK: %[[CMP:.*]] = arith.select %[[STEP_NEG]], %[[V_LT]], %[[V_GT]] : i1 +!CHECK: fir.if %[[CMP]] { +!CHECK: fir.store %[[V]] to %[[I]]#1 : !fir.ref +!CHECK: %[[I_VAL:.*]] = fir.load %[[I]]#0 : !fir.ref +!CHECK: hlfir.assign %[[I_VAL]] to %[[I2]]#0 temporary_lhs : i32, !fir.ref +!CHECK: } +!CHECK: omp.yield +!CHECK: } +!CHECK: omp.terminator !CHECK: } -!CHECK: omp.yield -!CHECK: } subroutine lastprivate_iv_inc() integer :: i @@ -34,28 +37,31 @@ subroutine lastprivate_iv_inc() end subroutine !CHECK-LABEL: func @_QPlastprivate_iv_dec -!CHECK: %[[I_MEM:.*]] = fir.alloca i32 {adapt.valuebyref, pinned} -!CHECK: %[[I:.*]]:2 = hlfir.declare %[[I_MEM]] {uniq_name = "_QFlastprivate_iv_decEi"} : (!fir.ref) -> (!fir.ref, !fir.ref) -!CHECK: %[[I2_MEM:.*]] = fir.alloca i32 {bindc_name = "i", uniq_name = "_QFlastprivate_iv_decEi"} -!CHECK: %[[I2:.*]]:2 = hlfir.declare %[[I2_MEM]] {uniq_name = "_QFlastprivate_iv_decEi"} : (!fir.ref) -> (!fir.ref, !fir.ref) -!CHECK: %[[LB:.*]] = arith.constant 10 : i32 -!CHECK: %[[UB:.*]] = arith.constant 1 : i32 -!CHECK: %[[STEP:.*]] = arith.constant -3 : i32 -!CHECK: omp.wsloop for (%[[IV:.*]]) : i32 = (%[[LB]]) to (%[[UB]]) inclusive step (%[[STEP]]) { -!CHECK: fir.store %[[IV]] to %[[I]]#1 : !fir.ref -!CHECK: %[[V:.*]] = arith.addi %[[IV]], %[[STEP]] : i32 -!CHECK: %[[C0:.*]] = arith.constant 0 : i32 -!CHECK: %[[STEP_NEG:.*]] = arith.cmpi slt, %[[STEP]], %[[C0]] : i32 -!CHECK: %[[V_LT:.*]] = arith.cmpi slt, %[[V]], %[[UB]] : i32 -!CHECK: %[[V_GT:.*]] = arith.cmpi sgt, %[[V]], %[[UB]] : i32 -!CHECK: %[[CMP:.*]] = arith.select %[[STEP_NEG]], %[[V_LT]], %[[V_GT]] : i1 -!CHECK: fir.if %[[CMP]] { -!CHECK: fir.store %[[V]] to %[[I]]#1 : !fir.ref -!CHECK: %[[I_VAL:.*]] = fir.load %[[I]]#0 : !fir.ref -!CHECK: hlfir.assign %[[I_VAL]] to %[[I2]]#0 temporary_lhs : i32, !fir.ref +!CHECK: %[[I_MEM:.*]] = fir.alloca i32 {adapt.valuebyref, pinned} +!CHECK: %[[I:.*]]:2 = hlfir.declare %[[I_MEM]] {uniq_name = "_QFlastprivate_iv_decEi"} : (!fir.ref) -> (!fir.ref, !fir.ref) +!CHECK: %[[I2_MEM:.*]] = fir.alloca i32 {bindc_name = "i", uniq_name = "_QFlastprivate_iv_decEi"} +!CHECK: %[[I2:.*]]:2 = hlfir.declare %[[I2_MEM]] {uniq_name = "_QFlastprivate_iv_decEi"} : (!fir.ref) -> (!fir.ref, !fir.ref) +!CHECK: %[[LB:.*]] = arith.constant 10 : i32 +!CHECK: %[[UB:.*]] = arith.constant 1 : i32 +!CHECK: %[[STEP:.*]] = arith.constant -3 : i32 +!CHECK: omp.wsloop { +!CHECK-NEXT: omp.loop_nest (%[[IV:.*]]) : i32 = (%[[LB]]) to (%[[UB]]) inclusive step (%[[STEP]]) { +!CHECK: fir.store %[[IV]] to %[[I]]#1 : !fir.ref +!CHECK: %[[V:.*]] = arith.addi %[[IV]], %[[STEP]] : i32 +!CHECK: %[[C0:.*]] = arith.constant 0 : i32 +!CHECK: %[[STEP_NEG:.*]] = arith.cmpi slt, %[[STEP]], %[[C0]] : i32 +!CHECK: %[[V_LT:.*]] = arith.cmpi slt, %[[V]], %[[UB]] : i32 +!CHECK: %[[V_GT:.*]] = arith.cmpi sgt, %[[V]], %[[UB]] : i32 +!CHECK: %[[CMP:.*]] = arith.select %[[STEP_NEG]], %[[V_LT]], %[[V_GT]] : i1 +!CHECK: fir.if %[[CMP]] { +!CHECK: fir.store %[[V]] to %[[I]]#1 : !fir.ref +!CHECK: %[[I_VAL:.*]] = fir.load %[[I]]#0 : !fir.ref +!CHECK: hlfir.assign %[[I_VAL]] to %[[I2]]#0 temporary_lhs : i32, !fir.ref +!CHECK: } +!CHECK: omp.yield +!CHECK: } +!CHECK: omp.terminator !CHECK: } -!CHECK: omp.yield -!CHECK: } subroutine lastprivate_iv_dec() integer :: i diff --git a/flang/test/Lower/OpenMP/location.f90 b/flang/test/Lower/OpenMP/location.f90 index 1e01a4828dd9e1b23c44f1bf3dbc344ee994539a..5d340937a81ce01fa710617dd684b6416489ae24 100644 --- a/flang/test/Lower/OpenMP/location.f90 +++ b/flang/test/Lower/OpenMP/location.f90 @@ -28,11 +28,14 @@ end !CHECK-LABEL: sub_loop subroutine sub_loop() -!CHECK: omp.wsloop {{.*}} { +!CHECK: omp.wsloop { +!CHECK-NEXT: omp.loop_nest {{.*}} { !$omp do do i=1,10 print *, i !CHECK: omp.yield loc(#[[LOOP_LOC:.*]]) +!CHECK: } loc(#[[LOOP_LOC]]) +!CHECK: omp.terminator loc(#[[LOOP_LOC]]) !CHECK: } loc(#[[LOOP_LOC]]) end do !$omp end do @@ -60,9 +63,9 @@ end subroutine !CHECK: #[[PAR_LOC]] = loc("{{.*}}location.f90":9:9) !CHECK: #[[TAR_LOC]] = loc("{{.*}}location.f90":21:9) -!CHECK: #[[LOOP_LOC]] = loc("{{.*}}location.f90":32:9) -!CHECK: #[[BAR_LOC]] = loc("{{.*}}location.f90":44:9) -!CHECK: #[[TW_LOC]] = loc("{{.*}}location.f90":46:9) -!CHECK: #[[TY_LOC]] = loc("{{.*}}location.f90":48:9) -!CHECK: #[[IF_LOC]] = loc("{{.*}}location.f90":55:14) -!CHECK: #[[TASK_LOC]] = loc("{{.*}}location.f90":55:9) +!CHECK: #[[LOOP_LOC]] = loc("{{.*}}location.f90":33:9) +!CHECK: #[[BAR_LOC]] = loc("{{.*}}location.f90":47:9) +!CHECK: #[[TW_LOC]] = loc("{{.*}}location.f90":49:9) +!CHECK: #[[TY_LOC]] = loc("{{.*}}location.f90":51:9) +!CHECK: #[[IF_LOC]] = loc("{{.*}}location.f90":58:14) +!CHECK: #[[TASK_LOC]] = loc("{{.*}}location.f90":58:9) diff --git a/flang/test/Lower/OpenMP/parallel-lastprivate-clause-scalar.f90 b/flang/test/Lower/OpenMP/parallel-lastprivate-clause-scalar.f90 index 28f59c95d60bbee292b8a44619d65d78cda8dae4..bb81e5eac62f56b04ea47f5aae817369990d7cb1 100644 --- a/flang/test/Lower/OpenMP/parallel-lastprivate-clause-scalar.f90 +++ b/flang/test/Lower/OpenMP/parallel-lastprivate-clause-scalar.f90 @@ -14,8 +14,9 @@ !CHECK-DAG: %[[ARG1_PVT_DECL:.*]]:2 = hlfir.declare %[[ARG1_PVT]] typeparams %[[FIVE]] {uniq_name = "_QFlastprivate_characterEarg1"} : (!fir.ref>, index) -> (!fir.ref>, !fir.ref>) ! Check that we are accessing the clone inside the loop -!CHECK-DAG: omp.wsloop for (%[[INDX_WS:.*]]) : {{.*}} { -!CHECK-DAG: %[[UNIT:.*]] = arith.constant 6 : i32 +!CHECK: omp.wsloop { +!CHECK-NEXT: omp.loop_nest (%[[INDX_WS:.*]]) : {{.*}} { +!CHECK: %[[UNIT:.*]] = arith.constant 6 : i32 !CHECK-NEXT: %[[ADDR:.*]] = fir.address_of(@_QQclX !CHECK-NEXT: %[[CVT0:.*]] = fir.convert %[[ADDR]] !CHECK-NEXT: %[[CNST:.*]] = arith.constant @@ -36,9 +37,12 @@ !CHECK: fir.store %[[V]] to %{{.*}} : !fir.ref ! Testing lastprivate val update -!CHECK-DAG: hlfir.assign %[[ARG1_PVT_DECL]]#0 to %[[ARG1_DECL]]#0 temporary_lhs : !fir.ref>, !fir.ref> -!CHECK-DAG: } -!CHECK-DAG: omp.yield +!CHECK: hlfir.assign %[[ARG1_PVT_DECL]]#0 to %[[ARG1_DECL]]#0 temporary_lhs : !fir.ref>, !fir.ref> +!CHECK: } +!CHECK: omp.yield +!CHECK: } +!CHECK: omp.terminator +!CHECK: } subroutine lastprivate_character(arg1) character(5) :: arg1 @@ -57,7 +61,8 @@ end subroutine !CHECK-DAG: omp.parallel { !CHECK-DAG: %[[CLONE:.*]] = fir.alloca i32 {bindc_name = "arg1" !CHECK-DAG: %[[CLONE_DECL:.*]]:2 = hlfir.declare %[[CLONE]] {uniq_name = "_QFlastprivate_intEarg1"} : (!fir.ref) -> (!fir.ref, !fir.ref) -!CHECK: omp.wsloop for (%[[INDX_WS:.*]]) : {{.*}} { +!CHECK: omp.wsloop { +!CHECK-NEXT: omp.loop_nest (%[[INDX_WS:.*]]) : {{.*}} { ! Testing last iteration check !CHECK: %[[V:.*]] = arith.addi %[[INDX_WS]], %{{.*}} : i32 @@ -72,8 +77,11 @@ end subroutine ! Testing lastprivate val update !CHECK-NEXT: %[[CLONE_LD:.*]] = fir.load %[[CLONE_DECL]]#0 : !fir.ref !CHECK: hlfir.assign %[[CLONE_LD]] to %[[ARG1_DECL]]#0 temporary_lhs : i32, !fir.ref -!CHECK-DAG: } -!CHECK-DAG: omp.yield +!CHECK: } +!CHECK: omp.yield +!CHECK: } +!CHECK: omp.terminator +!CHECK: } subroutine lastprivate_int(arg1) integer :: arg1 @@ -96,7 +104,8 @@ end subroutine !CHECK-DAG: %[[CLONE1_DECL:.*]]:2 = hlfir.declare %[[CLONE1]] {uniq_name = "_QFmult_lastprivate_intEarg1"} : (!fir.ref) -> (!fir.ref, !fir.ref) !CHECK-DAG: %[[CLONE2:.*]] = fir.alloca i32 {bindc_name = "arg2" !CHECK-DAG: %[[CLONE2_DECL:.*]]:2 = hlfir.declare %[[CLONE2]] {uniq_name = "_QFmult_lastprivate_intEarg2"} : (!fir.ref) -> (!fir.ref, !fir.ref) -!CHECK: omp.wsloop for (%[[INDX_WS:.*]]) : {{.*}} { +!CHECK: omp.wsloop { +!CHECK-NEXT: omp.loop_nest (%[[INDX_WS:.*]]) : {{.*}} { ! Testing last iteration check !CHECK: %[[V:.*]] = arith.addi %[[INDX_WS]], %{{.*}} : i32 @@ -114,6 +123,9 @@ end subroutine !CHECK-DAG: hlfir.assign %[[CLONE_LD2]] to %[[ARG2_DECL]]#0 temporary_lhs : i32, !fir.ref !CHECK: } !CHECK: omp.yield +!CHECK: } +!CHECK: omp.terminator +!CHECK: } subroutine mult_lastprivate_int(arg1, arg2) integer :: arg1, arg2 @@ -137,7 +149,8 @@ end subroutine !CHECK-DAG: %[[CLONE1_DECL:.*]]:2 = hlfir.declare %[[CLONE1]] {uniq_name = "_QFmult_lastprivate_int2Earg1"} : (!fir.ref) -> (!fir.ref, !fir.ref) !CHECK-DAG: %[[CLONE2:.*]] = fir.alloca i32 {bindc_name = "arg2" !CHECK-DAG: %[[CLONE2_DECL:.*]]:2 = hlfir.declare %[[CLONE2]] {uniq_name = "_QFmult_lastprivate_int2Earg2"} : (!fir.ref) -> (!fir.ref, !fir.ref) -!CHECK: omp.wsloop for (%[[INDX_WS:.*]]) : {{.*}} { +!CHECK: omp.wsloop { +!CHECK-NEXT: omp.loop_nest (%[[INDX_WS:.*]]) : {{.*}} { !Testing last iteration check !CHECK: %[[V:.*]] = arith.addi %[[INDX_WS]], %{{.*}} : i32 @@ -155,6 +168,9 @@ end subroutine !CHECK-DAG: hlfir.assign %[[CLONE_LD1]] to %[[ARG1_DECL]]#0 temporary_lhs : i32, !fir.ref !CHECK: } !CHECK: omp.yield +!CHECK: } +!CHECK: omp.terminator +!CHECK: } subroutine mult_lastprivate_int2(arg1, arg2) integer :: arg1, arg2 @@ -183,7 +199,8 @@ end subroutine !CHECK: %[[CLONE2:.*]] = fir.alloca i32 {bindc_name = "arg2" !CHECK: %[[CLONE2_DECL:.*]]:2 = hlfir.declare %[[CLONE2]] {uniq_name = "_QFfirstpriv_lastpriv_intEarg2"} : (!fir.ref) -> (!fir.ref, !fir.ref) !CHECK-NOT: omp.barrier -!CHECK: omp.wsloop for (%[[INDX_WS:.*]]) : {{.*}} { +!CHECK: omp.wsloop { +!CHECK-NEXT: omp.loop_nest (%[[INDX_WS:.*]]) : {{.*}} { ! Testing last iteration check !CHECK: %[[V:.*]] = arith.addi %[[INDX_WS]], %{{.*}} : i32 @@ -199,6 +216,9 @@ end subroutine !CHECK-NEXT: hlfir.assign %[[CLONE_LD]] to %[[ARG2_DECL]]#0 temporary_lhs : i32, !fir.ref !CHECK-NEXT: } !CHECK-NEXT: omp.yield +!CHECK-NEXT: } +!CHECK-NEXT: omp.terminator +!CHECK-NEXT: } subroutine firstpriv_lastpriv_int(arg1, arg2) integer :: arg1, arg2 @@ -223,7 +243,8 @@ end subroutine !CHECK-NEXT: %[[FPV_LD:.*]] = fir.load %[[ARG1_DECL]]#0 : !fir.ref !CHECK-NEXT: hlfir.assign %[[FPV_LD]] to %[[CLONE1_DECL]]#0 temporary_lhs : i32, !fir.ref !CHECK-NEXT: omp.barrier -!CHECK: omp.wsloop for (%[[INDX_WS:.*]]) : {{.*}} { +!CHECK: omp.wsloop { +!CHECK-NEXT: omp.loop_nest (%[[INDX_WS:.*]]) : {{.*}} { ! Testing last iteration check !CHECK: %[[V:.*]] = arith.addi %[[INDX_WS]], %{{.*}} : i32 !CHECK: %[[C0:.*]] = arith.constant 0 : i32 @@ -238,6 +259,9 @@ end subroutine !CHECK-NEXT: hlfir.assign %[[CLONE_LD]] to %[[ARG1_DECL]]#0 temporary_lhs : i32, !fir.ref !CHECK-NEXT: } !CHECK-NEXT: omp.yield +!CHECK-NEXT: } +!CHECK-NEXT: omp.terminator +!CHECK-NEXT: } subroutine firstpriv_lastpriv_int2(arg1) integer :: arg1 diff --git a/flang/test/Lower/OpenMP/parallel-private-clause-fixes.f90 b/flang/test/Lower/OpenMP/parallel-private-clause-fixes.f90 index 8533106b7ac487110753a08250529fedd570b101..93809fde98a269f4872bd43bae4f298e159c62ae 100644 --- a/flang/test/Lower/OpenMP/parallel-private-clause-fixes.f90 +++ b/flang/test/Lower/OpenMP/parallel-private-clause-fixes.f90 @@ -21,30 +21,33 @@ ! CHECK: %[[ONE:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_3:.*]] = fir.load %[[GAMA_DECL]]#0 : !fir.ref ! CHECK: %[[VAL_5:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop for (%[[VAL_6:.*]]) : i32 = (%[[ONE]]) to (%[[VAL_3]]) inclusive step (%[[VAL_5]]) { -! CHECK: fir.store %[[VAL_6]] to %[[PRIV_I_DECL]]#1 : !fir.ref -! CHECK: %[[VAL_7:.*]] = arith.constant 1 : i32 -! CHECK: %[[VAL_8:.*]] = fir.convert %[[VAL_7]] : (i32) -> index -! CHECK: %[[VAL_9:.*]] = fir.load %[[GAMA_DECL]]#0 : !fir.ref -! CHECK: %[[VAL_10:.*]] = fir.convert %[[VAL_9]] : (i32) -> index -! CHECK: %[[VAL_11:.*]] = arith.constant 1 : index -! CHECK: %[[LB:.*]] = fir.convert %[[VAL_8]] : (index) -> i32 -! CHECK: %[[VAL_12:.*]]:2 = fir.do_loop %[[VAL_13:[^ ]*]] = -! CHECK-SAME: %[[VAL_8]] to %[[VAL_10]] step %[[VAL_11]] -! CHECK-SAME: iter_args(%[[IV:.*]] = %[[LB]]) -> (index, i32) { -! CHECK: fir.store %[[IV]] to %[[PRIV_J_DECL]]#1 : !fir.ref -! CHECK: %[[LOAD:.*]] = fir.load %[[PRIV_I_DECL]]#0 : !fir.ref -! CHECK: %[[VAL_15:.*]] = fir.load %[[PRIV_J_DECL]]#0 : !fir.ref -! CHECK: %[[VAL_16:.*]] = arith.addi %[[LOAD]], %[[VAL_15]] : i32 -! CHECK: hlfir.assign %[[VAL_16]] to %[[PRIV_X_DECL]]#0 : i32, !fir.ref -! CHECK: %[[VAL_17:.*]] = arith.addi %[[VAL_13]], %[[VAL_11]] : index -! CHECK: %[[STEPCAST:.*]] = fir.convert %[[VAL_11]] : (index) -> i32 -! CHECK: %[[IVLOAD:.*]] = fir.load %[[PRIV_J_DECL]]#1 : !fir.ref -! CHECK: %[[IVINC:.*]] = arith.addi %[[IVLOAD]], %[[STEPCAST]] -! CHECK: fir.result %[[VAL_17]], %[[IVINC]] : index, i32 +! CHECK: omp.wsloop { +! CHECK-NEXT: omp.loop_nest (%[[VAL_6:.*]]) : i32 = (%[[ONE]]) to (%[[VAL_3]]) inclusive step (%[[VAL_5]]) { +! CHECK: fir.store %[[VAL_6]] to %[[PRIV_I_DECL]]#1 : !fir.ref +! CHECK: %[[VAL_7:.*]] = arith.constant 1 : i32 +! CHECK: %[[VAL_8:.*]] = fir.convert %[[VAL_7]] : (i32) -> index +! CHECK: %[[VAL_9:.*]] = fir.load %[[GAMA_DECL]]#0 : !fir.ref +! CHECK: %[[VAL_10:.*]] = fir.convert %[[VAL_9]] : (i32) -> index +! CHECK: %[[VAL_11:.*]] = arith.constant 1 : index +! CHECK: %[[LB:.*]] = fir.convert %[[VAL_8]] : (index) -> i32 +! CHECK: %[[VAL_12:.*]]:2 = fir.do_loop %[[VAL_13:[^ ]*]] = +! CHECK-SAME: %[[VAL_8]] to %[[VAL_10]] step %[[VAL_11]] +! CHECK-SAME: iter_args(%[[IV:.*]] = %[[LB]]) -> (index, i32) { +! CHECK: fir.store %[[IV]] to %[[PRIV_J_DECL]]#1 : !fir.ref +! CHECK: %[[LOAD:.*]] = fir.load %[[PRIV_I_DECL]]#0 : !fir.ref +! CHECK: %[[VAL_15:.*]] = fir.load %[[PRIV_J_DECL]]#0 : !fir.ref +! CHECK: %[[VAL_16:.*]] = arith.addi %[[LOAD]], %[[VAL_15]] : i32 +! CHECK: hlfir.assign %[[VAL_16]] to %[[PRIV_X_DECL]]#0 : i32, !fir.ref +! CHECK: %[[VAL_17:.*]] = arith.addi %[[VAL_13]], %[[VAL_11]] : index +! CHECK: %[[STEPCAST:.*]] = fir.convert %[[VAL_11]] : (index) -> i32 +! CHECK: %[[IVLOAD:.*]] = fir.load %[[PRIV_J_DECL]]#1 : !fir.ref +! CHECK: %[[IVINC:.*]] = arith.addi %[[IVLOAD]], %[[STEPCAST]] +! CHECK: fir.result %[[VAL_17]], %[[IVINC]] : index, i32 +! CHECK: } +! CHECK: fir.store %[[VAL_12]]#1 to %[[PRIV_J_DECL]]#1 : !fir.ref +! CHECK: omp.yield ! CHECK: } -! CHECK: fir.store %[[VAL_12]]#1 to %[[PRIV_J_DECL]]#1 : !fir.ref -! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } diff --git a/flang/test/Lower/OpenMP/parallel-private-clause.f90 b/flang/test/Lower/OpenMP/parallel-private-clause.f90 index 775f7b4f2cb1061a67af4b2ab8fbeaf343bc8aa8..b9b58a135aaa2ced6479302c1a58dba3e998c479 100644 --- a/flang/test/Lower/OpenMP/parallel-private-clause.f90 +++ b/flang/test/Lower/OpenMP/parallel-private-clause.f90 @@ -292,33 +292,35 @@ subroutine simple_loop_1 real, allocatable :: r; ! FIRDialect: omp.parallel !$OMP PARALLEL PRIVATE(r) - ! FIRDialect: %[[ALLOCA_IV:.*]] = fir.alloca i32 {{{.*}}, pinned} + ! FIRDialect: %[[ALLOCA_IV:.*]] = fir.alloca i32 {{{.*}}, pinned} - ! FIRDialect: %[[ALLOCA_IV_DECL:.*]]:2 = hlfir.declare %[[ALLOCA_IV]] {uniq_name = "_QFsimple_loop_1Ei"} : (!fir.ref) -> (!fir.ref, !fir.ref) - ! FIRDialect: [[R:%.*]] = fir.alloca !fir.box> {bindc_name = "r", pinned, uniq_name = "{{.*}}Er"} - ! FIRDialect: fir.store {{%.*}} to [[R]] : !fir.ref>> - ! FIRDialect: fir.store {{%.*}} to [[R]] : !fir.ref>> - ! FIRDialect: %[[R_DECL:.*]]:2 = hlfir.declare [[R]] {fortran_attrs = #fir.var_attrs, uniq_name = "_QFsimple_loop_1Er"} : (!fir.ref>>) -> (!fir.ref>>, !fir.ref>>) + ! FIRDialect: %[[ALLOCA_IV_DECL:.*]]:2 = hlfir.declare %[[ALLOCA_IV]] {uniq_name = "_QFsimple_loop_1Ei"} : (!fir.ref) -> (!fir.ref, !fir.ref) + ! FIRDialect: [[R:%.*]] = fir.alloca !fir.box> {bindc_name = "r", pinned, uniq_name = "{{.*}}Er"} + ! FIRDialect: fir.store {{%.*}} to [[R]] : !fir.ref>> + ! FIRDialect: fir.store {{%.*}} to [[R]] : !fir.ref>> + ! FIRDialect: %[[R_DECL:.*]]:2 = hlfir.declare [[R]] {fortran_attrs = #fir.var_attrs, uniq_name = "_QFsimple_loop_1Er"} : (!fir.ref>>) -> (!fir.ref>>, !fir.ref>>) - ! FIRDialect: %[[WS_LB:.*]] = arith.constant 1 : i32 - ! FIRDialect: %[[WS_UB:.*]] = arith.constant 9 : i32 - ! FIRDialect: %[[WS_STEP:.*]] = arith.constant 1 : i32 + ! FIRDialect: %[[WS_LB:.*]] = arith.constant 1 : i32 + ! FIRDialect: %[[WS_UB:.*]] = arith.constant 9 : i32 + ! FIRDialect: %[[WS_STEP:.*]] = arith.constant 1 : i32 - ! FIRDialect: omp.wsloop for (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) + ! FIRDialect: omp.wsloop { + ! FIRDialect-NEXT: omp.loop_nest (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) { !$OMP DO do i=1, 9 - ! FIRDialect: fir.store %[[I]] to %[[ALLOCA_IV_DECL]]#1 : !fir.ref - ! FIRDialect: %[[LOAD_IV:.*]] = fir.load %[[ALLOCA_IV_DECL]]#0 : !fir.ref - ! FIRDialect: fir.call @_FortranAioOutputInteger32({{.*}}, %[[LOAD_IV]]) {{.*}} : (!fir.ref, i32) -> i1 + ! FIRDialect: fir.store %[[I]] to %[[ALLOCA_IV_DECL]]#1 : !fir.ref + ! FIRDialect: %[[LOAD_IV:.*]] = fir.load %[[ALLOCA_IV_DECL]]#0 : !fir.ref + ! FIRDialect: fir.call @_FortranAioOutputInteger32({{.*}}, %[[LOAD_IV]]) {{.*}} : (!fir.ref, i32) -> i1 print*, i end do - ! FIRDialect: omp.yield - ! FIRDialect: {{%.*}} = fir.load %[[R_DECL]]#0 : !fir.ref>> - ! FIRDialect: fir.if {{%.*}} { - ! FIRDialect: [[LD:%.*]] = fir.load %[[R_DECL]]#0 : !fir.ref>> - ! FIRDialect: [[AD:%.*]] = fir.box_addr [[LD]] : (!fir.box>) -> !fir.heap - ! FIRDialect: fir.freemem [[AD]] : !fir.heap - ! FIRDialect: fir.store {{%.*}} to %[[R_DECL]]#0 : !fir.ref>> + ! FIRDialect: omp.yield + ! FIRDialect: omp.terminator + ! FIRDialect: {{%.*}} = fir.load %[[R_DECL]]#0 : !fir.ref>> + ! FIRDialect: fir.if {{%.*}} { + ! FIRDialect: [[LD:%.*]] = fir.load %[[R_DECL]]#0 : !fir.ref>> + ! FIRDialect: [[AD:%.*]] = fir.box_addr [[LD]] : (!fir.box>) -> !fir.heap + ! FIRDialect: fir.freemem [[AD]] : !fir.heap + ! FIRDialect: fir.store {{%.*}} to %[[R_DECL]]#0 : !fir.ref>> !$OMP END DO ! FIRDialect: omp.terminator !$OMP END PARALLEL @@ -330,19 +332,20 @@ subroutine simple_loop_2 real, allocatable :: r; ! FIRDialect: omp.parallel !$OMP PARALLEL - ! FIRDialect: %[[ALLOCA_IV:.*]] = fir.alloca i32 {{{.*}}, pinned} + ! FIRDialect: %[[ALLOCA_IV:.*]] = fir.alloca i32 {{{.*}}, pinned} - ! FIRDialect: %[[ALLOCA_IV_DECL:.*]]:2 = hlfir.declare %[[ALLOCA_IV]] {uniq_name = "{{.*}}Ei"} : (!fir.ref) -> (!fir.ref, !fir.ref) - ! FIRDialect: [[R:%.*]] = fir.alloca !fir.box> {bindc_name = "r", pinned, uniq_name = "{{.*}}Er"} - ! FIRDialect: fir.store {{%.*}} to [[R]] : !fir.ref>> - ! FIRDialect: fir.store {{%.*}} to [[R]] : !fir.ref>> - ! FIRDialect: %[[R_DECL:.*]]:2 = hlfir.declare [[R]] {fortran_attrs = #fir.var_attrs, uniq_name = "{{.*}}Er"} : (!fir.ref>>) -> (!fir.ref>>, !fir.ref>>) + ! FIRDialect: %[[ALLOCA_IV_DECL:.*]]:2 = hlfir.declare %[[ALLOCA_IV]] {uniq_name = "{{.*}}Ei"} : (!fir.ref) -> (!fir.ref, !fir.ref) + ! FIRDialect: [[R:%.*]] = fir.alloca !fir.box> {bindc_name = "r", pinned, uniq_name = "{{.*}}Er"} + ! FIRDialect: fir.store {{%.*}} to [[R]] : !fir.ref>> + ! FIRDialect: fir.store {{%.*}} to [[R]] : !fir.ref>> + ! FIRDialect: %[[R_DECL:.*]]:2 = hlfir.declare [[R]] {fortran_attrs = #fir.var_attrs, uniq_name = "{{.*}}Er"} : (!fir.ref>>) -> (!fir.ref>>, !fir.ref>>) - ! FIRDialect: %[[WS_LB:.*]] = arith.constant 1 : i32 - ! FIRDialect: %[[WS_UB:.*]] = arith.constant 9 : i32 - ! FIRDialect: %[[WS_STEP:.*]] = arith.constant 1 : i32 + ! FIRDialect: %[[WS_LB:.*]] = arith.constant 1 : i32 + ! FIRDialect: %[[WS_UB:.*]] = arith.constant 9 : i32 + ! FIRDialect: %[[WS_STEP:.*]] = arith.constant 1 : i32 - ! FIRDialect: omp.wsloop for (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) + ! FIRDialect: omp.wsloop { + ! FIRDialect-NEXT: omp.loop_nest (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) { !$OMP DO PRIVATE(r) do i=1, 9 ! FIRDialect: fir.store %[[I]] to %[[ALLOCA_IV_DECL]]#1 : !fir.ref @@ -351,6 +354,7 @@ subroutine simple_loop_2 print*, i end do ! FIRDialect: omp.yield + ! FIRDialect: omp.terminator ! FIRDialect: {{%.*}} = fir.load %[[R_DECL]]#0 : !fir.ref>> ! FIRDialect: fir.if {{%.*}} { ! FIRDialect: [[LD:%.*]] = fir.load %[[R_DECL]]#0 : !fir.ref>> @@ -367,33 +371,35 @@ subroutine simple_loop_3 integer :: i real, allocatable :: r; ! FIRDialect: omp.parallel - ! FIRDialect: %[[ALLOCA_IV:.*]] = fir.alloca i32 {{{.*}}, pinned} - ! FIRDialect: %[[ALLOCA_IV_DECL:.*]]:2 = hlfir.declare %[[ALLOCA_IV]] {uniq_name = "{{.*}}Ei"} : (!fir.ref) -> (!fir.ref, !fir.ref) + ! FIRDialect: %[[ALLOCA_IV:.*]] = fir.alloca i32 {{{.*}}, pinned} + ! FIRDialect: %[[ALLOCA_IV_DECL:.*]]:2 = hlfir.declare %[[ALLOCA_IV]] {uniq_name = "{{.*}}Ei"} : (!fir.ref) -> (!fir.ref, !fir.ref) - ! FIRDialect: [[R:%.*]] = fir.alloca !fir.box> {bindc_name = "r", pinned, uniq_name = "{{.*}}Er"} - ! FIRDialect: fir.store {{%.*}} to [[R]] : !fir.ref>> - ! FIRDialect: fir.store {{%.*}} to [[R]] : !fir.ref>> - ! FIRDialect: [[R_DECL:%.*]]:2 = hlfir.declare [[R]] {fortran_attrs = #fir.var_attrs, uniq_name = "{{.*}}Er"} : (!fir.ref>>) -> (!fir.ref>>, !fir.ref>>) + ! FIRDialect: [[R:%.*]] = fir.alloca !fir.box> {bindc_name = "r", pinned, uniq_name = "{{.*}}Er"} + ! FIRDialect: fir.store {{%.*}} to [[R]] : !fir.ref>> + ! FIRDialect: fir.store {{%.*}} to [[R]] : !fir.ref>> + ! FIRDialect: [[R_DECL:%.*]]:2 = hlfir.declare [[R]] {fortran_attrs = #fir.var_attrs, uniq_name = "{{.*}}Er"} : (!fir.ref>>) -> (!fir.ref>>, !fir.ref>>) - ! FIRDialect: %[[WS_LB:.*]] = arith.constant 1 : i32 - ! FIRDialect: %[[WS_UB:.*]] = arith.constant 9 : i32 - ! FIRDialect: %[[WS_STEP:.*]] = arith.constant 1 : i32 + ! FIRDialect: %[[WS_LB:.*]] = arith.constant 1 : i32 + ! FIRDialect: %[[WS_UB:.*]] = arith.constant 9 : i32 + ! FIRDialect: %[[WS_STEP:.*]] = arith.constant 1 : i32 - ! FIRDialect: omp.wsloop for (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) + ! FIRDialect: omp.wsloop { + ! FIRDialect-NEXT: omp.loop_nest (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) { !$OMP PARALLEL DO PRIVATE(r) do i=1, 9 - ! FIRDialect: fir.store %[[I]] to %[[ALLOCA_IV_DECL:.*]]#1 : !fir.ref - ! FIRDialect: %[[LOAD_IV:.*]] = fir.load %[[ALLOCA_IV_DECL]]#0 : !fir.ref - ! FIRDialect: fir.call @_FortranAioOutputInteger32({{.*}}, %[[LOAD_IV]]) {{.*}}: (!fir.ref, i32) -> i1 + ! FIRDialect: fir.store %[[I]] to %[[ALLOCA_IV_DECL:.*]]#1 : !fir.ref + ! FIRDialect: %[[LOAD_IV:.*]] = fir.load %[[ALLOCA_IV_DECL]]#0 : !fir.ref + ! FIRDialect: fir.call @_FortranAioOutputInteger32({{.*}}, %[[LOAD_IV]]) {{.*}}: (!fir.ref, i32) -> i1 print*, i end do - ! FIRDialect: omp.yield - ! FIRDialect: {{%.*}} = fir.load [[R_DECL]]#0 : !fir.ref>> - ! FIRDialect: fir.if {{%.*}} { - ! FIRDialect: [[LD:%.*]] = fir.load [[R_DECL]]#0 : !fir.ref>> - ! FIRDialect: [[AD:%.*]] = fir.box_addr [[LD]] : (!fir.box>) -> !fir.heap - ! FIRDialect: fir.freemem [[AD]] : !fir.heap - ! FIRDialect: fir.store {{%.*}} to [[R_DECL]]#0 : !fir.ref>> + ! FIRDialect: omp.yield + ! FIRDialect: omp.terminator + ! FIRDialect: {{%.*}} = fir.load [[R_DECL]]#0 : !fir.ref>> + ! FIRDialect: fir.if {{%.*}} { + ! FIRDialect: [[LD:%.*]] = fir.load [[R_DECL]]#0 : !fir.ref>> + ! FIRDialect: [[AD:%.*]] = fir.box_addr [[LD]] : (!fir.box>) -> !fir.heap + ! FIRDialect: fir.freemem [[AD]] : !fir.heap + ! FIRDialect: fir.store {{%.*}} to [[R_DECL]]#0 : !fir.ref>> !$OMP END PARALLEL DO ! FIRDialect: omp.terminator end subroutine diff --git a/flang/test/Lower/OpenMP/parallel-reduction-allocatable-array.f90 b/flang/test/Lower/OpenMP/parallel-reduction-allocatable-array.f90 index 890ae48ce0fc27c5f063e4b1b7e633005f7cd3a3..28216ef91c3a32ed03e131c74b979f404bea6c2c 100644 --- a/flang/test/Lower/OpenMP/parallel-reduction-allocatable-array.f90 +++ b/flang/test/Lower/OpenMP/parallel-reduction-allocatable-array.f90 @@ -37,9 +37,12 @@ end program ! CHECK: %[[VAL_6:.*]] = fir.allocmem !fir.array, %[[VAL_4]]#1 {bindc_name = ".tmp", uniq_name = ""} ! CHECK: %[[VAL_7:.*]] = arith.constant true ! CHECK: %[[VAL_8:.*]]:2 = hlfir.declare %[[VAL_6]](%[[VAL_5]]) {uniq_name = ".tmp"} : (!fir.heap>, !fir.shape<1>) -> (!fir.box>, !fir.heap>) -! CHECK: %[[VAL_9:.*]] = fir.convert %[[VAL_8]]#0 : (!fir.box>) -> !fir.box>> -! CHECK: hlfir.assign %[[VAL_1]] to %[[VAL_9]] : i32, !fir.box>> -! CHECK: fir.store %[[VAL_9]] to %[[VAL_10]] : !fir.ref>>> +! CHECK: %[[C0:.*]] = arith.constant 0 : index +! CHECK: %[[DIMS:.*]]:3 = fir.box_dims %[[VAL_2]], %[[C0]] : (!fir.box>>, index) -> (index, index, index) +! CHECK: %[[SHIFT:.*]] = fir.shape_shift %[[DIMS]]#0, %[[DIMS]]#1 : (index, index) -> !fir.shapeshift<1> +! CHECK: %[[REBOX:.*]] = fir.rebox %[[VAL_8]]#0(%[[SHIFT]]) : (!fir.box>, !fir.shapeshift<1>) -> !fir.box>> +! CHECK: hlfir.assign %[[VAL_1]] to %[[REBOX]] : i32, !fir.box>> +! CHECK: fir.store %[[REBOX]] to %[[VAL_10]] : !fir.ref>>> ! CHECK: } ! CHECK: omp.yield(%[[VAL_10]] : !fir.ref>>>) ! CHECK: } combiner { @@ -92,22 +95,25 @@ end program ! CHECK: %[[VAL_14:.*]] = arith.constant 0 : i32 ! CHECK: %[[VAL_15:.*]] = arith.constant 10 : i32 ! CHECK: %[[VAL_16:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@add_reduction_byref_box_heap_Uxi32 %[[VAL_3]]#0 -> %[[VAL_17:.*]] : !fir.ref>>>) for (%[[VAL_18:.*]]) : i32 = (%[[VAL_14]]) to (%[[VAL_15]]) inclusive step (%[[VAL_16]]) { -! CHECK: fir.store %[[VAL_18]] to %[[VAL_13]]#1 : !fir.ref -! CHECK: %[[VAL_19:.*]]:2 = hlfir.declare %[[VAL_17]] {fortran_attrs = {{.*}}, uniq_name = "_QFEr"} : (!fir.ref>>>) -> (!fir.ref>>>, !fir.ref>>>) -! CHECK: %[[VAL_20:.*]] = fir.load %[[VAL_13]]#0 : !fir.ref -! CHECK: %[[VAL_21:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref>>> -! CHECK: %[[VAL_22:.*]] = arith.constant 1 : index -! CHECK: %[[VAL_23:.*]] = hlfir.designate %[[VAL_21]] (%[[VAL_22]]) : (!fir.box>>, index) -> !fir.ref -! CHECK: hlfir.assign %[[VAL_20]] to %[[VAL_23]] : i32, !fir.ref -! CHECK: %[[VAL_24:.*]] = fir.load %[[VAL_13]]#0 : !fir.ref -! CHECK: %[[VAL_25:.*]] = arith.constant 0 : i32 -! CHECK: %[[VAL_26:.*]] = arith.subi %[[VAL_25]], %[[VAL_24]] : i32 -! CHECK: %[[VAL_27:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref>>> -! CHECK: %[[VAL_28:.*]] = arith.constant 2 : index -! CHECK: %[[VAL_29:.*]] = hlfir.designate %[[VAL_27]] (%[[VAL_28]]) : (!fir.box>>, index) -> !fir.ref -! CHECK: hlfir.assign %[[VAL_26]] to %[[VAL_29]] : i32, !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@add_reduction_byref_box_heap_Uxi32 %[[VAL_3]]#0 -> %[[VAL_17:.*]] : !fir.ref>>>) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_18:.*]]) : i32 = (%[[VAL_14]]) to (%[[VAL_15]]) inclusive step (%[[VAL_16]]) { +! CHECK: %[[VAL_19:.*]]:2 = hlfir.declare %[[VAL_17]] {fortran_attrs = {{.*}}, uniq_name = "_QFEr"} : (!fir.ref>>>) -> (!fir.ref>>>, !fir.ref>>>) +! CHECK: fir.store %[[VAL_18]] to %[[VAL_13]]#1 : !fir.ref +! CHECK: %[[VAL_20:.*]] = fir.load %[[VAL_13]]#0 : !fir.ref +! CHECK: %[[VAL_21:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref>>> +! CHECK: %[[VAL_22:.*]] = arith.constant 1 : index +! CHECK: %[[VAL_23:.*]] = hlfir.designate %[[VAL_21]] (%[[VAL_22]]) : (!fir.box>>, index) -> !fir.ref +! CHECK: hlfir.assign %[[VAL_20]] to %[[VAL_23]] : i32, !fir.ref +! CHECK: %[[VAL_24:.*]] = fir.load %[[VAL_13]]#0 : !fir.ref +! CHECK: %[[VAL_25:.*]] = arith.constant 0 : i32 +! CHECK: %[[VAL_26:.*]] = arith.subi %[[VAL_25]], %[[VAL_24]] : i32 +! CHECK: %[[VAL_27:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref>>> +! CHECK: %[[VAL_28:.*]] = arith.constant 2 : index +! CHECK: %[[VAL_29:.*]] = hlfir.designate %[[VAL_27]] (%[[VAL_28]]) : (!fir.box>>, index) -> !fir.ref +! CHECK: hlfir.assign %[[VAL_26]] to %[[VAL_29]] : i32, !fir.ref +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } diff --git a/flang/test/Lower/OpenMP/parallel-reduction-array-lb.f90 b/flang/test/Lower/OpenMP/parallel-reduction-array-lb.f90 new file mode 100644 index 0000000000000000000000000000000000000000..8202e6d897157d56685a83ea614ecdbf619c1145 --- /dev/null +++ b/flang/test/Lower/OpenMP/parallel-reduction-array-lb.f90 @@ -0,0 +1,90 @@ +! RUN: bbc -emit-hlfir -fopenmp -o - %s 2>&1 | FileCheck %s +! RUN: %flang_fc1 -emit-hlfir -fopenmp -o - %s 2>&1 | FileCheck %s + +program reduce +integer, dimension(2:4, 2) :: i = 0 + +!$omp parallel reduction(+:i) +i(3, 1) = 3 +!$omp end parallel + +print *,i + +end program + +! CHECK-LABEL: omp.declare_reduction @add_reduction_byref_box_3x2xi32 : !fir.ref>> init { +! CHECK: ^bb0(%[[VAL_0:.*]]: !fir.ref>>): +! CHECK: %[[VAL_1:.*]] = arith.constant 0 : i32 +! CHECK: %[[VAL_2:.*]] = fir.load %[[VAL_0]] : !fir.ref>> +! CHECK: %[[VAL_15:.*]] = fir.alloca !fir.box> +! CHECK: %[[VAL_3:.*]] = arith.constant 3 : index +! CHECK: %[[VAL_4:.*]] = arith.constant 2 : index +! CHECK: %[[VAL_5:.*]] = fir.shape %[[VAL_3]], %[[VAL_4]] : (index, index) -> !fir.shape<2> +! CHECK: %[[VAL_6:.*]] = fir.allocmem !fir.array<3x2xi32> {bindc_name = ".tmp", uniq_name = ""} +! CHECK: %[[VAL_7:.*]] = arith.constant true +! CHECK: %[[VAL_8:.*]]:2 = hlfir.declare %[[VAL_6]](%[[VAL_5]]) {uniq_name = ".tmp"} : (!fir.heap>, !fir.shape<2>) -> (!fir.heap>, !fir.heap>) +! CHECK: %[[VAL_9:.*]] = arith.constant 0 : index +! CHECK: %[[VAL_10:.*]]:3 = fir.box_dims %[[VAL_2]], %[[VAL_9]] : (!fir.box>, index) -> (index, index, index) +! CHECK: %[[VAL_11:.*]] = arith.constant 1 : index +! CHECK: %[[VAL_12:.*]]:3 = fir.box_dims %[[VAL_2]], %[[VAL_11]] : (!fir.box>, index) -> (index, index, index) +! CHECK: %[[VAL_13:.*]] = fir.shape_shift %[[VAL_10]]#0, %[[VAL_10]]#1, %[[VAL_12]]#0, %[[VAL_12]]#1 : (index, index, index, index) -> !fir.shapeshift<2> +! CHECK: %[[VAL_14:.*]] = fir.embox %[[VAL_8]]#0(%[[VAL_13]]) : (!fir.heap>, !fir.shapeshift<2>) -> !fir.box> +! CHECK: hlfir.assign %[[VAL_1]] to %[[VAL_14]] : i32, !fir.box> +! CHECK: fir.store %[[VAL_14]] to %[[VAL_15]] : !fir.ref>> +! CHECK: omp.yield(%[[VAL_15]] : !fir.ref>>) +! CHECK: } combiner { +! CHECK: ^bb0(%[[VAL_0:.*]]: !fir.ref>>, %[[VAL_1:.*]]: !fir.ref>>): +! CHECK: %[[VAL_2:.*]] = fir.load %[[VAL_0]] : !fir.ref>> +! CHECK: %[[VAL_3:.*]] = fir.load %[[VAL_1]] : !fir.ref>> +! CHECK: %[[VAL_4:.*]] = arith.constant 0 : index +! CHECK: %[[VAL_5:.*]]:3 = fir.box_dims %[[VAL_2]], %[[VAL_4]] : (!fir.box>, index) -> (index, index, index) +! CHECK: %[[VAL_6:.*]] = arith.constant 1 : index +! CHECK: %[[VAL_7:.*]]:3 = fir.box_dims %[[VAL_2]], %[[VAL_6]] : (!fir.box>, index) -> (index, index, index) +! CHECK: %[[VAL_8:.*]] = fir.shape_shift %[[VAL_5]]#0, %[[VAL_5]]#1, %[[VAL_7]]#0, %[[VAL_7]]#1 : (index, index, index, index) -> !fir.shapeshift<2> +! CHECK: %[[VAL_9:.*]] = arith.constant 1 : index +! CHECK: fir.do_loop %[[VAL_10:.*]] = %[[VAL_9]] to %[[VAL_7]]#1 step %[[VAL_9]] unordered { +! CHECK: fir.do_loop %[[VAL_11:.*]] = %[[VAL_9]] to %[[VAL_5]]#1 step %[[VAL_9]] unordered { +! CHECK: %[[VAL_12:.*]] = fir.array_coor %[[VAL_2]](%[[VAL_8]]) %[[VAL_11]], %[[VAL_10]] : (!fir.box>, !fir.shapeshift<2>, index, index) -> !fir.ref +! CHECK: %[[VAL_13:.*]] = fir.array_coor %[[VAL_3]](%[[VAL_8]]) %[[VAL_11]], %[[VAL_10]] : (!fir.box>, !fir.shapeshift<2>, index, index) -> !fir.ref +! CHECK: %[[VAL_14:.*]] = fir.load %[[VAL_12]] : !fir.ref +! CHECK: %[[VAL_15:.*]] = fir.load %[[VAL_13]] : !fir.ref +! CHECK: %[[VAL_16:.*]] = arith.addi %[[VAL_14]], %[[VAL_15]] : i32 +! CHECK: fir.store %[[VAL_16]] to %[[VAL_12]] : !fir.ref +! CHECK: } +! CHECK: } +! CHECK: omp.yield(%[[VAL_0]] : !fir.ref>>) +! CHECK: } cleanup { +! CHECK: ^bb0(%[[VAL_0:.*]]: !fir.ref>>): +! CHECK: %[[VAL_1:.*]] = fir.load %[[VAL_0]] : !fir.ref>> +! CHECK: %[[VAL_2:.*]] = fir.box_addr %[[VAL_1]] : (!fir.box>) -> !fir.ref> +! CHECK: %[[VAL_3:.*]] = fir.convert %[[VAL_2]] : (!fir.ref>) -> i64 +! CHECK: %[[VAL_4:.*]] = arith.constant 0 : i64 +! CHECK: %[[VAL_5:.*]] = arith.cmpi ne, %[[VAL_3]], %[[VAL_4]] : i64 +! CHECK: fir.if %[[VAL_5]] { +! CHECK: %[[VAL_6:.*]] = fir.convert %[[VAL_2]] : (!fir.ref>) -> !fir.heap> +! CHECK: fir.freemem %[[VAL_6]] : !fir.heap> +! CHECK: } +! CHECK: omp.yield +! CHECK: } + +! CHECK-LABEL: func.func @_QQmain() attributes {fir.bindc_name = "reduce"} { +! CHECK: %[[VAL_0:.*]] = fir.address_of(@_QFEi) : !fir.ref> +! CHECK: %[[VAL_1:.*]] = arith.constant 2 : index +! CHECK: %[[VAL_2:.*]] = arith.constant 3 : index +! CHECK: %[[VAL_3:.*]] = arith.constant 1 : index +! CHECK: %[[VAL_4:.*]] = arith.constant 2 : index +! CHECK: %[[VAL_5:.*]] = fir.shape_shift %[[VAL_1]], %[[VAL_2]], %[[VAL_3]], %[[VAL_4]] : (index, index, index, index) -> !fir.shapeshift<2> +! CHECK: %[[VAL_6:.*]]:2 = hlfir.declare %[[VAL_0]](%[[VAL_5]]) {uniq_name = "_QFEi"} : (!fir.ref>, !fir.shapeshift<2>) -> (!fir.box>, !fir.ref>) +! CHECK: %[[VAL_7:.*]] = fir.alloca !fir.box> +! CHECK: fir.store %[[VAL_6]]#0 to %[[VAL_7]] : !fir.ref>> +! CHECK: omp.parallel byref reduction(@add_reduction_byref_box_3x2xi32 %[[VAL_7]] -> %[[VAL_8:.*]] : !fir.ref>>) { +! CHECK: %[[VAL_9:.*]]:2 = hlfir.declare %[[VAL_8]] {uniq_name = "_QFEi"} : (!fir.ref>>) -> (!fir.ref>>, !fir.ref>>) +! CHECK: %[[VAL_10:.*]] = arith.constant 3 : i32 +! CHECK: %[[VAL_11:.*]] = fir.load %[[VAL_9]]#0 : !fir.ref>> +! CHECK: %[[VAL_12:.*]] = arith.constant 3 : index +! CHECK: %[[VAL_13:.*]] = arith.constant 1 : index +! CHECK: %[[VAL_14:.*]] = hlfir.designate %[[VAL_11]] (%[[VAL_12]], %[[VAL_13]]) : (!fir.box>, index, index) -> !fir.ref +! CHECK: hlfir.assign %[[VAL_10]] to %[[VAL_14]] : i32, !fir.ref +! CHECK: omp.terminator +! CHECK: } + diff --git a/flang/test/Lower/OpenMP/parallel-reduction-array.f90 b/flang/test/Lower/OpenMP/parallel-reduction-array.f90 index 32f77e66d17ad8ed353d2c035294c2251182d077..34f4ee0a9eb3a5f26868383211ae597372413c0b 100644 --- a/flang/test/Lower/OpenMP/parallel-reduction-array.f90 +++ b/flang/test/Lower/OpenMP/parallel-reduction-array.f90 @@ -24,7 +24,10 @@ end program ! CHECK: %[[TRUE:.*]] = arith.constant true ! CHECK: %[[VAL_6:.*]]:2 = hlfir.declare %[[VAL_1]](%[[VAL_5]]) {uniq_name = ".tmp"} : (!fir.heap>, !fir.shape<1>) -> (!fir.heap>, !fir.heap>) -! CHECK: %[[VAL_7:.*]] = fir.embox %[[VAL_6]]#0(%[[VAL_5]]) : (!fir.heap>, !fir.shape<1>) -> !fir.box> +! CHECK: %[[C0:.*]] = arith.constant 0 : index +! CHECK: %[[DIMS:.*]]:3 = fir.box_dims %[[VAL_3]], %[[C0]] : (!fir.box>, index) -> (index, index, index) +! CHECK: %[[SHIFT:.*]] = fir.shape_shift %[[DIMS]]#0, %[[DIMS]]#1 : (index, index) -> !fir.shapeshift<1> +! CHECK: %[[VAL_7:.*]] = fir.embox %[[VAL_6]]#0(%[[SHIFT]]) : (!fir.heap>, !fir.shapeshift<1>) -> !fir.box> ! CHECK: hlfir.assign %[[VAL_2]] to %[[VAL_7]] : i32, !fir.box> ! CHECK: fir.store %[[VAL_7]] to %[[VAL_8]] : !fir.ref>> ! CHECK: omp.yield(%[[VAL_8]] : !fir.ref>>) diff --git a/flang/test/Lower/OpenMP/parallel-reduction-array2.f90 b/flang/test/Lower/OpenMP/parallel-reduction-array2.f90 index 28914e78bf388217185de3ec59828d171447d00d..aa14092554eda28626b3fabed97a9681420eb681 100644 --- a/flang/test/Lower/OpenMP/parallel-reduction-array2.f90 +++ b/flang/test/Lower/OpenMP/parallel-reduction-array2.f90 @@ -22,9 +22,11 @@ end program ! CHECK: %[[VAL_5:.*]] = fir.shape %[[VAL_4]] : (index) -> !fir.shape<1> ! CHECK: %[[VAL_1:.*]] = fir.allocmem !fir.array<3xi32> ! CHECK: %[[TRUE:.*]] = arith.constant true -! CHECK: %[[VAL_6:.*]]:2 = hlfir.declare %[[VAL_1]](%[[VAL_5]]) {uniq_name = ".tmp"} : (!fir.heap>, -!fir.shape<1>) -> (!fir.heap>, !fir.heap>) -! CHECK: %[[VAL_7:.*]] = fir.embox %[[VAL_6]]#0(%[[VAL_5]]) : (!fir.heap>, !fir.shape<1>) -> !fir.box> +! CHECK: %[[VAL_6:.*]]:2 = hlfir.declare %[[VAL_1]](%[[VAL_5]]) {uniq_name = ".tmp"} : (!fir.heap>, !fir.shape<1>) -> (!fir.heap>, !fir.heap>) +! CHECK: %[[C0:.*]] = arith.constant 0 : index +! CHECK: %[[DIMS:.*]]:3 = fir.box_dims %[[VAL_3]], %[[C0]] : (!fir.box>, index) -> (index, index, index) +! CHECK: %[[SHIFT:.*]] = fir.shape_shift %[[DIMS]]#0, %[[DIMS]]#1 : (index, index) -> !fir.shapeshift<1> +! CHECK: %[[VAL_7:.*]] = fir.embox %[[VAL_6]]#0(%[[SHIFT]]) : (!fir.heap>, !fir.shapeshift<1>) -> !fir.box> ! CHECK: hlfir.assign %[[VAL_2]] to %[[VAL_7]] : i32, !fir.box> ! CHECK: fir.store %[[VAL_7]] to %[[VAL_8]] : !fir.ref>> ! CHECK: omp.yield(%[[VAL_8]] : !fir.ref>>) diff --git a/flang/test/Lower/OpenMP/parallel-reduction3.f90 b/flang/test/Lower/OpenMP/parallel-reduction3.f90 index 4d25a4c34bd9a4715f083d9708a505a66f24b7b6..2a4e338f255ebb842ff95cf68373f1ad588dccb2 100644 --- a/flang/test/Lower/OpenMP/parallel-reduction3.f90 +++ b/flang/test/Lower/OpenMP/parallel-reduction3.f90 @@ -12,8 +12,12 @@ ! CHECK: %[[VAL_6:.*]] = fir.allocmem !fir.array, %[[VAL_4]]#1 {bindc_name = ".tmp", uniq_name = ""} ! CHECK: %[[TRUE:.*]] = arith.constant true ! CHECK: %[[VAL_7:.*]]:2 = hlfir.declare %[[VAL_6]](%[[VAL_5]]) {uniq_name = ".tmp"} : (!fir.heap>, !fir.shape<1>) -> (!fir.box>, !fir.heap>) -! CHECK: hlfir.assign %[[VAL_1]] to %[[VAL_7]]#0 : i32, !fir.box> -! CHECK: fir.store %[[VAL_7]]#0 to %[[VAL_8]] : !fir.ref>> +! CHECK: %[[C0:.*]] = arith.constant 0 : index +! CHECK: %[[DIMS:.*]]:3 = fir.box_dims %[[VAL_2]], %[[C0]] : (!fir.box>, index) -> (index, index, index) +! CHECK: %[[SHIFT:.*]] = fir.shape_shift %[[DIMS]]#0, %[[DIMS]]#1 : (index, index) -> !fir.shapeshift<1> +! CHECK: %[[REBOX:.*]] = fir.rebox %[[VAL_7]]#0(%[[SHIFT]]) : (!fir.box>, !fir.shapeshift<1>) -> !fir.box> +! CHECK: hlfir.assign %[[VAL_1]] to %[[REBOX]] : i32, !fir.box> +! CHECK: fir.store %[[REBOX]] to %[[VAL_8]] : !fir.ref>> ! CHECK: omp.yield(%[[VAL_8]] : !fir.ref>>) ! CHECK: } combiner { ! CHECK: ^bb0(%[[VAL_0:.*]]: !fir.ref>>, %[[VAL_1:.*]]: !fir.ref>>): @@ -70,30 +74,33 @@ ! CHECK: %[[VAL_18:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_19:.*]] = fir.alloca !fir.box> ! CHECK: fir.store %[[VAL_12]]#0 to %[[VAL_19]] : !fir.ref>> -! CHECK: omp.wsloop byref reduction(@add_reduction_byref_box_Uxi32 %[[VAL_19]] -> %[[VAL_20:.*]] : !fir.ref>>) for (%[[VAL_21:.*]]) : i32 = (%[[VAL_16]]) to (%[[VAL_17]]) inclusive step (%[[VAL_18]]) { -! CHECK: fir.store %[[VAL_21]] to %[[VAL_15]]#1 : !fir.ref -! CHECK: %[[VAL_22:.*]]:2 = hlfir.declare %[[VAL_20]] {uniq_name = "_QFsEc"} : (!fir.ref>>) -> (!fir.ref>>, !fir.ref>>) -! CHECK: %[[VAL_23:.*]] = fir.load %[[VAL_22]]#0 : !fir.ref>> -! CHECK: %[[VAL_24:.*]] = fir.load %[[VAL_15]]#0 : !fir.ref -! CHECK: %[[VAL_25:.*]] = arith.constant 0 : index -! CHECK: %[[VAL_26:.*]]:3 = fir.box_dims %[[VAL_23]], %[[VAL_25]] : (!fir.box>, index) -> (index, index, index) -! CHECK: %[[VAL_27:.*]] = fir.shape %[[VAL_26]]#1 : (index) -> !fir.shape<1> -! CHECK: %[[VAL_28:.*]] = hlfir.elemental %[[VAL_27]] unordered : (!fir.shape<1>) -> !hlfir.expr { -! CHECK: ^bb0(%[[VAL_29:.*]]: index): -! CHECK: %[[VAL_30:.*]] = arith.constant 0 : index -! CHECK: %[[VAL_31:.*]]:3 = fir.box_dims %[[VAL_23]], %[[VAL_30]] : (!fir.box>, index) -> (index, index, index) -! CHECK: %[[VAL_32:.*]] = arith.constant 1 : index -! CHECK: %[[VAL_33:.*]] = arith.subi %[[VAL_31]]#0, %[[VAL_32]] : index -! CHECK: %[[VAL_34:.*]] = arith.addi %[[VAL_29]], %[[VAL_33]] : index -! CHECK: %[[VAL_35:.*]] = hlfir.designate %[[VAL_23]] (%[[VAL_34]]) : (!fir.box>, index) -> !fir.ref -! CHECK: %[[VAL_36:.*]] = fir.load %[[VAL_35]] : !fir.ref -! CHECK: %[[VAL_37:.*]] = arith.addi %[[VAL_36]], %[[VAL_24]] : i32 -! CHECK: hlfir.yield_element %[[VAL_37]] : i32 +! CHECK: omp.wsloop byref reduction(@add_reduction_byref_box_Uxi32 %[[VAL_19]] -> %[[VAL_20:.*]] : !fir.ref>>) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_21:.*]]) : i32 = (%[[VAL_16]]) to (%[[VAL_17]]) inclusive step (%[[VAL_18]]) { +! CHECK: %[[VAL_22:.*]]:2 = hlfir.declare %[[VAL_20]] {uniq_name = "_QFsEc"} : (!fir.ref>>) -> (!fir.ref>>, !fir.ref>>) +! CHECK: fir.store %[[VAL_21]] to %[[VAL_15]]#1 : !fir.ref +! CHECK: %[[VAL_23:.*]] = fir.load %[[VAL_22]]#0 : !fir.ref>> +! CHECK: %[[VAL_24:.*]] = fir.load %[[VAL_15]]#0 : !fir.ref +! CHECK: %[[VAL_25:.*]] = arith.constant 0 : index +! CHECK: %[[VAL_26:.*]]:3 = fir.box_dims %[[VAL_23]], %[[VAL_25]] : (!fir.box>, index) -> (index, index, index) +! CHECK: %[[VAL_27:.*]] = fir.shape %[[VAL_26]]#1 : (index) -> !fir.shape<1> +! CHECK: %[[VAL_28:.*]] = hlfir.elemental %[[VAL_27]] unordered : (!fir.shape<1>) -> !hlfir.expr { +! CHECK: ^bb0(%[[VAL_29:.*]]: index): +! CHECK: %[[VAL_30:.*]] = arith.constant 0 : index +! CHECK: %[[VAL_31:.*]]:3 = fir.box_dims %[[VAL_23]], %[[VAL_30]] : (!fir.box>, index) -> (index, index, index) +! CHECK: %[[VAL_32:.*]] = arith.constant 1 : index +! CHECK: %[[VAL_33:.*]] = arith.subi %[[VAL_31]]#0, %[[VAL_32]] : index +! CHECK: %[[VAL_34:.*]] = arith.addi %[[VAL_29]], %[[VAL_33]] : index +! CHECK: %[[VAL_35:.*]] = hlfir.designate %[[VAL_23]] (%[[VAL_34]]) : (!fir.box>, index) -> !fir.ref +! CHECK: %[[VAL_36:.*]] = fir.load %[[VAL_35]] : !fir.ref +! CHECK: %[[VAL_37:.*]] = arith.addi %[[VAL_36]], %[[VAL_24]] : i32 +! CHECK: hlfir.yield_element %[[VAL_37]] : i32 +! CHECK: } +! CHECK: %[[VAL_38:.*]] = fir.load %[[VAL_22]]#0 : !fir.ref>> +! CHECK: hlfir.assign %[[VAL_28]] to %[[VAL_38]] : !hlfir.expr, !fir.box> +! CHECK: hlfir.destroy %[[VAL_28]] : !hlfir.expr +! CHECK: omp.yield ! CHECK: } -! CHECK: %[[VAL_38:.*]] = fir.load %[[VAL_22]]#0 : !fir.ref>> -! CHECK: hlfir.assign %[[VAL_28]] to %[[VAL_38]] : !hlfir.expr, !fir.box> -! CHECK: hlfir.destroy %[[VAL_28]] : !hlfir.expr -! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } diff --git a/flang/test/Lower/OpenMP/parallel-wsloop-firstpriv.f90 b/flang/test/Lower/OpenMP/parallel-wsloop-firstpriv.f90 index 716a7d71bb62880c091b246893c78d733bb21815..ac8b9f50f54e67a8f9ff60ec5dba11919ab9f8a3 100644 --- a/flang/test/Lower/OpenMP/parallel-wsloop-firstpriv.f90 +++ b/flang/test/Lower/OpenMP/parallel-wsloop-firstpriv.f90 @@ -20,10 +20,14 @@ subroutine omp_do_firstprivate(a) ! CHECK: %[[LB:.*]] = arith.constant 1 : i32 ! CHECK-NEXT: %[[UB:.*]] = fir.load %[[A_PVT_DECL]]#0 : !fir.ref ! CHECK-NEXT: %[[STEP:.*]] = arith.constant 1 : i32 - ! CHECK-NEXT: omp.wsloop for (%[[ARG1:.*]]) : i32 = (%[[LB]]) to (%[[UB]]) inclusive step (%[[STEP]]) + ! CHECK-NEXT: omp.wsloop { + ! CHECK-NEXT: omp.loop_nest (%[[ARG1:.*]]) : i32 = (%[[LB]]) to (%[[UB]]) inclusive step (%[[STEP]]) { ! CHECK-NEXT: fir.store %[[ARG1]] to %[[I_PVT_DECL]]#1 : !fir.ref ! CHECK-NEXT: fir.call @_QPfoo(%[[I_PVT_DECL]]#1, %[[A_PVT_DECL]]#1) {{.*}}: (!fir.ref, !fir.ref) -> () ! CHECK-NEXT: omp.yield + ! CHECK-NEXT: } + ! CHECK-NEXT: omp.terminator + ! CHECK-NEXT: } do i=1, a call foo(i, a) end do @@ -56,10 +60,12 @@ subroutine omp_do_firstprivate2(a, n) ! CHECK: %[[LB:.*]] = fir.load %[[A_PVT_DECL]]#0 : !fir.ref ! CHECK: %[[UB:.*]] = fir.load %[[N_PVT_DECL]]#0 : !fir.ref ! CHECK: %[[STEP:.*]] = arith.constant 1 : i32 - ! CHECK: omp.wsloop for (%[[ARG2:.*]]) : i32 = (%[[LB]]) to (%[[UB]]) inclusive step (%[[STEP]]) + ! CHECK: omp.wsloop { + ! CHECK-NEXT: omp.loop_nest (%[[ARG2:.*]]) : i32 = (%[[LB]]) to (%[[UB]]) inclusive step (%[[STEP]]) { ! CHECK: fir.store %[[ARG2]] to %[[I_PVT_DECL]]#1 : !fir.ref ! CHECK: fir.call @_QPfoo(%[[I_PVT_DECL]]#1, %[[A_PVT_DECL]]#1) {{.*}}: (!fir.ref, !fir.ref) -> () ! CHECK: omp.yield + ! CHECK: omp.terminator do i= a, n call foo(i, a) end do diff --git a/flang/test/Lower/OpenMP/parallel-wsloop.f90 b/flang/test/Lower/OpenMP/parallel-wsloop.f90 index c06f941b74b582c0523d71908e4e52e04683fbd2..602b3d1c05f0de756f0f6ca64cc7da2e67553ab5 100644 --- a/flang/test/Lower/OpenMP/parallel-wsloop.f90 +++ b/flang/test/Lower/OpenMP/parallel-wsloop.f90 @@ -6,19 +6,21 @@ subroutine simple_parallel_do integer :: i ! CHECK: omp.parallel - ! CHECK: %[[WS_LB:.*]] = arith.constant 1 : i32 - ! CHECK: %[[WS_UB:.*]] = arith.constant 9 : i32 - ! CHECK: %[[WS_STEP:.*]] = arith.constant 1 : i32 - ! CHECK: omp.wsloop for (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) + ! CHECK: %[[WS_LB:.*]] = arith.constant 1 : i32 + ! CHECK: %[[WS_UB:.*]] = arith.constant 9 : i32 + ! CHECK: %[[WS_STEP:.*]] = arith.constant 1 : i32 + ! CHECK: omp.wsloop { + ! CHECK-NEXT: omp.loop_nest (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) { !$OMP PARALLEL DO do i=1, 9 - ! CHECK: fir.store %[[I]] to %[[IV_ADDR:.*]]#1 : !fir.ref - ! CHECK: %[[LOAD_IV:.*]] = fir.load %[[IV_ADDR]]#0 : !fir.ref - ! CHECK: fir.call @_FortranAioOutputInteger32({{.*}}, %[[LOAD_IV]]) {{.*}}: (!fir.ref, i32) -> i1 + ! CHECK: fir.store %[[I]] to %[[IV_ADDR:.*]]#1 : !fir.ref + ! CHECK: %[[LOAD_IV:.*]] = fir.load %[[IV_ADDR]]#0 : !fir.ref + ! CHECK: fir.call @_FortranAioOutputInteger32({{.*}}, %[[LOAD_IV]]) {{.*}}: (!fir.ref, i32) -> i1 print*, i end do - ! CHECK: omp.yield - ! CHECK: omp.terminator + ! CHECK: omp.yield + ! CHECK: omp.terminator + ! CHECK: omp.terminator !$OMP END PARALLEL DO end subroutine @@ -34,19 +36,21 @@ subroutine parallel_do_with_parallel_clauses(cond, nt) ! CHECK: %[[COND_CVT:.*]] = fir.convert %[[COND]] : (!fir.logical<4>) -> i1 ! CHECK: %[[NT:.*]] = fir.load %[[NT_DECL]]#0 : !fir.ref ! CHECK: omp.parallel if(%[[COND_CVT]] : i1) num_threads(%[[NT]] : i32) proc_bind(close) - ! CHECK: %[[WS_LB:.*]] = arith.constant 1 : i32 - ! CHECK: %[[WS_UB:.*]] = arith.constant 9 : i32 - ! CHECK: %[[WS_STEP:.*]] = arith.constant 1 : i32 - ! CHECK: omp.wsloop for (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) + ! CHECK: %[[WS_LB:.*]] = arith.constant 1 : i32 + ! CHECK: %[[WS_UB:.*]] = arith.constant 9 : i32 + ! CHECK: %[[WS_STEP:.*]] = arith.constant 1 : i32 + ! CHECK: omp.wsloop { + ! CHECK-NEXT: omp.loop_nest (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) { !$OMP PARALLEL DO IF(cond) NUM_THREADS(nt) PROC_BIND(close) do i=1, 9 - ! CHECK: fir.store %[[I]] to %[[IV_ADDR:.*]]#1 : !fir.ref - ! CHECK: %[[LOAD_IV:.*]] = fir.load %[[IV_ADDR]]#0 : !fir.ref - ! CHECK: fir.call @_FortranAioOutputInteger32({{.*}}, %[[LOAD_IV]]) {{.*}}: (!fir.ref, i32) -> i1 + ! CHECK: fir.store %[[I]] to %[[IV_ADDR:.*]]#1 : !fir.ref + ! CHECK: %[[LOAD_IV:.*]] = fir.load %[[IV_ADDR]]#0 : !fir.ref + ! CHECK: fir.call @_FortranAioOutputInteger32({{.*}}, %[[LOAD_IV]]) {{.*}}: (!fir.ref, i32) -> i1 print*, i end do - ! CHECK: omp.yield - ! CHECK: omp.terminator + ! CHECK: omp.yield + ! CHECK: omp.terminator + ! CHECK: omp.terminator !$OMP END PARALLEL DO end subroutine @@ -58,19 +62,21 @@ subroutine parallel_do_with_clauses(nt) integer :: i ! CHECK: %[[NT:.*]] = fir.load %[[NT_DECL]]#0 : !fir.ref ! CHECK: omp.parallel num_threads(%[[NT]] : i32) - ! CHECK: %[[WS_LB:.*]] = arith.constant 1 : i32 - ! CHECK: %[[WS_UB:.*]] = arith.constant 9 : i32 - ! CHECK: %[[WS_STEP:.*]] = arith.constant 1 : i32 - ! CHECK: omp.wsloop schedule(dynamic) for (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) + ! CHECK: %[[WS_LB:.*]] = arith.constant 1 : i32 + ! CHECK: %[[WS_UB:.*]] = arith.constant 9 : i32 + ! CHECK: %[[WS_STEP:.*]] = arith.constant 1 : i32 + ! CHECK: omp.wsloop schedule(dynamic) { + ! CHECK-NEXT: omp.loop_nest (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) { !$OMP PARALLEL DO NUM_THREADS(nt) SCHEDULE(dynamic) do i=1, 9 - ! CHECK: fir.store %[[I]] to %[[IV_ADDR:.*]]#1 : !fir.ref - ! CHECK: %[[LOAD_IV:.*]] = fir.load %[[IV_ADDR]]#0 : !fir.ref - ! CHECK: fir.call @_FortranAioOutputInteger32({{.*}}, %[[LOAD_IV]]) {{.*}}: (!fir.ref, i32) -> i1 + ! CHECK: fir.store %[[I]] to %[[IV_ADDR:.*]]#1 : !fir.ref + ! CHECK: %[[LOAD_IV:.*]] = fir.load %[[IV_ADDR]]#0 : !fir.ref + ! CHECK: fir.call @_FortranAioOutputInteger32({{.*}}, %[[LOAD_IV]]) {{.*}}: (!fir.ref, i32) -> i1 print*, i end do - ! CHECK: omp.yield - ! CHECK: omp.terminator + ! CHECK: omp.yield + ! CHECK: omp.terminator + ! CHECK: omp.terminator !$OMP END PARALLEL DO end subroutine @@ -88,20 +94,21 @@ subroutine parallel_do_with_privatisation_clauses(cond,nt) integer :: nt integer :: i ! CHECK: omp.parallel - ! CHECK: %[[PRIVATE_COND_REF:.*]] = fir.alloca !fir.logical<4> {bindc_name = "cond", pinned, uniq_name = "_QFparallel_do_with_privatisation_clausesEcond"} - ! CHECK: %[[PRIVATE_COND_DECL:.*]]:2 = hlfir.declare %[[PRIVATE_COND_REF]] {uniq_name = "_QFparallel_do_with_privatisation_clausesEcond"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) - ! CHECK: %[[PRIVATE_NT_REF:.*]] = fir.alloca i32 {bindc_name = "nt", pinned, uniq_name = "_QFparallel_do_with_privatisation_clausesEnt"} - ! CHECK: %[[PRIVATE_NT_DECL:.*]]:2 = hlfir.declare %[[PRIVATE_NT_REF]] {uniq_name = "_QFparallel_do_with_privatisation_clausesEnt"} : (!fir.ref) -> (!fir.ref, !fir.ref) - ! CHECK: %[[NT_VAL:.*]] = fir.load %[[NT_DECL]]#0 : !fir.ref - ! CHECK: hlfir.assign %[[NT_VAL]] to %[[PRIVATE_NT_DECL]]#0 temporary_lhs : i32, !fir.ref - ! CHECK: %[[WS_LB:.*]] = arith.constant 1 : i32 - ! CHECK: %[[WS_UB:.*]] = arith.constant 9 : i32 - ! CHECK: %[[WS_STEP:.*]] = arith.constant 1 : i32 - ! CHECK: omp.wsloop for (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) + ! CHECK: %[[PRIVATE_COND_REF:.*]] = fir.alloca !fir.logical<4> {bindc_name = "cond", pinned, uniq_name = "_QFparallel_do_with_privatisation_clausesEcond"} + ! CHECK: %[[PRIVATE_COND_DECL:.*]]:2 = hlfir.declare %[[PRIVATE_COND_REF]] {uniq_name = "_QFparallel_do_with_privatisation_clausesEcond"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) + ! CHECK: %[[PRIVATE_NT_REF:.*]] = fir.alloca i32 {bindc_name = "nt", pinned, uniq_name = "_QFparallel_do_with_privatisation_clausesEnt"} + ! CHECK: %[[PRIVATE_NT_DECL:.*]]:2 = hlfir.declare %[[PRIVATE_NT_REF]] {uniq_name = "_QFparallel_do_with_privatisation_clausesEnt"} : (!fir.ref) -> (!fir.ref, !fir.ref) + ! CHECK: %[[NT_VAL:.*]] = fir.load %[[NT_DECL]]#0 : !fir.ref + ! CHECK: hlfir.assign %[[NT_VAL]] to %[[PRIVATE_NT_DECL]]#0 temporary_lhs : i32, !fir.ref + ! CHECK: %[[WS_LB:.*]] = arith.constant 1 : i32 + ! CHECK: %[[WS_UB:.*]] = arith.constant 9 : i32 + ! CHECK: %[[WS_STEP:.*]] = arith.constant 1 : i32 + ! CHECK: omp.wsloop { + ! CHECK-NEXT: omp.loop_nest (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) { !$OMP PARALLEL DO PRIVATE(cond) FIRSTPRIVATE(nt) do i=1, 9 - ! CHECK: fir.store %[[I]] to %[[IV_ADDR:.*]]#1 : !fir.ref - ! CHECK: %[[LOAD_IV:.*]] = fir.load %[[IV_ADDR]]#0 : !fir.ref + ! CHECK: fir.store %[[I]] to %[[IV_ADDR:.*]]#1 : !fir.ref + ! CHECK: %[[LOAD_IV:.*]] = fir.load %[[IV_ADDR]]#0 : !fir.ref ! CHECK: fir.call @_FortranAioOutputInteger32({{.*}}, %[[LOAD_IV]]) {{.*}}: (!fir.ref, i32) -> i1 ! CHECK: %[[PRIVATE_COND_VAL:.*]] = fir.load %[[PRIVATE_COND_DECL]]#0 : !fir.ref> ! CHECK: %[[PRIVATE_COND_VAL_CVT:.*]] = fir.convert %[[PRIVATE_COND_VAL]] : (!fir.logical<4>) -> i1 @@ -112,6 +119,7 @@ subroutine parallel_do_with_privatisation_clauses(cond,nt) end do ! CHECK: omp.yield ! CHECK: omp.terminator + ! CHECK: omp.terminator !$OMP END PARALLEL DO end subroutine @@ -150,10 +158,13 @@ end subroutine parallel_private_do ! CHECK: %[[VAL_7:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_8:.*]] = arith.constant 9 : i32 ! CHECK: %[[VAL_9:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop for (%[[I:.*]]) : i32 = (%[[VAL_7]]) to (%[[VAL_8]]) inclusive step (%[[VAL_9]]) { -! CHECK: fir.store %[[I]] to %[[I_PRIV_DECL]]#1 : !fir.ref -! CHECK: fir.call @_QPfoo(%[[I_PRIV_DECL]]#1, %[[COND_DECL]]#1, %[[NT_PRIV_DECL]]#1) {{.*}}: (!fir.ref, !fir.ref>, !fir.ref) -> () -! CHECK: omp.yield +! CHECK: omp.wsloop { +! CHECK-NEXT: omp.loop_nest (%[[I:.*]]) : i32 = (%[[VAL_7]]) to (%[[VAL_8]]) inclusive step (%[[VAL_9]]) { +! CHECK: fir.store %[[I]] to %[[I_PRIV_DECL]]#1 : !fir.ref +! CHECK: fir.call @_QPfoo(%[[I_PRIV_DECL]]#1, %[[COND_DECL]]#1, %[[NT_PRIV_DECL]]#1) {{.*}}: (!fir.ref, !fir.ref>, !fir.ref) -> () +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } @@ -196,10 +207,13 @@ end subroutine omp_parallel_multiple_firstprivate_do ! CHECK: %[[VAL_8:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_9:.*]] = arith.constant 10 : i32 ! CHECK: %[[VAL_10:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop for (%[[I:.*]]) : i32 = (%[[VAL_8]]) to (%[[VAL_9]]) inclusive step (%[[VAL_10]]) { -! CHECK: fir.store %[[I]] to %[[I_PRIV_DECL]]#1 : !fir.ref -! CHECK: fir.call @_QPbar(%[[I_PRIV_DECL]]#1, %[[A_PRIV_DECL]]#1) {{.*}}: (!fir.ref, !fir.ref) -> () -! CHECK: omp.yield +! CHECK: omp.wsloop { +! CHECK-NEXT: omp.loop_nest (%[[I:.*]]) : i32 = (%[[VAL_8]]) to (%[[VAL_9]]) inclusive step (%[[VAL_10]]) { +! CHECK: fir.store %[[I]] to %[[I_PRIV_DECL]]#1 : !fir.ref +! CHECK: fir.call @_QPbar(%[[I_PRIV_DECL]]#1, %[[A_PRIV_DECL]]#1) {{.*}}: (!fir.ref, !fir.ref) -> () +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } @@ -241,10 +255,13 @@ end subroutine parallel_do_private ! CHECK: %[[VAL_7:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_8:.*]] = arith.constant 9 : i32 ! CHECK: %[[VAL_9:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop for (%[[I:.*]]) : i32 = (%[[VAL_7]]) to (%[[VAL_8]]) inclusive step (%[[VAL_9]]) { -! CHECK: fir.store %[[I]] to %[[I_PRIV_DECL]]#1 : !fir.ref -! CHECK: fir.call @_QPfoo(%[[I_PRIV_DECL]]#1, %[[COND_PRIV_DECL]]#1, %[[NT_PRIV_DECL]]#1) {{.*}}: (!fir.ref, !fir.ref>, !fir.ref) -> () -! CHECK: omp.yield +! CHECK: omp.wsloop { +! CHECK-NEXT: omp.loop_nest (%[[I:.*]]) : i32 = (%[[VAL_7]]) to (%[[VAL_8]]) inclusive step (%[[VAL_9]]) { +! CHECK: fir.store %[[I]] to %[[I_PRIV_DECL]]#1 : !fir.ref +! CHECK: fir.call @_QPfoo(%[[I_PRIV_DECL]]#1, %[[COND_PRIV_DECL]]#1, %[[NT_PRIV_DECL]]#1) {{.*}}: (!fir.ref, !fir.ref>, !fir.ref) -> () +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } @@ -271,9 +288,9 @@ end subroutine omp_parallel_do_multiple_firstprivate ! CHECK-LABEL: func.func @_QPomp_parallel_do_multiple_firstprivate( ! CHECK-SAME: %[[A_ADDR:.*]]: !fir.ref {fir.bindc_name = "a"}, ! CHECK-SAME: %[[B_ADDR:.*]]: !fir.ref {fir.bindc_name = "b"}) { -! CHECK: %[[A_DECL:.*]]:2 = hlfir.declare %[[A_ADDR]] {uniq_name = "_QFomp_parallel_do_multiple_firstprivateEa"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[B_DECL:.*]]:2 = hlfir.declare %[[B_ADDR]] {uniq_name = "_QFomp_parallel_do_multiple_firstprivateEb"} : (!fir.ref) -> (!fir.ref, !fir.ref -! CHECK: omp.parallel { +! CHECK: %[[A_DECL:.*]]:2 = hlfir.declare %[[A_ADDR]] {uniq_name = "_QFomp_parallel_do_multiple_firstprivateEa"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: %[[B_DECL:.*]]:2 = hlfir.declare %[[B_ADDR]] {uniq_name = "_QFomp_parallel_do_multiple_firstprivateEb"} : (!fir.ref) -> (!fir.ref, !fir.ref +! CHECK: omp.parallel { ! CHECK: %[[I_PRIV_ADDR:.*]] = fir.alloca i32 {adapt.valuebyref, pinned} ! CHECK: %[[I_PRIV_DECL:.*]]:2 = hlfir.declare %[[I_PRIV_ADDR]] {uniq_name = "_QFomp_parallel_do_multiple_firstprivateEi"} : (!fir.ref) -> (!fir.ref, !fir.ref) ! CHECK: %[[A_PRIV_ADDR:.*]] = fir.alloca i32 {bindc_name = "a", pinned, uniq_name = "_QFomp_parallel_do_multiple_firstprivateEa"} @@ -287,12 +304,15 @@ end subroutine omp_parallel_do_multiple_firstprivate ! CHECK: %[[VAL_8:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_9:.*]] = arith.constant 10 : i32 ! CHECK: %[[VAL_10:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop for (%[[I:.*]]) : i32 = (%[[VAL_8]]) to (%[[VAL_9]]) inclusive step (%[[VAL_10]]) { -! CHECK: fir.store %[[I]] to %[[I_PRIV_DECL]]#1 : !fir.ref -! CHECK: fir.call @_QPbar(%[[I_PRIV_DECL]]#1, %[[A_PRIV_DECL]]#1) {{.*}}: (!fir.ref, !fir.ref) -> () -! CHECK: omp.yield +! CHECK: omp.wsloop { +! CHECK-NEXT: omp.loop_nest (%[[I:.*]]) : i32 = (%[[VAL_8]]) to (%[[VAL_9]]) inclusive step (%[[VAL_10]]) { +! CHECK: fir.store %[[I]] to %[[I_PRIV_DECL]]#1 : !fir.ref +! CHECK: fir.call @_QPbar(%[[I_PRIV_DECL]]#1, %[[A_PRIV_DECL]]#1) {{.*}}: (!fir.ref, !fir.ref) -> () +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } -! CHECK: return +! CHECK: return ! CHECK: } diff --git a/flang/test/Lower/OpenMP/simd.f90 b/flang/test/Lower/OpenMP/simd.f90 index 190aa615212176cde1fe366a1cb2f6ad8715cd1a..8ec1a3cefb4a6086a9d6bfd35a8e6670fa050301 100644 --- a/flang/test/Lower/OpenMP/simd.f90 +++ b/flang/test/Lower/OpenMP/simd.f90 @@ -1,7 +1,8 @@ ! Tests for 2.9.3.1 Simd -!RUN: %flang_fc1 -flang-experimental-hlfir -emit-hlfir -fopenmp %s -o - | FileCheck %s -!RUN: bbc -hlfir -emit-hlfir -fopenmp %s -o - | FileCheck %s +! The "if" clause was added to the "simd" directive in OpenMP 5.0. +! RUN: %flang_fc1 -flang-experimental-hlfir -emit-hlfir -fopenmp -fopenmp-version=50 %s -o - | FileCheck %s +! RUN: bbc -hlfir -emit-hlfir -fopenmp -fopenmp-version=50 %s -o - | FileCheck %s !CHECK-LABEL: func @_QPsimd() subroutine simd diff --git a/flang/test/Lower/OpenMP/stop-stmt-in-region.f90 b/flang/test/Lower/OpenMP/stop-stmt-in-region.f90 index fdbabc21b2c9e94138c7c5ef2d8ded578ed37399..4f3819c5e4eb7c0caf2bd9cc291aa90babba8ffc 100644 --- a/flang/test/Lower/OpenMP/stop-stmt-in-region.f90 +++ b/flang/test/Lower/OpenMP/stop-stmt-in-region.f90 @@ -82,24 +82,27 @@ end ! CHECK: %[[VAL_3:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_4:.*]] = arith.constant 10 : i32 ! CHECK: %[[VAL_5:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop for (%[[VAL_6:.*]]) : i32 = (%[[VAL_3]]) to (%[[VAL_4]]) inclusive step (%[[VAL_5]]) { -! CHECK: fir.store %[[VAL_6]] to %[[VAL_0_DECL]]#1 : !fir.ref -! CHECK: cf.br ^bb1 -! CHECK: ^bb1: -! CHECK: %[[VAL_7:.*]] = arith.constant 3 : i32 -! CHECK: hlfir.assign %[[VAL_7]] to %[[VAL_2_DECL]]#0 : i32, !fir.ref -! CHECK: %[[VAL_8:.*]] = fir.load %[[VAL_2_DECL]]#0 : !fir.ref -! CHECK: %[[VAL_9:.*]] = arith.constant 1 : i32 -! CHECK: %[[VAL_10:.*]] = arith.cmpi sgt, %[[VAL_8]], %[[VAL_9]] : i32 -! CHECK: cf.cond_br %[[VAL_10]], ^bb2, ^bb3 -! CHECK: ^bb2: -! CHECK: %[[VAL_11:.*]] = fir.load %[[VAL_2_DECL]]#0 : !fir.ref -! CHECK: %[[VAL_12:.*]] = arith.constant false -! CHECK: %[[VAL_13:.*]] = arith.constant false -! CHECK: %[[VAL_14:.*]] = fir.call @_FortranAStopStatement(%[[VAL_11]], %[[VAL_12]], %[[VAL_13]]) {{.*}} : (i32, i1, i1) -> none -! CHECK: omp.yield -! CHECK: ^bb3: -! CHECK: omp.yield +! CHECK: omp.wsloop { +! CHECK-NEXT: omp.loop_nest (%[[VAL_6:.*]]) : i32 = (%[[VAL_3]]) to (%[[VAL_4]]) inclusive step (%[[VAL_5]]) { +! CHECK: fir.store %[[VAL_6]] to %[[VAL_0_DECL]]#1 : !fir.ref +! CHECK: cf.br ^bb1 +! CHECK: ^bb1: +! CHECK: %[[VAL_7:.*]] = arith.constant 3 : i32 +! CHECK: hlfir.assign %[[VAL_7]] to %[[VAL_2_DECL]]#0 : i32, !fir.ref +! CHECK: %[[VAL_8:.*]] = fir.load %[[VAL_2_DECL]]#0 : !fir.ref +! CHECK: %[[VAL_9:.*]] = arith.constant 1 : i32 +! CHECK: %[[VAL_10:.*]] = arith.cmpi sgt, %[[VAL_8]], %[[VAL_9]] : i32 +! CHECK: cf.cond_br %[[VAL_10]], ^bb2, ^bb3 +! CHECK: ^bb2: +! CHECK: %[[VAL_11:.*]] = fir.load %[[VAL_2_DECL]]#0 : !fir.ref +! CHECK: %[[VAL_12:.*]] = arith.constant false +! CHECK: %[[VAL_13:.*]] = arith.constant false +! CHECK: %[[VAL_14:.*]] = fir.call @_FortranAStopStatement(%[[VAL_11]], %[[VAL_12]], %[[VAL_13]]) {{.*}} : (i32, i1, i1) -> none +! CHECK: omp.yield +! CHECK: ^bb3: +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: cf.br ^bb1 ! CHECK: ^bb1: diff --git a/flang/test/Lower/OpenMP/target.f90 b/flang/test/Lower/OpenMP/target.f90 index 51b66327dfb24b087a877a694593033f9afbe555..44f77b5c33607b013a89c763515c89e15580c482 100644 --- a/flang/test/Lower/OpenMP/target.f90 +++ b/flang/test/Lower/OpenMP/target.f90 @@ -1,4 +1,5 @@ -!RUN: %flang_fc1 -emit-hlfir -fopenmp %s -o - | FileCheck %s +! The "thread_limit" clause was added to the "target" construct in OpenMP 5.1. +! RUN: %flang_fc1 -emit-hlfir -fopenmp -fopenmp-version=51 %s -o - | FileCheck %s !=============================================================================== ! Target_Enter Simple @@ -594,7 +595,8 @@ subroutine omp_target_parallel_do !$omp target parallel do map(tofrom: a) !CHECK: %[[I_PVT_ALLOCA:.*]] = fir.alloca i32 {adapt.valuebyref, pinned} !CHECK: %[[I_PVT_DECL:.*]]:2 = hlfir.declare %[[I_PVT_ALLOCA]] {uniq_name = "_QFomp_target_parallel_doEi"} : (!fir.ref) -> (!fir.ref, !fir.ref) - !CHECK: omp.wsloop for (%[[I_VAL:.*]]) : i32 + !CHECK: omp.wsloop { + !CHECK-NEXT: omp.loop_nest (%[[I_VAL:.*]]) : i32 do i = 1, 1024 !CHECK: fir.store %[[I_VAL]] to %[[I_PVT_DECL]]#1 : !fir.ref !CHECK: %[[C10:.*]] = arith.constant 10 : i32 @@ -606,6 +608,8 @@ subroutine omp_target_parallel_do end do !CHECK: omp.yield !CHECK: } + !CHECK: omp.terminator + !CHECK: } !CHECK: omp.terminator !CHECK: } !CHECK: omp.terminator diff --git a/flang/test/Lower/OpenMP/unstructured.f90 b/flang/test/Lower/OpenMP/unstructured.f90 index e5bf980ce90fd0ba2d82b65135f18cb2f6db8997..6a1331799d54779f782514b18e7da47c5bd373cb 100644 --- a/flang/test/Lower/OpenMP/unstructured.f90 +++ b/flang/test/Lower/OpenMP/unstructured.f90 @@ -70,27 +70,33 @@ end ! CHECK: ^bb1: // 2 preds: ^bb0, ^bb3 ! CHECK: cond_br %{{[0-9]*}}, ^bb2, ^bb4 ! CHECK: ^bb2: // pred: ^bb1 -! CHECK: omp.wsloop for (%[[ARG1:.*]]) : {{.*}} { -! CHECK: fir.store %[[ARG1]] to %[[OMP_LOOP_K_DECL]]#1 : !fir.ref -! CHECK: @_FortranAioBeginExternalListOutput -! CHECK: %[[LOAD_1:.*]] = fir.load %[[OMP_LOOP_K_DECL]]#0 : !fir.ref -! CHECK: @_FortranAioOutputInteger32(%{{.*}}, %[[LOAD_1]]) -! CHECK: omp.yield +! CHECK: omp.wsloop { +! CHECK: omp.loop_nest (%[[ARG1:.*]]) : {{.*}} { +! CHECK: fir.store %[[ARG1]] to %[[OMP_LOOP_K_DECL]]#1 : !fir.ref +! CHECK: @_FortranAioBeginExternalListOutput +! CHECK: %[[LOAD_1:.*]] = fir.load %[[OMP_LOOP_K_DECL]]#0 : !fir.ref +! CHECK: @_FortranAioOutputInteger32(%{{.*}}, %[[LOAD_1]]) +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } -! CHECK: omp.wsloop for (%[[ARG2:.*]]) : {{.*}} { -! CHECK: fir.store %[[ARG2]] to %[[OMP_LOOP_J_DECL]]#1 : !fir.ref -! CHECK: br ^bb1 -! CHECK: ^bb2: // 2 preds: ^bb1, ^bb5 -! CHECK: cond_br %{{[0-9]*}}, ^bb3, ^bb6 -! CHECK: ^bb3: // pred: ^bb2 -! CHECK: cond_br %{{[0-9]*}}, ^bb4, ^bb5 -! CHECK: ^bb4: // pred: ^bb3 -! CHECK: @_FortranAioBeginExternalListOutput -! CHECK: %[[LOAD_2:.*]] = fir.load %[[K_DECL]]#0 : !fir.ref -! CHECK: @_FortranAioOutputInteger32(%{{.*}}, %[[LOAD_2]]) -! CHECK: br ^bb2 -! CHECK: ^bb6: // 2 preds: ^bb2, ^bb4 -! CHECK: omp.yield +! CHECK: omp.wsloop { +! CHECK: omp.loop_nest (%[[ARG2:.*]]) : {{.*}} { +! CHECK: fir.store %[[ARG2]] to %[[OMP_LOOP_J_DECL]]#1 : !fir.ref +! CHECK: br ^bb1 +! CHECK: ^bb2: // 2 preds: ^bb1, ^bb5 +! CHECK: cond_br %{{[0-9]*}}, ^bb3, ^bb6 +! CHECK: ^bb3: // pred: ^bb2 +! CHECK: cond_br %{{[0-9]*}}, ^bb4, ^bb5 +! CHECK: ^bb4: // pred: ^bb3 +! CHECK: @_FortranAioBeginExternalListOutput +! CHECK: %[[LOAD_2:.*]] = fir.load %[[K_DECL]]#0 : !fir.ref +! CHECK: @_FortranAioOutputInteger32(%{{.*}}, %[[LOAD_2]]) +! CHECK: br ^bb2 +! CHECK: ^bb6: // 2 preds: ^bb2, ^bb4 +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: br ^bb1 ! CHECK: ^bb4: // pred: ^bb1 @@ -121,20 +127,23 @@ end ! CHECK: omp.parallel { ! CHECK: %[[ALLOCA:.*]] = fir.alloca i32 {{{.*}}, pinned} ! CHECK: %[[OMP_LOOP_J_DECL:.*]]:2 = hlfir.declare %[[ALLOCA]] {uniq_name = "_QFss4Ej"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: omp.wsloop for (%[[ARG:.*]]) : {{.*}} { -! CHECK: fir.store %[[ARG]] to %[[OMP_LOOP_J_DECL]]#1 : !fir.ref -! CHECK: %[[COND:.*]] = arith.cmpi eq, %{{.*}}, %{{.*}} -! CHECK: %[[COND_XOR:.*]] = arith.xori %[[COND]], %{{.*}} -! CHECK: fir.if %[[COND_XOR]] { -! CHECK: @_FortranAioBeginExternalListOutput -! CHECK: %[[LOAD:.*]] = fir.load %[[OMP_LOOP_J_DECL]]#0 : !fir.ref -! CHECK: @_FortranAioOutputInteger32(%{{.*}}, %[[LOAD]]) -! CHECK: } else { -! CHECK: } -! CHECK-NEXT: omp.yield +! CHECK: omp.wsloop { +! CHECK-NEXT: omp.loop_nest (%[[ARG:.*]]) : {{.*}} { +! CHECK: fir.store %[[ARG]] to %[[OMP_LOOP_J_DECL]]#1 : !fir.ref +! CHECK: %[[COND:.*]] = arith.cmpi eq, %{{.*}}, %{{.*}} +! CHECK: %[[COND_XOR:.*]] = arith.xori %[[COND]], %{{.*}} +! CHECK: fir.if %[[COND_XOR]] { +! CHECK: @_FortranAioBeginExternalListOutput +! CHECK: %[[LOAD:.*]] = fir.load %[[OMP_LOOP_J_DECL]]#0 : !fir.ref +! CHECK: @_FortranAioOutputInteger32(%{{.*}}, %[[LOAD]]) +! CHECK: } else { +! CHECK: } +! CHECK-NEXT: omp.yield +! CHECK-NEXT: } +! CHECK-NEXT: omp.terminator +! CHECK-NEXT: } +! CHECK: omp.terminator ! CHECK-NEXT: } -! CHECK: omp.terminator -! CHECK-NEXT:} subroutine ss4(n) ! CYCLE in OpenMP wsloop constructs !$omp parallel do i = 1, 3 @@ -150,20 +159,23 @@ end ! CHECK-LABEL: func @_QPss5() { ! CHECK: omp.parallel { -! CHECK: omp.wsloop {{.*}} { -! CHECK: br ^[[BB1:.*]] -! CHECK: ^[[BB1]]: -! CHECK: br ^[[BB2:.*]] -! CHECK: ^[[BB2]]: -! CHECK: cond_br %{{.*}}, ^[[BB3:.*]], ^[[BB6:.*]] -! CHECK: ^[[BB3]]: -! CHECK: cond_br %{{.*}}, ^[[BB4:.*]], ^[[BB3:.*]] -! CHECK: ^[[BB4]]: -! CHECK: br ^[[BB6]] -! CHECK: ^[[BB3]]: -! CHECK: br ^[[BB2]] -! CHECK: ^[[BB6]]: -! CHECK: omp.yield +! CHECK: omp.wsloop { +! CHECK: omp.loop_nest {{.*}} { +! CHECK: br ^[[BB1:.*]] +! CHECK: ^[[BB1]]: +! CHECK: br ^[[BB2:.*]] +! CHECK: ^[[BB2]]: +! CHECK: cond_br %{{.*}}, ^[[BB3:.*]], ^[[BB6:.*]] +! CHECK: ^[[BB3]]: +! CHECK: cond_br %{{.*}}, ^[[BB4:.*]], ^[[BB3:.*]] +! CHECK: ^[[BB4]]: +! CHECK: br ^[[BB6]] +! CHECK: ^[[BB3]]: +! CHECK: br ^[[BB2]] +! CHECK: ^[[BB6]]: +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } @@ -190,20 +202,23 @@ end ! CHECK: ^[[BB1_OUTER]]: ! CHECK: cond_br %{{.*}}, ^[[BB2_OUTER:.*]], ^[[BB3_OUTER:.*]] ! CHECK: ^[[BB2_OUTER]]: -! CHECK: omp.wsloop {{.*}} { -! CHECK: br ^[[BB1:.*]] -! CHECK: ^[[BB1]]: -! CHECK: br ^[[BB2:.*]] -! CHECK: ^[[BB2]]: -! CHECK: cond_br %{{.*}}, ^[[BB3:.*]], ^[[BB6:.*]] -! CHECK: ^[[BB3]]: -! CHECK: cond_br %{{.*}}, ^[[BB4:.*]], ^[[BB5:.*]] -! CHECK: ^[[BB4]]: -! CHECK: br ^[[BB6]] -! CHECK: ^[[BB5]] -! CHECK: br ^[[BB2]] -! CHECK: ^[[BB6]]: -! CHECK: omp.yield +! CHECK: omp.wsloop { +! CHECK: omp.loop_nest {{.*}} { +! CHECK: br ^[[BB1:.*]] +! CHECK: ^[[BB1]]: +! CHECK: br ^[[BB2:.*]] +! CHECK: ^[[BB2]]: +! CHECK: cond_br %{{.*}}, ^[[BB3:.*]], ^[[BB6:.*]] +! CHECK: ^[[BB3]]: +! CHECK: cond_br %{{.*}}, ^[[BB4:.*]], ^[[BB5:.*]] +! CHECK: ^[[BB4]]: +! CHECK: br ^[[BB6]] +! CHECK: ^[[BB5]] +! CHECK: br ^[[BB2]] +! CHECK: ^[[BB6]]: +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: br ^[[BB1_OUTER]] ! CHECK: ^[[BB3_OUTER]]: @@ -234,20 +249,23 @@ end ! CHECK: cond_br %{{.*}}, ^[[BB2_OUTER:.*]], ^[[BB3_OUTER:.*]] ! CHECK-NEXT: ^[[BB2_OUTER:.*]]: ! CHECK: omp.parallel { -! CHECK: omp.wsloop {{.*}} { -! CHECK: br ^[[BB1:.*]] -! CHECK-NEXT: ^[[BB1]]: -! CHECK: br ^[[BB2:.*]] -! CHECK-NEXT: ^[[BB2]]: -! CHECK: cond_br %{{.*}}, ^[[BB3:.*]], ^[[BB6:.*]] -! CHECK-NEXT: ^[[BB3]]: -! CHECK: cond_br %{{.*}}, ^[[BB4:.*]], ^[[BB5:.*]] -! CHECK-NEXT: ^[[BB4]]: -! CHECK: br ^[[BB6]] -! CHECK-NEXT: ^[[BB5]]: -! CHECK: br ^[[BB2]] -! CHECK-NEXT: ^[[BB6]]: -! CHECK: omp.yield +! CHECK: omp.wsloop { +! CHECK: omp.loop_nest {{.*}} { +! CHECK: br ^[[BB1:.*]] +! CHECK-NEXT: ^[[BB1]]: +! CHECK: br ^[[BB2:.*]] +! CHECK-NEXT: ^[[BB2]]: +! CHECK: cond_br %{{.*}}, ^[[BB3:.*]], ^[[BB6:.*]] +! CHECK-NEXT: ^[[BB3]]: +! CHECK: cond_br %{{.*}}, ^[[BB4:.*]], ^[[BB5:.*]] +! CHECK-NEXT: ^[[BB4]]: +! CHECK: br ^[[BB6]] +! CHECK-NEXT: ^[[BB5]]: +! CHECK: br ^[[BB2]] +! CHECK-NEXT: ^[[BB6]]: +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } @@ -272,20 +290,23 @@ end ! CHECK-LABEL: func @_QPss8() { ! CHECK: omp.parallel { -! CHECK: omp.wsloop {{.*}} { -! CHECK: br ^[[BB1:.*]] -! CHECK-NEXT: ^[[BB1]]: -! CHECK: br ^[[BB2:.*]] -! CHECK: ^[[BB2]]: -! CHECK: cond_br %{{.*}}, ^[[BB3:.*]], ^[[BB6:.*]] -! CHECK: ^[[BB3]]: -! CHECK: cond_br %{{.*}}, ^[[BB4:.*]], ^[[BB5:.*]] -! CHECK: ^[[BB4]]: -! CHECK-NEXT: br ^[[BB6]] -! CHECK: ^[[BB5]]: -! CHECK: br ^[[BB2]] -! CHECK-NEXT: ^[[BB6]]: -! CHECK: omp.yield +! CHECK: omp.wsloop { +! CHECK: omp.loop_nest {{.*}} { +! CHECK: br ^[[BB1:.*]] +! CHECK-NEXT: ^[[BB1]]: +! CHECK: br ^[[BB2:.*]] +! CHECK: ^[[BB2]]: +! CHECK: cond_br %{{.*}}, ^[[BB3:.*]], ^[[BB6:.*]] +! CHECK: ^[[BB3]]: +! CHECK: cond_br %{{.*}}, ^[[BB4:.*]], ^[[BB5:.*]] +! CHECK: ^[[BB4]]: +! CHECK-NEXT: br ^[[BB6]] +! CHECK: ^[[BB5]]: +! CHECK: br ^[[BB2]] +! CHECK-NEXT: ^[[BB6]]: +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } diff --git a/flang/test/Lower/OpenMP/use-device-ptr-to-use-device-addr.f90 b/flang/test/Lower/OpenMP/use-device-ptr-to-use-device-addr.f90 index d849dd206b94397d55f1a2163905df83feb8a5e6..90eede4f84108f951ea469709e753cbc1faedfa5 100644 --- a/flang/test/Lower/OpenMP/use-device-ptr-to-use-device-addr.f90 +++ b/flang/test/Lower/OpenMP/use-device-ptr-to-use-device-addr.f90 @@ -1,5 +1,6 @@ -!RUN: %flang_fc1 -emit-hlfir -fopenmp %s -o - | FileCheck %s -!RUN: bbc -emit-hlfir -fopenmp %s -o - | FileCheck %s +! The "use_device_addr" was added to the "target data" directive in OpenMP 5.0. +! RUN: %flang_fc1 -emit-hlfir -fopenmp -fopenmp-version=50 %s -o - | FileCheck %s +! RUN: bbc -emit-hlfir -fopenmp -fopenmp-version=50 %s -o - | FileCheck %s ! This tests primary goal is to check the promotion of ! non-CPTR arguments from use_device_ptr to diff --git a/flang/test/Lower/OpenMP/wsloop-chunks.f90 b/flang/test/Lower/OpenMP/wsloop-chunks.f90 index 5016c8985bda045973a2dd0c919bfac057fa3054..fa6ec219a490ebf54274c1eb3617de45ae3aa114 100644 --- a/flang/test/Lower/OpenMP/wsloop-chunks.f90 +++ b/flang/test/Lower/OpenMP/wsloop-chunks.f90 @@ -20,11 +20,14 @@ do i=1, 9 ! CHECK: %[[VAL_3:.*]] = arith.constant 9 : i32 ! CHECK: %[[VAL_4:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_5:.*]] = arith.constant 4 : i32 -! CHECK: omp.wsloop schedule(static = %[[VAL_5]] : i32) nowait for (%[[ARG0:.*]]) : i32 = (%[[VAL_2]]) to (%[[VAL_3]]) inclusive step (%[[VAL_4]]) { -! CHECK: fir.store %[[ARG0]] to %[[STORE_IV:.*]]#1 : !fir.ref -! CHECK: %[[LOAD_IV:.*]] = fir.load %[[STORE_IV]]#0 : !fir.ref -! CHECK: {{.*}} = fir.call @_FortranAioOutputInteger32({{.*}}, %[[LOAD_IV]]) {{.*}}: (!fir.ref, i32) -> i1 -! CHECK: omp.yield +! CHECK: omp.wsloop schedule(static = %[[VAL_5]] : i32) nowait { +! CHECK-NEXT: omp.loop_nest (%[[ARG0:.*]]) : i32 = (%[[VAL_2]]) to (%[[VAL_3]]) inclusive step (%[[VAL_4]]) { +! CHECK: fir.store %[[ARG0]] to %[[STORE_IV:.*]]#1 : !fir.ref +! CHECK: %[[LOAD_IV:.*]] = fir.load %[[STORE_IV]]#0 : !fir.ref +! CHECK: {{.*}} = fir.call @_FortranAioOutputInteger32({{.*}}, %[[LOAD_IV]]) {{.*}}: (!fir.ref, i32) -> i1 +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } end do @@ -38,13 +41,16 @@ do i=1, 9 ! CHECK: %[[VAL_15:.*]] = arith.constant 9 : i32 ! CHECK: %[[VAL_16:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_17:.*]] = arith.constant 4 : i32 -! CHECK: omp.wsloop schedule(static = %[[VAL_17]] : i32) nowait for (%[[ARG1:.*]]) : i32 = (%[[VAL_14]]) to (%[[VAL_15]]) inclusive step (%[[VAL_16]]) { -! CHECK: fir.store %[[ARG1]] to %[[STORE_IV1:.*]]#1 : !fir.ref -! CHECK: %[[VAL_24:.*]] = arith.constant 2 : i32 -! CHECK: %[[LOAD_IV1:.*]] = fir.load %[[STORE_IV1]]#0 : !fir.ref -! CHECK: %[[VAL_25:.*]] = arith.muli %[[VAL_24]], %[[LOAD_IV1]] : i32 -! CHECK: {{.*}} = fir.call @_FortranAioOutputInteger32({{.*}}, %[[VAL_25]]) {{.*}}: (!fir.ref, i32) -> i1 -! CHECK: omp.yield +! CHECK: omp.wsloop schedule(static = %[[VAL_17]] : i32) nowait { +! CHECK-NEXT: omp.loop_nest (%[[ARG1:.*]]) : i32 = (%[[VAL_14]]) to (%[[VAL_15]]) inclusive step (%[[VAL_16]]) { +! CHECK: fir.store %[[ARG1]] to %[[STORE_IV1:.*]]#1 : !fir.ref +! CHECK: %[[VAL_24:.*]] = arith.constant 2 : i32 +! CHECK: %[[LOAD_IV1:.*]] = fir.load %[[STORE_IV1]]#0 : !fir.ref +! CHECK: %[[VAL_25:.*]] = arith.muli %[[VAL_24]], %[[LOAD_IV1]] : i32 +! CHECK: {{.*}} = fir.call @_FortranAioOutputInteger32({{.*}}, %[[VAL_25]]) {{.*}}: (!fir.ref, i32) -> i1 +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } end do @@ -62,13 +68,16 @@ end do ! CHECK: %[[VAL_30:.*]] = arith.constant 9 : i32 ! CHECK: %[[VAL_31:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_32:.*]] = fir.load %[[VAL_0]]#0 : !fir.ref -! CHECK: omp.wsloop schedule(static = %[[VAL_32]] : i32) nowait for (%[[ARG2:.*]]) : i32 = (%[[VAL_29]]) to (%[[VAL_30]]) inclusive step (%[[VAL_31]]) { -! CHECK: fir.store %[[ARG2]] to %[[STORE_IV2:.*]]#1 : !fir.ref -! CHECK: %[[VAL_39:.*]] = arith.constant 3 : i32 -! CHECK: %[[LOAD_IV2:.*]] = fir.load %[[STORE_IV2]]#0 : !fir.ref -! CHECK: %[[VAL_40:.*]] = arith.muli %[[VAL_39]], %[[LOAD_IV2]] : i32 -! CHECK: {{.*}} = fir.call @_FortranAioOutputInteger32({{.*}}, %[[VAL_40]]) {{.*}}: (!fir.ref, i32) -> i1 -! CHECK: omp.yield +! CHECK: omp.wsloop schedule(static = %[[VAL_32]] : i32) nowait { +! CHECK-NEXT: omp.loop_nest (%[[ARG2:.*]]) : i32 = (%[[VAL_29]]) to (%[[VAL_30]]) inclusive step (%[[VAL_31]]) { +! CHECK: fir.store %[[ARG2]] to %[[STORE_IV2:.*]]#1 : !fir.ref +! CHECK: %[[VAL_39:.*]] = arith.constant 3 : i32 +! CHECK: %[[LOAD_IV2:.*]] = fir.load %[[STORE_IV2]]#0 : !fir.ref +! CHECK: %[[VAL_40:.*]] = arith.muli %[[VAL_39]], %[[LOAD_IV2]] : i32 +! CHECK: {{.*}} = fir.call @_FortranAioOutputInteger32({{.*}}, %[[VAL_40]]) {{.*}}: (!fir.ref, i32) -> i1 +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: return ! CHECK: } diff --git a/flang/test/Lower/OpenMP/wsloop-collapse.f90 b/flang/test/Lower/OpenMP/wsloop-collapse.f90 index c93fcf4ef968daaf9ee10ef66880c52b58704d2b..d9541e176f6a81acada33ea841ea74f8aae37343 100644 --- a/flang/test/Lower/OpenMP/wsloop-collapse.f90 +++ b/flang/test/Lower/OpenMP/wsloop-collapse.f90 @@ -49,23 +49,26 @@ program wsloop_collapse !CHECK: %[[VAL_30:.*]] = arith.constant 1 : i32 !CHECK: %[[VAL_31:.*]] = fir.load %[[VAL_11]]#0 : !fir.ref !CHECK: %[[VAL_32:.*]] = arith.constant 1 : i32 -!CHECK: omp.wsloop for (%[[VAL_33:.*]], %[[VAL_34:.*]], %[[VAL_35:.*]]) : i32 = (%[[VAL_24]], %[[VAL_27]], %[[VAL_30]]) to (%[[VAL_25]], %[[VAL_28]], %[[VAL_31]]) inclusive step (%[[VAL_26]], %[[VAL_29]], %[[VAL_32]]) { +!CHECK: omp.wsloop { +!CHECK-NEXT: omp.loop_nest (%[[VAL_33:.*]], %[[VAL_34:.*]], %[[VAL_35:.*]]) : i32 = (%[[VAL_24]], %[[VAL_27]], %[[VAL_30]]) to (%[[VAL_25]], %[[VAL_28]], %[[VAL_31]]) inclusive step (%[[VAL_26]], %[[VAL_29]], %[[VAL_32]]) { !$omp do collapse(3) do i = 1, a do j= 1, b do k = 1, c -!CHECK: fir.store %[[VAL_33]] to %[[VAL_5]]#1 : !fir.ref -!CHECK: fir.store %[[VAL_34]] to %[[VAL_3]]#1 : !fir.ref -!CHECK: fir.store %[[VAL_35]] to %[[VAL_1]]#1 : !fir.ref -!CHECK: %[[VAL_36:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref -!CHECK: %[[VAL_37:.*]] = fir.load %[[VAL_5]]#0 : !fir.ref -!CHECK: %[[VAL_38:.*]] = arith.addi %[[VAL_36]], %[[VAL_37]] : i32 -!CHECK: %[[VAL_39:.*]] = fir.load %[[VAL_3]]#0 : !fir.ref -!CHECK: %[[VAL_40:.*]] = arith.addi %[[VAL_38]], %[[VAL_39]] : i32 -!CHECK: %[[VAL_41:.*]] = fir.load %[[VAL_1]]#0 : !fir.ref -!CHECK: %[[VAL_42:.*]] = arith.addi %[[VAL_40]], %[[VAL_41]] : i32 -!CHECK: hlfir.assign %[[VAL_42]] to %[[VAL_19]]#0 : i32, !fir.ref -!CHECK: omp.yield +!CHECK: fir.store %[[VAL_33]] to %[[VAL_5]]#1 : !fir.ref +!CHECK: fir.store %[[VAL_34]] to %[[VAL_3]]#1 : !fir.ref +!CHECK: fir.store %[[VAL_35]] to %[[VAL_1]]#1 : !fir.ref +!CHECK: %[[VAL_36:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref +!CHECK: %[[VAL_37:.*]] = fir.load %[[VAL_5]]#0 : !fir.ref +!CHECK: %[[VAL_38:.*]] = arith.addi %[[VAL_36]], %[[VAL_37]] : i32 +!CHECK: %[[VAL_39:.*]] = fir.load %[[VAL_3]]#0 : !fir.ref +!CHECK: %[[VAL_40:.*]] = arith.addi %[[VAL_38]], %[[VAL_39]] : i32 +!CHECK: %[[VAL_41:.*]] = fir.load %[[VAL_1]]#0 : !fir.ref +!CHECK: %[[VAL_42:.*]] = arith.addi %[[VAL_40]], %[[VAL_41]] : i32 +!CHECK: hlfir.assign %[[VAL_42]] to %[[VAL_19]]#0 : i32, !fir.ref +!CHECK: omp.yield +!CHECK-NEXT: } +!CHECK-NEXT: omp.terminator x = x + i + j + k end do end do diff --git a/flang/test/Lower/OpenMP/wsloop-monotonic.f90 b/flang/test/Lower/OpenMP/wsloop-monotonic.f90 index fba9105b981813d889036837c2a305a21e01d829..531d995052f6c4711beb5422d3712bab2d07c722 100644 --- a/flang/test/Lower/OpenMP/wsloop-monotonic.f90 +++ b/flang/test/Lower/OpenMP/wsloop-monotonic.f90 @@ -15,19 +15,21 @@ program wsloop_dynamic !CHECK: %[[WS_LB:.*]] = arith.constant 1 : i32 !CHECK: %[[WS_UB:.*]] = arith.constant 9 : i32 !CHECK: %[[WS_STEP:.*]] = arith.constant 1 : i32 -!CHECK: omp.wsloop schedule(dynamic, monotonic) nowait for (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) -!CHECK: fir.store %[[I]] to %[[ALLOCA_IV:.*]]#1 : !fir.ref +!CHECK: omp.wsloop schedule(dynamic, monotonic) nowait { +!CHECK-NEXT: omp.loop_nest (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) { +!CHECK: fir.store %[[I]] to %[[ALLOCA_IV:.*]]#1 : !fir.ref do i=1, 9 print*, i -!CHECK: %[[RTBEGIN:.*]] = fir.call @_FortranAioBeginExternalListOutput -!CHECK: %[[LOAD:.*]] = fir.load %[[ALLOCA_IV]]#0 : !fir.ref -!CHECK: fir.call @_FortranAioOutputInteger32(%[[RTBEGIN]], %[[LOAD]]) {{.*}}: (!fir.ref, i32) -> i1 -!CHECK: fir.call @_FortranAioEndIoStatement(%[[RTBEGIN]]) {{.*}}: (!fir.ref) -> i32 +!CHECK: %[[RTBEGIN:.*]] = fir.call @_FortranAioBeginExternalListOutput +!CHECK: %[[LOAD:.*]] = fir.load %[[ALLOCA_IV]]#0 : !fir.ref +!CHECK: fir.call @_FortranAioOutputInteger32(%[[RTBEGIN]], %[[LOAD]]) {{.*}}: (!fir.ref, i32) -> i1 +!CHECK: fir.call @_FortranAioEndIoStatement(%[[RTBEGIN]]) {{.*}}: (!fir.ref) -> i32 end do -!CHECK: omp.yield +!CHECK: omp.yield !CHECK: omp.terminator -!CHECK: } +!CHECK: omp.terminator +!CHECK: } !$OMP END DO NOWAIT !$OMP END PARALLEL diff --git a/flang/test/Lower/OpenMP/wsloop-nonmonotonic.f90 b/flang/test/Lower/OpenMP/wsloop-nonmonotonic.f90 index 1bd7a2edc0f523396f5ce38f94bfc08357b3dfcf..420bc0bffaece3c62214124b0ab84983bc454e87 100644 --- a/flang/test/Lower/OpenMP/wsloop-nonmonotonic.f90 +++ b/flang/test/Lower/OpenMP/wsloop-nonmonotonic.f90 @@ -17,20 +17,23 @@ program wsloop_dynamic !CHECK: %[[WS_LB:.*]] = arith.constant 1 : i32 !CHECK: %[[WS_UB:.*]] = arith.constant 9 : i32 !CHECK: %[[WS_STEP:.*]] = arith.constant 1 : i32 -!CHECK: omp.wsloop schedule(dynamic, nonmonotonic) nowait for (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) -!CHECK: fir.store %[[I]] to %[[ALLOCA_IV]]#1 : !fir.ref +!CHECK: omp.wsloop schedule(dynamic, nonmonotonic) nowait { +!CHECK-NEXT: omp.loop_nest (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) { +!CHECK: fir.store %[[I]] to %[[ALLOCA_IV]]#1 : !fir.ref do i=1, 9 print*, i -!CHECK: %[[RTBEGIN:.*]] = fir.call @_FortranAioBeginExternalListOutput -!CHECK: %[[LOAD:.*]] = fir.load %[[ALLOCA_IV]]#0 : !fir.ref -!CHECK: fir.call @_FortranAioOutputInteger32(%[[RTBEGIN]], %[[LOAD]]) {{.*}}: (!fir.ref, i32) -> i1 -!CHECK: fir.call @_FortranAioEndIoStatement(%[[RTBEGIN]]) {{.*}}: (!fir.ref) -> i32 +!CHECK: %[[RTBEGIN:.*]] = fir.call @_FortranAioBeginExternalListOutput +!CHECK: %[[LOAD:.*]] = fir.load %[[ALLOCA_IV]]#0 : !fir.ref +!CHECK: fir.call @_FortranAioOutputInteger32(%[[RTBEGIN]], %[[LOAD]]) {{.*}}: (!fir.ref, i32) -> i1 +!CHECK: fir.call @_FortranAioEndIoStatement(%[[RTBEGIN]]) {{.*}}: (!fir.ref) -> i32 end do -!CHECK: omp.yield -!CHECK: } +!CHECK: omp.yield +!CHECK: } !CHECK: omp.terminator !CHECK: } +!CHECK: omp.terminator +!CHECK: } !$OMP END DO NOWAIT !$OMP END PARALLEL diff --git a/flang/test/Lower/OpenMP/wsloop-ordered.f90 b/flang/test/Lower/OpenMP/wsloop-ordered.f90 index 5185d2d085bac7ee1b1aca55a2a3ff76250b1db4..f4fa81c52315c8827f5545352313f131d18da79e 100644 --- a/flang/test/Lower/OpenMP/wsloop-ordered.f90 +++ b/flang/test/Lower/OpenMP/wsloop-ordered.f90 @@ -6,9 +6,12 @@ subroutine wsloop_ordered_no_para() integer :: a(10), i -! CHECK: omp.wsloop ordered(0) for (%{{.*}}) : i32 = (%{{.*}}) to (%{{.*}}) inclusive step (%{{.*}}) { -! CHECK: omp.yield -! CHECK: } +! CHECK: omp.wsloop ordered(0) { +! CHECK-NEXT: omp.loop_nest (%{{.*}}) : i32 = (%{{.*}}) to (%{{.*}}) inclusive step (%{{.*}}) { +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator +! CHECK: } !$omp do ordered do i = 2, 10 @@ -25,9 +28,12 @@ subroutine wsloop_ordered_with_para() integer :: a(10), i ! CHECK: func @_QPwsloop_ordered_with_para() { -! CHECK: omp.wsloop ordered(1) for (%{{.*}}) : i32 = (%{{.*}}) to (%{{.*}}) inclusive step (%{{.*}}) { -! CHECK: omp.yield -! CHECK: } +! CHECK: omp.wsloop ordered(1) { +! CHECK-NEXT: omp.loop_nest (%{{.*}}) : i32 = (%{{.*}}) to (%{{.*}}) inclusive step (%{{.*}}) { +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator +! CHECK: } !$omp do ordered(1) do i = 2, 10 diff --git a/flang/test/Lower/OpenMP/wsloop-reduction-add-byref.f90 b/flang/test/Lower/OpenMP/wsloop-reduction-add-byref.f90 index e63db33bbe2505530e8539f895cc74cc0f5e325b..c9d03435d9e18c7861dc1430714a9038716f3c2e 100644 --- a/flang/test/Lower/OpenMP/wsloop-reduction-add-byref.f90 +++ b/flang/test/Lower/OpenMP/wsloop-reduction-add-byref.f90 @@ -82,14 +82,17 @@ ! CHECK: %[[VAL_7:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_8:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_9:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@add_reduction_byref_i32 %[[VAL_3]]#0 -> %[[VAL_10:.*]] : !fir.ref) for (%[[VAL_11:.*]]) : i32 = (%[[VAL_7]]) to (%[[VAL_8]]) inclusive step (%[[VAL_9]]) { -! CHECK: fir.store %[[VAL_11]] to %[[VAL_6]]#1 : !fir.ref -! CHECK: %[[VAL_12:.*]]:2 = hlfir.declare %[[VAL_10]] {uniq_name = "_QFsimple_int_reductionEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_13:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref -! CHECK: %[[VAL_14:.*]] = fir.load %[[VAL_6]]#0 : !fir.ref -! CHECK: %[[VAL_15:.*]] = arith.addi %[[VAL_13]], %[[VAL_14]] : i32 -! CHECK: hlfir.assign %[[VAL_15]] to %[[VAL_12]]#0 : i32, !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@add_reduction_byref_i32 %[[VAL_3]]#0 -> %[[VAL_10:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_11:.*]]) : i32 = (%[[VAL_7]]) to (%[[VAL_8]]) inclusive step (%[[VAL_9]]) { +! CHECK: %[[VAL_12:.*]]:2 = hlfir.declare %[[VAL_10]] {uniq_name = "_QFsimple_int_reductionEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: fir.store %[[VAL_11]] to %[[VAL_6]]#1 : !fir.ref +! CHECK: %[[VAL_13:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref +! CHECK: %[[VAL_14:.*]] = fir.load %[[VAL_6]]#0 : !fir.ref +! CHECK: %[[VAL_15:.*]] = arith.addi %[[VAL_13]], %[[VAL_14]] : i32 +! CHECK: hlfir.assign %[[VAL_15]] to %[[VAL_12]]#0 : i32, !fir.ref +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } @@ -122,15 +125,18 @@ end subroutine ! CHECK: %[[VAL_7:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_8:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_9:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@add_reduction_byref_f32 %[[VAL_3]]#0 -> %[[VAL_10:.*]] : !fir.ref) for (%[[VAL_11:.*]]) : i32 = (%[[VAL_7]]) to (%[[VAL_8]]) inclusive step (%[[VAL_9]]) { -! CHECK: fir.store %[[VAL_11]] to %[[VAL_6]]#1 : !fir.ref -! CHECK: %[[VAL_12:.*]]:2 = hlfir.declare %[[VAL_10]] {uniq_name = "_QFsimple_real_reductionEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_13:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref -! CHECK: %[[VAL_14:.*]] = fir.load %[[VAL_6]]#0 : !fir.ref -! CHECK: %[[VAL_15:.*]] = fir.convert %[[VAL_14]] : (i32) -> f32 -! CHECK: %[[VAL_16:.*]] = arith.addf %[[VAL_13]], %[[VAL_15]] fastmath : f32 -! CHECK: hlfir.assign %[[VAL_16]] to %[[VAL_12]]#0 : f32, !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@add_reduction_byref_f32 %[[VAL_3]]#0 -> %[[VAL_10:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_11:.*]]) : i32 = (%[[VAL_7]]) to (%[[VAL_8]]) inclusive step (%[[VAL_9]]) { +! CHECK: %[[VAL_12:.*]]:2 = hlfir.declare %[[VAL_10]] {uniq_name = "_QFsimple_real_reductionEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: fir.store %[[VAL_11]] to %[[VAL_6]]#1 : !fir.ref +! CHECK: %[[VAL_13:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref +! CHECK: %[[VAL_14:.*]] = fir.load %[[VAL_6]]#0 : !fir.ref +! CHECK: %[[VAL_15:.*]] = fir.convert %[[VAL_14]] : (i32) -> f32 +! CHECK: %[[VAL_16:.*]] = arith.addf %[[VAL_13]], %[[VAL_15]] fastmath : f32 +! CHECK: hlfir.assign %[[VAL_16]] to %[[VAL_12]]#0 : f32, !fir.ref +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } @@ -163,14 +169,17 @@ end subroutine ! CHECK: %[[VAL_7:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_8:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_9:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@add_reduction_byref_i32 %[[VAL_3]]#0 -> %[[VAL_10:.*]] : !fir.ref) for (%[[VAL_11:.*]]) : i32 = (%[[VAL_7]]) to (%[[VAL_8]]) inclusive step (%[[VAL_9]]) { -! CHECK: fir.store %[[VAL_11]] to %[[VAL_6]]#1 : !fir.ref -! CHECK: %[[VAL_12:.*]]:2 = hlfir.declare %[[VAL_10]] {uniq_name = "_QFsimple_int_reduction_switch_orderEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_13:.*]] = fir.load %[[VAL_6]]#0 : !fir.ref -! CHECK: %[[VAL_14:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref -! CHECK: %[[VAL_15:.*]] = arith.addi %[[VAL_13]], %[[VAL_14]] : i32 -! CHECK: hlfir.assign %[[VAL_15]] to %[[VAL_12]]#0 : i32, !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@add_reduction_byref_i32 %[[VAL_3]]#0 -> %[[VAL_10:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_11:.*]]) : i32 = (%[[VAL_7]]) to (%[[VAL_8]]) inclusive step (%[[VAL_9]]) { +! CHECK: %[[VAL_12:.*]]:2 = hlfir.declare %[[VAL_10]] {uniq_name = "_QFsimple_int_reduction_switch_orderEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: fir.store %[[VAL_11]] to %[[VAL_6]]#1 : !fir.ref +! CHECK: %[[VAL_13:.*]] = fir.load %[[VAL_6]]#0 : !fir.ref +! CHECK: %[[VAL_14:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref +! CHECK: %[[VAL_15:.*]] = arith.addi %[[VAL_13]], %[[VAL_14]] : i32 +! CHECK: hlfir.assign %[[VAL_15]] to %[[VAL_12]]#0 : i32, !fir.ref +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } @@ -202,15 +211,18 @@ end subroutine ! CHECK: %[[VAL_7:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_8:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_9:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@add_reduction_byref_f32 %[[VAL_3]]#0 -> %[[VAL_10:.*]] : !fir.ref) for (%[[VAL_11:.*]]) : i32 = (%[[VAL_7]]) to (%[[VAL_8]]) inclusive step (%[[VAL_9]]) { -! CHECK: fir.store %[[VAL_11]] to %[[VAL_6]]#1 : !fir.ref -! CHECK: %[[VAL_12:.*]]:2 = hlfir.declare %[[VAL_10]] {uniq_name = "_QFsimple_real_reduction_switch_orderEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_13:.*]] = fir.load %[[VAL_6]]#0 : !fir.ref -! CHECK: %[[VAL_14:.*]] = fir.convert %[[VAL_13]] : (i32) -> f32 -! CHECK: %[[VAL_15:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref -! CHECK: %[[VAL_16:.*]] = arith.addf %[[VAL_14]], %[[VAL_15]] fastmath : f32 -! CHECK: hlfir.assign %[[VAL_16]] to %[[VAL_12]]#0 : f32, !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@add_reduction_byref_f32 %[[VAL_3]]#0 -> %[[VAL_10:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_11:.*]]) : i32 = (%[[VAL_7]]) to (%[[VAL_8]]) inclusive step (%[[VAL_9]]) { +! CHECK: %[[VAL_12:.*]]:2 = hlfir.declare %[[VAL_10]] {uniq_name = "_QFsimple_real_reduction_switch_orderEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: fir.store %[[VAL_11]] to %[[VAL_6]]#1 : !fir.ref +! CHECK: %[[VAL_13:.*]] = fir.load %[[VAL_6]]#0 : !fir.ref +! CHECK: %[[VAL_14:.*]] = fir.convert %[[VAL_13]] : (i32) -> f32 +! CHECK: %[[VAL_15:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref +! CHECK: %[[VAL_16:.*]] = arith.addf %[[VAL_14]], %[[VAL_15]] fastmath : f32 +! CHECK: hlfir.assign %[[VAL_16]] to %[[VAL_12]]#0 : f32, !fir.ref +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } @@ -250,24 +262,27 @@ end subroutine ! CHECK: %[[VAL_13:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_14:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_15:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@add_reduction_byref_i32 %[[VAL_3]]#0 -> %[[VAL_16:.*]] : !fir.ref, @add_reduction_byref_i32 %[[VAL_5]]#0 -> %[[VAL_17:.*]] : !fir.ref, @add_reduction_byref_i32 %[[VAL_7]]#0 -> %[[VAL_18:.*]] : !fir.ref) for (%[[VAL_19:.*]]) : i32 = (%[[VAL_13]]) to (%[[VAL_14]]) inclusive step (%[[VAL_15]]) { -! CHECK: fir.store %[[VAL_19]] to %[[VAL_12]]#1 : !fir.ref -! CHECK: %[[VAL_20:.*]]:2 = hlfir.declare %[[VAL_16]] {uniq_name = "_QFmultiple_int_reductions_same_typeEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_21:.*]]:2 = hlfir.declare %[[VAL_17]] {uniq_name = "_QFmultiple_int_reductions_same_typeEy"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_22:.*]]:2 = hlfir.declare %[[VAL_18]] {uniq_name = "_QFmultiple_int_reductions_same_typeEz"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_23:.*]] = fir.load %[[VAL_20]]#0 : !fir.ref -! CHECK: %[[VAL_24:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref -! CHECK: %[[VAL_25:.*]] = arith.addi %[[VAL_23]], %[[VAL_24]] : i32 -! CHECK: hlfir.assign %[[VAL_25]] to %[[VAL_20]]#0 : i32, !fir.ref -! CHECK: %[[VAL_26:.*]] = fir.load %[[VAL_21]]#0 : !fir.ref -! CHECK: %[[VAL_27:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref -! CHECK: %[[VAL_28:.*]] = arith.addi %[[VAL_26]], %[[VAL_27]] : i32 -! CHECK: hlfir.assign %[[VAL_28]] to %[[VAL_21]]#0 : i32, !fir.ref -! CHECK: %[[VAL_29:.*]] = fir.load %[[VAL_22]]#0 : !fir.ref -! CHECK: %[[VAL_30:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref -! CHECK: %[[VAL_31:.*]] = arith.addi %[[VAL_29]], %[[VAL_30]] : i32 -! CHECK: hlfir.assign %[[VAL_31]] to %[[VAL_22]]#0 : i32, !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@add_reduction_byref_i32 %[[VAL_3]]#0 -> %[[VAL_16:.*]] : !fir.ref, @add_reduction_byref_i32 %[[VAL_5]]#0 -> %[[VAL_17:.*]] : !fir.ref, @add_reduction_byref_i32 %[[VAL_7]]#0 -> %[[VAL_18:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_19:.*]]) : i32 = (%[[VAL_13]]) to (%[[VAL_14]]) inclusive step (%[[VAL_15]]) { +! CHECK: %[[VAL_20:.*]]:2 = hlfir.declare %[[VAL_16]] {uniq_name = "_QFmultiple_int_reductions_same_typeEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: %[[VAL_21:.*]]:2 = hlfir.declare %[[VAL_17]] {uniq_name = "_QFmultiple_int_reductions_same_typeEy"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: %[[VAL_22:.*]]:2 = hlfir.declare %[[VAL_18]] {uniq_name = "_QFmultiple_int_reductions_same_typeEz"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: fir.store %[[VAL_19]] to %[[VAL_12]]#1 : !fir.ref +! CHECK: %[[VAL_23:.*]] = fir.load %[[VAL_20]]#0 : !fir.ref +! CHECK: %[[VAL_24:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref +! CHECK: %[[VAL_25:.*]] = arith.addi %[[VAL_23]], %[[VAL_24]] : i32 +! CHECK: hlfir.assign %[[VAL_25]] to %[[VAL_20]]#0 : i32, !fir.ref +! CHECK: %[[VAL_26:.*]] = fir.load %[[VAL_21]]#0 : !fir.ref +! CHECK: %[[VAL_27:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref +! CHECK: %[[VAL_28:.*]] = arith.addi %[[VAL_26]], %[[VAL_27]] : i32 +! CHECK: hlfir.assign %[[VAL_28]] to %[[VAL_21]]#0 : i32, !fir.ref +! CHECK: %[[VAL_29:.*]] = fir.load %[[VAL_22]]#0 : !fir.ref +! CHECK: %[[VAL_30:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref +! CHECK: %[[VAL_31:.*]] = arith.addi %[[VAL_29]], %[[VAL_30]] : i32 +! CHECK: hlfir.assign %[[VAL_31]] to %[[VAL_22]]#0 : i32, !fir.ref +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } @@ -311,27 +326,30 @@ end subroutine ! CHECK: %[[VAL_13:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_14:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_15:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@add_reduction_byref_f32 %[[VAL_3]]#0 -> %[[VAL_16:.*]] : !fir.ref, @add_reduction_byref_f32 %[[VAL_5]]#0 -> %[[VAL_17:.*]] : !fir.ref, @add_reduction_byref_f32 %[[VAL_7]]#0 -> %[[VAL_18:.*]] : !fir.ref) for (%[[VAL_19:.*]]) : i32 = (%[[VAL_13]]) to (%[[VAL_14]]) inclusive step (%[[VAL_15]]) { -! CHECK: fir.store %[[VAL_19]] to %[[VAL_12]]#1 : !fir.ref -! CHECK: %[[VAL_20:.*]]:2 = hlfir.declare %[[VAL_16]] {uniq_name = "_QFmultiple_real_reductions_same_typeEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_21:.*]]:2 = hlfir.declare %[[VAL_17]] {uniq_name = "_QFmultiple_real_reductions_same_typeEy"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_22:.*]]:2 = hlfir.declare %[[VAL_18]] {uniq_name = "_QFmultiple_real_reductions_same_typeEz"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_23:.*]] = fir.load %[[VAL_20]]#0 : !fir.ref -! CHECK: %[[VAL_24:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref -! CHECK: %[[VAL_25:.*]] = fir.convert %[[VAL_24]] : (i32) -> f32 -! CHECK: %[[VAL_26:.*]] = arith.addf %[[VAL_23]], %[[VAL_25]] fastmath : f32 -! CHECK: hlfir.assign %[[VAL_26]] to %[[VAL_20]]#0 : f32, !fir.ref -! CHECK: %[[VAL_27:.*]] = fir.load %[[VAL_21]]#0 : !fir.ref -! CHECK: %[[VAL_28:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref -! CHECK: %[[VAL_29:.*]] = fir.convert %[[VAL_28]] : (i32) -> f32 -! CHECK: %[[VAL_30:.*]] = arith.addf %[[VAL_27]], %[[VAL_29]] fastmath : f32 -! CHECK: hlfir.assign %[[VAL_30]] to %[[VAL_21]]#0 : f32, !fir.ref -! CHECK: %[[VAL_31:.*]] = fir.load %[[VAL_22]]#0 : !fir.ref -! CHECK: %[[VAL_32:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref -! CHECK: %[[VAL_33:.*]] = fir.convert %[[VAL_32]] : (i32) -> f32 -! CHECK: %[[VAL_34:.*]] = arith.addf %[[VAL_31]], %[[VAL_33]] fastmath : f32 -! CHECK: hlfir.assign %[[VAL_34]] to %[[VAL_22]]#0 : f32, !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@add_reduction_byref_f32 %[[VAL_3]]#0 -> %[[VAL_16:.*]] : !fir.ref, @add_reduction_byref_f32 %[[VAL_5]]#0 -> %[[VAL_17:.*]] : !fir.ref, @add_reduction_byref_f32 %[[VAL_7]]#0 -> %[[VAL_18:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_19:.*]]) : i32 = (%[[VAL_13]]) to (%[[VAL_14]]) inclusive step (%[[VAL_15]]) { +! CHECK: %[[VAL_20:.*]]:2 = hlfir.declare %[[VAL_16]] {uniq_name = "_QFmultiple_real_reductions_same_typeEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: %[[VAL_21:.*]]:2 = hlfir.declare %[[VAL_17]] {uniq_name = "_QFmultiple_real_reductions_same_typeEy"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: %[[VAL_22:.*]]:2 = hlfir.declare %[[VAL_18]] {uniq_name = "_QFmultiple_real_reductions_same_typeEz"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: fir.store %[[VAL_19]] to %[[VAL_12]]#1 : !fir.ref +! CHECK: %[[VAL_23:.*]] = fir.load %[[VAL_20]]#0 : !fir.ref +! CHECK: %[[VAL_24:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref +! CHECK: %[[VAL_25:.*]] = fir.convert %[[VAL_24]] : (i32) -> f32 +! CHECK: %[[VAL_26:.*]] = arith.addf %[[VAL_23]], %[[VAL_25]] fastmath : f32 +! CHECK: hlfir.assign %[[VAL_26]] to %[[VAL_20]]#0 : f32, !fir.ref +! CHECK: %[[VAL_27:.*]] = fir.load %[[VAL_21]]#0 : !fir.ref +! CHECK: %[[VAL_28:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref +! CHECK: %[[VAL_29:.*]] = fir.convert %[[VAL_28]] : (i32) -> f32 +! CHECK: %[[VAL_30:.*]] = arith.addf %[[VAL_27]], %[[VAL_29]] fastmath : f32 +! CHECK: hlfir.assign %[[VAL_30]] to %[[VAL_21]]#0 : f32, !fir.ref +! CHECK: %[[VAL_31:.*]] = fir.load %[[VAL_22]]#0 : !fir.ref +! CHECK: %[[VAL_32:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref +! CHECK: %[[VAL_33:.*]] = fir.convert %[[VAL_32]] : (i32) -> f32 +! CHECK: %[[VAL_34:.*]] = arith.addf %[[VAL_31]], %[[VAL_33]] fastmath : f32 +! CHECK: hlfir.assign %[[VAL_34]] to %[[VAL_22]]#0 : f32, !fir.ref +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } @@ -379,32 +397,35 @@ end subroutine ! CHECK: %[[VAL_16:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_17:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_18:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@add_reduction_byref_i32 %[[VAL_5]]#0 -> %[[VAL_19:.*]] : !fir.ref, @add_reduction_byref_i64 %[[VAL_7]]#0 -> %[[VAL_20:.*]] : !fir.ref, @add_reduction_byref_f32 %[[VAL_9]]#0 -> %[[VAL_21:.*]] : !fir.ref, @add_reduction_byref_f64 %[[VAL_3]]#0 -> %[[VAL_22:.*]] : !fir.ref) for (%[[VAL_23:.*]]) : i32 = (%[[VAL_16]]) to (%[[VAL_17]]) inclusive step (%[[VAL_18]]) { -! CHECK: fir.store %[[VAL_23]] to %[[VAL_15]]#1 : !fir.ref -! CHECK: %[[VAL_24:.*]]:2 = hlfir.declare %[[VAL_19]] {uniq_name = "_QFmultiple_reductions_different_typeEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_25:.*]]:2 = hlfir.declare %[[VAL_20]] {uniq_name = "_QFmultiple_reductions_different_typeEy"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_26:.*]]:2 = hlfir.declare %[[VAL_21]] {uniq_name = "_QFmultiple_reductions_different_typeEz"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_27:.*]]:2 = hlfir.declare %[[VAL_22]] {uniq_name = "_QFmultiple_reductions_different_typeEw"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_28:.*]] = fir.load %[[VAL_24]]#0 : !fir.ref -! CHECK: %[[VAL_29:.*]] = fir.load %[[VAL_15]]#0 : !fir.ref -! CHECK: %[[VAL_30:.*]] = arith.addi %[[VAL_28]], %[[VAL_29]] : i32 -! CHECK: hlfir.assign %[[VAL_30]] to %[[VAL_24]]#0 : i32, !fir.ref -! CHECK: %[[VAL_31:.*]] = fir.load %[[VAL_25]]#0 : !fir.ref -! CHECK: %[[VAL_32:.*]] = fir.load %[[VAL_15]]#0 : !fir.ref -! CHECK: %[[VAL_33:.*]] = fir.convert %[[VAL_32]] : (i32) -> i64 -! CHECK: %[[VAL_34:.*]] = arith.addi %[[VAL_31]], %[[VAL_33]] : i64 -! CHECK: hlfir.assign %[[VAL_34]] to %[[VAL_25]]#0 : i64, !fir.ref -! CHECK: %[[VAL_35:.*]] = fir.load %[[VAL_26]]#0 : !fir.ref -! CHECK: %[[VAL_36:.*]] = fir.load %[[VAL_15]]#0 : !fir.ref -! CHECK: %[[VAL_37:.*]] = fir.convert %[[VAL_36]] : (i32) -> f32 -! CHECK: %[[VAL_38:.*]] = arith.addf %[[VAL_35]], %[[VAL_37]] fastmath : f32 -! CHECK: hlfir.assign %[[VAL_38]] to %[[VAL_26]]#0 : f32, !fir.ref -! CHECK: %[[VAL_39:.*]] = fir.load %[[VAL_27]]#0 : !fir.ref -! CHECK: %[[VAL_40:.*]] = fir.load %[[VAL_15]]#0 : !fir.ref -! CHECK: %[[VAL_41:.*]] = fir.convert %[[VAL_40]] : (i32) -> f64 -! CHECK: %[[VAL_42:.*]] = arith.addf %[[VAL_39]], %[[VAL_41]] fastmath : f64 -! CHECK: hlfir.assign %[[VAL_42]] to %[[VAL_27]]#0 : f64, !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@add_reduction_byref_i32 %[[VAL_5]]#0 -> %[[VAL_19:.*]] : !fir.ref, @add_reduction_byref_i64 %[[VAL_7]]#0 -> %[[VAL_20:.*]] : !fir.ref, @add_reduction_byref_f32 %[[VAL_9]]#0 -> %[[VAL_21:.*]] : !fir.ref, @add_reduction_byref_f64 %[[VAL_3]]#0 -> %[[VAL_22:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_23:.*]]) : i32 = (%[[VAL_16]]) to (%[[VAL_17]]) inclusive step (%[[VAL_18]]) { +! CHECK: %[[VAL_24:.*]]:2 = hlfir.declare %[[VAL_19]] {uniq_name = "_QFmultiple_reductions_different_typeEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: %[[VAL_25:.*]]:2 = hlfir.declare %[[VAL_20]] {uniq_name = "_QFmultiple_reductions_different_typeEy"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: %[[VAL_26:.*]]:2 = hlfir.declare %[[VAL_21]] {uniq_name = "_QFmultiple_reductions_different_typeEz"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: %[[VAL_27:.*]]:2 = hlfir.declare %[[VAL_22]] {uniq_name = "_QFmultiple_reductions_different_typeEw"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: fir.store %[[VAL_23]] to %[[VAL_15]]#1 : !fir.ref +! CHECK: %[[VAL_28:.*]] = fir.load %[[VAL_24]]#0 : !fir.ref +! CHECK: %[[VAL_29:.*]] = fir.load %[[VAL_15]]#0 : !fir.ref +! CHECK: %[[VAL_30:.*]] = arith.addi %[[VAL_28]], %[[VAL_29]] : i32 +! CHECK: hlfir.assign %[[VAL_30]] to %[[VAL_24]]#0 : i32, !fir.ref +! CHECK: %[[VAL_31:.*]] = fir.load %[[VAL_25]]#0 : !fir.ref +! CHECK: %[[VAL_32:.*]] = fir.load %[[VAL_15]]#0 : !fir.ref +! CHECK: %[[VAL_33:.*]] = fir.convert %[[VAL_32]] : (i32) -> i64 +! CHECK: %[[VAL_34:.*]] = arith.addi %[[VAL_31]], %[[VAL_33]] : i64 +! CHECK: hlfir.assign %[[VAL_34]] to %[[VAL_25]]#0 : i64, !fir.ref +! CHECK: %[[VAL_35:.*]] = fir.load %[[VAL_26]]#0 : !fir.ref +! CHECK: %[[VAL_36:.*]] = fir.load %[[VAL_15]]#0 : !fir.ref +! CHECK: %[[VAL_37:.*]] = fir.convert %[[VAL_36]] : (i32) -> f32 +! CHECK: %[[VAL_38:.*]] = arith.addf %[[VAL_35]], %[[VAL_37]] fastmath : f32 +! CHECK: hlfir.assign %[[VAL_38]] to %[[VAL_26]]#0 : f32, !fir.ref +! CHECK: %[[VAL_39:.*]] = fir.load %[[VAL_27]]#0 : !fir.ref +! CHECK: %[[VAL_40:.*]] = fir.load %[[VAL_15]]#0 : !fir.ref +! CHECK: %[[VAL_41:.*]] = fir.convert %[[VAL_40]] : (i32) -> f64 +! CHECK: %[[VAL_42:.*]] = arith.addf %[[VAL_39]], %[[VAL_41]] fastmath : f64 +! CHECK: hlfir.assign %[[VAL_42]] to %[[VAL_27]]#0 : f64, !fir.ref +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } diff --git a/flang/test/Lower/OpenMP/wsloop-reduction-add-hlfir-byref.f90 b/flang/test/Lower/OpenMP/wsloop-reduction-add-hlfir-byref.f90 index 3b4d9666c693733a9d4b8ea7cf5c8063678607ab..6a09fece80ae9d5d2d776871cdd3621eaeca997e 100644 --- a/flang/test/Lower/OpenMP/wsloop-reduction-add-hlfir-byref.f90 +++ b/flang/test/Lower/OpenMP/wsloop-reduction-add-hlfir-byref.f90 @@ -31,14 +31,16 @@ ! CHECK: %[[VAL_7:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_8:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_9:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@add_reduction_byref_i32 %[[VAL_3]]#0 -> %[[VAL_10:.*]] : !fir.ref) for (%[[VAL_11:.*]]) : i32 = (%[[VAL_7]]) to (%[[VAL_8]]) inclusive step (%[[VAL_9]]) -! CHECK: fir.store %[[VAL_11]] to %[[VAL_6]]#1 : !fir.ref -! CHECK: %[[VAL_12:.*]]:2 = hlfir.declare %[[VAL_10]] {uniq_name = "_QFsimple_int_reductionEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_13:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref -! CHECK: %[[VAL_14:.*]] = fir.load %[[VAL_6]]#0 : !fir.ref -! CHECK: %[[VAL_15:.*]] = arith.addi %[[VAL_13]], %[[VAL_14]] : i32 -! CHECK: hlfir.assign %[[VAL_15]] to %[[VAL_12]]#0 : i32, !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@add_reduction_byref_i32 %[[VAL_3]]#0 -> %[[VAL_10:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_11:.*]]) : i32 = (%[[VAL_7]]) to (%[[VAL_8]]) inclusive step (%[[VAL_9]]) { +! CHECK: %[[VAL_12:.*]]:2 = hlfir.declare %[[VAL_10]] {uniq_name = "_QFsimple_int_reductionEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: fir.store %[[VAL_11]] to %[[VAL_6]]#1 : !fir.ref +! CHECK: %[[VAL_13:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref +! CHECK: %[[VAL_14:.*]] = fir.load %[[VAL_6]]#0 : !fir.ref +! CHECK: %[[VAL_15:.*]] = arith.addi %[[VAL_13]], %[[VAL_14]] : i32 +! CHECK: hlfir.assign %[[VAL_15]] to %[[VAL_12]]#0 : i32, !fir.ref +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return diff --git a/flang/test/Lower/OpenMP/wsloop-reduction-add-hlfir.f90 b/flang/test/Lower/OpenMP/wsloop-reduction-add-hlfir.f90 index 7c9070592e468e1e3d14c35110b8b0ee95c17caf..c5cc5a95cef177d76b4aea0219ccee3ef3177577 100644 --- a/flang/test/Lower/OpenMP/wsloop-reduction-add-hlfir.f90 +++ b/flang/test/Lower/OpenMP/wsloop-reduction-add-hlfir.f90 @@ -27,14 +27,16 @@ ! CHECK: %[[VAL_7:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_8:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_9:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@add_reduction_i32 %[[VAL_3]]#0 -> %[[VAL_10:.*]] : !fir.ref) for (%[[VAL_11:.*]]) : i32 = (%[[VAL_7]]) to (%[[VAL_8]]) inclusive step (%[[VAL_9]]) -! CHECK: fir.store %[[VAL_11]] to %[[VAL_6]]#1 : !fir.ref -! CHECK: %[[VAL_12:.*]]:2 = hlfir.declare %[[VAL_10]] {uniq_name = "_QFsimple_int_reductionEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_13:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref -! CHECK: %[[VAL_14:.*]] = fir.load %[[VAL_6]]#0 : !fir.ref -! CHECK: %[[VAL_15:.*]] = arith.addi %[[VAL_13]], %[[VAL_14]] : i32 -! CHECK: hlfir.assign %[[VAL_15]] to %[[VAL_12]]#0 : i32, !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop reduction(@add_reduction_i32 %[[VAL_3]]#0 -> %[[VAL_10:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_11:.*]]) : i32 = (%[[VAL_7]]) to (%[[VAL_8]]) inclusive step (%[[VAL_9]]) { +! CHECK: %[[VAL_12:.*]]:2 = hlfir.declare %[[VAL_10]] {uniq_name = "_QFsimple_int_reductionEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: fir.store %[[VAL_11]] to %[[VAL_6]]#1 : !fir.ref +! CHECK: %[[VAL_13:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref +! CHECK: %[[VAL_14:.*]] = fir.load %[[VAL_6]]#0 : !fir.ref +! CHECK: %[[VAL_15:.*]] = arith.addi %[[VAL_13]], %[[VAL_14]] : i32 +! CHECK: hlfir.assign %[[VAL_15]] to %[[VAL_12]]#0 : i32, !fir.ref +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return diff --git a/flang/test/Lower/OpenMP/wsloop-reduction-add.f90 b/flang/test/Lower/OpenMP/wsloop-reduction-add.f90 index 11e1ffb79f8e4ee4d45b1bdf22bdf9696216cc7f..5b957959f40d50d44914be42543af1555703d077 100644 --- a/flang/test/Lower/OpenMP/wsloop-reduction-add.f90 +++ b/flang/test/Lower/OpenMP/wsloop-reduction-add.f90 @@ -58,14 +58,17 @@ ! CHECK: %[[VAL_7:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_8:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_9:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@add_reduction_i32 %[[VAL_3]]#0 -> %[[VAL_10:.*]] : !fir.ref) for (%[[VAL_11:.*]]) : i32 = (%[[VAL_7]]) to (%[[VAL_8]]) inclusive step (%[[VAL_9]]) { -! CHECK: fir.store %[[VAL_11]] to %[[VAL_6]]#1 : !fir.ref -! CHECK: %[[VAL_12:.*]]:2 = hlfir.declare %[[VAL_10]] {uniq_name = "_QFsimple_int_reductionEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_13:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref -! CHECK: %[[VAL_14:.*]] = fir.load %[[VAL_6]]#0 : !fir.ref -! CHECK: %[[VAL_15:.*]] = arith.addi %[[VAL_13]], %[[VAL_14]] : i32 -! CHECK: hlfir.assign %[[VAL_15]] to %[[VAL_12]]#0 : i32, !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop reduction(@add_reduction_i32 %[[VAL_3]]#0 -> %[[VAL_10:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_11:.*]]) : i32 = (%[[VAL_7]]) to (%[[VAL_8]]) inclusive step (%[[VAL_9]]) { +! CHECK: %[[VAL_12:.*]]:2 = hlfir.declare %[[VAL_10]] {uniq_name = "_QFsimple_int_reductionEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: fir.store %[[VAL_11]] to %[[VAL_6]]#1 : !fir.ref +! CHECK: %[[VAL_13:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref +! CHECK: %[[VAL_14:.*]] = fir.load %[[VAL_6]]#0 : !fir.ref +! CHECK: %[[VAL_15:.*]] = arith.addi %[[VAL_13]], %[[VAL_14]] : i32 +! CHECK: hlfir.assign %[[VAL_15]] to %[[VAL_12]]#0 : i32, !fir.ref +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } @@ -98,15 +101,18 @@ end subroutine ! CHECK: %[[VAL_7:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_8:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_9:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@add_reduction_f32 %[[VAL_3]]#0 -> %[[VAL_10:.*]] : !fir.ref) for (%[[VAL_11:.*]]) : i32 = (%[[VAL_7]]) to (%[[VAL_8]]) inclusive step (%[[VAL_9]]) { -! CHECK: fir.store %[[VAL_11]] to %[[VAL_6]]#1 : !fir.ref -! CHECK: %[[VAL_12:.*]]:2 = hlfir.declare %[[VAL_10]] {uniq_name = "_QFsimple_real_reductionEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_13:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref -! CHECK: %[[VAL_14:.*]] = fir.load %[[VAL_6]]#0 : !fir.ref -! CHECK: %[[VAL_15:.*]] = fir.convert %[[VAL_14]] : (i32) -> f32 -! CHECK: %[[VAL_16:.*]] = arith.addf %[[VAL_13]], %[[VAL_15]] fastmath : f32 -! CHECK: hlfir.assign %[[VAL_16]] to %[[VAL_12]]#0 : f32, !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop reduction(@add_reduction_f32 %[[VAL_3]]#0 -> %[[VAL_10:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_11:.*]]) : i32 = (%[[VAL_7]]) to (%[[VAL_8]]) inclusive step (%[[VAL_9]]) { +! CHECK: %[[VAL_12:.*]]:2 = hlfir.declare %[[VAL_10]] {uniq_name = "_QFsimple_real_reductionEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: fir.store %[[VAL_11]] to %[[VAL_6]]#1 : !fir.ref +! CHECK: %[[VAL_13:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref +! CHECK: %[[VAL_14:.*]] = fir.load %[[VAL_6]]#0 : !fir.ref +! CHECK: %[[VAL_15:.*]] = fir.convert %[[VAL_14]] : (i32) -> f32 +! CHECK: %[[VAL_16:.*]] = arith.addf %[[VAL_13]], %[[VAL_15]] fastmath : f32 +! CHECK: hlfir.assign %[[VAL_16]] to %[[VAL_12]]#0 : f32, !fir.ref +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } @@ -139,14 +145,17 @@ end subroutine ! CHECK: %[[VAL_7:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_8:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_9:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@add_reduction_i32 %[[VAL_3]]#0 -> %[[VAL_10:.*]] : !fir.ref) for (%[[VAL_11:.*]]) : i32 = (%[[VAL_7]]) to (%[[VAL_8]]) inclusive step (%[[VAL_9]]) { -! CHECK: fir.store %[[VAL_11]] to %[[VAL_6]]#1 : !fir.ref -! CHECK: %[[VAL_12:.*]]:2 = hlfir.declare %[[VAL_10]] {uniq_name = "_QFsimple_int_reduction_switch_orderEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_13:.*]] = fir.load %[[VAL_6]]#0 : !fir.ref -! CHECK: %[[VAL_14:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref -! CHECK: %[[VAL_15:.*]] = arith.addi %[[VAL_13]], %[[VAL_14]] : i32 -! CHECK: hlfir.assign %[[VAL_15]] to %[[VAL_12]]#0 : i32, !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop reduction(@add_reduction_i32 %[[VAL_3]]#0 -> %[[VAL_10:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_11:.*]]) : i32 = (%[[VAL_7]]) to (%[[VAL_8]]) inclusive step (%[[VAL_9]]) { +! CHECK: %[[VAL_12:.*]]:2 = hlfir.declare %[[VAL_10]] {uniq_name = "_QFsimple_int_reduction_switch_orderEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: fir.store %[[VAL_11]] to %[[VAL_6]]#1 : !fir.ref +! CHECK: %[[VAL_13:.*]] = fir.load %[[VAL_6]]#0 : !fir.ref +! CHECK: %[[VAL_14:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref +! CHECK: %[[VAL_15:.*]] = arith.addi %[[VAL_13]], %[[VAL_14]] : i32 +! CHECK: hlfir.assign %[[VAL_15]] to %[[VAL_12]]#0 : i32, !fir.ref +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } @@ -178,15 +187,18 @@ end subroutine ! CHECK: %[[VAL_7:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_8:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_9:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@add_reduction_f32 %[[VAL_3]]#0 -> %[[VAL_10:.*]] : !fir.ref) for (%[[VAL_11:.*]]) : i32 = (%[[VAL_7]]) to (%[[VAL_8]]) inclusive step (%[[VAL_9]]) { -! CHECK: fir.store %[[VAL_11]] to %[[VAL_6]]#1 : !fir.ref -! CHECK: %[[VAL_12:.*]]:2 = hlfir.declare %[[VAL_10]] {uniq_name = "_QFsimple_real_reduction_switch_orderEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_13:.*]] = fir.load %[[VAL_6]]#0 : !fir.ref -! CHECK: %[[VAL_14:.*]] = fir.convert %[[VAL_13]] : (i32) -> f32 -! CHECK: %[[VAL_15:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref -! CHECK: %[[VAL_16:.*]] = arith.addf %[[VAL_14]], %[[VAL_15]] fastmath : f32 -! CHECK: hlfir.assign %[[VAL_16]] to %[[VAL_12]]#0 : f32, !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop reduction(@add_reduction_f32 %[[VAL_3]]#0 -> %[[VAL_10:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_11:.*]]) : i32 = (%[[VAL_7]]) to (%[[VAL_8]]) inclusive step (%[[VAL_9]]) { +! CHECK: %[[VAL_12:.*]]:2 = hlfir.declare %[[VAL_10]] {uniq_name = "_QFsimple_real_reduction_switch_orderEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: fir.store %[[VAL_11]] to %[[VAL_6]]#1 : !fir.ref +! CHECK: %[[VAL_13:.*]] = fir.load %[[VAL_6]]#0 : !fir.ref +! CHECK: %[[VAL_14:.*]] = fir.convert %[[VAL_13]] : (i32) -> f32 +! CHECK: %[[VAL_15:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref +! CHECK: %[[VAL_16:.*]] = arith.addf %[[VAL_14]], %[[VAL_15]] fastmath : f32 +! CHECK: hlfir.assign %[[VAL_16]] to %[[VAL_12]]#0 : f32, !fir.ref +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } @@ -226,24 +238,27 @@ end subroutine ! CHECK: %[[VAL_13:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_14:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_15:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@add_reduction_i32 %[[VAL_3]]#0 -> %[[VAL_16:.*]] : !fir.ref, @add_reduction_i32 %[[VAL_5]]#0 -> %[[VAL_17:.*]] : !fir.ref, @add_reduction_i32 %[[VAL_7]]#0 -> %[[VAL_18:.*]] : !fir.ref) for (%[[VAL_19:.*]]) : i32 = (%[[VAL_13]]) to (%[[VAL_14]]) inclusive step (%[[VAL_15]]) { -! CHECK: fir.store %[[VAL_19]] to %[[VAL_12]]#1 : !fir.ref -! CHECK: %[[VAL_20:.*]]:2 = hlfir.declare %[[VAL_16]] {uniq_name = "_QFmultiple_int_reductions_same_typeEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_21:.*]]:2 = hlfir.declare %[[VAL_17]] {uniq_name = "_QFmultiple_int_reductions_same_typeEy"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_22:.*]]:2 = hlfir.declare %[[VAL_18]] {uniq_name = "_QFmultiple_int_reductions_same_typeEz"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_23:.*]] = fir.load %[[VAL_20]]#0 : !fir.ref -! CHECK: %[[VAL_24:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref -! CHECK: %[[VAL_25:.*]] = arith.addi %[[VAL_23]], %[[VAL_24]] : i32 -! CHECK: hlfir.assign %[[VAL_25]] to %[[VAL_20]]#0 : i32, !fir.ref -! CHECK: %[[VAL_26:.*]] = fir.load %[[VAL_21]]#0 : !fir.ref -! CHECK: %[[VAL_27:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref -! CHECK: %[[VAL_28:.*]] = arith.addi %[[VAL_26]], %[[VAL_27]] : i32 -! CHECK: hlfir.assign %[[VAL_28]] to %[[VAL_21]]#0 : i32, !fir.ref -! CHECK: %[[VAL_29:.*]] = fir.load %[[VAL_22]]#0 : !fir.ref -! CHECK: %[[VAL_30:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref -! CHECK: %[[VAL_31:.*]] = arith.addi %[[VAL_29]], %[[VAL_30]] : i32 -! CHECK: hlfir.assign %[[VAL_31]] to %[[VAL_22]]#0 : i32, !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop reduction(@add_reduction_i32 %[[VAL_3]]#0 -> %[[VAL_16:.*]] : !fir.ref, @add_reduction_i32 %[[VAL_5]]#0 -> %[[VAL_17:.*]] : !fir.ref, @add_reduction_i32 %[[VAL_7]]#0 -> %[[VAL_18:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_19:.*]]) : i32 = (%[[VAL_13]]) to (%[[VAL_14]]) inclusive step (%[[VAL_15]]) { +! CHECK: %[[VAL_20:.*]]:2 = hlfir.declare %[[VAL_16]] {uniq_name = "_QFmultiple_int_reductions_same_typeEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: %[[VAL_21:.*]]:2 = hlfir.declare %[[VAL_17]] {uniq_name = "_QFmultiple_int_reductions_same_typeEy"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: %[[VAL_22:.*]]:2 = hlfir.declare %[[VAL_18]] {uniq_name = "_QFmultiple_int_reductions_same_typeEz"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: fir.store %[[VAL_19]] to %[[VAL_12]]#1 : !fir.ref +! CHECK: %[[VAL_23:.*]] = fir.load %[[VAL_20]]#0 : !fir.ref +! CHECK: %[[VAL_24:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref +! CHECK: %[[VAL_25:.*]] = arith.addi %[[VAL_23]], %[[VAL_24]] : i32 +! CHECK: hlfir.assign %[[VAL_25]] to %[[VAL_20]]#0 : i32, !fir.ref +! CHECK: %[[VAL_26:.*]] = fir.load %[[VAL_21]]#0 : !fir.ref +! CHECK: %[[VAL_27:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref +! CHECK: %[[VAL_28:.*]] = arith.addi %[[VAL_26]], %[[VAL_27]] : i32 +! CHECK: hlfir.assign %[[VAL_28]] to %[[VAL_21]]#0 : i32, !fir.ref +! CHECK: %[[VAL_29:.*]] = fir.load %[[VAL_22]]#0 : !fir.ref +! CHECK: %[[VAL_30:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref +! CHECK: %[[VAL_31:.*]] = arith.addi %[[VAL_29]], %[[VAL_30]] : i32 +! CHECK: hlfir.assign %[[VAL_31]] to %[[VAL_22]]#0 : i32, !fir.ref +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } @@ -287,27 +302,30 @@ end subroutine ! CHECK: %[[VAL_13:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_14:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_15:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@add_reduction_f32 %[[VAL_3]]#0 -> %[[VAL_16:.*]] : !fir.ref, @add_reduction_f32 %[[VAL_5]]#0 -> %[[VAL_17:.*]] : !fir.ref, @add_reduction_f32 %[[VAL_7]]#0 -> %[[VAL_18:.*]] : !fir.ref) for (%[[VAL_19:.*]]) : i32 = (%[[VAL_13]]) to (%[[VAL_14]]) inclusive step (%[[VAL_15]]) { -! CHECK: fir.store %[[VAL_19]] to %[[VAL_12]]#1 : !fir.ref -! CHECK: %[[VAL_20:.*]]:2 = hlfir.declare %[[VAL_16]] {uniq_name = "_QFmultiple_real_reductions_same_typeEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_21:.*]]:2 = hlfir.declare %[[VAL_17]] {uniq_name = "_QFmultiple_real_reductions_same_typeEy"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_22:.*]]:2 = hlfir.declare %[[VAL_18]] {uniq_name = "_QFmultiple_real_reductions_same_typeEz"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_23:.*]] = fir.load %[[VAL_20]]#0 : !fir.ref -! CHECK: %[[VAL_24:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref -! CHECK: %[[VAL_25:.*]] = fir.convert %[[VAL_24]] : (i32) -> f32 -! CHECK: %[[VAL_26:.*]] = arith.addf %[[VAL_23]], %[[VAL_25]] fastmath : f32 -! CHECK: hlfir.assign %[[VAL_26]] to %[[VAL_20]]#0 : f32, !fir.ref -! CHECK: %[[VAL_27:.*]] = fir.load %[[VAL_21]]#0 : !fir.ref -! CHECK: %[[VAL_28:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref -! CHECK: %[[VAL_29:.*]] = fir.convert %[[VAL_28]] : (i32) -> f32 -! CHECK: %[[VAL_30:.*]] = arith.addf %[[VAL_27]], %[[VAL_29]] fastmath : f32 -! CHECK: hlfir.assign %[[VAL_30]] to %[[VAL_21]]#0 : f32, !fir.ref -! CHECK: %[[VAL_31:.*]] = fir.load %[[VAL_22]]#0 : !fir.ref -! CHECK: %[[VAL_32:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref -! CHECK: %[[VAL_33:.*]] = fir.convert %[[VAL_32]] : (i32) -> f32 -! CHECK: %[[VAL_34:.*]] = arith.addf %[[VAL_31]], %[[VAL_33]] fastmath : f32 -! CHECK: hlfir.assign %[[VAL_34]] to %[[VAL_22]]#0 : f32, !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop reduction(@add_reduction_f32 %[[VAL_3]]#0 -> %[[VAL_16:.*]] : !fir.ref, @add_reduction_f32 %[[VAL_5]]#0 -> %[[VAL_17:.*]] : !fir.ref, @add_reduction_f32 %[[VAL_7]]#0 -> %[[VAL_18:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_19:.*]]) : i32 = (%[[VAL_13]]) to (%[[VAL_14]]) inclusive step (%[[VAL_15]]) { +! CHECK: %[[VAL_20:.*]]:2 = hlfir.declare %[[VAL_16]] {uniq_name = "_QFmultiple_real_reductions_same_typeEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: %[[VAL_21:.*]]:2 = hlfir.declare %[[VAL_17]] {uniq_name = "_QFmultiple_real_reductions_same_typeEy"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: %[[VAL_22:.*]]:2 = hlfir.declare %[[VAL_18]] {uniq_name = "_QFmultiple_real_reductions_same_typeEz"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: fir.store %[[VAL_19]] to %[[VAL_12]]#1 : !fir.ref +! CHECK: %[[VAL_23:.*]] = fir.load %[[VAL_20]]#0 : !fir.ref +! CHECK: %[[VAL_24:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref +! CHECK: %[[VAL_25:.*]] = fir.convert %[[VAL_24]] : (i32) -> f32 +! CHECK: %[[VAL_26:.*]] = arith.addf %[[VAL_23]], %[[VAL_25]] fastmath : f32 +! CHECK: hlfir.assign %[[VAL_26]] to %[[VAL_20]]#0 : f32, !fir.ref +! CHECK: %[[VAL_27:.*]] = fir.load %[[VAL_21]]#0 : !fir.ref +! CHECK: %[[VAL_28:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref +! CHECK: %[[VAL_29:.*]] = fir.convert %[[VAL_28]] : (i32) -> f32 +! CHECK: %[[VAL_30:.*]] = arith.addf %[[VAL_27]], %[[VAL_29]] fastmath : f32 +! CHECK: hlfir.assign %[[VAL_30]] to %[[VAL_21]]#0 : f32, !fir.ref +! CHECK: %[[VAL_31:.*]] = fir.load %[[VAL_22]]#0 : !fir.ref +! CHECK: %[[VAL_32:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref +! CHECK: %[[VAL_33:.*]] = fir.convert %[[VAL_32]] : (i32) -> f32 +! CHECK: %[[VAL_34:.*]] = arith.addf %[[VAL_31]], %[[VAL_33]] fastmath : f32 +! CHECK: hlfir.assign %[[VAL_34]] to %[[VAL_22]]#0 : f32, !fir.ref +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } @@ -355,32 +373,35 @@ end subroutine ! CHECK: %[[VAL_16:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_17:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_18:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@add_reduction_i32 %[[VAL_5]]#0 -> %[[VAL_19:.*]] : !fir.ref, @add_reduction_i64 %[[VAL_7]]#0 -> %[[VAL_20:.*]] : !fir.ref, @add_reduction_f32 %[[VAL_9]]#0 -> %[[VAL_21:.*]] : !fir.ref, @add_reduction_f64 %[[VAL_3]]#0 -> %[[VAL_22:.*]] : !fir.ref) for (%[[VAL_23:.*]]) : i32 = (%[[VAL_16]]) to (%[[VAL_17]]) inclusive step (%[[VAL_18]]) { -! CHECK: fir.store %[[VAL_23]] to %[[VAL_15]]#1 : !fir.ref -! CHECK: %[[VAL_24:.*]]:2 = hlfir.declare %[[VAL_19]] {uniq_name = "_QFmultiple_reductions_different_typeEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_25:.*]]:2 = hlfir.declare %[[VAL_20]] {uniq_name = "_QFmultiple_reductions_different_typeEy"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_26:.*]]:2 = hlfir.declare %[[VAL_21]] {uniq_name = "_QFmultiple_reductions_different_typeEz"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_27:.*]]:2 = hlfir.declare %[[VAL_22]] {uniq_name = "_QFmultiple_reductions_different_typeEw"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_28:.*]] = fir.load %[[VAL_24]]#0 : !fir.ref -! CHECK: %[[VAL_29:.*]] = fir.load %[[VAL_15]]#0 : !fir.ref -! CHECK: %[[VAL_30:.*]] = arith.addi %[[VAL_28]], %[[VAL_29]] : i32 -! CHECK: hlfir.assign %[[VAL_30]] to %[[VAL_24]]#0 : i32, !fir.ref -! CHECK: %[[VAL_31:.*]] = fir.load %[[VAL_25]]#0 : !fir.ref -! CHECK: %[[VAL_32:.*]] = fir.load %[[VAL_15]]#0 : !fir.ref -! CHECK: %[[VAL_33:.*]] = fir.convert %[[VAL_32]] : (i32) -> i64 -! CHECK: %[[VAL_34:.*]] = arith.addi %[[VAL_31]], %[[VAL_33]] : i64 -! CHECK: hlfir.assign %[[VAL_34]] to %[[VAL_25]]#0 : i64, !fir.ref -! CHECK: %[[VAL_35:.*]] = fir.load %[[VAL_26]]#0 : !fir.ref -! CHECK: %[[VAL_36:.*]] = fir.load %[[VAL_15]]#0 : !fir.ref -! CHECK: %[[VAL_37:.*]] = fir.convert %[[VAL_36]] : (i32) -> f32 -! CHECK: %[[VAL_38:.*]] = arith.addf %[[VAL_35]], %[[VAL_37]] fastmath : f32 -! CHECK: hlfir.assign %[[VAL_38]] to %[[VAL_26]]#0 : f32, !fir.ref -! CHECK: %[[VAL_39:.*]] = fir.load %[[VAL_27]]#0 : !fir.ref -! CHECK: %[[VAL_40:.*]] = fir.load %[[VAL_15]]#0 : !fir.ref -! CHECK: %[[VAL_41:.*]] = fir.convert %[[VAL_40]] : (i32) -> f64 -! CHECK: %[[VAL_42:.*]] = arith.addf %[[VAL_39]], %[[VAL_41]] fastmath : f64 -! CHECK: hlfir.assign %[[VAL_42]] to %[[VAL_27]]#0 : f64, !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop reduction(@add_reduction_i32 %[[VAL_5]]#0 -> %[[VAL_19:.*]] : !fir.ref, @add_reduction_i64 %[[VAL_7]]#0 -> %[[VAL_20:.*]] : !fir.ref, @add_reduction_f32 %[[VAL_9]]#0 -> %[[VAL_21:.*]] : !fir.ref, @add_reduction_f64 %[[VAL_3]]#0 -> %[[VAL_22:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_23:.*]]) : i32 = (%[[VAL_16]]) to (%[[VAL_17]]) inclusive step (%[[VAL_18]]) { +! CHECK: %[[VAL_24:.*]]:2 = hlfir.declare %[[VAL_19]] {uniq_name = "_QFmultiple_reductions_different_typeEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: %[[VAL_25:.*]]:2 = hlfir.declare %[[VAL_20]] {uniq_name = "_QFmultiple_reductions_different_typeEy"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: %[[VAL_26:.*]]:2 = hlfir.declare %[[VAL_21]] {uniq_name = "_QFmultiple_reductions_different_typeEz"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: %[[VAL_27:.*]]:2 = hlfir.declare %[[VAL_22]] {uniq_name = "_QFmultiple_reductions_different_typeEw"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: fir.store %[[VAL_23]] to %[[VAL_15]]#1 : !fir.ref +! CHECK: %[[VAL_28:.*]] = fir.load %[[VAL_24]]#0 : !fir.ref +! CHECK: %[[VAL_29:.*]] = fir.load %[[VAL_15]]#0 : !fir.ref +! CHECK: %[[VAL_30:.*]] = arith.addi %[[VAL_28]], %[[VAL_29]] : i32 +! CHECK: hlfir.assign %[[VAL_30]] to %[[VAL_24]]#0 : i32, !fir.ref +! CHECK: %[[VAL_31:.*]] = fir.load %[[VAL_25]]#0 : !fir.ref +! CHECK: %[[VAL_32:.*]] = fir.load %[[VAL_15]]#0 : !fir.ref +! CHECK: %[[VAL_33:.*]] = fir.convert %[[VAL_32]] : (i32) -> i64 +! CHECK: %[[VAL_34:.*]] = arith.addi %[[VAL_31]], %[[VAL_33]] : i64 +! CHECK: hlfir.assign %[[VAL_34]] to %[[VAL_25]]#0 : i64, !fir.ref +! CHECK: %[[VAL_35:.*]] = fir.load %[[VAL_26]]#0 : !fir.ref +! CHECK: %[[VAL_36:.*]] = fir.load %[[VAL_15]]#0 : !fir.ref +! CHECK: %[[VAL_37:.*]] = fir.convert %[[VAL_36]] : (i32) -> f32 +! CHECK: %[[VAL_38:.*]] = arith.addf %[[VAL_35]], %[[VAL_37]] fastmath : f32 +! CHECK: hlfir.assign %[[VAL_38]] to %[[VAL_26]]#0 : f32, !fir.ref +! CHECK: %[[VAL_39:.*]] = fir.load %[[VAL_27]]#0 : !fir.ref +! CHECK: %[[VAL_40:.*]] = fir.load %[[VAL_15]]#0 : !fir.ref +! CHECK: %[[VAL_41:.*]] = fir.convert %[[VAL_40]] : (i32) -> f64 +! CHECK: %[[VAL_42:.*]] = arith.addf %[[VAL_39]], %[[VAL_41]] fastmath : f64 +! CHECK: hlfir.assign %[[VAL_42]] to %[[VAL_27]]#0 : f64, !fir.ref +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } diff --git a/flang/test/Lower/OpenMP/wsloop-reduction-allocatable.f90 b/flang/test/Lower/OpenMP/wsloop-reduction-allocatable.f90 index fe3a2505d17c0459ba2b65e64f842d63c09f07fd..8310aeb23df088967f2d36abf1ab44872ae10c8e 100644 --- a/flang/test/Lower/OpenMP/wsloop-reduction-allocatable.f90 +++ b/flang/test/Lower/OpenMP/wsloop-reduction-allocatable.f90 @@ -80,14 +80,17 @@ end program ! CHECK: %[[VAL_11:.*]] = arith.constant 0 : i32 ! CHECK: %[[VAL_12:.*]] = arith.constant 10 : i32 ! CHECK: %[[VAL_13:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@add_reduction_byref_box_heap_i32 %[[VAL_5]]#0 -> %[[VAL_14:.*]] : !fir.ref>>) for (%[[VAL_15:.*]]) : i32 = (%[[VAL_11]]) to (%[[VAL_12]]) inclusive step (%[[VAL_13]]) { -! CHECK: fir.store %[[VAL_15]] to %[[VAL_10]]#1 : !fir.ref -! CHECK: %[[VAL_16:.*]]:2 = hlfir.declare %[[VAL_14]] {fortran_attrs = {{.*}}, uniq_name = "_QFEr"} : (!fir.ref>>) -> (!fir.ref>>, !fir.ref>>) -! CHECK: %[[VAL_17:.*]] = fir.load %[[VAL_10]]#0 : !fir.ref -! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_16]]#0 : !fir.ref>> -! CHECK: %[[VAL_19:.*]] = fir.box_addr %[[VAL_18]] : (!fir.box>) -> !fir.heap -! CHECK: hlfir.assign %[[VAL_17]] to %[[VAL_19]] : i32, !fir.heap -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@add_reduction_byref_box_heap_i32 %[[VAL_5]]#0 -> %[[VAL_14:.*]] : !fir.ref>>) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_15:.*]]) : i32 = (%[[VAL_11]]) to (%[[VAL_12]]) inclusive step (%[[VAL_13]]) { +! CHECK: %[[VAL_16:.*]]:2 = hlfir.declare %[[VAL_14]] {fortran_attrs = {{.*}}, uniq_name = "_QFEr"} : (!fir.ref>>) -> (!fir.ref>>, !fir.ref>>) +! CHECK: fir.store %[[VAL_15]] to %[[VAL_10]]#1 : !fir.ref +! CHECK: %[[VAL_17:.*]] = fir.load %[[VAL_10]]#0 : !fir.ref +! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_16]]#0 : !fir.ref>> +! CHECK: %[[VAL_19:.*]] = fir.box_addr %[[VAL_18]] : (!fir.box>) -> !fir.heap +! CHECK: hlfir.assign %[[VAL_17]] to %[[VAL_19]] : i32, !fir.heap +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } diff --git a/flang/test/Lower/OpenMP/wsloop-reduction-array-assumed-shape.f90 b/flang/test/Lower/OpenMP/wsloop-reduction-array-assumed-shape.f90 index c22407cd35ad01979ac1503548dc9460807151db..6c9bc75b81d70073b692c0fcb818ae40101d0524 100644 --- a/flang/test/Lower/OpenMP/wsloop-reduction-array-assumed-shape.f90 +++ b/flang/test/Lower/OpenMP/wsloop-reduction-array-assumed-shape.f90 @@ -33,10 +33,13 @@ end program ! CHECK: %[[VAL_6:.*]] = fir.allocmem !fir.array, %[[VAL_4]]#1 {bindc_name = ".tmp", uniq_name = ""} ! CHECK: %[[TRUE:.*]] = arith.constant true ! CHECK: %[[VAL_7:.*]]:2 = hlfir.declare %[[VAL_6]](%[[VAL_5]]) {uniq_name = ".tmp"} : (!fir.heap>, !fir.shape<1>) -> (!fir.box>, !fir.heap>) -! CHECK: hlfir.assign %[[VAL_1]] to %[[VAL_7]]#0 : f64, !fir.box> -! CHECK: fir.store %[[VAL_7]]#0 to %[[VAL_8]] : !fir.ref>> +! CHECK: %[[C0:.*]] = arith.constant 0 : index +! CHECK: %[[DIMS:.*]]:3 = fir.box_dims %[[VAL_2]], %[[C0]] : (!fir.box>, index) -> (index, index, index) +! CHECK: %[[SHIFT:.*]] = fir.shape_shift %[[DIMS]]#0, %[[DIMS]]#1 : (index, index) -> !fir.shapeshift<1> +! CHECK: %[[REBOX:.*]] = fir.rebox %[[VAL_7]]#0(%[[SHIFT]]) : (!fir.box>, !fir.shapeshift<1>) -> !fir.box +! CHECK: hlfir.assign %[[VAL_1]] to %[[REBOX]] : f64, !fir.box> +! CHECK: fir.store %[[REBOX]] to %[[VAL_8]] : !fir.ref>> ! CHECK: omp.yield(%[[VAL_8]] : !fir.ref>>) - ! CHECK-LABEL: } combiner { ! CHECK: ^bb0(%[[VAL_0:.*]]: !fir.ref>>, %[[VAL_1:.*]]: !fir.ref>>): ! CHECK: %[[VAL_2:.*]] = fir.load %[[VAL_0]] : !fir.ref>> @@ -81,21 +84,24 @@ end program ! CHECK: %[[VAL_8:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_9:.*]] = fir.alloca !fir.box> ! CHECK: fir.store %[[VAL_3]]#1 to %[[VAL_9]] : !fir.ref>> -! CHECK: omp.wsloop byref reduction(@add_reduction_byref_box_Uxf64 %[[VAL_9]] -> %[[VAL_10:.*]] : !fir.ref>>) for (%[[VAL_11:.*]]) : i32 = (%[[VAL_6]]) to (%[[VAL_7]]) inclusive step (%[[VAL_8]]) { -! CHECK: fir.store %[[VAL_11]] to %[[VAL_5]]#1 : !fir.ref -! CHECK: %[[VAL_12:.*]]:2 = hlfir.declare %[[VAL_10]] {fortran_attrs = {{.*}}, uniq_name = "_QFFreduceEr"} : (!fir.ref>>) -> (!fir.ref>>, !fir.ref>>) -! CHECK: %[[VAL_13:.*]] = fir.load %[[VAL_5]]#0 : !fir.ref -! CHECK: %[[VAL_14:.*]] = fir.convert %[[VAL_13]] : (i32) -> f64 -! CHECK: %[[VAL_15:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref>> -! CHECK: %[[VAL_16:.*]] = arith.constant 1 : index -! CHECK: %[[VAL_17:.*]] = hlfir.designate %[[VAL_15]] (%[[VAL_16]]) : (!fir.box>, index) -> !fir.ref -! CHECK: hlfir.assign %[[VAL_14]] to %[[VAL_17]] : f64, !fir.ref -! CHECK: %[[VAL_18:.*]] = arith.constant 1.000000e+00 : f64 -! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref>> -! CHECK: %[[VAL_20:.*]] = arith.constant 2 : index -! CHECK: %[[VAL_21:.*]] = hlfir.designate %[[VAL_19]] (%[[VAL_20]]) : (!fir.box>, index) -> !fir.ref -! CHECK: hlfir.assign %[[VAL_18]] to %[[VAL_21]] : f64, !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@add_reduction_byref_box_Uxf64 %[[VAL_9]] -> %[[VAL_10:.*]] : !fir.ref>>) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_11:.*]]) : i32 = (%[[VAL_6]]) to (%[[VAL_7]]) inclusive step (%[[VAL_8]]) { +! CHECK: %[[VAL_12:.*]]:2 = hlfir.declare %[[VAL_10]] {fortran_attrs = {{.*}}, uniq_name = "_QFFreduceEr"} : (!fir.ref>>) -> (!fir.ref>>, !fir.ref>>) +! CHECK: fir.store %[[VAL_11]] to %[[VAL_5]]#1 : !fir.ref +! CHECK: %[[VAL_13:.*]] = fir.load %[[VAL_5]]#0 : !fir.ref +! CHECK: %[[VAL_14:.*]] = fir.convert %[[VAL_13]] : (i32) -> f64 +! CHECK: %[[VAL_15:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref>> +! CHECK: %[[VAL_16:.*]] = arith.constant 1 : index +! CHECK: %[[VAL_17:.*]] = hlfir.designate %[[VAL_15]] (%[[VAL_16]]) : (!fir.box>, index) -> !fir.ref +! CHECK: hlfir.assign %[[VAL_14]] to %[[VAL_17]] : f64, !fir.ref +! CHECK: %[[VAL_18:.*]] = arith.constant 1.000000e+00 : f64 +! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref>> +! CHECK: %[[VAL_20:.*]] = arith.constant 2 : index +! CHECK: %[[VAL_21:.*]] = hlfir.designate %[[VAL_19]] (%[[VAL_20]]) : (!fir.box>, index) -> !fir.ref +! CHECK: hlfir.assign %[[VAL_18]] to %[[VAL_21]] : f64, !fir.ref +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } diff --git a/flang/test/Lower/OpenMP/wsloop-reduction-array.f90 b/flang/test/Lower/OpenMP/wsloop-reduction-array.f90 index ef122e81d392785b0fa408ac9a5844df304904fe..7aecf870cf800a60bc1b99639ce30c690dfd8993 100644 --- a/flang/test/Lower/OpenMP/wsloop-reduction-array.f90 +++ b/flang/test/Lower/OpenMP/wsloop-reduction-array.f90 @@ -24,7 +24,10 @@ end program ! CHECK: %[[VAL_1:.*]] = fir.allocmem !fir.array<2xi32> {bindc_name = ".tmp", uniq_name = ""} ! CHECK: %[[TRUE:.*]] = arith.constant true ! CHECK: %[[VAL_6:.*]]:2 = hlfir.declare %[[VAL_1]](%[[VAL_5]]) {uniq_name = ".tmp"} : (!fir.heap>, !fir.shape<1>) -> (!fir.heap>, !fir.heap>) -! CHECK: %[[VAL_7:.*]] = fir.embox %[[VAL_6]]#0(%[[VAL_5]]) : (!fir.heap>, !fir.shape<1>) -> !fir.box> +! CHECK: %[[C0:.*]] = arith.constant 0 : index +! CHECK: %[[DIMS:.*]]:3 = fir.box_dims %[[VAL_3]], %[[C0]] : (!fir.box>, index) -> (index, index, index) +! CHECK: %[[SHIFT:.*]] = fir.shape_shift %[[DIMS]]#0, %[[DIMS]]#1 : (index, index) -> !fir.shapeshift<1> +! CHECK: %[[VAL_7:.*]] = fir.embox %[[VAL_6]]#0(%[[SHIFT]]) : (!fir.heap>, !fir.shapeshift<1>) -> !fir.box> ! CHECK: hlfir.assign %[[VAL_2]] to %[[VAL_7]] : i32, !fir.box> ! CHECK: fir.store %[[VAL_7]] to %[[VAL_8]] : !fir.ref>> ! CHECK: omp.yield(%[[VAL_8]] : !fir.ref>>) @@ -76,22 +79,25 @@ end program ! CHECK: %[[VAL_11:.*]] = fir.embox %[[VAL_5]]#0(%[[VAL_4]]) : (!fir.ref>, !fir.shape<1>) -> !fir.box> ! CHECK: %[[VAL_12:.*]] = fir.alloca !fir.box> ! CHECK: fir.store %[[VAL_11]] to %[[VAL_12]] : !fir.ref>> -! CHECK: omp.wsloop byref reduction(@add_reduction_byref_box_2xi32 %[[VAL_12]] -> %[[VAL_13:.*]] : !fir.ref>>) for (%[[VAL_14:.*]]) : i32 = (%[[VAL_8]]) to (%[[VAL_9]]) inclusive step (%[[VAL_10]]) { -! CHECK: fir.store %[[VAL_14]] to %[[VAL_7]]#1 : !fir.ref -! CHECK: %[[VAL_15:.*]]:2 = hlfir.declare %[[VAL_13]] {uniq_name = "_QFEr"} : (!fir.ref>>) -> (!fir.ref>>, !fir.ref>>) -! CHECK: %[[VAL_16:.*]] = fir.load %[[VAL_7]]#0 : !fir.ref -! CHECK: %[[VAL_17:.*]] = fir.load %[[VAL_15]]#0 : !fir.ref>> -! CHECK: %[[VAL_18:.*]] = arith.constant 1 : index -! CHECK: %[[VAL_19:.*]] = hlfir.designate %[[VAL_17]] (%[[VAL_18]]) : (!fir.box>, index) -> !fir.ref -! CHECK: hlfir.assign %[[VAL_16]] to %[[VAL_19]] : i32, !fir.ref -! CHECK: %[[VAL_20:.*]] = fir.load %[[VAL_7]]#0 : !fir.ref -! CHECK: %[[VAL_21:.*]] = arith.constant 0 : i32 -! CHECK: %[[VAL_22:.*]] = arith.subi %[[VAL_21]], %[[VAL_20]] : i32 -! CHECK: %[[VAL_23:.*]] = fir.load %[[VAL_15]]#0 : !fir.ref>> -! CHECK: %[[VAL_24:.*]] = arith.constant 2 : index -! CHECK: %[[VAL_25:.*]] = hlfir.designate %[[VAL_23]] (%[[VAL_24]]) : (!fir.box>, index) -> !fir.ref -! CHECK: hlfir.assign %[[VAL_22]] to %[[VAL_25]] : i32, !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@add_reduction_byref_box_2xi32 %[[VAL_12]] -> %[[VAL_13:.*]] : !fir.ref>>) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_14:.*]]) : i32 = (%[[VAL_8]]) to (%[[VAL_9]]) inclusive step (%[[VAL_10]]) { +! CHECK: %[[VAL_15:.*]]:2 = hlfir.declare %[[VAL_13]] {uniq_name = "_QFEr"} : (!fir.ref>>) -> (!fir.ref>>, !fir.ref>>) +! CHECK: fir.store %[[VAL_14]] to %[[VAL_7]]#1 : !fir.ref +! CHECK: %[[VAL_16:.*]] = fir.load %[[VAL_7]]#0 : !fir.ref +! CHECK: %[[VAL_17:.*]] = fir.load %[[VAL_15]]#0 : !fir.ref>> +! CHECK: %[[VAL_18:.*]] = arith.constant 1 : index +! CHECK: %[[VAL_19:.*]] = hlfir.designate %[[VAL_17]] (%[[VAL_18]]) : (!fir.box>, index) -> !fir.ref +! CHECK: hlfir.assign %[[VAL_16]] to %[[VAL_19]] : i32, !fir.ref +! CHECK: %[[VAL_20:.*]] = fir.load %[[VAL_7]]#0 : !fir.ref +! CHECK: %[[VAL_21:.*]] = arith.constant 0 : i32 +! CHECK: %[[VAL_22:.*]] = arith.subi %[[VAL_21]], %[[VAL_20]] : i32 +! CHECK: %[[VAL_23:.*]] = fir.load %[[VAL_15]]#0 : !fir.ref>> +! CHECK: %[[VAL_24:.*]] = arith.constant 2 : index +! CHECK: %[[VAL_25:.*]] = hlfir.designate %[[VAL_23]] (%[[VAL_24]]) : (!fir.box>, index) -> !fir.ref +! CHECK: hlfir.assign %[[VAL_22]] to %[[VAL_25]] : i32, !fir.ref +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } diff --git a/flang/test/Lower/OpenMP/wsloop-reduction-array2.f90 b/flang/test/Lower/OpenMP/wsloop-reduction-array2.f90 index 6de8c8eb2e48d7e41c8de152a77ae8324c6114b4..d1d8a2c599444af8d77bbb233b9631dbe0e02d87 100644 --- a/flang/test/Lower/OpenMP/wsloop-reduction-array2.f90 +++ b/flang/test/Lower/OpenMP/wsloop-reduction-array2.f90 @@ -24,7 +24,10 @@ end program ! CHECK: %[[VAL_1:.*]] = fir.allocmem !fir.array<2xi32> {bindc_name = ".tmp", uniq_name = ""} ! CHECK: %[[TRUE:.*]] = arith.constant true ! CHECK: %[[VAL_6:.*]]:2 = hlfir.declare %[[VAL_1]](%[[VAL_5]]) {uniq_name = ".tmp"} : (!fir.heap>, !fir.shape<1>) -> (!fir.heap>, !fir.heap>) -! CHECK: %[[VAL_7:.*]] = fir.embox %[[VAL_6]]#0(%[[VAL_5]]) : (!fir.heap>, !fir.shape<1>) -> !fir.box> +! CHECK: %[[C0:.*]] = arith.constant 0 : index +! CHECK: %[[DIMS:.*]]:3 = fir.box_dims %[[VAL_3]], %[[C0]] : (!fir.box>, index) -> (index, index, index) +! CHECK: %[[SHIFT:.*]] = fir.shape_shift %[[DIMS]]#0, %[[DIMS]]#1 : (index, index) -> !fir.shapeshift<1> +! CHECK: %[[VAL_7:.*]] = fir.embox %[[VAL_6]]#0(%[[SHIFT]]) : (!fir.heap>, !fir.shapeshift<1>) -> !fir.box> ! CHECK: hlfir.assign %[[VAL_2]] to %[[VAL_7]] : i32, !fir.box> ! CHECK: fir.store %[[VAL_7]] to %[[VAL_8]] : !fir.ref>> ! CHECK: omp.yield(%[[VAL_8]] : !fir.ref>>) @@ -76,30 +79,33 @@ end program ! CHECK: %[[VAL_11:.*]] = fir.embox %[[VAL_5]]#0(%[[VAL_4]]) : (!fir.ref>, !fir.shape<1>) -> !fir.box> ! CHECK: %[[VAL_12:.*]] = fir.alloca !fir.box> ! CHECK: fir.store %[[VAL_11]] to %[[VAL_12]] : !fir.ref>> -! CHECK: omp.wsloop byref reduction(@add_reduction_byref_box_2xi32 %[[VAL_12]] -> %[[VAL_13:.*]] : !fir.ref>>) for (%[[VAL_14:.*]]) : i32 = (%[[VAL_8]]) to (%[[VAL_9]]) inclusive step (%[[VAL_10]]) { -! CHECK: fir.store %[[VAL_14]] to %[[VAL_7]]#1 : !fir.ref -! CHECK: %[[VAL_15:.*]]:2 = hlfir.declare %[[VAL_13]] {uniq_name = "_QFEr"} : (!fir.ref>>) -> (!fir.ref>>, !fir.ref>>) -! CHECK: %[[VAL_16:.*]] = fir.load %[[VAL_15]]#0 : !fir.ref>> -! CHECK: %[[VAL_17:.*]] = arith.constant 1 : index -! CHECK: %[[VAL_18:.*]] = hlfir.designate %[[VAL_16]] (%[[VAL_17]]) : (!fir.box>, index) -> !fir.ref -! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_18]] : !fir.ref -! CHECK: %[[VAL_20:.*]] = fir.load %[[VAL_7]]#0 : !fir.ref -! CHECK: %[[VAL_21:.*]] = arith.addi %[[VAL_19]], %[[VAL_20]] : i32 -! CHECK: %[[VAL_22:.*]] = fir.load %[[VAL_15]]#0 : !fir.ref>> -! CHECK: %[[VAL_23:.*]] = arith.constant 1 : index -! CHECK: %[[VAL_24:.*]] = hlfir.designate %[[VAL_22]] (%[[VAL_23]]) : (!fir.box>, index) -> !fir.ref -! CHECK: hlfir.assign %[[VAL_21]] to %[[VAL_24]] : i32, !fir.ref -! CHECK: %[[VAL_25:.*]] = fir.load %[[VAL_15]]#0 : !fir.ref>> -! CHECK: %[[VAL_26:.*]] = arith.constant 2 : index -! CHECK: %[[VAL_27:.*]] = hlfir.designate %[[VAL_25]] (%[[VAL_26]]) : (!fir.box>, index) -> !fir.ref -! CHECK: %[[VAL_28:.*]] = fir.load %[[VAL_27]] : !fir.ref -! CHECK: %[[VAL_29:.*]] = fir.load %[[VAL_7]]#0 : !fir.ref -! CHECK: %[[VAL_30:.*]] = arith.subi %[[VAL_28]], %[[VAL_29]] : i32 -! CHECK: %[[VAL_31:.*]] = fir.load %[[VAL_15]]#0 : !fir.ref>> -! CHECK: %[[VAL_32:.*]] = arith.constant 2 : index -! CHECK: %[[VAL_33:.*]] = hlfir.designate %[[VAL_31]] (%[[VAL_32]]) : (!fir.box>, index) -> !fir.ref -! CHECK: hlfir.assign %[[VAL_30]] to %[[VAL_33]] : i32, !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@add_reduction_byref_box_2xi32 %[[VAL_12]] -> %[[VAL_13:.*]] : !fir.ref>>) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_14:.*]]) : i32 = (%[[VAL_8]]) to (%[[VAL_9]]) inclusive step (%[[VAL_10]]) { +! CHECK: %[[VAL_15:.*]]:2 = hlfir.declare %[[VAL_13]] {uniq_name = "_QFEr"} : (!fir.ref>>) -> (!fir.ref>>, !fir.ref>>) +! CHECK: fir.store %[[VAL_14]] to %[[VAL_7]]#1 : !fir.ref +! CHECK: %[[VAL_16:.*]] = fir.load %[[VAL_15]]#0 : !fir.ref>> +! CHECK: %[[VAL_17:.*]] = arith.constant 1 : index +! CHECK: %[[VAL_18:.*]] = hlfir.designate %[[VAL_16]] (%[[VAL_17]]) : (!fir.box>, index) -> !fir.ref +! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_18]] : !fir.ref +! CHECK: %[[VAL_20:.*]] = fir.load %[[VAL_7]]#0 : !fir.ref +! CHECK: %[[VAL_21:.*]] = arith.addi %[[VAL_19]], %[[VAL_20]] : i32 +! CHECK: %[[VAL_22:.*]] = fir.load %[[VAL_15]]#0 : !fir.ref>> +! CHECK: %[[VAL_23:.*]] = arith.constant 1 : index +! CHECK: %[[VAL_24:.*]] = hlfir.designate %[[VAL_22]] (%[[VAL_23]]) : (!fir.box>, index) -> !fir.ref +! CHECK: hlfir.assign %[[VAL_21]] to %[[VAL_24]] : i32, !fir.ref +! CHECK: %[[VAL_25:.*]] = fir.load %[[VAL_15]]#0 : !fir.ref>> +! CHECK: %[[VAL_26:.*]] = arith.constant 2 : index +! CHECK: %[[VAL_27:.*]] = hlfir.designate %[[VAL_25]] (%[[VAL_26]]) : (!fir.box>, index) -> !fir.ref +! CHECK: %[[VAL_28:.*]] = fir.load %[[VAL_27]] : !fir.ref +! CHECK: %[[VAL_29:.*]] = fir.load %[[VAL_7]]#0 : !fir.ref +! CHECK: %[[VAL_30:.*]] = arith.subi %[[VAL_28]], %[[VAL_29]] : i32 +! CHECK: %[[VAL_31:.*]] = fir.load %[[VAL_15]]#0 : !fir.ref>> +! CHECK: %[[VAL_32:.*]] = arith.constant 2 : index +! CHECK: %[[VAL_33:.*]] = hlfir.designate %[[VAL_31]] (%[[VAL_32]]) : (!fir.box>, index) -> !fir.ref +! CHECK: hlfir.assign %[[VAL_30]] to %[[VAL_33]] : i32, !fir.ref +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } diff --git a/flang/test/Lower/OpenMP/wsloop-reduction-iand-byref.f90 b/flang/test/Lower/OpenMP/wsloop-reduction-iand-byref.f90 index e3f06a446ed4c1aca20da314624f04fb24594132..40280c56dad6b3bcffbb02c36e22ab0944287908 100644 --- a/flang/test/Lower/OpenMP/wsloop-reduction-iand-byref.f90 +++ b/flang/test/Lower/OpenMP/wsloop-reduction-iand-byref.f90 @@ -35,17 +35,19 @@ ! CHECK: %[[VAL_9:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_10:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_11:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@iand_byref_i32 %[[VAL_4]]#0 -> %[[VAL_12:.*]] : !fir.ref) for (%[[VAL_13:.*]]) : i32 = (%[[VAL_9]]) to (%[[VAL_10]]) inclusive step (%[[VAL_11]]) { -! CHECK: fir.store %[[VAL_13]] to %[[VAL_8]]#1 : !fir.ref -! CHECK: %[[VAL_14:.*]]:2 = hlfir.declare %[[VAL_12]] {uniq_name = "_QFreduction_iandEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_15:.*]] = fir.load %[[VAL_8]]#0 : !fir.ref -! CHECK: %[[VAL_16:.*]] = fir.convert %[[VAL_15]] : (i32) -> i64 -! CHECK: %[[VAL_17:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_16]]) : (!fir.box>, i64) -> !fir.ref -! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_14]]#0 : !fir.ref -! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_17]] : !fir.ref -! CHECK: %[[VAL_20:.*]] = arith.andi %[[VAL_18]], %[[VAL_19]] : i32 -! CHECK: hlfir.assign %[[VAL_20]] to %[[VAL_14]]#0 : i32, !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@iand_byref_i32 %[[VAL_4]]#0 -> %[[VAL_12:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_13:.*]]) : i32 = (%[[VAL_9]]) to (%[[VAL_10]]) inclusive step (%[[VAL_11]]) { +! CHECK: %[[VAL_14:.*]]:2 = hlfir.declare %[[VAL_12]] {uniq_name = "_QFreduction_iandEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: fir.store %[[VAL_13]] to %[[VAL_8]]#1 : !fir.ref +! CHECK: %[[VAL_15:.*]] = fir.load %[[VAL_8]]#0 : !fir.ref +! CHECK: %[[VAL_16:.*]] = fir.convert %[[VAL_15]] : (i32) -> i64 +! CHECK: %[[VAL_17:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_16]]) : (!fir.box>, i64) -> !fir.ref +! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_14]]#0 : !fir.ref +! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_17]] : !fir.ref +! CHECK: %[[VAL_20:.*]] = arith.andi %[[VAL_18]], %[[VAL_19]] : i32 +! CHECK: hlfir.assign %[[VAL_20]] to %[[VAL_14]]#0 : i32, !fir.ref +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator diff --git a/flang/test/Lower/OpenMP/wsloop-reduction-iand.f90 b/flang/test/Lower/OpenMP/wsloop-reduction-iand.f90 index 746617e210624b666e48c57c5a061b53f425a73e..986892d3584f945665cb0beac50c895f57e54259 100644 --- a/flang/test/Lower/OpenMP/wsloop-reduction-iand.f90 +++ b/flang/test/Lower/OpenMP/wsloop-reduction-iand.f90 @@ -29,17 +29,19 @@ ! CHECK: %[[VAL_9:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_10:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_11:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@iand_i32 %[[VAL_4]]#0 -> %[[VAL_12:.*]] : !fir.ref) for (%[[VAL_13:.*]]) : i32 = (%[[VAL_9]]) to (%[[VAL_10]]) inclusive step (%[[VAL_11]]) { -! CHECK: fir.store %[[VAL_13]] to %[[VAL_8]]#1 : !fir.ref -! CHECK: %[[VAL_14:.*]]:2 = hlfir.declare %[[VAL_12]] {uniq_name = "_QFreduction_iandEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_15:.*]] = fir.load %[[VAL_8]]#0 : !fir.ref -! CHECK: %[[VAL_16:.*]] = fir.convert %[[VAL_15]] : (i32) -> i64 -! CHECK: %[[VAL_17:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_16]]) : (!fir.box>, i64) -> !fir.ref -! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_14]]#0 : !fir.ref -! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_17]] : !fir.ref -! CHECK: %[[VAL_20:.*]] = arith.andi %[[VAL_18]], %[[VAL_19]] : i32 -! CHECK: hlfir.assign %[[VAL_20]] to %[[VAL_14]]#0 : i32, !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop reduction(@iand_i32 %[[VAL_4]]#0 -> %[[VAL_12:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_13:.*]]) : i32 = (%[[VAL_9]]) to (%[[VAL_10]]) inclusive step (%[[VAL_11]]) { +! CHECK: %[[VAL_14:.*]]:2 = hlfir.declare %[[VAL_12]] {uniq_name = "_QFreduction_iandEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: fir.store %[[VAL_13]] to %[[VAL_8]]#1 : !fir.ref +! CHECK: %[[VAL_15:.*]] = fir.load %[[VAL_8]]#0 : !fir.ref +! CHECK: %[[VAL_16:.*]] = fir.convert %[[VAL_15]] : (i32) -> i64 +! CHECK: %[[VAL_17:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_16]]) : (!fir.box>, i64) -> !fir.ref +! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_14]]#0 : !fir.ref +! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_17]] : !fir.ref +! CHECK: %[[VAL_20:.*]] = arith.andi %[[VAL_18]], %[[VAL_19]] : i32 +! CHECK: hlfir.assign %[[VAL_20]] to %[[VAL_14]]#0 : i32, !fir.ref +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator diff --git a/flang/test/Lower/OpenMP/wsloop-reduction-ieor-byref.f90 b/flang/test/Lower/OpenMP/wsloop-reduction-ieor-byref.f90 index 7e3a283bf783c8f436765e317634cbab83aacef5..ee33ce2f348d874adaf52901aa9e99e064dc5370 100644 --- a/flang/test/Lower/OpenMP/wsloop-reduction-ieor-byref.f90 +++ b/flang/test/Lower/OpenMP/wsloop-reduction-ieor-byref.f90 @@ -28,9 +28,10 @@ !CHECK: omp.parallel !CHECK: %[[I_REF:.*]] = fir.alloca i32 {adapt.valuebyref, pinned} !CHECK: %[[I_DECL:.*]]:2 = hlfir.declare %[[I_REF]] {uniq_name = "_QFreduction_ieorEi"} : (!fir.ref) -> (!fir.ref, !fir.ref) -!CHECK: omp.wsloop byref reduction(@ieor_byref_i32 %[[X_DECL]]#0 -> %[[PRV:.+]] : !fir.ref) for -!CHECK: fir.store %{{.*}} to %[[I_DECL]]#1 : !fir.ref +!CHECK: omp.wsloop byref reduction(@ieor_byref_i32 %[[X_DECL]]#0 -> %[[PRV:.+]] : !fir.ref) +!CHECK-NEXT: omp.loop_nest !CHECK: %[[PRV_DECL:.+]]:2 = hlfir.declare %[[PRV]] {{.*}} : (!fir.ref) -> (!fir.ref, !fir.ref) +!CHECK: fir.store %{{.*}} to %[[I_DECL]]#1 : !fir.ref !CHECK: %[[I_32:.*]] = fir.load %[[I_DECL]]#0 : !fir.ref !CHECK: %[[I_64:.*]] = fir.convert %[[I_32]] : (i32) -> i64 !CHECK: %[[Y_I_REF:.*]] = hlfir.designate %[[Y_DECL]]#0 (%[[I_64]]) : (!fir.box>, i64) -> !fir.ref @@ -40,6 +41,7 @@ !CHECK: hlfir.assign %[[RES]] to %[[PRV_DECL]]#0 : i32, !fir.ref !CHECK: omp.yield !CHECK: omp.terminator +!CHECK: omp.terminator subroutine reduction_ieor(y) integer :: x, y(:) diff --git a/flang/test/Lower/OpenMP/wsloop-reduction-ieor.f90 b/flang/test/Lower/OpenMP/wsloop-reduction-ieor.f90 index 11245c4ac95e034bed6488bf7222da9b36fd3973..b362731b33710a86ea764dc6a58c6bc7abde2e9b 100644 --- a/flang/test/Lower/OpenMP/wsloop-reduction-ieor.f90 +++ b/flang/test/Lower/OpenMP/wsloop-reduction-ieor.f90 @@ -19,9 +19,10 @@ !CHECK: omp.parallel !CHECK: %[[I_REF:.*]] = fir.alloca i32 {adapt.valuebyref, pinned} !CHECK: %[[I_DECL:.*]]:2 = hlfir.declare %[[I_REF]] {uniq_name = "_QFreduction_ieorEi"} : (!fir.ref) -> (!fir.ref, !fir.ref) -!CHECK: omp.wsloop reduction(@[[IEOR_DECLARE_I]] %[[X_DECL]]#0 -> %[[PRV:.+]] : !fir.ref) for -!CHECK: fir.store %{{.*}} to %[[I_DECL]]#1 : !fir.ref +!CHECK: omp.wsloop reduction(@[[IEOR_DECLARE_I]] %[[X_DECL]]#0 -> %[[PRV:.+]] : !fir.ref) +!CHECK-NEXT: omp.loop_nest !CHECK: %[[PRV_DECL:.+]]:2 = hlfir.declare %[[PRV]] {{.*}} : (!fir.ref) -> (!fir.ref, !fir.ref) +!CHECK: fir.store %{{.*}} to %[[I_DECL]]#1 : !fir.ref !CHECK: %[[I_32:.*]] = fir.load %[[I_DECL]]#0 : !fir.ref !CHECK: %[[I_64:.*]] = fir.convert %[[I_32]] : (i32) -> i64 !CHECK: %[[Y_I_REF:.*]] = hlfir.designate %[[Y_DECL]]#0 (%[[I_64]]) : (!fir.box>, i64) -> !fir.ref @@ -31,6 +32,7 @@ !CHECK: hlfir.assign %[[RES]] to %[[PRV_DECL]]#0 : i32, !fir.ref !CHECK: omp.yield !CHECK: omp.terminator +!CHECK: omp.terminator subroutine reduction_ieor(y) integer :: x, y(:) diff --git a/flang/test/Lower/OpenMP/wsloop-reduction-ior-byref.f90 b/flang/test/Lower/OpenMP/wsloop-reduction-ior-byref.f90 index c7f8e8bdede5480d45d401dc04e8a3386824a87e..0052773bb5adc61a90a917761a3d9d6a5b8a2831 100644 --- a/flang/test/Lower/OpenMP/wsloop-reduction-ior-byref.f90 +++ b/flang/test/Lower/OpenMP/wsloop-reduction-ior-byref.f90 @@ -33,17 +33,19 @@ ! CHECK: %[[VAL_9:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_10:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_11:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@ior_byref_i32 %[[VAL_4]]#0 -> %[[VAL_12:.*]] : !fir.ref) for (%[[VAL_13:.*]]) : i32 = (%[[VAL_9]]) to (%[[VAL_10]]) inclusive step (%[[VAL_11]]) -! CHECK: fir.store %[[VAL_13]] to %[[VAL_8]]#1 : !fir.ref -! CHECK: %[[VAL_14:.*]]:2 = hlfir.declare %[[VAL_12]] {uniq_name = "_QFreduction_iorEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_15:.*]] = fir.load %[[VAL_8]]#0 : !fir.ref -! CHECK: %[[VAL_16:.*]] = fir.convert %[[VAL_15]] : (i32) -> i64 -! CHECK: %[[VAL_17:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_16]]) : (!fir.box>, i64) -> !fir.ref -! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_14]]#0 : !fir.ref -! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_17]] : !fir.ref -! CHECK: %[[VAL_20:.*]] = arith.ori %[[VAL_18]], %[[VAL_19]] : i32 -! CHECK: hlfir.assign %[[VAL_20]] to %[[VAL_14]]#0 : i32, !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@ior_byref_i32 %[[VAL_4]]#0 -> %[[VAL_12:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_13:.*]]) : i32 = (%[[VAL_9]]) to (%[[VAL_10]]) inclusive step (%[[VAL_11]]) { +! CHECK: %[[VAL_14:.*]]:2 = hlfir.declare %[[VAL_12]] {uniq_name = "_QFreduction_iorEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: fir.store %[[VAL_13]] to %[[VAL_8]]#1 : !fir.ref +! CHECK: %[[VAL_15:.*]] = fir.load %[[VAL_8]]#0 : !fir.ref +! CHECK: %[[VAL_16:.*]] = fir.convert %[[VAL_15]] : (i32) -> i64 +! CHECK: %[[VAL_17:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_16]]) : (!fir.box>, i64) -> !fir.ref +! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_14]]#0 : !fir.ref +! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_17]] : !fir.ref +! CHECK: %[[VAL_20:.*]] = arith.ori %[[VAL_18]], %[[VAL_19]] : i32 +! CHECK: hlfir.assign %[[VAL_20]] to %[[VAL_14]]#0 : i32, !fir.ref +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator diff --git a/flang/test/Lower/OpenMP/wsloop-reduction-ior.f90 b/flang/test/Lower/OpenMP/wsloop-reduction-ior.f90 index dd0bbeb1a0761f097cf5e6916c872b20c5f71374..f32be43b9b71a53a613de2b243b6e804f79732a5 100644 --- a/flang/test/Lower/OpenMP/wsloop-reduction-ior.f90 +++ b/flang/test/Lower/OpenMP/wsloop-reduction-ior.f90 @@ -29,17 +29,19 @@ ! CHECK: %[[VAL_9:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_10:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_11:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@ior_i32 %[[VAL_4]]#0 -> %[[VAL_12:.*]] : !fir.ref) for (%[[VAL_13:.*]]) : i32 = (%[[VAL_9]]) to (%[[VAL_10]]) inclusive step (%[[VAL_11]]) -! CHECK: fir.store %[[VAL_13]] to %[[VAL_8]]#1 : !fir.ref -! CHECK: %[[VAL_14:.*]]:2 = hlfir.declare %[[VAL_12]] {uniq_name = "_QFreduction_iorEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_15:.*]] = fir.load %[[VAL_8]]#0 : !fir.ref -! CHECK: %[[VAL_16:.*]] = fir.convert %[[VAL_15]] : (i32) -> i64 -! CHECK: %[[VAL_17:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_16]]) : (!fir.box>, i64) -> !fir.ref -! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_14]]#0 : !fir.ref -! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_17]] : !fir.ref -! CHECK: %[[VAL_20:.*]] = arith.ori %[[VAL_18]], %[[VAL_19]] : i32 -! CHECK: hlfir.assign %[[VAL_20]] to %[[VAL_14]]#0 : i32, !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop reduction(@ior_i32 %[[VAL_4]]#0 -> %[[VAL_12:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_13:.*]]) : i32 = (%[[VAL_9]]) to (%[[VAL_10]]) inclusive step (%[[VAL_11]]) { +! CHECK: %[[VAL_14:.*]]:2 = hlfir.declare %[[VAL_12]] {uniq_name = "_QFreduction_iorEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: fir.store %[[VAL_13]] to %[[VAL_8]]#1 : !fir.ref +! CHECK: %[[VAL_15:.*]] = fir.load %[[VAL_8]]#0 : !fir.ref +! CHECK: %[[VAL_16:.*]] = fir.convert %[[VAL_15]] : (i32) -> i64 +! CHECK: %[[VAL_17:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_16]]) : (!fir.box>, i64) -> !fir.ref +! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_14]]#0 : !fir.ref +! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_17]] : !fir.ref +! CHECK: %[[VAL_20:.*]] = arith.ori %[[VAL_18]], %[[VAL_19]] : i32 +! CHECK: hlfir.assign %[[VAL_20]] to %[[VAL_14]]#0 : i32, !fir.ref +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator diff --git a/flang/test/Lower/OpenMP/wsloop-reduction-logical-and-byref.f90 b/flang/test/Lower/OpenMP/wsloop-reduction-logical-and-byref.f90 index 59411534e4a5c074a25066a7c67901861c3fc668..dfc018ed7c5aa8a29e5c7ff4c255569af33a7b2f 100644 --- a/flang/test/Lower/OpenMP/wsloop-reduction-logical-and-byref.f90 +++ b/flang/test/Lower/OpenMP/wsloop-reduction-logical-and-byref.f90 @@ -42,20 +42,22 @@ ! CHECK: %[[VAL_12:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_13:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_14:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@and_reduction %[[VAL_4]]#0 -> %[[VAL_15:.*]] : !fir.ref>) for (%[[VAL_16:.*]]) : i32 = (%[[VAL_12]]) to (%[[VAL_13]]) inclusive step (%[[VAL_14]]) { -! CHECK: fir.store %[[VAL_16]] to %[[VAL_11]]#1 : !fir.ref -! CHECK: %[[VAL_17:.*]]:2 = hlfir.declare %[[VAL_15]] {uniq_name = "_QFsimple_reductionEx"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) -! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_17]]#0 : !fir.ref> -! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_11]]#0 : !fir.ref -! CHECK: %[[VAL_20:.*]] = fir.convert %[[VAL_19]] : (i32) -> i64 -! CHECK: %[[VAL_21:.*]] = hlfir.designate %[[VAL_7]]#0 (%[[VAL_20]]) : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_22:.*]] = fir.load %[[VAL_21]] : !fir.ref> -! CHECK: %[[VAL_23:.*]] = fir.convert %[[VAL_18]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_24:.*]] = fir.convert %[[VAL_22]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_25:.*]] = arith.andi %[[VAL_23]], %[[VAL_24]] : i1 -! CHECK: %[[VAL_26:.*]] = fir.convert %[[VAL_25]] : (i1) -> !fir.logical<4> -! CHECK: hlfir.assign %[[VAL_26]] to %[[VAL_17]]#0 : !fir.logical<4>, !fir.ref> -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@and_reduction %[[VAL_4]]#0 -> %[[VAL_15:.*]] : !fir.ref>) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_16:.*]]) : i32 = (%[[VAL_12]]) to (%[[VAL_13]]) inclusive step (%[[VAL_14]]) { +! CHECK: %[[VAL_17:.*]]:2 = hlfir.declare %[[VAL_15]] {uniq_name = "_QFsimple_reductionEx"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) +! CHECK: fir.store %[[VAL_16]] to %[[VAL_11]]#1 : !fir.ref +! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_17]]#0 : !fir.ref> +! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_11]]#0 : !fir.ref +! CHECK: %[[VAL_20:.*]] = fir.convert %[[VAL_19]] : (i32) -> i64 +! CHECK: %[[VAL_21:.*]] = hlfir.designate %[[VAL_7]]#0 (%[[VAL_20]]) : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_22:.*]] = fir.load %[[VAL_21]] : !fir.ref> +! CHECK: %[[VAL_23:.*]] = fir.convert %[[VAL_18]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_24:.*]] = fir.convert %[[VAL_22]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_25:.*]] = arith.andi %[[VAL_23]], %[[VAL_24]] : i1 +! CHECK: %[[VAL_26:.*]] = fir.convert %[[VAL_25]] : (i1) -> !fir.logical<4> +! CHECK: hlfir.assign %[[VAL_26]] to %[[VAL_17]]#0 : !fir.logical<4>, !fir.ref> +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return @@ -90,20 +92,22 @@ end subroutine simple_reduction ! CHECK: %[[VAL_12:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_13:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_14:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@and_reduction %[[VAL_4]]#0 -> %[[VAL_15:.*]] : !fir.ref>) for (%[[VAL_16:.*]]) : i32 = (%[[VAL_12]]) to (%[[VAL_13]]) inclusive step (%[[VAL_14]]) { -! CHECK: fir.store %[[VAL_16]] to %[[VAL_11]]#1 : !fir.ref -! CHECK: %[[VAL_17:.*]]:2 = hlfir.declare %[[VAL_15]] {uniq_name = "_QFsimple_reduction_switch_orderEx"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) -! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_11]]#0 : !fir.ref -! CHECK: %[[VAL_19:.*]] = fir.convert %[[VAL_18]] : (i32) -> i64 -! CHECK: %[[VAL_20:.*]] = hlfir.designate %[[VAL_7]]#0 (%[[VAL_19]]) : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_21:.*]] = fir.load %[[VAL_20]] : !fir.ref> -! CHECK: %[[VAL_22:.*]] = fir.load %[[VAL_17]]#0 : !fir.ref> -! CHECK: %[[VAL_23:.*]] = fir.convert %[[VAL_21]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_24:.*]] = fir.convert %[[VAL_22]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_25:.*]] = arith.andi %[[VAL_23]], %[[VAL_24]] : i1 -! CHECK: %[[VAL_26:.*]] = fir.convert %[[VAL_25]] : (i1) -> !fir.logical<4> -! CHECK: hlfir.assign %[[VAL_26]] to %[[VAL_17]]#0 : !fir.logical<4>, !fir.ref> -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@and_reduction %[[VAL_4]]#0 -> %[[VAL_15:.*]] : !fir.ref>) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_16:.*]]) : i32 = (%[[VAL_12]]) to (%[[VAL_13]]) inclusive step (%[[VAL_14]]) { +! CHECK: %[[VAL_17:.*]]:2 = hlfir.declare %[[VAL_15]] {uniq_name = "_QFsimple_reduction_switch_orderEx"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) +! CHECK: fir.store %[[VAL_16]] to %[[VAL_11]]#1 : !fir.ref +! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_11]]#0 : !fir.ref +! CHECK: %[[VAL_19:.*]] = fir.convert %[[VAL_18]] : (i32) -> i64 +! CHECK: %[[VAL_20:.*]] = hlfir.designate %[[VAL_7]]#0 (%[[VAL_19]]) : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_21:.*]] = fir.load %[[VAL_20]] : !fir.ref> +! CHECK: %[[VAL_22:.*]] = fir.load %[[VAL_17]]#0 : !fir.ref> +! CHECK: %[[VAL_23:.*]] = fir.convert %[[VAL_21]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_24:.*]] = fir.convert %[[VAL_22]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_25:.*]] = arith.andi %[[VAL_23]], %[[VAL_24]] : i1 +! CHECK: %[[VAL_26:.*]] = fir.convert %[[VAL_25]] : (i1) -> !fir.logical<4> +! CHECK: hlfir.assign %[[VAL_26]] to %[[VAL_17]]#0 : !fir.logical<4>, !fir.ref> +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return @@ -147,42 +151,44 @@ end subroutine ! CHECK: %[[VAL_20:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_21:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_22:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@and_reduction %[[VAL_7]]#0 -> %[[VAL_23:.*]] : !fir.ref>, @and_reduction %[[VAL_9]]#0 -> %[[VAL_24:.*]] : !fir.ref>, @and_reduction %[[VAL_11]]#0 -> %[[VAL_25:.*]] : !fir.ref>) for (%[[VAL_26:.*]]) : i32 = (%[[VAL_20]]) to (%[[VAL_21]]) inclusive step (%[[VAL_22]]) { -! CHECK: fir.store %[[VAL_26]] to %[[VAL_19]]#1 : !fir.ref -! CHECK: %[[VAL_27:.*]]:2 = hlfir.declare %[[VAL_23]] {uniq_name = "_QFmultiple_reductionsEx"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) -! CHECK: %[[VAL_28:.*]]:2 = hlfir.declare %[[VAL_24]] {uniq_name = "_QFmultiple_reductionsEy"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) -! CHECK: %[[VAL_29:.*]]:2 = hlfir.declare %[[VAL_25]] {uniq_name = "_QFmultiple_reductionsEz"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) -! CHECK: %[[VAL_30:.*]] = fir.load %[[VAL_27]]#0 : !fir.ref> -! CHECK: %[[VAL_31:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref -! CHECK: %[[VAL_32:.*]] = fir.convert %[[VAL_31]] : (i32) -> i64 -! CHECK: %[[VAL_33:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_32]]) : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_34:.*]] = fir.load %[[VAL_33]] : !fir.ref> -! CHECK: %[[VAL_35:.*]] = fir.convert %[[VAL_30]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_36:.*]] = fir.convert %[[VAL_34]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_37:.*]] = arith.andi %[[VAL_35]], %[[VAL_36]] : i1 -! CHECK: %[[VAL_38:.*]] = fir.convert %[[VAL_37]] : (i1) -> !fir.logical<4> -! CHECK: hlfir.assign %[[VAL_38]] to %[[VAL_27]]#0 : !fir.logical<4>, !fir.ref> -! CHECK: %[[VAL_39:.*]] = fir.load %[[VAL_28]]#0 : !fir.ref> -! CHECK: %[[VAL_40:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref -! CHECK: %[[VAL_41:.*]] = fir.convert %[[VAL_40]] : (i32) -> i64 -! CHECK: %[[VAL_42:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_41]]) : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_43:.*]] = fir.load %[[VAL_42]] : !fir.ref> -! CHECK: %[[VAL_44:.*]] = fir.convert %[[VAL_39]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_45:.*]] = fir.convert %[[VAL_43]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_46:.*]] = arith.andi %[[VAL_44]], %[[VAL_45]] : i1 -! CHECK: %[[VAL_47:.*]] = fir.convert %[[VAL_46]] : (i1) -> !fir.logical<4> -! CHECK: hlfir.assign %[[VAL_47]] to %[[VAL_28]]#0 : !fir.logical<4>, !fir.ref> -! CHECK: %[[VAL_48:.*]] = fir.load %[[VAL_29]]#0 : !fir.ref> -! CHECK: %[[VAL_49:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref -! CHECK: %[[VAL_50:.*]] = fir.convert %[[VAL_49]] : (i32) -> i64 -! CHECK: %[[VAL_51:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_50]]) : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_52:.*]] = fir.load %[[VAL_51]] : !fir.ref> -! CHECK: %[[VAL_53:.*]] = fir.convert %[[VAL_48]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_54:.*]] = fir.convert %[[VAL_52]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_55:.*]] = arith.andi %[[VAL_53]], %[[VAL_54]] : i1 -! CHECK: %[[VAL_56:.*]] = fir.convert %[[VAL_55]] : (i1) -> !fir.logical<4> -! CHECK: hlfir.assign %[[VAL_56]] to %[[VAL_29]]#0 : !fir.logical<4>, !fir.ref> -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@and_reduction %[[VAL_7]]#0 -> %[[VAL_23:.*]] : !fir.ref>, @and_reduction %[[VAL_9]]#0 -> %[[VAL_24:.*]] : !fir.ref>, @and_reduction %[[VAL_11]]#0 -> %[[VAL_25:.*]] : !fir.ref>) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_26:.*]]) : i32 = (%[[VAL_20]]) to (%[[VAL_21]]) inclusive step (%[[VAL_22]]) { +! CHECK: %[[VAL_27:.*]]:2 = hlfir.declare %[[VAL_23]] {uniq_name = "_QFmultiple_reductionsEx"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) +! CHECK: %[[VAL_28:.*]]:2 = hlfir.declare %[[VAL_24]] {uniq_name = "_QFmultiple_reductionsEy"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) +! CHECK: %[[VAL_29:.*]]:2 = hlfir.declare %[[VAL_25]] {uniq_name = "_QFmultiple_reductionsEz"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) +! CHECK: fir.store %[[VAL_26]] to %[[VAL_19]]#1 : !fir.ref +! CHECK: %[[VAL_30:.*]] = fir.load %[[VAL_27]]#0 : !fir.ref> +! CHECK: %[[VAL_31:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref +! CHECK: %[[VAL_32:.*]] = fir.convert %[[VAL_31]] : (i32) -> i64 +! CHECK: %[[VAL_33:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_32]]) : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_34:.*]] = fir.load %[[VAL_33]] : !fir.ref> +! CHECK: %[[VAL_35:.*]] = fir.convert %[[VAL_30]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_36:.*]] = fir.convert %[[VAL_34]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_37:.*]] = arith.andi %[[VAL_35]], %[[VAL_36]] : i1 +! CHECK: %[[VAL_38:.*]] = fir.convert %[[VAL_37]] : (i1) -> !fir.logical<4> +! CHECK: hlfir.assign %[[VAL_38]] to %[[VAL_27]]#0 : !fir.logical<4>, !fir.ref> +! CHECK: %[[VAL_39:.*]] = fir.load %[[VAL_28]]#0 : !fir.ref> +! CHECK: %[[VAL_40:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref +! CHECK: %[[VAL_41:.*]] = fir.convert %[[VAL_40]] : (i32) -> i64 +! CHECK: %[[VAL_42:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_41]]) : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_43:.*]] = fir.load %[[VAL_42]] : !fir.ref> +! CHECK: %[[VAL_44:.*]] = fir.convert %[[VAL_39]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_45:.*]] = fir.convert %[[VAL_43]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_46:.*]] = arith.andi %[[VAL_44]], %[[VAL_45]] : i1 +! CHECK: %[[VAL_47:.*]] = fir.convert %[[VAL_46]] : (i1) -> !fir.logical<4> +! CHECK: hlfir.assign %[[VAL_47]] to %[[VAL_28]]#0 : !fir.logical<4>, !fir.ref> +! CHECK: %[[VAL_48:.*]] = fir.load %[[VAL_29]]#0 : !fir.ref> +! CHECK: %[[VAL_49:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref +! CHECK: %[[VAL_50:.*]] = fir.convert %[[VAL_49]] : (i32) -> i64 +! CHECK: %[[VAL_51:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_50]]) : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_52:.*]] = fir.load %[[VAL_51]] : !fir.ref> +! CHECK: %[[VAL_53:.*]] = fir.convert %[[VAL_48]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_54:.*]] = fir.convert %[[VAL_52]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_55:.*]] = arith.andi %[[VAL_53]], %[[VAL_54]] : i1 +! CHECK: %[[VAL_56:.*]] = fir.convert %[[VAL_55]] : (i1) -> !fir.logical<4> +! CHECK: hlfir.assign %[[VAL_56]] to %[[VAL_29]]#0 : !fir.logical<4>, !fir.ref> +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return diff --git a/flang/test/Lower/OpenMP/wsloop-reduction-logical-and.f90 b/flang/test/Lower/OpenMP/wsloop-reduction-logical-and.f90 index 9ca733281c2f031376b9b2caa3a5945c4f2bcbec..c529bd4755b6c667e173d462c5c024523c387d22 100644 --- a/flang/test/Lower/OpenMP/wsloop-reduction-logical-and.f90 +++ b/flang/test/Lower/OpenMP/wsloop-reduction-logical-and.f90 @@ -36,20 +36,22 @@ ! CHECK: %[[VAL_12:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_13:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_14:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@and_reduction %[[VAL_4]]#0 -> %[[VAL_15:.*]] : !fir.ref>) for (%[[VAL_16:.*]]) : i32 = (%[[VAL_12]]) to (%[[VAL_13]]) inclusive step (%[[VAL_14]]) { -! CHECK: fir.store %[[VAL_16]] to %[[VAL_11]]#1 : !fir.ref -! CHECK: %[[VAL_17:.*]]:2 = hlfir.declare %[[VAL_15]] {uniq_name = "_QFsimple_reductionEx"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) -! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_17]]#0 : !fir.ref> -! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_11]]#0 : !fir.ref -! CHECK: %[[VAL_20:.*]] = fir.convert %[[VAL_19]] : (i32) -> i64 -! CHECK: %[[VAL_21:.*]] = hlfir.designate %[[VAL_7]]#0 (%[[VAL_20]]) : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_22:.*]] = fir.load %[[VAL_21]] : !fir.ref> -! CHECK: %[[VAL_23:.*]] = fir.convert %[[VAL_18]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_24:.*]] = fir.convert %[[VAL_22]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_25:.*]] = arith.andi %[[VAL_23]], %[[VAL_24]] : i1 -! CHECK: %[[VAL_26:.*]] = fir.convert %[[VAL_25]] : (i1) -> !fir.logical<4> -! CHECK: hlfir.assign %[[VAL_26]] to %[[VAL_17]]#0 : !fir.logical<4>, !fir.ref> -! CHECK: omp.yield +! CHECK: omp.wsloop reduction(@and_reduction %[[VAL_4]]#0 -> %[[VAL_15:.*]] : !fir.ref>) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_16:.*]]) : i32 = (%[[VAL_12]]) to (%[[VAL_13]]) inclusive step (%[[VAL_14]]) { +! CHECK: %[[VAL_17:.*]]:2 = hlfir.declare %[[VAL_15]] {uniq_name = "_QFsimple_reductionEx"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) +! CHECK: fir.store %[[VAL_16]] to %[[VAL_11]]#1 : !fir.ref +! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_17]]#0 : !fir.ref> +! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_11]]#0 : !fir.ref +! CHECK: %[[VAL_20:.*]] = fir.convert %[[VAL_19]] : (i32) -> i64 +! CHECK: %[[VAL_21:.*]] = hlfir.designate %[[VAL_7]]#0 (%[[VAL_20]]) : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_22:.*]] = fir.load %[[VAL_21]] : !fir.ref> +! CHECK: %[[VAL_23:.*]] = fir.convert %[[VAL_18]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_24:.*]] = fir.convert %[[VAL_22]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_25:.*]] = arith.andi %[[VAL_23]], %[[VAL_24]] : i1 +! CHECK: %[[VAL_26:.*]] = fir.convert %[[VAL_25]] : (i1) -> !fir.logical<4> +! CHECK: hlfir.assign %[[VAL_26]] to %[[VAL_17]]#0 : !fir.logical<4>, !fir.ref> +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return @@ -84,20 +86,22 @@ end subroutine simple_reduction ! CHECK: %[[VAL_12:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_13:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_14:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@and_reduction %[[VAL_4]]#0 -> %[[VAL_15:.*]] : !fir.ref>) for (%[[VAL_16:.*]]) : i32 = (%[[VAL_12]]) to (%[[VAL_13]]) inclusive step (%[[VAL_14]]) { -! CHECK: fir.store %[[VAL_16]] to %[[VAL_11]]#1 : !fir.ref -! CHECK: %[[VAL_17:.*]]:2 = hlfir.declare %[[VAL_15]] {uniq_name = "_QFsimple_reduction_switch_orderEx"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) -! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_11]]#0 : !fir.ref -! CHECK: %[[VAL_19:.*]] = fir.convert %[[VAL_18]] : (i32) -> i64 -! CHECK: %[[VAL_20:.*]] = hlfir.designate %[[VAL_7]]#0 (%[[VAL_19]]) : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_21:.*]] = fir.load %[[VAL_20]] : !fir.ref> -! CHECK: %[[VAL_22:.*]] = fir.load %[[VAL_17]]#0 : !fir.ref> -! CHECK: %[[VAL_23:.*]] = fir.convert %[[VAL_21]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_24:.*]] = fir.convert %[[VAL_22]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_25:.*]] = arith.andi %[[VAL_23]], %[[VAL_24]] : i1 -! CHECK: %[[VAL_26:.*]] = fir.convert %[[VAL_25]] : (i1) -> !fir.logical<4> -! CHECK: hlfir.assign %[[VAL_26]] to %[[VAL_17]]#0 : !fir.logical<4>, !fir.ref> -! CHECK: omp.yield +! CHECK: omp.wsloop reduction(@and_reduction %[[VAL_4]]#0 -> %[[VAL_15:.*]] : !fir.ref>) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_16:.*]]) : i32 = (%[[VAL_12]]) to (%[[VAL_13]]) inclusive step (%[[VAL_14]]) { +! CHECK: %[[VAL_17:.*]]:2 = hlfir.declare %[[VAL_15]] {uniq_name = "_QFsimple_reduction_switch_orderEx"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) +! CHECK: fir.store %[[VAL_16]] to %[[VAL_11]]#1 : !fir.ref +! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_11]]#0 : !fir.ref +! CHECK: %[[VAL_19:.*]] = fir.convert %[[VAL_18]] : (i32) -> i64 +! CHECK: %[[VAL_20:.*]] = hlfir.designate %[[VAL_7]]#0 (%[[VAL_19]]) : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_21:.*]] = fir.load %[[VAL_20]] : !fir.ref> +! CHECK: %[[VAL_22:.*]] = fir.load %[[VAL_17]]#0 : !fir.ref> +! CHECK: %[[VAL_23:.*]] = fir.convert %[[VAL_21]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_24:.*]] = fir.convert %[[VAL_22]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_25:.*]] = arith.andi %[[VAL_23]], %[[VAL_24]] : i1 +! CHECK: %[[VAL_26:.*]] = fir.convert %[[VAL_25]] : (i1) -> !fir.logical<4> +! CHECK: hlfir.assign %[[VAL_26]] to %[[VAL_17]]#0 : !fir.logical<4>, !fir.ref> +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return @@ -141,42 +145,44 @@ end subroutine ! CHECK: %[[VAL_20:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_21:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_22:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@and_reduction %[[VAL_7]]#0 -> %[[VAL_23:.*]] : !fir.ref>, @and_reduction %[[VAL_9]]#0 -> %[[VAL_24:.*]] : !fir.ref>, @and_reduction %[[VAL_11]]#0 -> %[[VAL_25:.*]] : !fir.ref>) for (%[[VAL_26:.*]]) : i32 = (%[[VAL_20]]) to (%[[VAL_21]]) inclusive step (%[[VAL_22]]) { -! CHECK: fir.store %[[VAL_26]] to %[[VAL_19]]#1 : !fir.ref -! CHECK: %[[VAL_27:.*]]:2 = hlfir.declare %[[VAL_23]] {uniq_name = "_QFmultiple_reductionsEx"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) -! CHECK: %[[VAL_28:.*]]:2 = hlfir.declare %[[VAL_24]] {uniq_name = "_QFmultiple_reductionsEy"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) -! CHECK: %[[VAL_29:.*]]:2 = hlfir.declare %[[VAL_25]] {uniq_name = "_QFmultiple_reductionsEz"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) -! CHECK: %[[VAL_30:.*]] = fir.load %[[VAL_27]]#0 : !fir.ref> -! CHECK: %[[VAL_31:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref -! CHECK: %[[VAL_32:.*]] = fir.convert %[[VAL_31]] : (i32) -> i64 -! CHECK: %[[VAL_33:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_32]]) : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_34:.*]] = fir.load %[[VAL_33]] : !fir.ref> -! CHECK: %[[VAL_35:.*]] = fir.convert %[[VAL_30]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_36:.*]] = fir.convert %[[VAL_34]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_37:.*]] = arith.andi %[[VAL_35]], %[[VAL_36]] : i1 -! CHECK: %[[VAL_38:.*]] = fir.convert %[[VAL_37]] : (i1) -> !fir.logical<4> -! CHECK: hlfir.assign %[[VAL_38]] to %[[VAL_27]]#0 : !fir.logical<4>, !fir.ref> -! CHECK: %[[VAL_39:.*]] = fir.load %[[VAL_28]]#0 : !fir.ref> -! CHECK: %[[VAL_40:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref -! CHECK: %[[VAL_41:.*]] = fir.convert %[[VAL_40]] : (i32) -> i64 -! CHECK: %[[VAL_42:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_41]]) : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_43:.*]] = fir.load %[[VAL_42]] : !fir.ref> -! CHECK: %[[VAL_44:.*]] = fir.convert %[[VAL_39]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_45:.*]] = fir.convert %[[VAL_43]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_46:.*]] = arith.andi %[[VAL_44]], %[[VAL_45]] : i1 -! CHECK: %[[VAL_47:.*]] = fir.convert %[[VAL_46]] : (i1) -> !fir.logical<4> -! CHECK: hlfir.assign %[[VAL_47]] to %[[VAL_28]]#0 : !fir.logical<4>, !fir.ref> -! CHECK: %[[VAL_48:.*]] = fir.load %[[VAL_29]]#0 : !fir.ref> -! CHECK: %[[VAL_49:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref -! CHECK: %[[VAL_50:.*]] = fir.convert %[[VAL_49]] : (i32) -> i64 -! CHECK: %[[VAL_51:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_50]]) : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_52:.*]] = fir.load %[[VAL_51]] : !fir.ref> -! CHECK: %[[VAL_53:.*]] = fir.convert %[[VAL_48]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_54:.*]] = fir.convert %[[VAL_52]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_55:.*]] = arith.andi %[[VAL_53]], %[[VAL_54]] : i1 -! CHECK: %[[VAL_56:.*]] = fir.convert %[[VAL_55]] : (i1) -> !fir.logical<4> -! CHECK: hlfir.assign %[[VAL_56]] to %[[VAL_29]]#0 : !fir.logical<4>, !fir.ref> -! CHECK: omp.yield +! CHECK: omp.wsloop reduction(@and_reduction %[[VAL_7]]#0 -> %[[VAL_23:.*]] : !fir.ref>, @and_reduction %[[VAL_9]]#0 -> %[[VAL_24:.*]] : !fir.ref>, @and_reduction %[[VAL_11]]#0 -> %[[VAL_25:.*]] : !fir.ref>) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_26:.*]]) : i32 = (%[[VAL_20]]) to (%[[VAL_21]]) inclusive step (%[[VAL_22]]) { +! CHECK: %[[VAL_27:.*]]:2 = hlfir.declare %[[VAL_23]] {uniq_name = "_QFmultiple_reductionsEx"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) +! CHECK: %[[VAL_28:.*]]:2 = hlfir.declare %[[VAL_24]] {uniq_name = "_QFmultiple_reductionsEy"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) +! CHECK: %[[VAL_29:.*]]:2 = hlfir.declare %[[VAL_25]] {uniq_name = "_QFmultiple_reductionsEz"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) +! CHECK: fir.store %[[VAL_26]] to %[[VAL_19]]#1 : !fir.ref +! CHECK: %[[VAL_30:.*]] = fir.load %[[VAL_27]]#0 : !fir.ref> +! CHECK: %[[VAL_31:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref +! CHECK: %[[VAL_32:.*]] = fir.convert %[[VAL_31]] : (i32) -> i64 +! CHECK: %[[VAL_33:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_32]]) : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_34:.*]] = fir.load %[[VAL_33]] : !fir.ref> +! CHECK: %[[VAL_35:.*]] = fir.convert %[[VAL_30]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_36:.*]] = fir.convert %[[VAL_34]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_37:.*]] = arith.andi %[[VAL_35]], %[[VAL_36]] : i1 +! CHECK: %[[VAL_38:.*]] = fir.convert %[[VAL_37]] : (i1) -> !fir.logical<4> +! CHECK: hlfir.assign %[[VAL_38]] to %[[VAL_27]]#0 : !fir.logical<4>, !fir.ref> +! CHECK: %[[VAL_39:.*]] = fir.load %[[VAL_28]]#0 : !fir.ref> +! CHECK: %[[VAL_40:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref +! CHECK: %[[VAL_41:.*]] = fir.convert %[[VAL_40]] : (i32) -> i64 +! CHECK: %[[VAL_42:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_41]]) : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_43:.*]] = fir.load %[[VAL_42]] : !fir.ref> +! CHECK: %[[VAL_44:.*]] = fir.convert %[[VAL_39]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_45:.*]] = fir.convert %[[VAL_43]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_46:.*]] = arith.andi %[[VAL_44]], %[[VAL_45]] : i1 +! CHECK: %[[VAL_47:.*]] = fir.convert %[[VAL_46]] : (i1) -> !fir.logical<4> +! CHECK: hlfir.assign %[[VAL_47]] to %[[VAL_28]]#0 : !fir.logical<4>, !fir.ref> +! CHECK: %[[VAL_48:.*]] = fir.load %[[VAL_29]]#0 : !fir.ref> +! CHECK: %[[VAL_49:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref +! CHECK: %[[VAL_50:.*]] = fir.convert %[[VAL_49]] : (i32) -> i64 +! CHECK: %[[VAL_51:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_50]]) : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_52:.*]] = fir.load %[[VAL_51]] : !fir.ref> +! CHECK: %[[VAL_53:.*]] = fir.convert %[[VAL_48]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_54:.*]] = fir.convert %[[VAL_52]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_55:.*]] = arith.andi %[[VAL_53]], %[[VAL_54]] : i1 +! CHECK: %[[VAL_56:.*]] = fir.convert %[[VAL_55]] : (i1) -> !fir.logical<4> +! CHECK: hlfir.assign %[[VAL_56]] to %[[VAL_29]]#0 : !fir.logical<4>, !fir.ref> +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return diff --git a/flang/test/Lower/OpenMP/wsloop-reduction-logical-eqv-byref.f90 b/flang/test/Lower/OpenMP/wsloop-reduction-logical-eqv-byref.f90 index 1d6e1b0545c3bcffb96d7d47697d39b55d6e2845..a54795a4446f4719ad9c6095aa2814e21321ad48 100644 --- a/flang/test/Lower/OpenMP/wsloop-reduction-logical-eqv-byref.f90 +++ b/flang/test/Lower/OpenMP/wsloop-reduction-logical-eqv-byref.f90 @@ -42,20 +42,22 @@ ! CHECK: %[[VAL_12:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_13:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_14:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@eqv_reduction %[[VAL_4]]#0 -> %[[VAL_15:.*]] : !fir.ref>) for (%[[VAL_16:.*]]) : i32 = (%[[VAL_12]]) to (%[[VAL_13]]) inclusive step (%[[VAL_14]]) { -! CHECK: fir.store %[[VAL_16]] to %[[VAL_11]]#1 : !fir.ref -! CHECK: %[[VAL_17:.*]]:2 = hlfir.declare %[[VAL_15]] {uniq_name = "_QFsimple_reductionEx"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) -! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_17]]#0 : !fir.ref> -! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_11]]#0 : !fir.ref -! CHECK: %[[VAL_20:.*]] = fir.convert %[[VAL_19]] : (i32) -> i64 -! CHECK: %[[VAL_21:.*]] = hlfir.designate %[[VAL_7]]#0 (%[[VAL_20]]) : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_22:.*]] = fir.load %[[VAL_21]] : !fir.ref> -! CHECK: %[[VAL_23:.*]] = fir.convert %[[VAL_18]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_24:.*]] = fir.convert %[[VAL_22]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_25:.*]] = arith.cmpi eq, %[[VAL_23]], %[[VAL_24]] : i1 -! CHECK: %[[VAL_26:.*]] = fir.convert %[[VAL_25]] : (i1) -> !fir.logical<4> -! CHECK: hlfir.assign %[[VAL_26]] to %[[VAL_17]]#0 : !fir.logical<4>, !fir.ref> -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@eqv_reduction %[[VAL_4]]#0 -> %[[VAL_15:.*]] : !fir.ref>) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_16:.*]]) : i32 = (%[[VAL_12]]) to (%[[VAL_13]]) inclusive step (%[[VAL_14]]) { +! CHECK: %[[VAL_17:.*]]:2 = hlfir.declare %[[VAL_15]] {uniq_name = "_QFsimple_reductionEx"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) +! CHECK: fir.store %[[VAL_16]] to %[[VAL_11]]#1 : !fir.ref +! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_17]]#0 : !fir.ref> +! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_11]]#0 : !fir.ref +! CHECK: %[[VAL_20:.*]] = fir.convert %[[VAL_19]] : (i32) -> i64 +! CHECK: %[[VAL_21:.*]] = hlfir.designate %[[VAL_7]]#0 (%[[VAL_20]]) : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_22:.*]] = fir.load %[[VAL_21]] : !fir.ref> +! CHECK: %[[VAL_23:.*]] = fir.convert %[[VAL_18]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_24:.*]] = fir.convert %[[VAL_22]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_25:.*]] = arith.cmpi eq, %[[VAL_23]], %[[VAL_24]] : i1 +! CHECK: %[[VAL_26:.*]] = fir.convert %[[VAL_25]] : (i1) -> !fir.logical<4> +! CHECK: hlfir.assign %[[VAL_26]] to %[[VAL_17]]#0 : !fir.logical<4>, !fir.ref> +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return @@ -89,20 +91,22 @@ end subroutine ! CHECK: %[[VAL_12:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_13:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_14:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@eqv_reduction %[[VAL_4]]#0 -> %[[VAL_15:.*]] : !fir.ref>) for (%[[VAL_16:.*]]) : i32 = (%[[VAL_12]]) to (%[[VAL_13]]) inclusive step (%[[VAL_14]]) { -! CHECK: fir.store %[[VAL_16]] to %[[VAL_11]]#1 : !fir.ref -! CHECK: %[[VAL_17:.*]]:2 = hlfir.declare %[[VAL_15]] {uniq_name = "_QFsimple_reduction_switch_orderEx"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) -! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_11]]#0 : !fir.ref -! CHECK: %[[VAL_19:.*]] = fir.convert %[[VAL_18]] : (i32) -> i64 -! CHECK: %[[VAL_20:.*]] = hlfir.designate %[[VAL_7]]#0 (%[[VAL_19]]) : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_21:.*]] = fir.load %[[VAL_20]] : !fir.ref> -! CHECK: %[[VAL_22:.*]] = fir.load %[[VAL_17]]#0 : !fir.ref> -! CHECK: %[[VAL_23:.*]] = fir.convert %[[VAL_21]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_24:.*]] = fir.convert %[[VAL_22]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_25:.*]] = arith.cmpi eq, %[[VAL_23]], %[[VAL_24]] : i1 -! CHECK: %[[VAL_26:.*]] = fir.convert %[[VAL_25]] : (i1) -> !fir.logical<4> -! CHECK: hlfir.assign %[[VAL_26]] to %[[VAL_17]]#0 : !fir.logical<4>, !fir.ref> -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@eqv_reduction %[[VAL_4]]#0 -> %[[VAL_15:.*]] : !fir.ref>) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_16:.*]]) : i32 = (%[[VAL_12]]) to (%[[VAL_13]]) inclusive step (%[[VAL_14]]) { +! CHECK: %[[VAL_17:.*]]:2 = hlfir.declare %[[VAL_15]] {uniq_name = "_QFsimple_reduction_switch_orderEx"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) +! CHECK: fir.store %[[VAL_16]] to %[[VAL_11]]#1 : !fir.ref +! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_11]]#0 : !fir.ref +! CHECK: %[[VAL_19:.*]] = fir.convert %[[VAL_18]] : (i32) -> i64 +! CHECK: %[[VAL_20:.*]] = hlfir.designate %[[VAL_7]]#0 (%[[VAL_19]]) : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_21:.*]] = fir.load %[[VAL_20]] : !fir.ref> +! CHECK: %[[VAL_22:.*]] = fir.load %[[VAL_17]]#0 : !fir.ref> +! CHECK: %[[VAL_23:.*]] = fir.convert %[[VAL_21]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_24:.*]] = fir.convert %[[VAL_22]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_25:.*]] = arith.cmpi eq, %[[VAL_23]], %[[VAL_24]] : i1 +! CHECK: %[[VAL_26:.*]] = fir.convert %[[VAL_25]] : (i1) -> !fir.logical<4> +! CHECK: hlfir.assign %[[VAL_26]] to %[[VAL_17]]#0 : !fir.logical<4>, !fir.ref> +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return @@ -146,42 +150,44 @@ end subroutine ! CHECK: %[[VAL_20:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_21:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_22:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@eqv_reduction %[[VAL_7]]#0 -> %[[VAL_23:.*]] : !fir.ref>, @eqv_reduction %[[VAL_9]]#0 -> %[[VAL_24:.*]] : !fir.ref>, @eqv_reduction %[[VAL_11]]#0 -> %[[VAL_25:.*]] : !fir.ref>) for (%[[VAL_26:.*]]) : i32 = (%[[VAL_20]]) to (%[[VAL_21]]) inclusive step (%[[VAL_22]]) { -! CHECK: fir.store %[[VAL_26]] to %[[VAL_19]]#1 : !fir.ref -! CHECK: %[[VAL_27:.*]]:2 = hlfir.declare %[[VAL_23]] {uniq_name = "_QFmultiple_reductionsEx"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) -! CHECK: %[[VAL_28:.*]]:2 = hlfir.declare %[[VAL_24]] {uniq_name = "_QFmultiple_reductionsEy"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) -! CHECK: %[[VAL_29:.*]]:2 = hlfir.declare %[[VAL_25]] {uniq_name = "_QFmultiple_reductionsEz"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) -! CHECK: %[[VAL_30:.*]] = fir.load %[[VAL_27]]#0 : !fir.ref> -! CHECK: %[[VAL_31:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref -! CHECK: %[[VAL_32:.*]] = fir.convert %[[VAL_31]] : (i32) -> i64 -! CHECK: %[[VAL_33:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_32]]) : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_34:.*]] = fir.load %[[VAL_33]] : !fir.ref> -! CHECK: %[[VAL_35:.*]] = fir.convert %[[VAL_30]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_36:.*]] = fir.convert %[[VAL_34]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_37:.*]] = arith.cmpi eq, %[[VAL_35]], %[[VAL_36]] : i1 -! CHECK: %[[VAL_38:.*]] = fir.convert %[[VAL_37]] : (i1) -> !fir.logical<4> -! CHECK: hlfir.assign %[[VAL_38]] to %[[VAL_27]]#0 : !fir.logical<4>, !fir.ref> -! CHECK: %[[VAL_39:.*]] = fir.load %[[VAL_28]]#0 : !fir.ref> -! CHECK: %[[VAL_40:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref -! CHECK: %[[VAL_41:.*]] = fir.convert %[[VAL_40]] : (i32) -> i64 -! CHECK: %[[VAL_42:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_41]]) : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_43:.*]] = fir.load %[[VAL_42]] : !fir.ref> -! CHECK: %[[VAL_44:.*]] = fir.convert %[[VAL_39]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_45:.*]] = fir.convert %[[VAL_43]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_46:.*]] = arith.cmpi eq, %[[VAL_44]], %[[VAL_45]] : i1 -! CHECK: %[[VAL_47:.*]] = fir.convert %[[VAL_46]] : (i1) -> !fir.logical<4> -! CHECK: hlfir.assign %[[VAL_47]] to %[[VAL_28]]#0 : !fir.logical<4>, !fir.ref> -! CHECK: %[[VAL_48:.*]] = fir.load %[[VAL_29]]#0 : !fir.ref> -! CHECK: %[[VAL_49:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref -! CHECK: %[[VAL_50:.*]] = fir.convert %[[VAL_49]] : (i32) -> i64 -! CHECK: %[[VAL_51:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_50]]) : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_52:.*]] = fir.load %[[VAL_51]] : !fir.ref> -! CHECK: %[[VAL_53:.*]] = fir.convert %[[VAL_48]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_54:.*]] = fir.convert %[[VAL_52]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_55:.*]] = arith.cmpi eq, %[[VAL_53]], %[[VAL_54]] : i1 -! CHECK: %[[VAL_56:.*]] = fir.convert %[[VAL_55]] : (i1) -> !fir.logical<4> -! CHECK: hlfir.assign %[[VAL_56]] to %[[VAL_29]]#0 : !fir.logical<4>, !fir.ref> -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@eqv_reduction %[[VAL_7]]#0 -> %[[VAL_23:.*]] : !fir.ref>, @eqv_reduction %[[VAL_9]]#0 -> %[[VAL_24:.*]] : !fir.ref>, @eqv_reduction %[[VAL_11]]#0 -> %[[VAL_25:.*]] : !fir.ref>) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_26:.*]]) : i32 = (%[[VAL_20]]) to (%[[VAL_21]]) inclusive step (%[[VAL_22]]) { +! CHECK: %[[VAL_27:.*]]:2 = hlfir.declare %[[VAL_23]] {uniq_name = "_QFmultiple_reductionsEx"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) +! CHECK: %[[VAL_28:.*]]:2 = hlfir.declare %[[VAL_24]] {uniq_name = "_QFmultiple_reductionsEy"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) +! CHECK: %[[VAL_29:.*]]:2 = hlfir.declare %[[VAL_25]] {uniq_name = "_QFmultiple_reductionsEz"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) +! CHECK: fir.store %[[VAL_26]] to %[[VAL_19]]#1 : !fir.ref +! CHECK: %[[VAL_30:.*]] = fir.load %[[VAL_27]]#0 : !fir.ref> +! CHECK: %[[VAL_31:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref +! CHECK: %[[VAL_32:.*]] = fir.convert %[[VAL_31]] : (i32) -> i64 +! CHECK: %[[VAL_33:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_32]]) : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_34:.*]] = fir.load %[[VAL_33]] : !fir.ref> +! CHECK: %[[VAL_35:.*]] = fir.convert %[[VAL_30]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_36:.*]] = fir.convert %[[VAL_34]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_37:.*]] = arith.cmpi eq, %[[VAL_35]], %[[VAL_36]] : i1 +! CHECK: %[[VAL_38:.*]] = fir.convert %[[VAL_37]] : (i1) -> !fir.logical<4> +! CHECK: hlfir.assign %[[VAL_38]] to %[[VAL_27]]#0 : !fir.logical<4>, !fir.ref> +! CHECK: %[[VAL_39:.*]] = fir.load %[[VAL_28]]#0 : !fir.ref> +! CHECK: %[[VAL_40:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref +! CHECK: %[[VAL_41:.*]] = fir.convert %[[VAL_40]] : (i32) -> i64 +! CHECK: %[[VAL_42:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_41]]) : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_43:.*]] = fir.load %[[VAL_42]] : !fir.ref> +! CHECK: %[[VAL_44:.*]] = fir.convert %[[VAL_39]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_45:.*]] = fir.convert %[[VAL_43]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_46:.*]] = arith.cmpi eq, %[[VAL_44]], %[[VAL_45]] : i1 +! CHECK: %[[VAL_47:.*]] = fir.convert %[[VAL_46]] : (i1) -> !fir.logical<4> +! CHECK: hlfir.assign %[[VAL_47]] to %[[VAL_28]]#0 : !fir.logical<4>, !fir.ref> +! CHECK: %[[VAL_48:.*]] = fir.load %[[VAL_29]]#0 : !fir.ref> +! CHECK: %[[VAL_49:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref +! CHECK: %[[VAL_50:.*]] = fir.convert %[[VAL_49]] : (i32) -> i64 +! CHECK: %[[VAL_51:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_50]]) : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_52:.*]] = fir.load %[[VAL_51]] : !fir.ref> +! CHECK: %[[VAL_53:.*]] = fir.convert %[[VAL_48]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_54:.*]] = fir.convert %[[VAL_52]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_55:.*]] = arith.cmpi eq, %[[VAL_53]], %[[VAL_54]] : i1 +! CHECK: %[[VAL_56:.*]] = fir.convert %[[VAL_55]] : (i1) -> !fir.logical<4> +! CHECK: hlfir.assign %[[VAL_56]] to %[[VAL_29]]#0 : !fir.logical<4>, !fir.ref> +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return diff --git a/flang/test/Lower/OpenMP/wsloop-reduction-logical-eqv.f90 b/flang/test/Lower/OpenMP/wsloop-reduction-logical-eqv.f90 index a1bfa462cd599ae4171e96b0c00ed37f0a384f40..1021b5926b9179866b244c0e8fdc45ff7be1e996 100644 --- a/flang/test/Lower/OpenMP/wsloop-reduction-logical-eqv.f90 +++ b/flang/test/Lower/OpenMP/wsloop-reduction-logical-eqv.f90 @@ -36,20 +36,22 @@ ! CHECK: %[[VAL_12:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_13:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_14:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@eqv_reduction %[[VAL_4]]#0 -> %[[VAL_15:.*]] : !fir.ref>) for (%[[VAL_16:.*]]) : i32 = (%[[VAL_12]]) to (%[[VAL_13]]) inclusive step (%[[VAL_14]]) { -! CHECK: fir.store %[[VAL_16]] to %[[VAL_11]]#1 : !fir.ref -! CHECK: %[[VAL_17:.*]]:2 = hlfir.declare %[[VAL_15]] {uniq_name = "_QFsimple_reductionEx"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) -! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_17]]#0 : !fir.ref> -! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_11]]#0 : !fir.ref -! CHECK: %[[VAL_20:.*]] = fir.convert %[[VAL_19]] : (i32) -> i64 -! CHECK: %[[VAL_21:.*]] = hlfir.designate %[[VAL_7]]#0 (%[[VAL_20]]) : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_22:.*]] = fir.load %[[VAL_21]] : !fir.ref> -! CHECK: %[[VAL_23:.*]] = fir.convert %[[VAL_18]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_24:.*]] = fir.convert %[[VAL_22]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_25:.*]] = arith.cmpi eq, %[[VAL_23]], %[[VAL_24]] : i1 -! CHECK: %[[VAL_26:.*]] = fir.convert %[[VAL_25]] : (i1) -> !fir.logical<4> -! CHECK: hlfir.assign %[[VAL_26]] to %[[VAL_17]]#0 : !fir.logical<4>, !fir.ref> -! CHECK: omp.yield +! CHECK: omp.wsloop reduction(@eqv_reduction %[[VAL_4]]#0 -> %[[VAL_15:.*]] : !fir.ref>) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_16:.*]]) : i32 = (%[[VAL_12]]) to (%[[VAL_13]]) inclusive step (%[[VAL_14]]) { +! CHECK: %[[VAL_17:.*]]:2 = hlfir.declare %[[VAL_15]] {uniq_name = "_QFsimple_reductionEx"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) +! CHECK: fir.store %[[VAL_16]] to %[[VAL_11]]#1 : !fir.ref +! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_17]]#0 : !fir.ref> +! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_11]]#0 : !fir.ref +! CHECK: %[[VAL_20:.*]] = fir.convert %[[VAL_19]] : (i32) -> i64 +! CHECK: %[[VAL_21:.*]] = hlfir.designate %[[VAL_7]]#0 (%[[VAL_20]]) : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_22:.*]] = fir.load %[[VAL_21]] : !fir.ref> +! CHECK: %[[VAL_23:.*]] = fir.convert %[[VAL_18]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_24:.*]] = fir.convert %[[VAL_22]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_25:.*]] = arith.cmpi eq, %[[VAL_23]], %[[VAL_24]] : i1 +! CHECK: %[[VAL_26:.*]] = fir.convert %[[VAL_25]] : (i1) -> !fir.logical<4> +! CHECK: hlfir.assign %[[VAL_26]] to %[[VAL_17]]#0 : !fir.logical<4>, !fir.ref> +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return @@ -83,20 +85,22 @@ end subroutine ! CHECK: %[[VAL_12:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_13:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_14:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@eqv_reduction %[[VAL_4]]#0 -> %[[VAL_15:.*]] : !fir.ref>) for (%[[VAL_16:.*]]) : i32 = (%[[VAL_12]]) to (%[[VAL_13]]) inclusive step (%[[VAL_14]]) { -! CHECK: fir.store %[[VAL_16]] to %[[VAL_11]]#1 : !fir.ref -! CHECK: %[[VAL_17:.*]]:2 = hlfir.declare %[[VAL_15]] {uniq_name = "_QFsimple_reduction_switch_orderEx"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) -! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_11]]#0 : !fir.ref -! CHECK: %[[VAL_19:.*]] = fir.convert %[[VAL_18]] : (i32) -> i64 -! CHECK: %[[VAL_20:.*]] = hlfir.designate %[[VAL_7]]#0 (%[[VAL_19]]) : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_21:.*]] = fir.load %[[VAL_20]] : !fir.ref> -! CHECK: %[[VAL_22:.*]] = fir.load %[[VAL_17]]#0 : !fir.ref> -! CHECK: %[[VAL_23:.*]] = fir.convert %[[VAL_21]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_24:.*]] = fir.convert %[[VAL_22]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_25:.*]] = arith.cmpi eq, %[[VAL_23]], %[[VAL_24]] : i1 -! CHECK: %[[VAL_26:.*]] = fir.convert %[[VAL_25]] : (i1) -> !fir.logical<4> -! CHECK: hlfir.assign %[[VAL_26]] to %[[VAL_17]]#0 : !fir.logical<4>, !fir.ref> -! CHECK: omp.yield +! CHECK: omp.wsloop reduction(@eqv_reduction %[[VAL_4]]#0 -> %[[VAL_15:.*]] : !fir.ref>) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_16:.*]]) : i32 = (%[[VAL_12]]) to (%[[VAL_13]]) inclusive step (%[[VAL_14]]) { +! CHECK: %[[VAL_17:.*]]:2 = hlfir.declare %[[VAL_15]] {uniq_name = "_QFsimple_reduction_switch_orderEx"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) +! CHECK: fir.store %[[VAL_16]] to %[[VAL_11]]#1 : !fir.ref +! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_11]]#0 : !fir.ref +! CHECK: %[[VAL_19:.*]] = fir.convert %[[VAL_18]] : (i32) -> i64 +! CHECK: %[[VAL_20:.*]] = hlfir.designate %[[VAL_7]]#0 (%[[VAL_19]]) : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_21:.*]] = fir.load %[[VAL_20]] : !fir.ref> +! CHECK: %[[VAL_22:.*]] = fir.load %[[VAL_17]]#0 : !fir.ref> +! CHECK: %[[VAL_23:.*]] = fir.convert %[[VAL_21]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_24:.*]] = fir.convert %[[VAL_22]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_25:.*]] = arith.cmpi eq, %[[VAL_23]], %[[VAL_24]] : i1 +! CHECK: %[[VAL_26:.*]] = fir.convert %[[VAL_25]] : (i1) -> !fir.logical<4> +! CHECK: hlfir.assign %[[VAL_26]] to %[[VAL_17]]#0 : !fir.logical<4>, !fir.ref> +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return @@ -140,42 +144,44 @@ end subroutine ! CHECK: %[[VAL_20:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_21:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_22:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@eqv_reduction %[[VAL_7]]#0 -> %[[VAL_23:.*]] : !fir.ref>, @eqv_reduction %[[VAL_9]]#0 -> %[[VAL_24:.*]] : !fir.ref>, @eqv_reduction %[[VAL_11]]#0 -> %[[VAL_25:.*]] : !fir.ref>) for (%[[VAL_26:.*]]) : i32 = (%[[VAL_20]]) to (%[[VAL_21]]) inclusive step (%[[VAL_22]]) { -! CHECK: fir.store %[[VAL_26]] to %[[VAL_19]]#1 : !fir.ref -! CHECK: %[[VAL_27:.*]]:2 = hlfir.declare %[[VAL_23]] {uniq_name = "_QFmultiple_reductionsEx"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) -! CHECK: %[[VAL_28:.*]]:2 = hlfir.declare %[[VAL_24]] {uniq_name = "_QFmultiple_reductionsEy"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) -! CHECK: %[[VAL_29:.*]]:2 = hlfir.declare %[[VAL_25]] {uniq_name = "_QFmultiple_reductionsEz"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) -! CHECK: %[[VAL_30:.*]] = fir.load %[[VAL_27]]#0 : !fir.ref> -! CHECK: %[[VAL_31:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref -! CHECK: %[[VAL_32:.*]] = fir.convert %[[VAL_31]] : (i32) -> i64 -! CHECK: %[[VAL_33:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_32]]) : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_34:.*]] = fir.load %[[VAL_33]] : !fir.ref> -! CHECK: %[[VAL_35:.*]] = fir.convert %[[VAL_30]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_36:.*]] = fir.convert %[[VAL_34]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_37:.*]] = arith.cmpi eq, %[[VAL_35]], %[[VAL_36]] : i1 -! CHECK: %[[VAL_38:.*]] = fir.convert %[[VAL_37]] : (i1) -> !fir.logical<4> -! CHECK: hlfir.assign %[[VAL_38]] to %[[VAL_27]]#0 : !fir.logical<4>, !fir.ref> -! CHECK: %[[VAL_39:.*]] = fir.load %[[VAL_28]]#0 : !fir.ref> -! CHECK: %[[VAL_40:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref -! CHECK: %[[VAL_41:.*]] = fir.convert %[[VAL_40]] : (i32) -> i64 -! CHECK: %[[VAL_42:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_41]]) : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_43:.*]] = fir.load %[[VAL_42]] : !fir.ref> -! CHECK: %[[VAL_44:.*]] = fir.convert %[[VAL_39]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_45:.*]] = fir.convert %[[VAL_43]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_46:.*]] = arith.cmpi eq, %[[VAL_44]], %[[VAL_45]] : i1 -! CHECK: %[[VAL_47:.*]] = fir.convert %[[VAL_46]] : (i1) -> !fir.logical<4> -! CHECK: hlfir.assign %[[VAL_47]] to %[[VAL_28]]#0 : !fir.logical<4>, !fir.ref> -! CHECK: %[[VAL_48:.*]] = fir.load %[[VAL_29]]#0 : !fir.ref> -! CHECK: %[[VAL_49:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref -! CHECK: %[[VAL_50:.*]] = fir.convert %[[VAL_49]] : (i32) -> i64 -! CHECK: %[[VAL_51:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_50]]) : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_52:.*]] = fir.load %[[VAL_51]] : !fir.ref> -! CHECK: %[[VAL_53:.*]] = fir.convert %[[VAL_48]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_54:.*]] = fir.convert %[[VAL_52]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_55:.*]] = arith.cmpi eq, %[[VAL_53]], %[[VAL_54]] : i1 -! CHECK: %[[VAL_56:.*]] = fir.convert %[[VAL_55]] : (i1) -> !fir.logical<4> -! CHECK: hlfir.assign %[[VAL_56]] to %[[VAL_29]]#0 : !fir.logical<4>, !fir.ref> -! CHECK: omp.yield +! CHECK: omp.wsloop reduction(@eqv_reduction %[[VAL_7]]#0 -> %[[VAL_23:.*]] : !fir.ref>, @eqv_reduction %[[VAL_9]]#0 -> %[[VAL_24:.*]] : !fir.ref>, @eqv_reduction %[[VAL_11]]#0 -> %[[VAL_25:.*]] : !fir.ref>) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_26:.*]]) : i32 = (%[[VAL_20]]) to (%[[VAL_21]]) inclusive step (%[[VAL_22]]) { +! CHECK: %[[VAL_27:.*]]:2 = hlfir.declare %[[VAL_23]] {uniq_name = "_QFmultiple_reductionsEx"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) +! CHECK: %[[VAL_28:.*]]:2 = hlfir.declare %[[VAL_24]] {uniq_name = "_QFmultiple_reductionsEy"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) +! CHECK: %[[VAL_29:.*]]:2 = hlfir.declare %[[VAL_25]] {uniq_name = "_QFmultiple_reductionsEz"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) +! CHECK: fir.store %[[VAL_26]] to %[[VAL_19]]#1 : !fir.ref +! CHECK: %[[VAL_30:.*]] = fir.load %[[VAL_27]]#0 : !fir.ref> +! CHECK: %[[VAL_31:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref +! CHECK: %[[VAL_32:.*]] = fir.convert %[[VAL_31]] : (i32) -> i64 +! CHECK: %[[VAL_33:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_32]]) : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_34:.*]] = fir.load %[[VAL_33]] : !fir.ref> +! CHECK: %[[VAL_35:.*]] = fir.convert %[[VAL_30]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_36:.*]] = fir.convert %[[VAL_34]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_37:.*]] = arith.cmpi eq, %[[VAL_35]], %[[VAL_36]] : i1 +! CHECK: %[[VAL_38:.*]] = fir.convert %[[VAL_37]] : (i1) -> !fir.logical<4> +! CHECK: hlfir.assign %[[VAL_38]] to %[[VAL_27]]#0 : !fir.logical<4>, !fir.ref> +! CHECK: %[[VAL_39:.*]] = fir.load %[[VAL_28]]#0 : !fir.ref> +! CHECK: %[[VAL_40:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref +! CHECK: %[[VAL_41:.*]] = fir.convert %[[VAL_40]] : (i32) -> i64 +! CHECK: %[[VAL_42:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_41]]) : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_43:.*]] = fir.load %[[VAL_42]] : !fir.ref> +! CHECK: %[[VAL_44:.*]] = fir.convert %[[VAL_39]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_45:.*]] = fir.convert %[[VAL_43]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_46:.*]] = arith.cmpi eq, %[[VAL_44]], %[[VAL_45]] : i1 +! CHECK: %[[VAL_47:.*]] = fir.convert %[[VAL_46]] : (i1) -> !fir.logical<4> +! CHECK: hlfir.assign %[[VAL_47]] to %[[VAL_28]]#0 : !fir.logical<4>, !fir.ref> +! CHECK: %[[VAL_48:.*]] = fir.load %[[VAL_29]]#0 : !fir.ref> +! CHECK: %[[VAL_49:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref +! CHECK: %[[VAL_50:.*]] = fir.convert %[[VAL_49]] : (i32) -> i64 +! CHECK: %[[VAL_51:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_50]]) : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_52:.*]] = fir.load %[[VAL_51]] : !fir.ref> +! CHECK: %[[VAL_53:.*]] = fir.convert %[[VAL_48]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_54:.*]] = fir.convert %[[VAL_52]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_55:.*]] = arith.cmpi eq, %[[VAL_53]], %[[VAL_54]] : i1 +! CHECK: %[[VAL_56:.*]] = fir.convert %[[VAL_55]] : (i1) -> !fir.logical<4> +! CHECK: hlfir.assign %[[VAL_56]] to %[[VAL_29]]#0 : !fir.logical<4>, !fir.ref> +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return diff --git a/flang/test/Lower/OpenMP/wsloop-reduction-logical-neqv-byref.f90 b/flang/test/Lower/OpenMP/wsloop-reduction-logical-neqv-byref.f90 index a94b67a97832fc5aee066c09a4f84e1151c8aa9c..854cb19ecd750ce053e8d8053f788f7c7dca8fc6 100644 --- a/flang/test/Lower/OpenMP/wsloop-reduction-logical-neqv-byref.f90 +++ b/flang/test/Lower/OpenMP/wsloop-reduction-logical-neqv-byref.f90 @@ -42,20 +42,22 @@ ! CHECK: %[[VAL_12:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_13:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_14:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@neqv_reduction %[[VAL_4]]#0 -> %[[VAL_15:.*]] : !fir.ref>) for (%[[VAL_16:.*]]) : i32 = (%[[VAL_12]]) to (%[[VAL_13]]) inclusive step (%[[VAL_14]]) { -! CHECK: fir.store %[[VAL_16]] to %[[VAL_11]]#1 : !fir.ref -! CHECK: %[[VAL_17:.*]]:2 = hlfir.declare %[[VAL_15]] {uniq_name = "_QFsimple_reductionEx"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) -! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_17]]#0 : !fir.ref> -! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_11]]#0 : !fir.ref -! CHECK: %[[VAL_20:.*]] = fir.convert %[[VAL_19]] : (i32) -> i64 -! CHECK: %[[VAL_21:.*]] = hlfir.designate %[[VAL_7]]#0 (%[[VAL_20]]) : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_22:.*]] = fir.load %[[VAL_21]] : !fir.ref> -! CHECK: %[[VAL_23:.*]] = fir.convert %[[VAL_18]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_24:.*]] = fir.convert %[[VAL_22]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_25:.*]] = arith.cmpi ne, %[[VAL_23]], %[[VAL_24]] : i1 -! CHECK: %[[VAL_26:.*]] = fir.convert %[[VAL_25]] : (i1) -> !fir.logical<4> -! CHECK: hlfir.assign %[[VAL_26]] to %[[VAL_17]]#0 : !fir.logical<4>, !fir.ref> -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@neqv_reduction %[[VAL_4]]#0 -> %[[VAL_15:.*]] : !fir.ref>) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_16:.*]]) : i32 = (%[[VAL_12]]) to (%[[VAL_13]]) inclusive step (%[[VAL_14]]) { +! CHECK: %[[VAL_17:.*]]:2 = hlfir.declare %[[VAL_15]] {uniq_name = "_QFsimple_reductionEx"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) +! CHECK: fir.store %[[VAL_16]] to %[[VAL_11]]#1 : !fir.ref +! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_17]]#0 : !fir.ref> +! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_11]]#0 : !fir.ref +! CHECK: %[[VAL_20:.*]] = fir.convert %[[VAL_19]] : (i32) -> i64 +! CHECK: %[[VAL_21:.*]] = hlfir.designate %[[VAL_7]]#0 (%[[VAL_20]]) : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_22:.*]] = fir.load %[[VAL_21]] : !fir.ref> +! CHECK: %[[VAL_23:.*]] = fir.convert %[[VAL_18]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_24:.*]] = fir.convert %[[VAL_22]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_25:.*]] = arith.cmpi ne, %[[VAL_23]], %[[VAL_24]] : i1 +! CHECK: %[[VAL_26:.*]] = fir.convert %[[VAL_25]] : (i1) -> !fir.logical<4> +! CHECK: hlfir.assign %[[VAL_26]] to %[[VAL_17]]#0 : !fir.logical<4>, !fir.ref> +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return @@ -90,20 +92,22 @@ end subroutine ! CHECK: %[[VAL_12:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_13:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_14:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@neqv_reduction %[[VAL_4]]#0 -> %[[VAL_15:.*]] : !fir.ref>) for (%[[VAL_16:.*]]) : i32 = (%[[VAL_12]]) to (%[[VAL_13]]) inclusive step (%[[VAL_14]]) { -! CHECK: fir.store %[[VAL_16]] to %[[VAL_11]]#1 : !fir.ref -! CHECK: %[[VAL_17:.*]]:2 = hlfir.declare %[[VAL_15]] {uniq_name = "_QFsimple_reduction_switch_orderEx"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) -! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_11]]#0 : !fir.ref -! CHECK: %[[VAL_19:.*]] = fir.convert %[[VAL_18]] : (i32) -> i64 -! CHECK: %[[VAL_20:.*]] = hlfir.designate %[[VAL_7]]#0 (%[[VAL_19]]) : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_21:.*]] = fir.load %[[VAL_20]] : !fir.ref> -! CHECK: %[[VAL_22:.*]] = fir.load %[[VAL_17]]#0 : !fir.ref> -! CHECK: %[[VAL_23:.*]] = fir.convert %[[VAL_21]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_24:.*]] = fir.convert %[[VAL_22]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_25:.*]] = arith.cmpi ne, %[[VAL_23]], %[[VAL_24]] : i1 -! CHECK: %[[VAL_26:.*]] = fir.convert %[[VAL_25]] : (i1) -> !fir.logical<4> -! CHECK: hlfir.assign %[[VAL_26]] to %[[VAL_17]]#0 : !fir.logical<4>, !fir.ref> -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@neqv_reduction %[[VAL_4]]#0 -> %[[VAL_15:.*]] : !fir.ref>) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_16:.*]]) : i32 = (%[[VAL_12]]) to (%[[VAL_13]]) inclusive step (%[[VAL_14]]) { +! CHECK: %[[VAL_17:.*]]:2 = hlfir.declare %[[VAL_15]] {uniq_name = "_QFsimple_reduction_switch_orderEx"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) +! CHECK: fir.store %[[VAL_16]] to %[[VAL_11]]#1 : !fir.ref +! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_11]]#0 : !fir.ref +! CHECK: %[[VAL_19:.*]] = fir.convert %[[VAL_18]] : (i32) -> i64 +! CHECK: %[[VAL_20:.*]] = hlfir.designate %[[VAL_7]]#0 (%[[VAL_19]]) : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_21:.*]] = fir.load %[[VAL_20]] : !fir.ref> +! CHECK: %[[VAL_22:.*]] = fir.load %[[VAL_17]]#0 : !fir.ref> +! CHECK: %[[VAL_23:.*]] = fir.convert %[[VAL_21]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_24:.*]] = fir.convert %[[VAL_22]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_25:.*]] = arith.cmpi ne, %[[VAL_23]], %[[VAL_24]] : i1 +! CHECK: %[[VAL_26:.*]] = fir.convert %[[VAL_25]] : (i1) -> !fir.logical<4> +! CHECK: hlfir.assign %[[VAL_26]] to %[[VAL_17]]#0 : !fir.logical<4>, !fir.ref> +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return @@ -149,42 +153,44 @@ end subroutine ! CHECK: %[[VAL_20:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_21:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_22:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@neqv_reduction %[[VAL_7]]#0 -> %[[VAL_23:.*]] : !fir.ref>, @neqv_reduction %[[VAL_9]]#0 -> %[[VAL_24:.*]] : !fir.ref>, @neqv_reduction %[[VAL_11]]#0 -> %[[VAL_25:.*]] : !fir.ref>) for (%[[VAL_26:.*]]) : i32 = (%[[VAL_20]]) to (%[[VAL_21]]) inclusive step (%[[VAL_22]]) { -! CHECK: fir.store %[[VAL_26]] to %[[VAL_19]]#1 : !fir.ref -! CHECK: %[[VAL_27:.*]]:2 = hlfir.declare %[[VAL_23]] {uniq_name = "_QFmultiple_reductionsEx"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) -! CHECK: %[[VAL_28:.*]]:2 = hlfir.declare %[[VAL_24]] {uniq_name = "_QFmultiple_reductionsEy"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) -! CHECK: %[[VAL_29:.*]]:2 = hlfir.declare %[[VAL_25]] {uniq_name = "_QFmultiple_reductionsEz"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) -! CHECK: %[[VAL_30:.*]] = fir.load %[[VAL_27]]#0 : !fir.ref> -! CHECK: %[[VAL_31:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref -! CHECK: %[[VAL_32:.*]] = fir.convert %[[VAL_31]] : (i32) -> i64 -! CHECK: %[[VAL_33:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_32]]) : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_34:.*]] = fir.load %[[VAL_33]] : !fir.ref> -! CHECK: %[[VAL_35:.*]] = fir.convert %[[VAL_30]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_36:.*]] = fir.convert %[[VAL_34]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_37:.*]] = arith.cmpi ne, %[[VAL_35]], %[[VAL_36]] : i1 -! CHECK: %[[VAL_38:.*]] = fir.convert %[[VAL_37]] : (i1) -> !fir.logical<4> -! CHECK: hlfir.assign %[[VAL_38]] to %[[VAL_27]]#0 : !fir.logical<4>, !fir.ref> -! CHECK: %[[VAL_39:.*]] = fir.load %[[VAL_28]]#0 : !fir.ref> -! CHECK: %[[VAL_40:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref -! CHECK: %[[VAL_41:.*]] = fir.convert %[[VAL_40]] : (i32) -> i64 -! CHECK: %[[VAL_42:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_41]]) : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_43:.*]] = fir.load %[[VAL_42]] : !fir.ref> -! CHECK: %[[VAL_44:.*]] = fir.convert %[[VAL_39]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_45:.*]] = fir.convert %[[VAL_43]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_46:.*]] = arith.cmpi ne, %[[VAL_44]], %[[VAL_45]] : i1 -! CHECK: %[[VAL_47:.*]] = fir.convert %[[VAL_46]] : (i1) -> !fir.logical<4> -! CHECK: hlfir.assign %[[VAL_47]] to %[[VAL_28]]#0 : !fir.logical<4>, !fir.ref> -! CHECK: %[[VAL_48:.*]] = fir.load %[[VAL_29]]#0 : !fir.ref> -! CHECK: %[[VAL_49:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref -! CHECK: %[[VAL_50:.*]] = fir.convert %[[VAL_49]] : (i32) -> i64 -! CHECK: %[[VAL_51:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_50]]) : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_52:.*]] = fir.load %[[VAL_51]] : !fir.ref> -! CHECK: %[[VAL_53:.*]] = fir.convert %[[VAL_48]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_54:.*]] = fir.convert %[[VAL_52]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_55:.*]] = arith.cmpi ne, %[[VAL_53]], %[[VAL_54]] : i1 -! CHECK: %[[VAL_56:.*]] = fir.convert %[[VAL_55]] : (i1) -> !fir.logical<4> -! CHECK: hlfir.assign %[[VAL_56]] to %[[VAL_29]]#0 : !fir.logical<4>, !fir.ref> -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@neqv_reduction %[[VAL_7]]#0 -> %[[VAL_23:.*]] : !fir.ref>, @neqv_reduction %[[VAL_9]]#0 -> %[[VAL_24:.*]] : !fir.ref>, @neqv_reduction %[[VAL_11]]#0 -> %[[VAL_25:.*]] : !fir.ref>) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_26:.*]]) : i32 = (%[[VAL_20]]) to (%[[VAL_21]]) inclusive step (%[[VAL_22]]) { +! CHECK: %[[VAL_27:.*]]:2 = hlfir.declare %[[VAL_23]] {uniq_name = "_QFmultiple_reductionsEx"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) +! CHECK: %[[VAL_28:.*]]:2 = hlfir.declare %[[VAL_24]] {uniq_name = "_QFmultiple_reductionsEy"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) +! CHECK: %[[VAL_29:.*]]:2 = hlfir.declare %[[VAL_25]] {uniq_name = "_QFmultiple_reductionsEz"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) +! CHECK: fir.store %[[VAL_26]] to %[[VAL_19]]#1 : !fir.ref +! CHECK: %[[VAL_30:.*]] = fir.load %[[VAL_27]]#0 : !fir.ref> +! CHECK: %[[VAL_31:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref +! CHECK: %[[VAL_32:.*]] = fir.convert %[[VAL_31]] : (i32) -> i64 +! CHECK: %[[VAL_33:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_32]]) : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_34:.*]] = fir.load %[[VAL_33]] : !fir.ref> +! CHECK: %[[VAL_35:.*]] = fir.convert %[[VAL_30]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_36:.*]] = fir.convert %[[VAL_34]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_37:.*]] = arith.cmpi ne, %[[VAL_35]], %[[VAL_36]] : i1 +! CHECK: %[[VAL_38:.*]] = fir.convert %[[VAL_37]] : (i1) -> !fir.logical<4> +! CHECK: hlfir.assign %[[VAL_38]] to %[[VAL_27]]#0 : !fir.logical<4>, !fir.ref> +! CHECK: %[[VAL_39:.*]] = fir.load %[[VAL_28]]#0 : !fir.ref> +! CHECK: %[[VAL_40:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref +! CHECK: %[[VAL_41:.*]] = fir.convert %[[VAL_40]] : (i32) -> i64 +! CHECK: %[[VAL_42:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_41]]) : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_43:.*]] = fir.load %[[VAL_42]] : !fir.ref> +! CHECK: %[[VAL_44:.*]] = fir.convert %[[VAL_39]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_45:.*]] = fir.convert %[[VAL_43]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_46:.*]] = arith.cmpi ne, %[[VAL_44]], %[[VAL_45]] : i1 +! CHECK: %[[VAL_47:.*]] = fir.convert %[[VAL_46]] : (i1) -> !fir.logical<4> +! CHECK: hlfir.assign %[[VAL_47]] to %[[VAL_28]]#0 : !fir.logical<4>, !fir.ref> +! CHECK: %[[VAL_48:.*]] = fir.load %[[VAL_29]]#0 : !fir.ref> +! CHECK: %[[VAL_49:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref +! CHECK: %[[VAL_50:.*]] = fir.convert %[[VAL_49]] : (i32) -> i64 +! CHECK: %[[VAL_51:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_50]]) : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_52:.*]] = fir.load %[[VAL_51]] : !fir.ref> +! CHECK: %[[VAL_53:.*]] = fir.convert %[[VAL_48]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_54:.*]] = fir.convert %[[VAL_52]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_55:.*]] = arith.cmpi ne, %[[VAL_53]], %[[VAL_54]] : i1 +! CHECK: %[[VAL_56:.*]] = fir.convert %[[VAL_55]] : (i1) -> !fir.logical<4> +! CHECK: hlfir.assign %[[VAL_56]] to %[[VAL_29]]#0 : !fir.logical<4>, !fir.ref> +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return ! CHECK: } diff --git a/flang/test/Lower/OpenMP/wsloop-reduction-logical-neqv.f90 b/flang/test/Lower/OpenMP/wsloop-reduction-logical-neqv.f90 index 08d6a2efd3993627cb6ea33977346d6452f60eef..f5c84aaaf4858b5ff5663a6aa28544c5d8da3d6d 100644 --- a/flang/test/Lower/OpenMP/wsloop-reduction-logical-neqv.f90 +++ b/flang/test/Lower/OpenMP/wsloop-reduction-logical-neqv.f90 @@ -36,20 +36,22 @@ ! CHECK: %[[VAL_12:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_13:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_14:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@neqv_reduction %[[VAL_4]]#0 -> %[[VAL_15:.*]] : !fir.ref>) for (%[[VAL_16:.*]]) : i32 = (%[[VAL_12]]) to (%[[VAL_13]]) inclusive step (%[[VAL_14]]) { -! CHECK: fir.store %[[VAL_16]] to %[[VAL_11]]#1 : !fir.ref -! CHECK: %[[VAL_17:.*]]:2 = hlfir.declare %[[VAL_15]] {uniq_name = "_QFsimple_reductionEx"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) -! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_17]]#0 : !fir.ref> -! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_11]]#0 : !fir.ref -! CHECK: %[[VAL_20:.*]] = fir.convert %[[VAL_19]] : (i32) -> i64 -! CHECK: %[[VAL_21:.*]] = hlfir.designate %[[VAL_7]]#0 (%[[VAL_20]]) : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_22:.*]] = fir.load %[[VAL_21]] : !fir.ref> -! CHECK: %[[VAL_23:.*]] = fir.convert %[[VAL_18]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_24:.*]] = fir.convert %[[VAL_22]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_25:.*]] = arith.cmpi ne, %[[VAL_23]], %[[VAL_24]] : i1 -! CHECK: %[[VAL_26:.*]] = fir.convert %[[VAL_25]] : (i1) -> !fir.logical<4> -! CHECK: hlfir.assign %[[VAL_26]] to %[[VAL_17]]#0 : !fir.logical<4>, !fir.ref> -! CHECK: omp.yield +! CHECK: omp.wsloop reduction(@neqv_reduction %[[VAL_4]]#0 -> %[[VAL_15:.*]] : !fir.ref>) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_16:.*]]) : i32 = (%[[VAL_12]]) to (%[[VAL_13]]) inclusive step (%[[VAL_14]]) { +! CHECK: %[[VAL_17:.*]]:2 = hlfir.declare %[[VAL_15]] {uniq_name = "_QFsimple_reductionEx"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) +! CHECK: fir.store %[[VAL_16]] to %[[VAL_11]]#1 : !fir.ref +! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_17]]#0 : !fir.ref> +! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_11]]#0 : !fir.ref +! CHECK: %[[VAL_20:.*]] = fir.convert %[[VAL_19]] : (i32) -> i64 +! CHECK: %[[VAL_21:.*]] = hlfir.designate %[[VAL_7]]#0 (%[[VAL_20]]) : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_22:.*]] = fir.load %[[VAL_21]] : !fir.ref> +! CHECK: %[[VAL_23:.*]] = fir.convert %[[VAL_18]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_24:.*]] = fir.convert %[[VAL_22]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_25:.*]] = arith.cmpi ne, %[[VAL_23]], %[[VAL_24]] : i1 +! CHECK: %[[VAL_26:.*]] = fir.convert %[[VAL_25]] : (i1) -> !fir.logical<4> +! CHECK: hlfir.assign %[[VAL_26]] to %[[VAL_17]]#0 : !fir.logical<4>, !fir.ref> +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return @@ -84,20 +86,22 @@ end subroutine ! CHECK: %[[VAL_12:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_13:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_14:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@neqv_reduction %[[VAL_4]]#0 -> %[[VAL_15:.*]] : !fir.ref>) for (%[[VAL_16:.*]]) : i32 = (%[[VAL_12]]) to (%[[VAL_13]]) inclusive step (%[[VAL_14]]) { -! CHECK: fir.store %[[VAL_16]] to %[[VAL_11]]#1 : !fir.ref -! CHECK: %[[VAL_17:.*]]:2 = hlfir.declare %[[VAL_15]] {uniq_name = "_QFsimple_reduction_switch_orderEx"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) -! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_11]]#0 : !fir.ref -! CHECK: %[[VAL_19:.*]] = fir.convert %[[VAL_18]] : (i32) -> i64 -! CHECK: %[[VAL_20:.*]] = hlfir.designate %[[VAL_7]]#0 (%[[VAL_19]]) : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_21:.*]] = fir.load %[[VAL_20]] : !fir.ref> -! CHECK: %[[VAL_22:.*]] = fir.load %[[VAL_17]]#0 : !fir.ref> -! CHECK: %[[VAL_23:.*]] = fir.convert %[[VAL_21]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_24:.*]] = fir.convert %[[VAL_22]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_25:.*]] = arith.cmpi ne, %[[VAL_23]], %[[VAL_24]] : i1 -! CHECK: %[[VAL_26:.*]] = fir.convert %[[VAL_25]] : (i1) -> !fir.logical<4> -! CHECK: hlfir.assign %[[VAL_26]] to %[[VAL_17]]#0 : !fir.logical<4>, !fir.ref> -! CHECK: omp.yield +! CHECK: omp.wsloop reduction(@neqv_reduction %[[VAL_4]]#0 -> %[[VAL_15:.*]] : !fir.ref>) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_16:.*]]) : i32 = (%[[VAL_12]]) to (%[[VAL_13]]) inclusive step (%[[VAL_14]]) { +! CHECK: %[[VAL_17:.*]]:2 = hlfir.declare %[[VAL_15]] {uniq_name = "_QFsimple_reduction_switch_orderEx"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) +! CHECK: fir.store %[[VAL_16]] to %[[VAL_11]]#1 : !fir.ref +! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_11]]#0 : !fir.ref +! CHECK: %[[VAL_19:.*]] = fir.convert %[[VAL_18]] : (i32) -> i64 +! CHECK: %[[VAL_20:.*]] = hlfir.designate %[[VAL_7]]#0 (%[[VAL_19]]) : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_21:.*]] = fir.load %[[VAL_20]] : !fir.ref> +! CHECK: %[[VAL_22:.*]] = fir.load %[[VAL_17]]#0 : !fir.ref> +! CHECK: %[[VAL_23:.*]] = fir.convert %[[VAL_21]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_24:.*]] = fir.convert %[[VAL_22]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_25:.*]] = arith.cmpi ne, %[[VAL_23]], %[[VAL_24]] : i1 +! CHECK: %[[VAL_26:.*]] = fir.convert %[[VAL_25]] : (i1) -> !fir.logical<4> +! CHECK: hlfir.assign %[[VAL_26]] to %[[VAL_17]]#0 : !fir.logical<4>, !fir.ref> +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return @@ -143,42 +147,44 @@ end subroutine ! CHECK: %[[VAL_20:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_21:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_22:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@neqv_reduction %[[VAL_7]]#0 -> %[[VAL_23:.*]] : !fir.ref>, @neqv_reduction %[[VAL_9]]#0 -> %[[VAL_24:.*]] : !fir.ref>, @neqv_reduction %[[VAL_11]]#0 -> %[[VAL_25:.*]] : !fir.ref>) for (%[[VAL_26:.*]]) : i32 = (%[[VAL_20]]) to (%[[VAL_21]]) inclusive step (%[[VAL_22]]) { -! CHECK: fir.store %[[VAL_26]] to %[[VAL_19]]#1 : !fir.ref -! CHECK: %[[VAL_27:.*]]:2 = hlfir.declare %[[VAL_23]] {uniq_name = "_QFmultiple_reductionsEx"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) -! CHECK: %[[VAL_28:.*]]:2 = hlfir.declare %[[VAL_24]] {uniq_name = "_QFmultiple_reductionsEy"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) -! CHECK: %[[VAL_29:.*]]:2 = hlfir.declare %[[VAL_25]] {uniq_name = "_QFmultiple_reductionsEz"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) -! CHECK: %[[VAL_30:.*]] = fir.load %[[VAL_27]]#0 : !fir.ref> -! CHECK: %[[VAL_31:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref -! CHECK: %[[VAL_32:.*]] = fir.convert %[[VAL_31]] : (i32) -> i64 -! CHECK: %[[VAL_33:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_32]]) : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_34:.*]] = fir.load %[[VAL_33]] : !fir.ref> -! CHECK: %[[VAL_35:.*]] = fir.convert %[[VAL_30]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_36:.*]] = fir.convert %[[VAL_34]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_37:.*]] = arith.cmpi ne, %[[VAL_35]], %[[VAL_36]] : i1 -! CHECK: %[[VAL_38:.*]] = fir.convert %[[VAL_37]] : (i1) -> !fir.logical<4> -! CHECK: hlfir.assign %[[VAL_38]] to %[[VAL_27]]#0 : !fir.logical<4>, !fir.ref> -! CHECK: %[[VAL_39:.*]] = fir.load %[[VAL_28]]#0 : !fir.ref> -! CHECK: %[[VAL_40:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref -! CHECK: %[[VAL_41:.*]] = fir.convert %[[VAL_40]] : (i32) -> i64 -! CHECK: %[[VAL_42:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_41]]) : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_43:.*]] = fir.load %[[VAL_42]] : !fir.ref> -! CHECK: %[[VAL_44:.*]] = fir.convert %[[VAL_39]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_45:.*]] = fir.convert %[[VAL_43]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_46:.*]] = arith.cmpi ne, %[[VAL_44]], %[[VAL_45]] : i1 -! CHECK: %[[VAL_47:.*]] = fir.convert %[[VAL_46]] : (i1) -> !fir.logical<4> -! CHECK: hlfir.assign %[[VAL_47]] to %[[VAL_28]]#0 : !fir.logical<4>, !fir.ref> -! CHECK: %[[VAL_48:.*]] = fir.load %[[VAL_29]]#0 : !fir.ref> -! CHECK: %[[VAL_49:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref -! CHECK: %[[VAL_50:.*]] = fir.convert %[[VAL_49]] : (i32) -> i64 -! CHECK: %[[VAL_51:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_50]]) : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_52:.*]] = fir.load %[[VAL_51]] : !fir.ref> -! CHECK: %[[VAL_53:.*]] = fir.convert %[[VAL_48]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_54:.*]] = fir.convert %[[VAL_52]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_55:.*]] = arith.cmpi ne, %[[VAL_53]], %[[VAL_54]] : i1 -! CHECK: %[[VAL_56:.*]] = fir.convert %[[VAL_55]] : (i1) -> !fir.logical<4> -! CHECK: hlfir.assign %[[VAL_56]] to %[[VAL_29]]#0 : !fir.logical<4>, !fir.ref> -! CHECK: omp.yield +! CHECK: omp.wsloop reduction(@neqv_reduction %[[VAL_7]]#0 -> %[[VAL_23:.*]] : !fir.ref>, @neqv_reduction %[[VAL_9]]#0 -> %[[VAL_24:.*]] : !fir.ref>, @neqv_reduction %[[VAL_11]]#0 -> %[[VAL_25:.*]] : !fir.ref>) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_26:.*]]) : i32 = (%[[VAL_20]]) to (%[[VAL_21]]) inclusive step (%[[VAL_22]]) { +! CHECK: %[[VAL_27:.*]]:2 = hlfir.declare %[[VAL_23]] {uniq_name = "_QFmultiple_reductionsEx"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) +! CHECK: %[[VAL_28:.*]]:2 = hlfir.declare %[[VAL_24]] {uniq_name = "_QFmultiple_reductionsEy"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) +! CHECK: %[[VAL_29:.*]]:2 = hlfir.declare %[[VAL_25]] {uniq_name = "_QFmultiple_reductionsEz"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) +! CHECK: fir.store %[[VAL_26]] to %[[VAL_19]]#1 : !fir.ref +! CHECK: %[[VAL_30:.*]] = fir.load %[[VAL_27]]#0 : !fir.ref> +! CHECK: %[[VAL_31:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref +! CHECK: %[[VAL_32:.*]] = fir.convert %[[VAL_31]] : (i32) -> i64 +! CHECK: %[[VAL_33:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_32]]) : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_34:.*]] = fir.load %[[VAL_33]] : !fir.ref> +! CHECK: %[[VAL_35:.*]] = fir.convert %[[VAL_30]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_36:.*]] = fir.convert %[[VAL_34]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_37:.*]] = arith.cmpi ne, %[[VAL_35]], %[[VAL_36]] : i1 +! CHECK: %[[VAL_38:.*]] = fir.convert %[[VAL_37]] : (i1) -> !fir.logical<4> +! CHECK: hlfir.assign %[[VAL_38]] to %[[VAL_27]]#0 : !fir.logical<4>, !fir.ref> +! CHECK: %[[VAL_39:.*]] = fir.load %[[VAL_28]]#0 : !fir.ref> +! CHECK: %[[VAL_40:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref +! CHECK: %[[VAL_41:.*]] = fir.convert %[[VAL_40]] : (i32) -> i64 +! CHECK: %[[VAL_42:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_41]]) : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_43:.*]] = fir.load %[[VAL_42]] : !fir.ref> +! CHECK: %[[VAL_44:.*]] = fir.convert %[[VAL_39]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_45:.*]] = fir.convert %[[VAL_43]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_46:.*]] = arith.cmpi ne, %[[VAL_44]], %[[VAL_45]] : i1 +! CHECK: %[[VAL_47:.*]] = fir.convert %[[VAL_46]] : (i1) -> !fir.logical<4> +! CHECK: hlfir.assign %[[VAL_47]] to %[[VAL_28]]#0 : !fir.logical<4>, !fir.ref> +! CHECK: %[[VAL_48:.*]] = fir.load %[[VAL_29]]#0 : !fir.ref> +! CHECK: %[[VAL_49:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref +! CHECK: %[[VAL_50:.*]] = fir.convert %[[VAL_49]] : (i32) -> i64 +! CHECK: %[[VAL_51:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_50]]) : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_52:.*]] = fir.load %[[VAL_51]] : !fir.ref> +! CHECK: %[[VAL_53:.*]] = fir.convert %[[VAL_48]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_54:.*]] = fir.convert %[[VAL_52]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_55:.*]] = arith.cmpi ne, %[[VAL_53]], %[[VAL_54]] : i1 +! CHECK: %[[VAL_56:.*]] = fir.convert %[[VAL_55]] : (i1) -> !fir.logical<4> +! CHECK: hlfir.assign %[[VAL_56]] to %[[VAL_29]]#0 : !fir.logical<4>, !fir.ref> +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return ! CHECK: } diff --git a/flang/test/Lower/OpenMP/wsloop-reduction-logical-or-byref.f90 b/flang/test/Lower/OpenMP/wsloop-reduction-logical-or-byref.f90 index ca69ccee4a38e34258475429de708a31cb7b6d8b..e268c6ff6cf51e10eefaef6efbf617b8785ef31f 100644 --- a/flang/test/Lower/OpenMP/wsloop-reduction-logical-or-byref.f90 +++ b/flang/test/Lower/OpenMP/wsloop-reduction-logical-or-byref.f90 @@ -41,20 +41,22 @@ ! CHECK: %[[VAL_12:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_13:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_14:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@or_reduction %[[VAL_4]]#0 -> %[[VAL_15:.*]] : !fir.ref>) for (%[[VAL_16:.*]]) : i32 = (%[[VAL_12]]) to (%[[VAL_13]]) inclusive step (%[[VAL_14]]) { -! CHECK: fir.store %[[VAL_16]] to %[[VAL_11]]#1 : !fir.ref -! CHECK: %[[VAL_17:.*]]:2 = hlfir.declare %[[VAL_15]] {uniq_name = "_QFsimple_reductionEx"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) -! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_17]]#0 : !fir.ref> -! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_11]]#0 : !fir.ref -! CHECK: %[[VAL_20:.*]] = fir.convert %[[VAL_19]] : (i32) -> i64 -! CHECK: %[[VAL_21:.*]] = hlfir.designate %[[VAL_7]]#0 (%[[VAL_20]]) : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_22:.*]] = fir.load %[[VAL_21]] : !fir.ref> -! CHECK: %[[VAL_23:.*]] = fir.convert %[[VAL_18]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_24:.*]] = fir.convert %[[VAL_22]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_25:.*]] = arith.ori %[[VAL_23]], %[[VAL_24]] : i1 -! CHECK: %[[VAL_26:.*]] = fir.convert %[[VAL_25]] : (i1) -> !fir.logical<4> -! CHECK: hlfir.assign %[[VAL_26]] to %[[VAL_17]]#0 : !fir.logical<4>, !fir.ref> -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@or_reduction %[[VAL_4]]#0 -> %[[VAL_15:.*]] : !fir.ref>) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_16:.*]]) : i32 = (%[[VAL_12]]) to (%[[VAL_13]]) inclusive step (%[[VAL_14]]) { +! CHECK: %[[VAL_17:.*]]:2 = hlfir.declare %[[VAL_15]] {uniq_name = "_QFsimple_reductionEx"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) +! CHECK: fir.store %[[VAL_16]] to %[[VAL_11]]#1 : !fir.ref +! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_17]]#0 : !fir.ref> +! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_11]]#0 : !fir.ref +! CHECK: %[[VAL_20:.*]] = fir.convert %[[VAL_19]] : (i32) -> i64 +! CHECK: %[[VAL_21:.*]] = hlfir.designate %[[VAL_7]]#0 (%[[VAL_20]]) : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_22:.*]] = fir.load %[[VAL_21]] : !fir.ref> +! CHECK: %[[VAL_23:.*]] = fir.convert %[[VAL_18]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_24:.*]] = fir.convert %[[VAL_22]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_25:.*]] = arith.ori %[[VAL_23]], %[[VAL_24]] : i1 +! CHECK: %[[VAL_26:.*]] = fir.convert %[[VAL_25]] : (i1) -> !fir.logical<4> +! CHECK: hlfir.assign %[[VAL_26]] to %[[VAL_17]]#0 : !fir.logical<4>, !fir.ref> +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return @@ -88,20 +90,22 @@ end subroutine ! CHECK: %[[VAL_12:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_13:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_14:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@or_reduction %[[VAL_4]]#0 -> %[[VAL_15:.*]] : !fir.ref>) for (%[[VAL_16:.*]]) : i32 = (%[[VAL_12]]) to (%[[VAL_13]]) inclusive step (%[[VAL_14]]) { -! CHECK: fir.store %[[VAL_16]] to %[[VAL_11]]#1 : !fir.ref -! CHECK: %[[VAL_17:.*]]:2 = hlfir.declare %[[VAL_15]] {uniq_name = "_QFsimple_reduction_switch_orderEx"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) -! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_11]]#0 : !fir.ref -! CHECK: %[[VAL_19:.*]] = fir.convert %[[VAL_18]] : (i32) -> i64 -! CHECK: %[[VAL_20:.*]] = hlfir.designate %[[VAL_7]]#0 (%[[VAL_19]]) : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_21:.*]] = fir.load %[[VAL_20]] : !fir.ref> -! CHECK: %[[VAL_22:.*]] = fir.load %[[VAL_17]]#0 : !fir.ref> -! CHECK: %[[VAL_23:.*]] = fir.convert %[[VAL_21]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_24:.*]] = fir.convert %[[VAL_22]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_25:.*]] = arith.ori %[[VAL_23]], %[[VAL_24]] : i1 -! CHECK: %[[VAL_26:.*]] = fir.convert %[[VAL_25]] : (i1) -> !fir.logical<4> -! CHECK: hlfir.assign %[[VAL_26]] to %[[VAL_17]]#0 : !fir.logical<4>, !fir.ref> -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@or_reduction %[[VAL_4]]#0 -> %[[VAL_15:.*]] : !fir.ref>) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_16:.*]]) : i32 = (%[[VAL_12]]) to (%[[VAL_13]]) inclusive step (%[[VAL_14]]) { +! CHECK: %[[VAL_17:.*]]:2 = hlfir.declare %[[VAL_15]] {uniq_name = "_QFsimple_reduction_switch_orderEx"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) +! CHECK: fir.store %[[VAL_16]] to %[[VAL_11]]#1 : !fir.ref +! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_11]]#0 : !fir.ref +! CHECK: %[[VAL_19:.*]] = fir.convert %[[VAL_18]] : (i32) -> i64 +! CHECK: %[[VAL_20:.*]] = hlfir.designate %[[VAL_7]]#0 (%[[VAL_19]]) : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_21:.*]] = fir.load %[[VAL_20]] : !fir.ref> +! CHECK: %[[VAL_22:.*]] = fir.load %[[VAL_17]]#0 : !fir.ref> +! CHECK: %[[VAL_23:.*]] = fir.convert %[[VAL_21]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_24:.*]] = fir.convert %[[VAL_22]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_25:.*]] = arith.ori %[[VAL_23]], %[[VAL_24]] : i1 +! CHECK: %[[VAL_26:.*]] = fir.convert %[[VAL_25]] : (i1) -> !fir.logical<4> +! CHECK: hlfir.assign %[[VAL_26]] to %[[VAL_17]]#0 : !fir.logical<4>, !fir.ref> +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return @@ -145,42 +149,44 @@ end subroutine ! CHECK: %[[VAL_20:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_21:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_22:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@or_reduction %[[VAL_7]]#0 -> %[[VAL_23:.*]] : !fir.ref>, @or_reduction %[[VAL_9]]#0 -> %[[VAL_24:.*]] : !fir.ref>, @or_reduction %[[VAL_11]]#0 -> %[[VAL_25:.*]] : !fir.ref>) for (%[[VAL_26:.*]]) : i32 = (%[[VAL_20]]) to (%[[VAL_21]]) inclusive step (%[[VAL_22]]) { -! CHECK: fir.store %[[VAL_26]] to %[[VAL_19]]#1 : !fir.ref -! CHECK: %[[VAL_27:.*]]:2 = hlfir.declare %[[VAL_23]] {uniq_name = "_QFmultiple_reductionsEx"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) -! CHECK: %[[VAL_28:.*]]:2 = hlfir.declare %[[VAL_24]] {uniq_name = "_QFmultiple_reductionsEy"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) -! CHECK: %[[VAL_29:.*]]:2 = hlfir.declare %[[VAL_25]] {uniq_name = "_QFmultiple_reductionsEz"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) -! CHECK: %[[VAL_30:.*]] = fir.load %[[VAL_27]]#0 : !fir.ref> -! CHECK: %[[VAL_31:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref -! CHECK: %[[VAL_32:.*]] = fir.convert %[[VAL_31]] : (i32) -> i64 -! CHECK: %[[VAL_33:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_32]]) : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_34:.*]] = fir.load %[[VAL_33]] : !fir.ref> -! CHECK: %[[VAL_35:.*]] = fir.convert %[[VAL_30]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_36:.*]] = fir.convert %[[VAL_34]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_37:.*]] = arith.ori %[[VAL_35]], %[[VAL_36]] : i1 -! CHECK: %[[VAL_38:.*]] = fir.convert %[[VAL_37]] : (i1) -> !fir.logical<4> -! CHECK: hlfir.assign %[[VAL_38]] to %[[VAL_27]]#0 : !fir.logical<4>, !fir.ref> -! CHECK: %[[VAL_39:.*]] = fir.load %[[VAL_28]]#0 : !fir.ref> -! CHECK: %[[VAL_40:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref -! CHECK: %[[VAL_41:.*]] = fir.convert %[[VAL_40]] : (i32) -> i64 -! CHECK: %[[VAL_42:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_41]]) : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_43:.*]] = fir.load %[[VAL_42]] : !fir.ref> -! CHECK: %[[VAL_44:.*]] = fir.convert %[[VAL_39]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_45:.*]] = fir.convert %[[VAL_43]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_46:.*]] = arith.ori %[[VAL_44]], %[[VAL_45]] : i1 -! CHECK: %[[VAL_47:.*]] = fir.convert %[[VAL_46]] : (i1) -> !fir.logical<4> -! CHECK: hlfir.assign %[[VAL_47]] to %[[VAL_28]]#0 : !fir.logical<4>, !fir.ref> -! CHECK: %[[VAL_48:.*]] = fir.load %[[VAL_29]]#0 : !fir.ref> -! CHECK: %[[VAL_49:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref -! CHECK: %[[VAL_50:.*]] = fir.convert %[[VAL_49]] : (i32) -> i64 -! CHECK: %[[VAL_51:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_50]]) : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_52:.*]] = fir.load %[[VAL_51]] : !fir.ref> -! CHECK: %[[VAL_53:.*]] = fir.convert %[[VAL_48]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_54:.*]] = fir.convert %[[VAL_52]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_55:.*]] = arith.ori %[[VAL_53]], %[[VAL_54]] : i1 -! CHECK: %[[VAL_56:.*]] = fir.convert %[[VAL_55]] : (i1) -> !fir.logical<4> -! CHECK: hlfir.assign %[[VAL_56]] to %[[VAL_29]]#0 : !fir.logical<4>, !fir.ref> -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@or_reduction %[[VAL_7]]#0 -> %[[VAL_23:.*]] : !fir.ref>, @or_reduction %[[VAL_9]]#0 -> %[[VAL_24:.*]] : !fir.ref>, @or_reduction %[[VAL_11]]#0 -> %[[VAL_25:.*]] : !fir.ref>) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_26:.*]]) : i32 = (%[[VAL_20]]) to (%[[VAL_21]]) inclusive step (%[[VAL_22]]) { +! CHECK: %[[VAL_27:.*]]:2 = hlfir.declare %[[VAL_23]] {uniq_name = "_QFmultiple_reductionsEx"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) +! CHECK: %[[VAL_28:.*]]:2 = hlfir.declare %[[VAL_24]] {uniq_name = "_QFmultiple_reductionsEy"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) +! CHECK: %[[VAL_29:.*]]:2 = hlfir.declare %[[VAL_25]] {uniq_name = "_QFmultiple_reductionsEz"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) +! CHECK: fir.store %[[VAL_26]] to %[[VAL_19]]#1 : !fir.ref +! CHECK: %[[VAL_30:.*]] = fir.load %[[VAL_27]]#0 : !fir.ref> +! CHECK: %[[VAL_31:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref +! CHECK: %[[VAL_32:.*]] = fir.convert %[[VAL_31]] : (i32) -> i64 +! CHECK: %[[VAL_33:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_32]]) : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_34:.*]] = fir.load %[[VAL_33]] : !fir.ref> +! CHECK: %[[VAL_35:.*]] = fir.convert %[[VAL_30]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_36:.*]] = fir.convert %[[VAL_34]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_37:.*]] = arith.ori %[[VAL_35]], %[[VAL_36]] : i1 +! CHECK: %[[VAL_38:.*]] = fir.convert %[[VAL_37]] : (i1) -> !fir.logical<4> +! CHECK: hlfir.assign %[[VAL_38]] to %[[VAL_27]]#0 : !fir.logical<4>, !fir.ref> +! CHECK: %[[VAL_39:.*]] = fir.load %[[VAL_28]]#0 : !fir.ref> +! CHECK: %[[VAL_40:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref +! CHECK: %[[VAL_41:.*]] = fir.convert %[[VAL_40]] : (i32) -> i64 +! CHECK: %[[VAL_42:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_41]]) : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_43:.*]] = fir.load %[[VAL_42]] : !fir.ref> +! CHECK: %[[VAL_44:.*]] = fir.convert %[[VAL_39]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_45:.*]] = fir.convert %[[VAL_43]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_46:.*]] = arith.ori %[[VAL_44]], %[[VAL_45]] : i1 +! CHECK: %[[VAL_47:.*]] = fir.convert %[[VAL_46]] : (i1) -> !fir.logical<4> +! CHECK: hlfir.assign %[[VAL_47]] to %[[VAL_28]]#0 : !fir.logical<4>, !fir.ref> +! CHECK: %[[VAL_48:.*]] = fir.load %[[VAL_29]]#0 : !fir.ref> +! CHECK: %[[VAL_49:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref +! CHECK: %[[VAL_50:.*]] = fir.convert %[[VAL_49]] : (i32) -> i64 +! CHECK: %[[VAL_51:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_50]]) : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_52:.*]] = fir.load %[[VAL_51]] : !fir.ref> +! CHECK: %[[VAL_53:.*]] = fir.convert %[[VAL_48]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_54:.*]] = fir.convert %[[VAL_52]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_55:.*]] = arith.ori %[[VAL_53]], %[[VAL_54]] : i1 +! CHECK: %[[VAL_56:.*]] = fir.convert %[[VAL_55]] : (i1) -> !fir.logical<4> +! CHECK: hlfir.assign %[[VAL_56]] to %[[VAL_29]]#0 : !fir.logical<4>, !fir.ref> +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return diff --git a/flang/test/Lower/OpenMP/wsloop-reduction-logical-or.f90 b/flang/test/Lower/OpenMP/wsloop-reduction-logical-or.f90 index c4bf8e9d65ae7bc7d6a67d2c1443b6f54f794275..26dc0c327aad1a818c1133846ef01b8f424312c4 100644 --- a/flang/test/Lower/OpenMP/wsloop-reduction-logical-or.f90 +++ b/flang/test/Lower/OpenMP/wsloop-reduction-logical-or.f90 @@ -36,20 +36,22 @@ ! CHECK: %[[VAL_12:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_13:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_14:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@or_reduction %[[VAL_4]]#0 -> %[[VAL_15:.*]] : !fir.ref>) for (%[[VAL_16:.*]]) : i32 = (%[[VAL_12]]) to (%[[VAL_13]]) inclusive step (%[[VAL_14]]) { -! CHECK: fir.store %[[VAL_16]] to %[[VAL_11]]#1 : !fir.ref -! CHECK: %[[VAL_17:.*]]:2 = hlfir.declare %[[VAL_15]] {uniq_name = "_QFsimple_reductionEx"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) -! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_17]]#0 : !fir.ref> -! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_11]]#0 : !fir.ref -! CHECK: %[[VAL_20:.*]] = fir.convert %[[VAL_19]] : (i32) -> i64 -! CHECK: %[[VAL_21:.*]] = hlfir.designate %[[VAL_7]]#0 (%[[VAL_20]]) : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_22:.*]] = fir.load %[[VAL_21]] : !fir.ref> -! CHECK: %[[VAL_23:.*]] = fir.convert %[[VAL_18]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_24:.*]] = fir.convert %[[VAL_22]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_25:.*]] = arith.ori %[[VAL_23]], %[[VAL_24]] : i1 -! CHECK: %[[VAL_26:.*]] = fir.convert %[[VAL_25]] : (i1) -> !fir.logical<4> -! CHECK: hlfir.assign %[[VAL_26]] to %[[VAL_17]]#0 : !fir.logical<4>, !fir.ref> -! CHECK: omp.yield +! CHECK: omp.wsloop reduction(@or_reduction %[[VAL_4]]#0 -> %[[VAL_15:.*]] : !fir.ref>) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_16:.*]]) : i32 = (%[[VAL_12]]) to (%[[VAL_13]]) inclusive step (%[[VAL_14]]) { +! CHECK: %[[VAL_17:.*]]:2 = hlfir.declare %[[VAL_15]] {uniq_name = "_QFsimple_reductionEx"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) +! CHECK: fir.store %[[VAL_16]] to %[[VAL_11]]#1 : !fir.ref +! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_17]]#0 : !fir.ref> +! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_11]]#0 : !fir.ref +! CHECK: %[[VAL_20:.*]] = fir.convert %[[VAL_19]] : (i32) -> i64 +! CHECK: %[[VAL_21:.*]] = hlfir.designate %[[VAL_7]]#0 (%[[VAL_20]]) : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_22:.*]] = fir.load %[[VAL_21]] : !fir.ref> +! CHECK: %[[VAL_23:.*]] = fir.convert %[[VAL_18]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_24:.*]] = fir.convert %[[VAL_22]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_25:.*]] = arith.ori %[[VAL_23]], %[[VAL_24]] : i1 +! CHECK: %[[VAL_26:.*]] = fir.convert %[[VAL_25]] : (i1) -> !fir.logical<4> +! CHECK: hlfir.assign %[[VAL_26]] to %[[VAL_17]]#0 : !fir.logical<4>, !fir.ref> +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return @@ -83,20 +85,22 @@ end subroutine ! CHECK: %[[VAL_12:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_13:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_14:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@or_reduction %[[VAL_4]]#0 -> %[[VAL_15:.*]] : !fir.ref>) for (%[[VAL_16:.*]]) : i32 = (%[[VAL_12]]) to (%[[VAL_13]]) inclusive step (%[[VAL_14]]) { -! CHECK: fir.store %[[VAL_16]] to %[[VAL_11]]#1 : !fir.ref -! CHECK: %[[VAL_17:.*]]:2 = hlfir.declare %[[VAL_15]] {uniq_name = "_QFsimple_reduction_switch_orderEx"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) -! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_11]]#0 : !fir.ref -! CHECK: %[[VAL_19:.*]] = fir.convert %[[VAL_18]] : (i32) -> i64 -! CHECK: %[[VAL_20:.*]] = hlfir.designate %[[VAL_7]]#0 (%[[VAL_19]]) : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_21:.*]] = fir.load %[[VAL_20]] : !fir.ref> -! CHECK: %[[VAL_22:.*]] = fir.load %[[VAL_17]]#0 : !fir.ref> -! CHECK: %[[VAL_23:.*]] = fir.convert %[[VAL_21]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_24:.*]] = fir.convert %[[VAL_22]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_25:.*]] = arith.ori %[[VAL_23]], %[[VAL_24]] : i1 -! CHECK: %[[VAL_26:.*]] = fir.convert %[[VAL_25]] : (i1) -> !fir.logical<4> -! CHECK: hlfir.assign %[[VAL_26]] to %[[VAL_17]]#0 : !fir.logical<4>, !fir.ref> -! CHECK: omp.yield +! CHECK: omp.wsloop reduction(@or_reduction %[[VAL_4]]#0 -> %[[VAL_15:.*]] : !fir.ref>) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_16:.*]]) : i32 = (%[[VAL_12]]) to (%[[VAL_13]]) inclusive step (%[[VAL_14]]) { +! CHECK: %[[VAL_17:.*]]:2 = hlfir.declare %[[VAL_15]] {uniq_name = "_QFsimple_reduction_switch_orderEx"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) +! CHECK: fir.store %[[VAL_16]] to %[[VAL_11]]#1 : !fir.ref +! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_11]]#0 : !fir.ref +! CHECK: %[[VAL_19:.*]] = fir.convert %[[VAL_18]] : (i32) -> i64 +! CHECK: %[[VAL_20:.*]] = hlfir.designate %[[VAL_7]]#0 (%[[VAL_19]]) : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_21:.*]] = fir.load %[[VAL_20]] : !fir.ref> +! CHECK: %[[VAL_22:.*]] = fir.load %[[VAL_17]]#0 : !fir.ref> +! CHECK: %[[VAL_23:.*]] = fir.convert %[[VAL_21]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_24:.*]] = fir.convert %[[VAL_22]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_25:.*]] = arith.ori %[[VAL_23]], %[[VAL_24]] : i1 +! CHECK: %[[VAL_26:.*]] = fir.convert %[[VAL_25]] : (i1) -> !fir.logical<4> +! CHECK: hlfir.assign %[[VAL_26]] to %[[VAL_17]]#0 : !fir.logical<4>, !fir.ref> +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return @@ -140,42 +144,44 @@ end subroutine ! CHECK: %[[VAL_20:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_21:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_22:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@or_reduction %[[VAL_7]]#0 -> %[[VAL_23:.*]] : !fir.ref>, @or_reduction %[[VAL_9]]#0 -> %[[VAL_24:.*]] : !fir.ref>, @or_reduction %[[VAL_11]]#0 -> %[[VAL_25:.*]] : !fir.ref>) for (%[[VAL_26:.*]]) : i32 = (%[[VAL_20]]) to (%[[VAL_21]]) inclusive step (%[[VAL_22]]) { -! CHECK: fir.store %[[VAL_26]] to %[[VAL_19]]#1 : !fir.ref -! CHECK: %[[VAL_27:.*]]:2 = hlfir.declare %[[VAL_23]] {uniq_name = "_QFmultiple_reductionsEx"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) -! CHECK: %[[VAL_28:.*]]:2 = hlfir.declare %[[VAL_24]] {uniq_name = "_QFmultiple_reductionsEy"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) -! CHECK: %[[VAL_29:.*]]:2 = hlfir.declare %[[VAL_25]] {uniq_name = "_QFmultiple_reductionsEz"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) -! CHECK: %[[VAL_30:.*]] = fir.load %[[VAL_27]]#0 : !fir.ref> -! CHECK: %[[VAL_31:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref -! CHECK: %[[VAL_32:.*]] = fir.convert %[[VAL_31]] : (i32) -> i64 -! CHECK: %[[VAL_33:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_32]]) : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_34:.*]] = fir.load %[[VAL_33]] : !fir.ref> -! CHECK: %[[VAL_35:.*]] = fir.convert %[[VAL_30]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_36:.*]] = fir.convert %[[VAL_34]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_37:.*]] = arith.ori %[[VAL_35]], %[[VAL_36]] : i1 -! CHECK: %[[VAL_38:.*]] = fir.convert %[[VAL_37]] : (i1) -> !fir.logical<4> -! CHECK: hlfir.assign %[[VAL_38]] to %[[VAL_27]]#0 : !fir.logical<4>, !fir.ref> -! CHECK: %[[VAL_39:.*]] = fir.load %[[VAL_28]]#0 : !fir.ref> -! CHECK: %[[VAL_40:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref -! CHECK: %[[VAL_41:.*]] = fir.convert %[[VAL_40]] : (i32) -> i64 -! CHECK: %[[VAL_42:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_41]]) : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_43:.*]] = fir.load %[[VAL_42]] : !fir.ref> -! CHECK: %[[VAL_44:.*]] = fir.convert %[[VAL_39]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_45:.*]] = fir.convert %[[VAL_43]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_46:.*]] = arith.ori %[[VAL_44]], %[[VAL_45]] : i1 -! CHECK: %[[VAL_47:.*]] = fir.convert %[[VAL_46]] : (i1) -> !fir.logical<4> -! CHECK: hlfir.assign %[[VAL_47]] to %[[VAL_28]]#0 : !fir.logical<4>, !fir.ref> -! CHECK: %[[VAL_48:.*]] = fir.load %[[VAL_29]]#0 : !fir.ref> -! CHECK: %[[VAL_49:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref -! CHECK: %[[VAL_50:.*]] = fir.convert %[[VAL_49]] : (i32) -> i64 -! CHECK: %[[VAL_51:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_50]]) : (!fir.ref>>, i64) -> !fir.ref> -! CHECK: %[[VAL_52:.*]] = fir.load %[[VAL_51]] : !fir.ref> -! CHECK: %[[VAL_53:.*]] = fir.convert %[[VAL_48]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_54:.*]] = fir.convert %[[VAL_52]] : (!fir.logical<4>) -> i1 -! CHECK: %[[VAL_55:.*]] = arith.ori %[[VAL_53]], %[[VAL_54]] : i1 -! CHECK: %[[VAL_56:.*]] = fir.convert %[[VAL_55]] : (i1) -> !fir.logical<4> -! CHECK: hlfir.assign %[[VAL_56]] to %[[VAL_29]]#0 : !fir.logical<4>, !fir.ref> -! CHECK: omp.yield +! CHECK: omp.wsloop reduction(@or_reduction %[[VAL_7]]#0 -> %[[VAL_23:.*]] : !fir.ref>, @or_reduction %[[VAL_9]]#0 -> %[[VAL_24:.*]] : !fir.ref>, @or_reduction %[[VAL_11]]#0 -> %[[VAL_25:.*]] : !fir.ref>) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_26:.*]]) : i32 = (%[[VAL_20]]) to (%[[VAL_21]]) inclusive step (%[[VAL_22]]) { +! CHECK: %[[VAL_27:.*]]:2 = hlfir.declare %[[VAL_23]] {uniq_name = "_QFmultiple_reductionsEx"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) +! CHECK: %[[VAL_28:.*]]:2 = hlfir.declare %[[VAL_24]] {uniq_name = "_QFmultiple_reductionsEy"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) +! CHECK: %[[VAL_29:.*]]:2 = hlfir.declare %[[VAL_25]] {uniq_name = "_QFmultiple_reductionsEz"} : (!fir.ref>) -> (!fir.ref>, !fir.ref>) +! CHECK: fir.store %[[VAL_26]] to %[[VAL_19]]#1 : !fir.ref +! CHECK: %[[VAL_30:.*]] = fir.load %[[VAL_27]]#0 : !fir.ref> +! CHECK: %[[VAL_31:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref +! CHECK: %[[VAL_32:.*]] = fir.convert %[[VAL_31]] : (i32) -> i64 +! CHECK: %[[VAL_33:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_32]]) : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_34:.*]] = fir.load %[[VAL_33]] : !fir.ref> +! CHECK: %[[VAL_35:.*]] = fir.convert %[[VAL_30]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_36:.*]] = fir.convert %[[VAL_34]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_37:.*]] = arith.ori %[[VAL_35]], %[[VAL_36]] : i1 +! CHECK: %[[VAL_38:.*]] = fir.convert %[[VAL_37]] : (i1) -> !fir.logical<4> +! CHECK: hlfir.assign %[[VAL_38]] to %[[VAL_27]]#0 : !fir.logical<4>, !fir.ref> +! CHECK: %[[VAL_39:.*]] = fir.load %[[VAL_28]]#0 : !fir.ref> +! CHECK: %[[VAL_40:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref +! CHECK: %[[VAL_41:.*]] = fir.convert %[[VAL_40]] : (i32) -> i64 +! CHECK: %[[VAL_42:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_41]]) : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_43:.*]] = fir.load %[[VAL_42]] : !fir.ref> +! CHECK: %[[VAL_44:.*]] = fir.convert %[[VAL_39]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_45:.*]] = fir.convert %[[VAL_43]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_46:.*]] = arith.ori %[[VAL_44]], %[[VAL_45]] : i1 +! CHECK: %[[VAL_47:.*]] = fir.convert %[[VAL_46]] : (i1) -> !fir.logical<4> +! CHECK: hlfir.assign %[[VAL_47]] to %[[VAL_28]]#0 : !fir.logical<4>, !fir.ref> +! CHECK: %[[VAL_48:.*]] = fir.load %[[VAL_29]]#0 : !fir.ref> +! CHECK: %[[VAL_49:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref +! CHECK: %[[VAL_50:.*]] = fir.convert %[[VAL_49]] : (i32) -> i64 +! CHECK: %[[VAL_51:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_50]]) : (!fir.ref>>, i64) -> !fir.ref> +! CHECK: %[[VAL_52:.*]] = fir.load %[[VAL_51]] : !fir.ref> +! CHECK: %[[VAL_53:.*]] = fir.convert %[[VAL_48]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_54:.*]] = fir.convert %[[VAL_52]] : (!fir.logical<4>) -> i1 +! CHECK: %[[VAL_55:.*]] = arith.ori %[[VAL_53]], %[[VAL_54]] : i1 +! CHECK: %[[VAL_56:.*]] = fir.convert %[[VAL_55]] : (i1) -> !fir.logical<4> +! CHECK: hlfir.assign %[[VAL_56]] to %[[VAL_29]]#0 : !fir.logical<4>, !fir.ref> +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return diff --git a/flang/test/Lower/OpenMP/wsloop-reduction-max-byref.f90 b/flang/test/Lower/OpenMP/wsloop-reduction-max-byref.f90 index 2f6921edcb42a5225893915e7663362e94f53f52..95bdc98f18c2bc0da4c45c47a31fd00681aa3022 100644 --- a/flang/test/Lower/OpenMP/wsloop-reduction-max-byref.f90 +++ b/flang/test/Lower/OpenMP/wsloop-reduction-max-byref.f90 @@ -46,18 +46,20 @@ ! CHECK: %[[VAL_9:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_10:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_11:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@max_byref_i32 %[[VAL_4]]#0 -> %[[VAL_12:.*]] : !fir.ref) for (%[[VAL_13:.*]]) : i32 = (%[[VAL_9]]) to (%[[VAL_10]]) inclusive step (%[[VAL_11]]) { -! CHECK: fir.store %[[VAL_13]] to %[[VAL_8]]#1 : !fir.ref -! CHECK: %[[VAL_14:.*]]:2 = hlfir.declare %[[VAL_12]] {uniq_name = "_QFreduction_max_intEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_15:.*]] = fir.load %[[VAL_8]]#0 : !fir.ref -! CHECK: %[[VAL_16:.*]] = fir.convert %[[VAL_15]] : (i32) -> i64 -! CHECK: %[[VAL_17:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_16]]) : (!fir.box>, i64) -> !fir.ref -! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_14]]#0 : !fir.ref -! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_17]] : !fir.ref -! CHECK: %[[VAL_20:.*]] = arith.cmpi sgt, %[[VAL_18]], %[[VAL_19]] : i32 -! CHECK: %[[VAL_21:.*]] = arith.select %[[VAL_20]], %[[VAL_18]], %[[VAL_19]] : i32 -! CHECK: hlfir.assign %[[VAL_21]] to %[[VAL_14]]#0 : i32, !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@max_byref_i32 %[[VAL_4]]#0 -> %[[VAL_12:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_13:.*]]) : i32 = (%[[VAL_9]]) to (%[[VAL_10]]) inclusive step (%[[VAL_11]]) { +! CHECK: %[[VAL_14:.*]]:2 = hlfir.declare %[[VAL_12]] {uniq_name = "_QFreduction_max_intEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: fir.store %[[VAL_13]] to %[[VAL_8]]#1 : !fir.ref +! CHECK: %[[VAL_15:.*]] = fir.load %[[VAL_8]]#0 : !fir.ref +! CHECK: %[[VAL_16:.*]] = fir.convert %[[VAL_15]] : (i32) -> i64 +! CHECK: %[[VAL_17:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_16]]) : (!fir.box>, i64) -> !fir.ref +! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_14]]#0 : !fir.ref +! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_17]] : !fir.ref +! CHECK: %[[VAL_20:.*]] = arith.cmpi sgt, %[[VAL_18]], %[[VAL_19]] : i32 +! CHECK: %[[VAL_21:.*]] = arith.select %[[VAL_20]], %[[VAL_18]], %[[VAL_19]] : i32 +! CHECK: hlfir.assign %[[VAL_21]] to %[[VAL_14]]#0 : i32, !fir.ref +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK-LABEL: func.func @_QPreduction_max_real( @@ -75,18 +77,20 @@ ! CHECK: %[[VAL_9:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_10:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_11:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@max_byref_f32 %[[VAL_4]]#0 -> %[[VAL_12:.*]] : !fir.ref) for (%[[VAL_13:.*]]) : i32 = (%[[VAL_9]]) to (%[[VAL_10]]) inclusive step (%[[VAL_11]]) { -! CHECK: fir.store %[[VAL_13]] to %[[VAL_8]]#1 : !fir.ref -! CHECK: %[[VAL_14:.*]]:2 = hlfir.declare %[[VAL_12]] {uniq_name = "_QFreduction_max_realEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_15:.*]] = fir.load %[[VAL_8]]#0 : !fir.ref -! CHECK: %[[VAL_16:.*]] = fir.convert %[[VAL_15]] : (i32) -> i64 -! CHECK: %[[VAL_17:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_16]]) : (!fir.box>, i64) -> !fir.ref -! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_17]] : !fir.ref -! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_14]]#0 : !fir.ref -! CHECK: %[[VAL_20:.*]] = arith.cmpf ogt, %[[VAL_18]], %[[VAL_19]] fastmath : f32 -! CHECK: %[[VAL_21:.*]] = arith.select %[[VAL_20]], %[[VAL_18]], %[[VAL_19]] : f32 -! CHECK: hlfir.assign %[[VAL_21]] to %[[VAL_14]]#0 : f32, !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@max_byref_f32 %[[VAL_4]]#0 -> %[[VAL_12:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_13:.*]]) : i32 = (%[[VAL_9]]) to (%[[VAL_10]]) inclusive step (%[[VAL_11]]) { +! CHECK: %[[VAL_14:.*]]:2 = hlfir.declare %[[VAL_12]] {uniq_name = "_QFreduction_max_realEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: fir.store %[[VAL_13]] to %[[VAL_8]]#1 : !fir.ref +! CHECK: %[[VAL_15:.*]] = fir.load %[[VAL_8]]#0 : !fir.ref +! CHECK: %[[VAL_16:.*]] = fir.convert %[[VAL_15]] : (i32) -> i64 +! CHECK: %[[VAL_17:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_16]]) : (!fir.box>, i64) -> !fir.ref +! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_17]] : !fir.ref +! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_14]]#0 : !fir.ref +! CHECK: %[[VAL_20:.*]] = arith.cmpf ogt, %[[VAL_18]], %[[VAL_19]] fastmath : f32 +! CHECK: %[[VAL_21:.*]] = arith.select %[[VAL_20]], %[[VAL_18]], %[[VAL_19]] : f32 +! CHECK: hlfir.assign %[[VAL_21]] to %[[VAL_14]]#0 : f32, !fir.ref +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: omp.parallel { ! CHECK: %[[VAL_30:.*]] = fir.alloca i32 {adapt.valuebyref, pinned} @@ -94,24 +98,26 @@ ! CHECK: %[[VAL_32:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_33:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_34:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@max_byref_f32 %[[VAL_4]]#0 -> %[[VAL_35:.*]] : !fir.ref) for (%[[VAL_36:.*]]) : i32 = (%[[VAL_32]]) to (%[[VAL_33]]) inclusive step (%[[VAL_34]]) { -! CHECK: fir.store %[[VAL_36]] to %[[VAL_31]]#1 : !fir.ref -! CHECK: %[[VAL_37:.*]]:2 = hlfir.declare %[[VAL_35]] {uniq_name = "_QFreduction_max_realEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_38:.*]] = fir.load %[[VAL_31]]#0 : !fir.ref -! CHECK: %[[VAL_39:.*]] = fir.convert %[[VAL_38]] : (i32) -> i64 -! CHECK: %[[VAL_40:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_39]]) : (!fir.box>, i64) -> !fir.ref -! CHECK: %[[VAL_41:.*]] = fir.load %[[VAL_40]] : !fir.ref -! CHECK: %[[VAL_42:.*]] = fir.load %[[VAL_37]]#0 : !fir.ref -! CHECK: %[[VAL_43:.*]] = arith.cmpf ogt, %[[VAL_41]], %[[VAL_42]] fastmath : f32 -! CHECK: fir.if %[[VAL_43]] { -! CHECK: %[[VAL_44:.*]] = fir.load %[[VAL_31]]#0 : !fir.ref -! CHECK: %[[VAL_45:.*]] = fir.convert %[[VAL_44]] : (i32) -> i64 -! CHECK: %[[VAL_46:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_45]]) : (!fir.box>, i64) -> !fir.ref -! CHECK: %[[VAL_47:.*]] = fir.load %[[VAL_46]] : !fir.ref -! CHECK: hlfir.assign %[[VAL_47]] to %[[VAL_37]]#0 : f32, !fir.ref -! CHECK: } else { -! CHECK: } -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@max_byref_f32 %[[VAL_4]]#0 -> %[[VAL_35:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_36:.*]]) : i32 = (%[[VAL_32]]) to (%[[VAL_33]]) inclusive step (%[[VAL_34]]) { +! CHECK: %[[VAL_37:.*]]:2 = hlfir.declare %[[VAL_35]] {uniq_name = "_QFreduction_max_realEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: fir.store %[[VAL_36]] to %[[VAL_31]]#1 : !fir.ref +! CHECK: %[[VAL_38:.*]] = fir.load %[[VAL_31]]#0 : !fir.ref +! CHECK: %[[VAL_39:.*]] = fir.convert %[[VAL_38]] : (i32) -> i64 +! CHECK: %[[VAL_40:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_39]]) : (!fir.box>, i64) -> !fir.ref +! CHECK: %[[VAL_41:.*]] = fir.load %[[VAL_40]] : !fir.ref +! CHECK: %[[VAL_42:.*]] = fir.load %[[VAL_37]]#0 : !fir.ref +! CHECK: %[[VAL_43:.*]] = arith.cmpf ogt, %[[VAL_41]], %[[VAL_42]] fastmath : f32 +! CHECK: fir.if %[[VAL_43]] { +! CHECK: %[[VAL_44:.*]] = fir.load %[[VAL_31]]#0 : !fir.ref +! CHECK: %[[VAL_45:.*]] = fir.convert %[[VAL_44]] : (i32) -> i64 +! CHECK: %[[VAL_46:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_45]]) : (!fir.box>, i64) -> !fir.ref +! CHECK: %[[VAL_47:.*]] = fir.load %[[VAL_46]] : !fir.ref +! CHECK: hlfir.assign %[[VAL_47]] to %[[VAL_37]]#0 : f32, !fir.ref +! CHECK: } else { +! CHECK: } +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator diff --git a/flang/test/Lower/OpenMP/wsloop-reduction-max-hlfir-byref.f90 b/flang/test/Lower/OpenMP/wsloop-reduction-max-hlfir-byref.f90 index 10bba6ac4b51bddb31ad4211103b2f2ef0ab6be2..352888bb94f51219c31f82585e6f74ed12f12718 100644 --- a/flang/test/Lower/OpenMP/wsloop-reduction-max-hlfir-byref.f90 +++ b/flang/test/Lower/OpenMP/wsloop-reduction-max-hlfir-byref.f90 @@ -33,18 +33,20 @@ ! CHECK: %[[VAL_9:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_10:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_11:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@max_byref_i32 %[[VAL_4]]#0 -> %[[VAL_12:.*]] : !fir.ref) for (%[[VAL_13:.*]]) : i32 = (%[[VAL_9]]) to (%[[VAL_10]]) inclusive step (%[[VAL_11]]) { -! CHECK: fir.store %[[VAL_13]] to %[[VAL_8]]#1 : !fir.ref -! CHECK: %[[VAL_14:.*]]:2 = hlfir.declare %[[VAL_12]] {uniq_name = "_QFreduction_max_intEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_15:.*]] = fir.load %[[VAL_8]]#0 : !fir.ref -! CHECK: %[[VAL_16:.*]] = fir.convert %[[VAL_15]] : (i32) -> i64 -! CHECK: %[[VAL_17:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_16]]) : (!fir.box>, i64) -> !fir.ref -! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_14]]#0 : !fir.ref -! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_17]] : !fir.ref -! CHECK: %[[VAL_20:.*]] = arith.cmpi sgt, %[[VAL_18]], %[[VAL_19]] : i32 -! CHECK: %[[VAL_21:.*]] = arith.select %[[VAL_20]], %[[VAL_18]], %[[VAL_19]] : i32 -! CHECK: hlfir.assign %[[VAL_21]] to %[[VAL_14]]#0 : i32, !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@max_byref_i32 %[[VAL_4]]#0 -> %[[VAL_12:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_13:.*]]) : i32 = (%[[VAL_9]]) to (%[[VAL_10]]) inclusive step (%[[VAL_11]]) { +! CHECK: %[[VAL_14:.*]]:2 = hlfir.declare %[[VAL_12]] {uniq_name = "_QFreduction_max_intEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: fir.store %[[VAL_13]] to %[[VAL_8]]#1 : !fir.ref +! CHECK: %[[VAL_15:.*]] = fir.load %[[VAL_8]]#0 : !fir.ref +! CHECK: %[[VAL_16:.*]] = fir.convert %[[VAL_15]] : (i32) -> i64 +! CHECK: %[[VAL_17:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_16]]) : (!fir.box>, i64) -> !fir.ref +! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_14]]#0 : !fir.ref +! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_17]] : !fir.ref +! CHECK: %[[VAL_20:.*]] = arith.cmpi sgt, %[[VAL_18]], %[[VAL_19]] : i32 +! CHECK: %[[VAL_21:.*]] = arith.select %[[VAL_20]], %[[VAL_18]], %[[VAL_19]] : i32 +! CHECK: hlfir.assign %[[VAL_21]] to %[[VAL_14]]#0 : i32, !fir.ref +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator diff --git a/flang/test/Lower/OpenMP/wsloop-reduction-max-hlfir.f90 b/flang/test/Lower/OpenMP/wsloop-reduction-max-hlfir.f90 index 5ea5d6626f186d6e93f0f8e544aaab1d3163cf8b..f4caea5a269a181281dbcdebdf66e7ab0b127e56 100644 --- a/flang/test/Lower/OpenMP/wsloop-reduction-max-hlfir.f90 +++ b/flang/test/Lower/OpenMP/wsloop-reduction-max-hlfir.f90 @@ -29,18 +29,20 @@ ! CHECK: %[[VAL_9:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_10:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_11:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@max_i32 %[[VAL_4]]#0 -> %[[VAL_12:.*]] : !fir.ref) for (%[[VAL_13:.*]]) : i32 = (%[[VAL_9]]) to (%[[VAL_10]]) inclusive step (%[[VAL_11]]) { -! CHECK: fir.store %[[VAL_13]] to %[[VAL_8]]#1 : !fir.ref -! CHECK: %[[VAL_14:.*]]:2 = hlfir.declare %[[VAL_12]] {uniq_name = "_QFreduction_max_intEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_15:.*]] = fir.load %[[VAL_8]]#0 : !fir.ref -! CHECK: %[[VAL_16:.*]] = fir.convert %[[VAL_15]] : (i32) -> i64 -! CHECK: %[[VAL_17:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_16]]) : (!fir.box>, i64) -> !fir.ref -! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_14]]#0 : !fir.ref -! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_17]] : !fir.ref -! CHECK: %[[VAL_20:.*]] = arith.cmpi sgt, %[[VAL_18]], %[[VAL_19]] : i32 -! CHECK: %[[VAL_21:.*]] = arith.select %[[VAL_20]], %[[VAL_18]], %[[VAL_19]] : i32 -! CHECK: hlfir.assign %[[VAL_21]] to %[[VAL_14]]#0 : i32, !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop reduction(@max_i32 %[[VAL_4]]#0 -> %[[VAL_12:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_13:.*]]) : i32 = (%[[VAL_9]]) to (%[[VAL_10]]) inclusive step (%[[VAL_11]]) { +! CHECK: %[[VAL_14:.*]]:2 = hlfir.declare %[[VAL_12]] {uniq_name = "_QFreduction_max_intEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: fir.store %[[VAL_13]] to %[[VAL_8]]#1 : !fir.ref +! CHECK: %[[VAL_15:.*]] = fir.load %[[VAL_8]]#0 : !fir.ref +! CHECK: %[[VAL_16:.*]] = fir.convert %[[VAL_15]] : (i32) -> i64 +! CHECK: %[[VAL_17:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_16]]) : (!fir.box>, i64) -> !fir.ref +! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_14]]#0 : !fir.ref +! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_17]] : !fir.ref +! CHECK: %[[VAL_20:.*]] = arith.cmpi sgt, %[[VAL_18]], %[[VAL_19]] : i32 +! CHECK: %[[VAL_21:.*]] = arith.select %[[VAL_20]], %[[VAL_18]], %[[VAL_19]] : i32 +! CHECK: hlfir.assign %[[VAL_21]] to %[[VAL_14]]#0 : i32, !fir.ref +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator diff --git a/flang/test/Lower/OpenMP/wsloop-reduction-max.f90 b/flang/test/Lower/OpenMP/wsloop-reduction-max.f90 index c9cf5cbf4f8c02d367de1b397b37ac8c6df5742b..ff005f32487e41f4882d59b3f63cc768638ecf30 100644 --- a/flang/test/Lower/OpenMP/wsloop-reduction-max.f90 +++ b/flang/test/Lower/OpenMP/wsloop-reduction-max.f90 @@ -40,18 +40,20 @@ ! CHECK: %[[VAL_9:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_10:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_11:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@max_i32 %[[VAL_4]]#0 -> %[[VAL_12:.*]] : !fir.ref) for (%[[VAL_13:.*]]) : i32 = (%[[VAL_9]]) to (%[[VAL_10]]) inclusive step (%[[VAL_11]]) { -! CHECK: fir.store %[[VAL_13]] to %[[VAL_8]]#1 : !fir.ref -! CHECK: %[[VAL_14:.*]]:2 = hlfir.declare %[[VAL_12]] {uniq_name = "_QFreduction_max_intEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_15:.*]] = fir.load %[[VAL_8]]#0 : !fir.ref -! CHECK: %[[VAL_16:.*]] = fir.convert %[[VAL_15]] : (i32) -> i64 -! CHECK: %[[VAL_17:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_16]]) : (!fir.box>, i64) -> !fir.ref -! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_14]]#0 : !fir.ref -! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_17]] : !fir.ref -! CHECK: %[[VAL_20:.*]] = arith.cmpi sgt, %[[VAL_18]], %[[VAL_19]] : i32 -! CHECK: %[[VAL_21:.*]] = arith.select %[[VAL_20]], %[[VAL_18]], %[[VAL_19]] : i32 -! CHECK: hlfir.assign %[[VAL_21]] to %[[VAL_14]]#0 : i32, !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop reduction(@max_i32 %[[VAL_4]]#0 -> %[[VAL_12:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_13:.*]]) : i32 = (%[[VAL_9]]) to (%[[VAL_10]]) inclusive step (%[[VAL_11]]) { +! CHECK: %[[VAL_14:.*]]:2 = hlfir.declare %[[VAL_12]] {uniq_name = "_QFreduction_max_intEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: fir.store %[[VAL_13]] to %[[VAL_8]]#1 : !fir.ref +! CHECK: %[[VAL_15:.*]] = fir.load %[[VAL_8]]#0 : !fir.ref +! CHECK: %[[VAL_16:.*]] = fir.convert %[[VAL_15]] : (i32) -> i64 +! CHECK: %[[VAL_17:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_16]]) : (!fir.box>, i64) -> !fir.ref +! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_14]]#0 : !fir.ref +! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_17]] : !fir.ref +! CHECK: %[[VAL_20:.*]] = arith.cmpi sgt, %[[VAL_18]], %[[VAL_19]] : i32 +! CHECK: %[[VAL_21:.*]] = arith.select %[[VAL_20]], %[[VAL_18]], %[[VAL_19]] : i32 +! CHECK: hlfir.assign %[[VAL_21]] to %[[VAL_14]]#0 : i32, !fir.ref +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK-LABEL: func.func @_QPreduction_max_real( @@ -69,18 +71,20 @@ ! CHECK: %[[VAL_9:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_10:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_11:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@max_f32 %[[VAL_4]]#0 -> %[[VAL_12:.*]] : !fir.ref) for (%[[VAL_13:.*]]) : i32 = (%[[VAL_9]]) to (%[[VAL_10]]) inclusive step (%[[VAL_11]]) { -! CHECK: fir.store %[[VAL_13]] to %[[VAL_8]]#1 : !fir.ref -! CHECK: %[[VAL_14:.*]]:2 = hlfir.declare %[[VAL_12]] {uniq_name = "_QFreduction_max_realEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_15:.*]] = fir.load %[[VAL_8]]#0 : !fir.ref -! CHECK: %[[VAL_16:.*]] = fir.convert %[[VAL_15]] : (i32) -> i64 -! CHECK: %[[VAL_17:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_16]]) : (!fir.box>, i64) -> !fir.ref -! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_17]] : !fir.ref -! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_14]]#0 : !fir.ref -! CHECK: %[[VAL_20:.*]] = arith.cmpf ogt, %[[VAL_18]], %[[VAL_19]] fastmath : f32 -! CHECK: %[[VAL_21:.*]] = arith.select %[[VAL_20]], %[[VAL_18]], %[[VAL_19]] : f32 -! CHECK: hlfir.assign %[[VAL_21]] to %[[VAL_14]]#0 : f32, !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop reduction(@max_f32 %[[VAL_4]]#0 -> %[[VAL_12:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_13:.*]]) : i32 = (%[[VAL_9]]) to (%[[VAL_10]]) inclusive step (%[[VAL_11]]) { +! CHECK: %[[VAL_14:.*]]:2 = hlfir.declare %[[VAL_12]] {uniq_name = "_QFreduction_max_realEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: fir.store %[[VAL_13]] to %[[VAL_8]]#1 : !fir.ref +! CHECK: %[[VAL_15:.*]] = fir.load %[[VAL_8]]#0 : !fir.ref +! CHECK: %[[VAL_16:.*]] = fir.convert %[[VAL_15]] : (i32) -> i64 +! CHECK: %[[VAL_17:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_16]]) : (!fir.box>, i64) -> !fir.ref +! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_17]] : !fir.ref +! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_14]]#0 : !fir.ref +! CHECK: %[[VAL_20:.*]] = arith.cmpf ogt, %[[VAL_18]], %[[VAL_19]] fastmath : f32 +! CHECK: %[[VAL_21:.*]] = arith.select %[[VAL_20]], %[[VAL_18]], %[[VAL_19]] : f32 +! CHECK: hlfir.assign %[[VAL_21]] to %[[VAL_14]]#0 : f32, !fir.ref +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: omp.parallel { ! CHECK: %[[VAL_30:.*]] = fir.alloca i32 {adapt.valuebyref, pinned} @@ -88,24 +92,26 @@ ! CHECK: %[[VAL_32:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_33:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_34:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@max_f32 %[[VAL_4]]#0 -> %[[VAL_35:.*]] : !fir.ref) for (%[[VAL_36:.*]]) : i32 = (%[[VAL_32]]) to (%[[VAL_33]]) inclusive step (%[[VAL_34]]) { -! CHECK: fir.store %[[VAL_36]] to %[[VAL_31]]#1 : !fir.ref -! CHECK: %[[VAL_37:.*]]:2 = hlfir.declare %[[VAL_35]] {uniq_name = "_QFreduction_max_realEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_38:.*]] = fir.load %[[VAL_31]]#0 : !fir.ref -! CHECK: %[[VAL_39:.*]] = fir.convert %[[VAL_38]] : (i32) -> i64 -! CHECK: %[[VAL_40:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_39]]) : (!fir.box>, i64) -> !fir.ref -! CHECK: %[[VAL_41:.*]] = fir.load %[[VAL_40]] : !fir.ref -! CHECK: %[[VAL_42:.*]] = fir.load %[[VAL_37]]#0 : !fir.ref -! CHECK: %[[VAL_43:.*]] = arith.cmpf ogt, %[[VAL_41]], %[[VAL_42]] fastmath : f32 -! CHECK: fir.if %[[VAL_43]] { -! CHECK: %[[VAL_44:.*]] = fir.load %[[VAL_31]]#0 : !fir.ref -! CHECK: %[[VAL_45:.*]] = fir.convert %[[VAL_44]] : (i32) -> i64 -! CHECK: %[[VAL_46:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_45]]) : (!fir.box>, i64) -> !fir.ref -! CHECK: %[[VAL_47:.*]] = fir.load %[[VAL_46]] : !fir.ref -! CHECK: hlfir.assign %[[VAL_47]] to %[[VAL_37]]#0 : f32, !fir.ref -! CHECK: } else { -! CHECK: } -! CHECK: omp.yield +! CHECK: omp.wsloop reduction(@max_f32 %[[VAL_4]]#0 -> %[[VAL_35:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_36:.*]]) : i32 = (%[[VAL_32]]) to (%[[VAL_33]]) inclusive step (%[[VAL_34]]) { +! CHECK: %[[VAL_37:.*]]:2 = hlfir.declare %[[VAL_35]] {uniq_name = "_QFreduction_max_realEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: fir.store %[[VAL_36]] to %[[VAL_31]]#1 : !fir.ref +! CHECK: %[[VAL_38:.*]] = fir.load %[[VAL_31]]#0 : !fir.ref +! CHECK: %[[VAL_39:.*]] = fir.convert %[[VAL_38]] : (i32) -> i64 +! CHECK: %[[VAL_40:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_39]]) : (!fir.box>, i64) -> !fir.ref +! CHECK: %[[VAL_41:.*]] = fir.load %[[VAL_40]] : !fir.ref +! CHECK: %[[VAL_42:.*]] = fir.load %[[VAL_37]]#0 : !fir.ref +! CHECK: %[[VAL_43:.*]] = arith.cmpf ogt, %[[VAL_41]], %[[VAL_42]] fastmath : f32 +! CHECK: fir.if %[[VAL_43]] { +! CHECK: %[[VAL_44:.*]] = fir.load %[[VAL_31]]#0 : !fir.ref +! CHECK: %[[VAL_45:.*]] = fir.convert %[[VAL_44]] : (i32) -> i64 +! CHECK: %[[VAL_46:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_45]]) : (!fir.box>, i64) -> !fir.ref +! CHECK: %[[VAL_47:.*]] = fir.load %[[VAL_46]] : !fir.ref +! CHECK: hlfir.assign %[[VAL_47]] to %[[VAL_37]]#0 : f32, !fir.ref +! CHECK: } else { +! CHECK: } +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator diff --git a/flang/test/Lower/OpenMP/wsloop-reduction-min-byref.f90 b/flang/test/Lower/OpenMP/wsloop-reduction-min-byref.f90 index 84a376b46b8fbe607a650d7a0127fb7c6bc2306b..9787512ab078aeab88c97def499b5c651b1bca48 100644 --- a/flang/test/Lower/OpenMP/wsloop-reduction-min-byref.f90 +++ b/flang/test/Lower/OpenMP/wsloop-reduction-min-byref.f90 @@ -46,18 +46,20 @@ ! CHECK: %[[VAL_9:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_10:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_11:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@min_byref_i32 %[[VAL_4]]#0 -> %[[VAL_12:.*]] : !fir.ref) for (%[[VAL_13:.*]]) : i32 = (%[[VAL_9]]) to (%[[VAL_10]]) inclusive step (%[[VAL_11]]) { -! CHECK: fir.store %[[VAL_13]] to %[[VAL_8]]#1 : !fir.ref -! CHECK: %[[VAL_14:.*]]:2 = hlfir.declare %[[VAL_12]] {uniq_name = "_QFreduction_min_intEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_15:.*]] = fir.load %[[VAL_8]]#0 : !fir.ref -! CHECK: %[[VAL_16:.*]] = fir.convert %[[VAL_15]] : (i32) -> i64 -! CHECK: %[[VAL_17:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_16]]) : (!fir.box>, i64) -> !fir.ref -! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_14]]#0 : !fir.ref -! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_17]] : !fir.ref -! CHECK: %[[VAL_20:.*]] = arith.cmpi slt, %[[VAL_18]], %[[VAL_19]] : i32 -! CHECK: %[[VAL_21:.*]] = arith.select %[[VAL_20]], %[[VAL_18]], %[[VAL_19]] : i32 -! CHECK: hlfir.assign %[[VAL_21]] to %[[VAL_14]]#0 : i32, !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@min_byref_i32 %[[VAL_4]]#0 -> %[[VAL_12:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_13:.*]]) : i32 = (%[[VAL_9]]) to (%[[VAL_10]]) inclusive step (%[[VAL_11]]) { +! CHECK: %[[VAL_14:.*]]:2 = hlfir.declare %[[VAL_12]] {uniq_name = "_QFreduction_min_intEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: fir.store %[[VAL_13]] to %[[VAL_8]]#1 : !fir.ref +! CHECK: %[[VAL_15:.*]] = fir.load %[[VAL_8]]#0 : !fir.ref +! CHECK: %[[VAL_16:.*]] = fir.convert %[[VAL_15]] : (i32) -> i64 +! CHECK: %[[VAL_17:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_16]]) : (!fir.box>, i64) -> !fir.ref +! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_14]]#0 : !fir.ref +! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_17]] : !fir.ref +! CHECK: %[[VAL_20:.*]] = arith.cmpi slt, %[[VAL_18]], %[[VAL_19]] : i32 +! CHECK: %[[VAL_21:.*]] = arith.select %[[VAL_20]], %[[VAL_18]], %[[VAL_19]] : i32 +! CHECK: hlfir.assign %[[VAL_21]] to %[[VAL_14]]#0 : i32, !fir.ref +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK-LABEL: func.func @_QPreduction_min_real( @@ -75,19 +77,21 @@ ! CHECK: %[[VAL_9:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_10:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_11:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@min_byref_f32 %[[VAL_4]]#0 -> %[[VAL_12:.*]] : !fir.ref) for (%[[VAL_13:.*]]) : i32 = (%[[VAL_9]]) to (%[[VAL_10]]) inclusive step (%[[VAL_11]]) { -! CHECK: fir.store %[[VAL_13]] to %[[VAL_8]]#1 : !fir.ref -! CHECK: %[[VAL_14:.*]]:2 = hlfir.declare %[[VAL_12]] {uniq_name = "_QFreduction_min_realEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_15:.*]] = fir.load %[[VAL_8]]#0 : !fir.ref -! CHECK: %[[VAL_16:.*]] = fir.convert %[[VAL_15]] : (i32) -> i64 -! CHECK: %[[VAL_17:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_16]]) : (!fir.box>, i64) -> !fir.ref -! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_17]] : !fir.ref -! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_14]]#0 : !fir.ref -! CHECK: %[[VAL_20:.*]] = arith.cmpf olt, %[[VAL_18]], %[[VAL_19]] fastmath : f32 -! CHECK: %[[VAL_21:.*]] = arith.select %[[VAL_20]], %[[VAL_18]], %[[VAL_19]] : f32 -! CHECK: hlfir.assign %[[VAL_21]] to %[[VAL_14]]#0 : f32, !fir.ref -! CHECK: omp.yield -! CHECK: } +! CHECK: omp.wsloop byref reduction(@min_byref_f32 %[[VAL_4]]#0 -> %[[VAL_12:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_13:.*]]) : i32 = (%[[VAL_9]]) to (%[[VAL_10]]) inclusive step (%[[VAL_11]]) { +! CHECK: %[[VAL_14:.*]]:2 = hlfir.declare %[[VAL_12]] {uniq_name = "_QFreduction_min_realEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: fir.store %[[VAL_13]] to %[[VAL_8]]#1 : !fir.ref +! CHECK: %[[VAL_15:.*]] = fir.load %[[VAL_8]]#0 : !fir.ref +! CHECK: %[[VAL_16:.*]] = fir.convert %[[VAL_15]] : (i32) -> i64 +! CHECK: %[[VAL_17:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_16]]) : (!fir.box>, i64) -> !fir.ref +! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_17]] : !fir.ref +! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_14]]#0 : !fir.ref +! CHECK: %[[VAL_20:.*]] = arith.cmpf olt, %[[VAL_18]], %[[VAL_19]] fastmath : f32 +! CHECK: %[[VAL_21:.*]] = arith.select %[[VAL_20]], %[[VAL_18]], %[[VAL_19]] : f32 +! CHECK: hlfir.assign %[[VAL_21]] to %[[VAL_14]]#0 : f32, !fir.ref +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.parallel { @@ -96,24 +100,26 @@ ! CHECK: %[[VAL_32:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_33:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_34:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@min_byref_f32 %[[VAL_4]]#0 -> %[[VAL_35:.*]] : !fir.ref) for (%[[VAL_36:.*]]) : i32 = (%[[VAL_32]]) to (%[[VAL_33]]) inclusive step (%[[VAL_34]]) { -! CHECK: fir.store %[[VAL_36]] to %[[VAL_31]]#1 : !fir.ref -! CHECK: %[[VAL_37:.*]]:2 = hlfir.declare %[[VAL_35]] {uniq_name = "_QFreduction_min_realEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_38:.*]] = fir.load %[[VAL_31]]#0 : !fir.ref -! CHECK: %[[VAL_39:.*]] = fir.convert %[[VAL_38]] : (i32) -> i64 -! CHECK: %[[VAL_40:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_39]]) : (!fir.box>, i64) -> !fir.ref -! CHECK: %[[VAL_41:.*]] = fir.load %[[VAL_40]] : !fir.ref -! CHECK: %[[VAL_42:.*]] = fir.load %[[VAL_37]]#0 : !fir.ref -! CHECK: %[[VAL_43:.*]] = arith.cmpf ogt, %[[VAL_41]], %[[VAL_42]] fastmath : f32 -! CHECK: fir.if %[[VAL_43]] { -! CHECK: %[[VAL_44:.*]] = fir.load %[[VAL_31]]#0 : !fir.ref -! CHECK: %[[VAL_45:.*]] = fir.convert %[[VAL_44]] : (i32) -> i64 -! CHECK: %[[VAL_46:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_45]]) : (!fir.box>, i64) -> !fir.ref -! CHECK: %[[VAL_47:.*]] = fir.load %[[VAL_46]] : !fir.ref -! CHECK: hlfir.assign %[[VAL_47]] to %[[VAL_37]]#0 : f32, !fir.ref -! CHECK: } else { -! CHECK: } -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@min_byref_f32 %[[VAL_4]]#0 -> %[[VAL_35:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_36:.*]]) : i32 = (%[[VAL_32]]) to (%[[VAL_33]]) inclusive step (%[[VAL_34]]) { +! CHECK: %[[VAL_37:.*]]:2 = hlfir.declare %[[VAL_35]] {uniq_name = "_QFreduction_min_realEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: fir.store %[[VAL_36]] to %[[VAL_31]]#1 : !fir.ref +! CHECK: %[[VAL_38:.*]] = fir.load %[[VAL_31]]#0 : !fir.ref +! CHECK: %[[VAL_39:.*]] = fir.convert %[[VAL_38]] : (i32) -> i64 +! CHECK: %[[VAL_40:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_39]]) : (!fir.box>, i64) -> !fir.ref +! CHECK: %[[VAL_41:.*]] = fir.load %[[VAL_40]] : !fir.ref +! CHECK: %[[VAL_42:.*]] = fir.load %[[VAL_37]]#0 : !fir.ref +! CHECK: %[[VAL_43:.*]] = arith.cmpf ogt, %[[VAL_41]], %[[VAL_42]] fastmath : f32 +! CHECK: fir.if %[[VAL_43]] { +! CHECK: %[[VAL_44:.*]] = fir.load %[[VAL_31]]#0 : !fir.ref +! CHECK: %[[VAL_45:.*]] = fir.convert %[[VAL_44]] : (i32) -> i64 +! CHECK: %[[VAL_46:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_45]]) : (!fir.box>, i64) -> !fir.ref +! CHECK: %[[VAL_47:.*]] = fir.load %[[VAL_46]] : !fir.ref +! CHECK: hlfir.assign %[[VAL_47]] to %[[VAL_37]]#0 : f32, !fir.ref +! CHECK: } else { +! CHECK: } +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator diff --git a/flang/test/Lower/OpenMP/wsloop-reduction-min.f90 b/flang/test/Lower/OpenMP/wsloop-reduction-min.f90 index 3ba279acd14c41f8d821ea62520a14a8483e70a7..801ef99480a21cdb503f59ff951fb6da8103adfd 100644 --- a/flang/test/Lower/OpenMP/wsloop-reduction-min.f90 +++ b/flang/test/Lower/OpenMP/wsloop-reduction-min.f90 @@ -40,18 +40,20 @@ ! CHECK: %[[VAL_9:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_10:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_11:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@min_i32 %[[VAL_4]]#0 -> %[[VAL_12:.*]] : !fir.ref) for (%[[VAL_13:.*]]) : i32 = (%[[VAL_9]]) to (%[[VAL_10]]) inclusive step (%[[VAL_11]]) { -! CHECK: fir.store %[[VAL_13]] to %[[VAL_8]]#1 : !fir.ref -! CHECK: %[[VAL_14:.*]]:2 = hlfir.declare %[[VAL_12]] {uniq_name = "_QFreduction_min_intEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_15:.*]] = fir.load %[[VAL_8]]#0 : !fir.ref -! CHECK: %[[VAL_16:.*]] = fir.convert %[[VAL_15]] : (i32) -> i64 -! CHECK: %[[VAL_17:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_16]]) : (!fir.box>, i64) -> !fir.ref -! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_14]]#0 : !fir.ref -! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_17]] : !fir.ref -! CHECK: %[[VAL_20:.*]] = arith.cmpi slt, %[[VAL_18]], %[[VAL_19]] : i32 -! CHECK: %[[VAL_21:.*]] = arith.select %[[VAL_20]], %[[VAL_18]], %[[VAL_19]] : i32 -! CHECK: hlfir.assign %[[VAL_21]] to %[[VAL_14]]#0 : i32, !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop reduction(@min_i32 %[[VAL_4]]#0 -> %[[VAL_12:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_13:.*]]) : i32 = (%[[VAL_9]]) to (%[[VAL_10]]) inclusive step (%[[VAL_11]]) { +! CHECK: %[[VAL_14:.*]]:2 = hlfir.declare %[[VAL_12]] {uniq_name = "_QFreduction_min_intEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: fir.store %[[VAL_13]] to %[[VAL_8]]#1 : !fir.ref +! CHECK: %[[VAL_15:.*]] = fir.load %[[VAL_8]]#0 : !fir.ref +! CHECK: %[[VAL_16:.*]] = fir.convert %[[VAL_15]] : (i32) -> i64 +! CHECK: %[[VAL_17:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_16]]) : (!fir.box>, i64) -> !fir.ref +! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_14]]#0 : !fir.ref +! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_17]] : !fir.ref +! CHECK: %[[VAL_20:.*]] = arith.cmpi slt, %[[VAL_18]], %[[VAL_19]] : i32 +! CHECK: %[[VAL_21:.*]] = arith.select %[[VAL_20]], %[[VAL_18]], %[[VAL_19]] : i32 +! CHECK: hlfir.assign %[[VAL_21]] to %[[VAL_14]]#0 : i32, !fir.ref +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK-LABEL: func.func @_QPreduction_min_real( @@ -69,19 +71,21 @@ ! CHECK: %[[VAL_9:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_10:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_11:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@min_f32 %[[VAL_4]]#0 -> %[[VAL_12:.*]] : !fir.ref) for (%[[VAL_13:.*]]) : i32 = (%[[VAL_9]]) to (%[[VAL_10]]) inclusive step (%[[VAL_11]]) { -! CHECK: fir.store %[[VAL_13]] to %[[VAL_8]]#1 : !fir.ref -! CHECK: %[[VAL_14:.*]]:2 = hlfir.declare %[[VAL_12]] {uniq_name = "_QFreduction_min_realEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_15:.*]] = fir.load %[[VAL_8]]#0 : !fir.ref -! CHECK: %[[VAL_16:.*]] = fir.convert %[[VAL_15]] : (i32) -> i64 -! CHECK: %[[VAL_17:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_16]]) : (!fir.box>, i64) -> !fir.ref -! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_17]] : !fir.ref -! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_14]]#0 : !fir.ref -! CHECK: %[[VAL_20:.*]] = arith.cmpf olt, %[[VAL_18]], %[[VAL_19]] fastmath : f32 -! CHECK: %[[VAL_21:.*]] = arith.select %[[VAL_20]], %[[VAL_18]], %[[VAL_19]] : f32 -! CHECK: hlfir.assign %[[VAL_21]] to %[[VAL_14]]#0 : f32, !fir.ref -! CHECK: omp.yield -! CHECK: } +! CHECK: omp.wsloop reduction(@min_f32 %[[VAL_4]]#0 -> %[[VAL_12:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_13:.*]]) : i32 = (%[[VAL_9]]) to (%[[VAL_10]]) inclusive step (%[[VAL_11]]) { +! CHECK: %[[VAL_14:.*]]:2 = hlfir.declare %[[VAL_12]] {uniq_name = "_QFreduction_min_realEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: fir.store %[[VAL_13]] to %[[VAL_8]]#1 : !fir.ref +! CHECK: %[[VAL_15:.*]] = fir.load %[[VAL_8]]#0 : !fir.ref +! CHECK: %[[VAL_16:.*]] = fir.convert %[[VAL_15]] : (i32) -> i64 +! CHECK: %[[VAL_17:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_16]]) : (!fir.box>, i64) -> !fir.ref +! CHECK: %[[VAL_18:.*]] = fir.load %[[VAL_17]] : !fir.ref +! CHECK: %[[VAL_19:.*]] = fir.load %[[VAL_14]]#0 : !fir.ref +! CHECK: %[[VAL_20:.*]] = arith.cmpf olt, %[[VAL_18]], %[[VAL_19]] fastmath : f32 +! CHECK: %[[VAL_21:.*]] = arith.select %[[VAL_20]], %[[VAL_18]], %[[VAL_19]] : f32 +! CHECK: hlfir.assign %[[VAL_21]] to %[[VAL_14]]#0 : f32, !fir.ref +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.parallel { @@ -90,24 +94,26 @@ ! CHECK: %[[VAL_32:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_33:.*]] = arith.constant 100 : i32 ! CHECK: %[[VAL_34:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@min_f32 %[[VAL_4]]#0 -> %[[VAL_35:.*]] : !fir.ref) for (%[[VAL_36:.*]]) : i32 = (%[[VAL_32]]) to (%[[VAL_33]]) inclusive step (%[[VAL_34]]) { -! CHECK: fir.store %[[VAL_36]] to %[[VAL_31]]#1 : !fir.ref -! CHECK: %[[VAL_37:.*]]:2 = hlfir.declare %[[VAL_35]] {uniq_name = "_QFreduction_min_realEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_38:.*]] = fir.load %[[VAL_31]]#0 : !fir.ref -! CHECK: %[[VAL_39:.*]] = fir.convert %[[VAL_38]] : (i32) -> i64 -! CHECK: %[[VAL_40:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_39]]) : (!fir.box>, i64) -> !fir.ref -! CHECK: %[[VAL_41:.*]] = fir.load %[[VAL_40]] : !fir.ref -! CHECK: %[[VAL_42:.*]] = fir.load %[[VAL_37]]#0 : !fir.ref -! CHECK: %[[VAL_43:.*]] = arith.cmpf ogt, %[[VAL_41]], %[[VAL_42]] fastmath : f32 -! CHECK: fir.if %[[VAL_43]] { -! CHECK: %[[VAL_44:.*]] = fir.load %[[VAL_31]]#0 : !fir.ref -! CHECK: %[[VAL_45:.*]] = fir.convert %[[VAL_44]] : (i32) -> i64 -! CHECK: %[[VAL_46:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_45]]) : (!fir.box>, i64) -> !fir.ref -! CHECK: %[[VAL_47:.*]] = fir.load %[[VAL_46]] : !fir.ref -! CHECK: hlfir.assign %[[VAL_47]] to %[[VAL_37]]#0 : f32, !fir.ref -! CHECK: } else { -! CHECK: } -! CHECK: omp.yield +! CHECK: omp.wsloop reduction(@min_f32 %[[VAL_4]]#0 -> %[[VAL_35:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_36:.*]]) : i32 = (%[[VAL_32]]) to (%[[VAL_33]]) inclusive step (%[[VAL_34]]) { +! CHECK: %[[VAL_37:.*]]:2 = hlfir.declare %[[VAL_35]] {uniq_name = "_QFreduction_min_realEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: fir.store %[[VAL_36]] to %[[VAL_31]]#1 : !fir.ref +! CHECK: %[[VAL_38:.*]] = fir.load %[[VAL_31]]#0 : !fir.ref +! CHECK: %[[VAL_39:.*]] = fir.convert %[[VAL_38]] : (i32) -> i64 +! CHECK: %[[VAL_40:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_39]]) : (!fir.box>, i64) -> !fir.ref +! CHECK: %[[VAL_41:.*]] = fir.load %[[VAL_40]] : !fir.ref +! CHECK: %[[VAL_42:.*]] = fir.load %[[VAL_37]]#0 : !fir.ref +! CHECK: %[[VAL_43:.*]] = arith.cmpf ogt, %[[VAL_41]], %[[VAL_42]] fastmath : f32 +! CHECK: fir.if %[[VAL_43]] { +! CHECK: %[[VAL_44:.*]] = fir.load %[[VAL_31]]#0 : !fir.ref +! CHECK: %[[VAL_45:.*]] = fir.convert %[[VAL_44]] : (i32) -> i64 +! CHECK: %[[VAL_46:.*]] = hlfir.designate %[[VAL_5]]#0 (%[[VAL_45]]) : (!fir.box>, i64) -> !fir.ref +! CHECK: %[[VAL_47:.*]] = fir.load %[[VAL_46]] : !fir.ref +! CHECK: hlfir.assign %[[VAL_47]] to %[[VAL_37]]#0 : f32, !fir.ref +! CHECK: } else { +! CHECK: } +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator diff --git a/flang/test/Lower/OpenMP/wsloop-reduction-min2.f90 b/flang/test/Lower/OpenMP/wsloop-reduction-min2.f90 index 0138a9578206150567b90ef64afb9f8c59eaf122..a4c99f190dd2e5904088e1bd684e757bf056cec0 100644 --- a/flang/test/Lower/OpenMP/wsloop-reduction-min2.f90 +++ b/flang/test/Lower/OpenMP/wsloop-reduction-min2.f90 @@ -39,12 +39,14 @@ end program ! CHECK: %[[VAL_6:.*]] = arith.constant 0 : i32 ! CHECK: %[[VAL_7:.*]] = arith.constant 10 : i32 ! CHECK: %[[VAL_8:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@min_i32 %[[VAL_3]]#0 -> %[[VAL_9:.*]] : !fir.ref) for (%[[VAL_10:.*]]) : i32 = (%[[VAL_6]]) to (%[[VAL_7]]) inclusive step (%[[VAL_8]]) { -! CHECK: fir.store %[[VAL_10]] to %[[VAL_5]]#1 : !fir.ref -! CHECK: %[[VAL_11:.*]]:2 = hlfir.declare %[[VAL_9]] {uniq_name = "_QFEr"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_12:.*]] = fir.load %[[VAL_5]]#0 : !fir.ref -! CHECK: hlfir.assign %[[VAL_12]] to %[[VAL_11]]#0 : i32, !fir.ref -! CHECK: omp.yield -! CHECK: } +! CHECK: omp.wsloop reduction(@min_i32 %[[VAL_3]]#0 -> %[[VAL_9:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_10:.*]]) : i32 = (%[[VAL_6]]) to (%[[VAL_7]]) inclusive step (%[[VAL_8]]) { +! CHECK: %[[VAL_11:.*]]:2 = hlfir.declare %[[VAL_9]] {uniq_name = "_QFEr"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: fir.store %[[VAL_10]] to %[[VAL_5]]#1 : !fir.ref +! CHECK: %[[VAL_12:.*]] = fir.load %[[VAL_5]]#0 : !fir.ref +! CHECK: hlfir.assign %[[VAL_12]] to %[[VAL_11]]#0 : i32, !fir.ref +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: } diff --git a/flang/test/Lower/OpenMP/wsloop-reduction-mul-byref.f90 b/flang/test/Lower/OpenMP/wsloop-reduction-mul-byref.f90 index a2829948d472a82a72a1d01d544016e82c98e57b..7c538cdd470f8ba8c78ab8e829ff1f22f5e057c4 100644 --- a/flang/test/Lower/OpenMP/wsloop-reduction-mul-byref.f90 +++ b/flang/test/Lower/OpenMP/wsloop-reduction-mul-byref.f90 @@ -85,14 +85,16 @@ ! CHECK: %[[VAL_7:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_8:.*]] = arith.constant 10 : i32 ! CHECK: %[[VAL_9:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@multiply_reduction_byref_i32 %[[VAL_3]]#0 -> %[[VAL_10:.*]] : !fir.ref) for (%[[VAL_11:.*]]) : i32 = (%[[VAL_7]]) to (%[[VAL_8]]) inclusive step (%[[VAL_9]]) { -! CHECK: fir.store %[[VAL_11]] to %[[VAL_6]]#1 : !fir.ref -! CHECK: %[[VAL_12:.*]]:2 = hlfir.declare %[[VAL_10]] {uniq_name = "_QFsimple_int_reductionEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_13:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref -! CHECK: %[[VAL_14:.*]] = fir.load %[[VAL_6]]#0 : !fir.ref -! CHECK: %[[VAL_15:.*]] = arith.muli %[[VAL_13]], %[[VAL_14]] : i32 -! CHECK: hlfir.assign %[[VAL_15]] to %[[VAL_12]]#0 : i32, !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@multiply_reduction_byref_i32 %[[VAL_3]]#0 -> %[[VAL_10:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_11:.*]]) : i32 = (%[[VAL_7]]) to (%[[VAL_8]]) inclusive step (%[[VAL_9]]) { +! CHECK: %[[VAL_12:.*]]:2 = hlfir.declare %[[VAL_10]] {uniq_name = "_QFsimple_int_reductionEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: fir.store %[[VAL_11]] to %[[VAL_6]]#1 : !fir.ref +! CHECK: %[[VAL_13:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref +! CHECK: %[[VAL_14:.*]] = fir.load %[[VAL_6]]#0 : !fir.ref +! CHECK: %[[VAL_15:.*]] = arith.muli %[[VAL_13]], %[[VAL_14]] : i32 +! CHECK: hlfir.assign %[[VAL_15]] to %[[VAL_12]]#0 : i32, !fir.ref +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return @@ -121,15 +123,17 @@ end subroutine ! CHECK: %[[VAL_7:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_8:.*]] = arith.constant 10 : i32 ! CHECK: %[[VAL_9:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@multiply_reduction_byref_f32 %[[VAL_3]]#0 -> %[[VAL_10:.*]] : !fir.ref) for (%[[VAL_11:.*]]) : i32 = (%[[VAL_7]]) to (%[[VAL_8]]) inclusive step (%[[VAL_9]]) { -! CHECK: fir.store %[[VAL_11]] to %[[VAL_6]]#1 : !fir.ref -! CHECK: %[[VAL_12:.*]]:2 = hlfir.declare %[[VAL_10]] {uniq_name = "_QFsimple_real_reductionEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_13:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref -! CHECK: %[[VAL_14:.*]] = fir.load %[[VAL_6]]#0 : !fir.ref -! CHECK: %[[VAL_15:.*]] = fir.convert %[[VAL_14]] : (i32) -> f32 -! CHECK: %[[VAL_16:.*]] = arith.mulf %[[VAL_13]], %[[VAL_15]] fastmath : f32 -! CHECK: hlfir.assign %[[VAL_16]] to %[[VAL_12]]#0 : f32, !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@multiply_reduction_byref_f32 %[[VAL_3]]#0 -> %[[VAL_10:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_11:.*]]) : i32 = (%[[VAL_7]]) to (%[[VAL_8]]) inclusive step (%[[VAL_9]]) { +! CHECK: %[[VAL_12:.*]]:2 = hlfir.declare %[[VAL_10]] {uniq_name = "_QFsimple_real_reductionEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: fir.store %[[VAL_11]] to %[[VAL_6]]#1 : !fir.ref +! CHECK: %[[VAL_13:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref +! CHECK: %[[VAL_14:.*]] = fir.load %[[VAL_6]]#0 : !fir.ref +! CHECK: %[[VAL_15:.*]] = fir.convert %[[VAL_14]] : (i32) -> f32 +! CHECK: %[[VAL_16:.*]] = arith.mulf %[[VAL_13]], %[[VAL_15]] fastmath : f32 +! CHECK: hlfir.assign %[[VAL_16]] to %[[VAL_12]]#0 : f32, !fir.ref +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return @@ -158,14 +162,16 @@ end subroutine ! CHECK: %[[VAL_7:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_8:.*]] = arith.constant 10 : i32 ! CHECK: %[[VAL_9:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@multiply_reduction_byref_i32 %[[VAL_3]]#0 -> %[[VAL_10:.*]] : !fir.ref) for (%[[VAL_11:.*]]) : i32 = (%[[VAL_7]]) to (%[[VAL_8]]) inclusive step (%[[VAL_9]]) { -! CHECK: fir.store %[[VAL_11]] to %[[VAL_6]]#1 : !fir.ref -! CHECK: %[[VAL_12:.*]]:2 = hlfir.declare %[[VAL_10]] {uniq_name = "_QFsimple_int_reduction_switch_orderEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_13:.*]] = fir.load %[[VAL_6]]#0 : !fir.ref -! CHECK: %[[VAL_14:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref -! CHECK: %[[VAL_15:.*]] = arith.muli %[[VAL_13]], %[[VAL_14]] : i32 -! CHECK: hlfir.assign %[[VAL_15]] to %[[VAL_12]]#0 : i32, !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@multiply_reduction_byref_i32 %[[VAL_3]]#0 -> %[[VAL_10:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_11:.*]]) : i32 = (%[[VAL_7]]) to (%[[VAL_8]]) inclusive step (%[[VAL_9]]) { +! CHECK: %[[VAL_12:.*]]:2 = hlfir.declare %[[VAL_10]] {uniq_name = "_QFsimple_int_reduction_switch_orderEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: fir.store %[[VAL_11]] to %[[VAL_6]]#1 : !fir.ref +! CHECK: %[[VAL_13:.*]] = fir.load %[[VAL_6]]#0 : !fir.ref +! CHECK: %[[VAL_14:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref +! CHECK: %[[VAL_15:.*]] = arith.muli %[[VAL_13]], %[[VAL_14]] : i32 +! CHECK: hlfir.assign %[[VAL_15]] to %[[VAL_12]]#0 : i32, !fir.ref +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return @@ -194,15 +200,17 @@ end subroutine ! CHECK: %[[VAL_7:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_8:.*]] = arith.constant 10 : i32 ! CHECK: %[[VAL_9:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@multiply_reduction_byref_f32 %[[VAL_3]]#0 -> %[[VAL_10:.*]] : !fir.ref) for (%[[VAL_11:.*]]) : i32 = (%[[VAL_7]]) to (%[[VAL_8]]) inclusive step (%[[VAL_9]]) { -! CHECK: fir.store %[[VAL_11]] to %[[VAL_6]]#1 : !fir.ref -! CHECK: %[[VAL_12:.*]]:2 = hlfir.declare %[[VAL_10]] {uniq_name = "_QFsimple_real_reduction_switch_orderEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_13:.*]] = fir.load %[[VAL_6]]#0 : !fir.ref -! CHECK: %[[VAL_14:.*]] = fir.convert %[[VAL_13]] : (i32) -> f32 -! CHECK: %[[VAL_15:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref -! CHECK: %[[VAL_16:.*]] = arith.mulf %[[VAL_14]], %[[VAL_15]] fastmath : f32 -! CHECK: hlfir.assign %[[VAL_16]] to %[[VAL_12]]#0 : f32, !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@multiply_reduction_byref_f32 %[[VAL_3]]#0 -> %[[VAL_10:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_11:.*]]) : i32 = (%[[VAL_7]]) to (%[[VAL_8]]) inclusive step (%[[VAL_9]]) { +! CHECK: %[[VAL_12:.*]]:2 = hlfir.declare %[[VAL_10]] {uniq_name = "_QFsimple_real_reduction_switch_orderEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: fir.store %[[VAL_11]] to %[[VAL_6]]#1 : !fir.ref +! CHECK: %[[VAL_13:.*]] = fir.load %[[VAL_6]]#0 : !fir.ref +! CHECK: %[[VAL_14:.*]] = fir.convert %[[VAL_13]] : (i32) -> f32 +! CHECK: %[[VAL_15:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref +! CHECK: %[[VAL_16:.*]] = arith.mulf %[[VAL_14]], %[[VAL_15]] fastmath : f32 +! CHECK: hlfir.assign %[[VAL_16]] to %[[VAL_12]]#0 : f32, !fir.ref +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return @@ -239,24 +247,26 @@ end subroutine ! CHECK: %[[VAL_13:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_14:.*]] = arith.constant 10 : i32 ! CHECK: %[[VAL_15:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@multiply_reduction_byref_i32 %[[VAL_3]]#0 -> %[[VAL_16:.*]] : !fir.ref, @multiply_reduction_byref_i32 %[[VAL_5]]#0 -> %[[VAL_17:.*]] : !fir.ref, @multiply_reduction_byref_i32 %[[VAL_7]]#0 -> %[[VAL_18:.*]] : !fir.ref) for (%[[VAL_19:.*]]) : i32 = (%[[VAL_13]]) to (%[[VAL_14]]) inclusive step (%[[VAL_15]]) { -! CHECK: fir.store %[[VAL_19]] to %[[VAL_12]]#1 : !fir.ref -! CHECK: %[[VAL_20:.*]]:2 = hlfir.declare %[[VAL_16]] {uniq_name = "_QFmultiple_int_reductions_same_typeEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_21:.*]]:2 = hlfir.declare %[[VAL_17]] {uniq_name = "_QFmultiple_int_reductions_same_typeEy"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_22:.*]]:2 = hlfir.declare %[[VAL_18]] {uniq_name = "_QFmultiple_int_reductions_same_typeEz"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_23:.*]] = fir.load %[[VAL_20]]#0 : !fir.ref -! CHECK: %[[VAL_24:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref -! CHECK: %[[VAL_25:.*]] = arith.muli %[[VAL_23]], %[[VAL_24]] : i32 -! CHECK: hlfir.assign %[[VAL_25]] to %[[VAL_20]]#0 : i32, !fir.ref -! CHECK: %[[VAL_26:.*]] = fir.load %[[VAL_21]]#0 : !fir.ref -! CHECK: %[[VAL_27:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref -! CHECK: %[[VAL_28:.*]] = arith.muli %[[VAL_26]], %[[VAL_27]] : i32 -! CHECK: hlfir.assign %[[VAL_28]] to %[[VAL_21]]#0 : i32, !fir.ref -! CHECK: %[[VAL_29:.*]] = fir.load %[[VAL_22]]#0 : !fir.ref -! CHECK: %[[VAL_30:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref -! CHECK: %[[VAL_31:.*]] = arith.muli %[[VAL_29]], %[[VAL_30]] : i32 -! CHECK: hlfir.assign %[[VAL_31]] to %[[VAL_22]]#0 : i32, !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@multiply_reduction_byref_i32 %[[VAL_3]]#0 -> %[[VAL_16:.*]] : !fir.ref, @multiply_reduction_byref_i32 %[[VAL_5]]#0 -> %[[VAL_17:.*]] : !fir.ref, @multiply_reduction_byref_i32 %[[VAL_7]]#0 -> %[[VAL_18:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_19:.*]]) : i32 = (%[[VAL_13]]) to (%[[VAL_14]]) inclusive step (%[[VAL_15]]) { +! CHECK: %[[VAL_20:.*]]:2 = hlfir.declare %[[VAL_16]] {uniq_name = "_QFmultiple_int_reductions_same_typeEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: %[[VAL_21:.*]]:2 = hlfir.declare %[[VAL_17]] {uniq_name = "_QFmultiple_int_reductions_same_typeEy"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: %[[VAL_22:.*]]:2 = hlfir.declare %[[VAL_18]] {uniq_name = "_QFmultiple_int_reductions_same_typeEz"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: fir.store %[[VAL_19]] to %[[VAL_12]]#1 : !fir.ref +! CHECK: %[[VAL_23:.*]] = fir.load %[[VAL_20]]#0 : !fir.ref +! CHECK: %[[VAL_24:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref +! CHECK: %[[VAL_25:.*]] = arith.muli %[[VAL_23]], %[[VAL_24]] : i32 +! CHECK: hlfir.assign %[[VAL_25]] to %[[VAL_20]]#0 : i32, !fir.ref +! CHECK: %[[VAL_26:.*]] = fir.load %[[VAL_21]]#0 : !fir.ref +! CHECK: %[[VAL_27:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref +! CHECK: %[[VAL_28:.*]] = arith.muli %[[VAL_26]], %[[VAL_27]] : i32 +! CHECK: hlfir.assign %[[VAL_28]] to %[[VAL_21]]#0 : i32, !fir.ref +! CHECK: %[[VAL_29:.*]] = fir.load %[[VAL_22]]#0 : !fir.ref +! CHECK: %[[VAL_30:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref +! CHECK: %[[VAL_31:.*]] = arith.muli %[[VAL_29]], %[[VAL_30]] : i32 +! CHECK: hlfir.assign %[[VAL_31]] to %[[VAL_22]]#0 : i32, !fir.ref +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return @@ -297,27 +307,29 @@ end subroutine ! CHECK: %[[VAL_13:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_14:.*]] = arith.constant 10 : i32 ! CHECK: %[[VAL_15:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@multiply_reduction_byref_f32 %[[VAL_3]]#0 -> %[[VAL_16:.*]] : !fir.ref, @multiply_reduction_byref_f32 %[[VAL_5]]#0 -> %[[VAL_17:.*]] : !fir.ref, @multiply_reduction_byref_f32 %[[VAL_7]]#0 -> %[[VAL_18:.*]] : !fir.ref) for (%[[VAL_19:.*]]) : i32 = (%[[VAL_13]]) to (%[[VAL_14]]) inclusive step (%[[VAL_15]]) { -! CHECK: fir.store %[[VAL_19]] to %[[VAL_12]]#1 : !fir.ref -! CHECK: %[[VAL_20:.*]]:2 = hlfir.declare %[[VAL_16]] {uniq_name = "_QFmultiple_real_reductions_same_typeEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_21:.*]]:2 = hlfir.declare %[[VAL_17]] {uniq_name = "_QFmultiple_real_reductions_same_typeEy"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_22:.*]]:2 = hlfir.declare %[[VAL_18]] {uniq_name = "_QFmultiple_real_reductions_same_typeEz"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_23:.*]] = fir.load %[[VAL_20]]#0 : !fir.ref -! CHECK: %[[VAL_24:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref -! CHECK: %[[VAL_25:.*]] = fir.convert %[[VAL_24]] : (i32) -> f32 -! CHECK: %[[VAL_26:.*]] = arith.mulf %[[VAL_23]], %[[VAL_25]] fastmath : f32 -! CHECK: hlfir.assign %[[VAL_26]] to %[[VAL_20]]#0 : f32, !fir.ref -! CHECK: %[[VAL_27:.*]] = fir.load %[[VAL_21]]#0 : !fir.ref -! CHECK: %[[VAL_28:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref -! CHECK: %[[VAL_29:.*]] = fir.convert %[[VAL_28]] : (i32) -> f32 -! CHECK: %[[VAL_30:.*]] = arith.mulf %[[VAL_27]], %[[VAL_29]] fastmath : f32 -! CHECK: hlfir.assign %[[VAL_30]] to %[[VAL_21]]#0 : f32, !fir.ref -! CHECK: %[[VAL_31:.*]] = fir.load %[[VAL_22]]#0 : !fir.ref -! CHECK: %[[VAL_32:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref -! CHECK: %[[VAL_33:.*]] = fir.convert %[[VAL_32]] : (i32) -> f32 -! CHECK: %[[VAL_34:.*]] = arith.mulf %[[VAL_31]], %[[VAL_33]] fastmath : f32 -! CHECK: hlfir.assign %[[VAL_34]] to %[[VAL_22]]#0 : f32, !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@multiply_reduction_byref_f32 %[[VAL_3]]#0 -> %[[VAL_16:.*]] : !fir.ref, @multiply_reduction_byref_f32 %[[VAL_5]]#0 -> %[[VAL_17:.*]] : !fir.ref, @multiply_reduction_byref_f32 %[[VAL_7]]#0 -> %[[VAL_18:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_19:.*]]) : i32 = (%[[VAL_13]]) to (%[[VAL_14]]) inclusive step (%[[VAL_15]]) { +! CHECK: %[[VAL_20:.*]]:2 = hlfir.declare %[[VAL_16]] {uniq_name = "_QFmultiple_real_reductions_same_typeEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: %[[VAL_21:.*]]:2 = hlfir.declare %[[VAL_17]] {uniq_name = "_QFmultiple_real_reductions_same_typeEy"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: %[[VAL_22:.*]]:2 = hlfir.declare %[[VAL_18]] {uniq_name = "_QFmultiple_real_reductions_same_typeEz"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: fir.store %[[VAL_19]] to %[[VAL_12]]#1 : !fir.ref +! CHECK: %[[VAL_23:.*]] = fir.load %[[VAL_20]]#0 : !fir.ref +! CHECK: %[[VAL_24:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref +! CHECK: %[[VAL_25:.*]] = fir.convert %[[VAL_24]] : (i32) -> f32 +! CHECK: %[[VAL_26:.*]] = arith.mulf %[[VAL_23]], %[[VAL_25]] fastmath : f32 +! CHECK: hlfir.assign %[[VAL_26]] to %[[VAL_20]]#0 : f32, !fir.ref +! CHECK: %[[VAL_27:.*]] = fir.load %[[VAL_21]]#0 : !fir.ref +! CHECK: %[[VAL_28:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref +! CHECK: %[[VAL_29:.*]] = fir.convert %[[VAL_28]] : (i32) -> f32 +! CHECK: %[[VAL_30:.*]] = arith.mulf %[[VAL_27]], %[[VAL_29]] fastmath : f32 +! CHECK: hlfir.assign %[[VAL_30]] to %[[VAL_21]]#0 : f32, !fir.ref +! CHECK: %[[VAL_31:.*]] = fir.load %[[VAL_22]]#0 : !fir.ref +! CHECK: %[[VAL_32:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref +! CHECK: %[[VAL_33:.*]] = fir.convert %[[VAL_32]] : (i32) -> f32 +! CHECK: %[[VAL_34:.*]] = arith.mulf %[[VAL_31]], %[[VAL_33]] fastmath : f32 +! CHECK: hlfir.assign %[[VAL_34]] to %[[VAL_22]]#0 : f32, !fir.ref +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return @@ -362,32 +374,34 @@ end subroutine ! CHECK: %[[VAL_16:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_17:.*]] = arith.constant 10 : i32 ! CHECK: %[[VAL_18:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop byref reduction(@multiply_reduction_byref_i32 %[[VAL_5]]#0 -> %[[VAL_19:.*]] : !fir.ref, @multiply_reduction_byref_i64 %[[VAL_7]]#0 -> %[[VAL_20:.*]] : !fir.ref, @multiply_reduction_byref_f32 %[[VAL_9]]#0 -> %[[VAL_21:.*]] : !fir.ref, @multiply_reduction_byref_f64 %[[VAL_3]]#0 -> %[[VAL_22:.*]] : !fir.ref) for (%[[VAL_23:.*]]) : i32 = (%[[VAL_16]]) to (%[[VAL_17]]) inclusive step (%[[VAL_18]]) { -! CHECK: fir.store %[[VAL_23]] to %[[VAL_15]]#1 : !fir.ref -! CHECK: %[[VAL_24:.*]]:2 = hlfir.declare %[[VAL_19]] {uniq_name = "_QFmultiple_reductions_different_typeEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_25:.*]]:2 = hlfir.declare %[[VAL_20]] {uniq_name = "_QFmultiple_reductions_different_typeEy"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_26:.*]]:2 = hlfir.declare %[[VAL_21]] {uniq_name = "_QFmultiple_reductions_different_typeEz"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_27:.*]]:2 = hlfir.declare %[[VAL_22]] {uniq_name = "_QFmultiple_reductions_different_typeEw"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_28:.*]] = fir.load %[[VAL_24]]#0 : !fir.ref -! CHECK: %[[VAL_29:.*]] = fir.load %[[VAL_15]]#0 : !fir.ref -! CHECK: %[[VAL_30:.*]] = arith.muli %[[VAL_28]], %[[VAL_29]] : i32 -! CHECK: hlfir.assign %[[VAL_30]] to %[[VAL_24]]#0 : i32, !fir.ref -! CHECK: %[[VAL_31:.*]] = fir.load %[[VAL_25]]#0 : !fir.ref -! CHECK: %[[VAL_32:.*]] = fir.load %[[VAL_15]]#0 : !fir.ref -! CHECK: %[[VAL_33:.*]] = fir.convert %[[VAL_32]] : (i32) -> i64 -! CHECK: %[[VAL_34:.*]] = arith.muli %[[VAL_31]], %[[VAL_33]] : i64 -! CHECK: hlfir.assign %[[VAL_34]] to %[[VAL_25]]#0 : i64, !fir.ref -! CHECK: %[[VAL_35:.*]] = fir.load %[[VAL_26]]#0 : !fir.ref -! CHECK: %[[VAL_36:.*]] = fir.load %[[VAL_15]]#0 : !fir.ref -! CHECK: %[[VAL_37:.*]] = fir.convert %[[VAL_36]] : (i32) -> f32 -! CHECK: %[[VAL_38:.*]] = arith.mulf %[[VAL_35]], %[[VAL_37]] fastmath : f32 -! CHECK: hlfir.assign %[[VAL_38]] to %[[VAL_26]]#0 : f32, !fir.ref -! CHECK: %[[VAL_39:.*]] = fir.load %[[VAL_27]]#0 : !fir.ref -! CHECK: %[[VAL_40:.*]] = fir.load %[[VAL_15]]#0 : !fir.ref -! CHECK: %[[VAL_41:.*]] = fir.convert %[[VAL_40]] : (i32) -> f64 -! CHECK: %[[VAL_42:.*]] = arith.mulf %[[VAL_39]], %[[VAL_41]] fastmath : f64 -! CHECK: hlfir.assign %[[VAL_42]] to %[[VAL_27]]#0 : f64, !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop byref reduction(@multiply_reduction_byref_i32 %[[VAL_5]]#0 -> %[[VAL_19:.*]] : !fir.ref, @multiply_reduction_byref_i64 %[[VAL_7]]#0 -> %[[VAL_20:.*]] : !fir.ref, @multiply_reduction_byref_f32 %[[VAL_9]]#0 -> %[[VAL_21:.*]] : !fir.ref, @multiply_reduction_byref_f64 %[[VAL_3]]#0 -> %[[VAL_22:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_23:.*]]) : i32 = (%[[VAL_16]]) to (%[[VAL_17]]) inclusive step (%[[VAL_18]]) { +! CHECK: %[[VAL_24:.*]]:2 = hlfir.declare %[[VAL_19]] {uniq_name = "_QFmultiple_reductions_different_typeEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: %[[VAL_25:.*]]:2 = hlfir.declare %[[VAL_20]] {uniq_name = "_QFmultiple_reductions_different_typeEy"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: %[[VAL_26:.*]]:2 = hlfir.declare %[[VAL_21]] {uniq_name = "_QFmultiple_reductions_different_typeEz"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: %[[VAL_27:.*]]:2 = hlfir.declare %[[VAL_22]] {uniq_name = "_QFmultiple_reductions_different_typeEw"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: fir.store %[[VAL_23]] to %[[VAL_15]]#1 : !fir.ref +! CHECK: %[[VAL_28:.*]] = fir.load %[[VAL_24]]#0 : !fir.ref +! CHECK: %[[VAL_29:.*]] = fir.load %[[VAL_15]]#0 : !fir.ref +! CHECK: %[[VAL_30:.*]] = arith.muli %[[VAL_28]], %[[VAL_29]] : i32 +! CHECK: hlfir.assign %[[VAL_30]] to %[[VAL_24]]#0 : i32, !fir.ref +! CHECK: %[[VAL_31:.*]] = fir.load %[[VAL_25]]#0 : !fir.ref +! CHECK: %[[VAL_32:.*]] = fir.load %[[VAL_15]]#0 : !fir.ref +! CHECK: %[[VAL_33:.*]] = fir.convert %[[VAL_32]] : (i32) -> i64 +! CHECK: %[[VAL_34:.*]] = arith.muli %[[VAL_31]], %[[VAL_33]] : i64 +! CHECK: hlfir.assign %[[VAL_34]] to %[[VAL_25]]#0 : i64, !fir.ref +! CHECK: %[[VAL_35:.*]] = fir.load %[[VAL_26]]#0 : !fir.ref +! CHECK: %[[VAL_36:.*]] = fir.load %[[VAL_15]]#0 : !fir.ref +! CHECK: %[[VAL_37:.*]] = fir.convert %[[VAL_36]] : (i32) -> f32 +! CHECK: %[[VAL_38:.*]] = arith.mulf %[[VAL_35]], %[[VAL_37]] fastmath : f32 +! CHECK: hlfir.assign %[[VAL_38]] to %[[VAL_26]]#0 : f32, !fir.ref +! CHECK: %[[VAL_39:.*]] = fir.load %[[VAL_27]]#0 : !fir.ref +! CHECK: %[[VAL_40:.*]] = fir.load %[[VAL_15]]#0 : !fir.ref +! CHECK: %[[VAL_41:.*]] = fir.convert %[[VAL_40]] : (i32) -> f64 +! CHECK: %[[VAL_42:.*]] = arith.mulf %[[VAL_39]], %[[VAL_41]] fastmath : f64 +! CHECK: hlfir.assign %[[VAL_42]] to %[[VAL_27]]#0 : f64, !fir.ref +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return diff --git a/flang/test/Lower/OpenMP/wsloop-reduction-mul.f90 b/flang/test/Lower/OpenMP/wsloop-reduction-mul.f90 index 90d9aa5e839bde13001e2f388ea9728c67e935fb..08be4d84c1a62fdfaa6e3b386b07a27c153d73fc 100644 --- a/flang/test/Lower/OpenMP/wsloop-reduction-mul.f90 +++ b/flang/test/Lower/OpenMP/wsloop-reduction-mul.f90 @@ -60,14 +60,16 @@ ! CHECK: %[[VAL_7:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_8:.*]] = arith.constant 10 : i32 ! CHECK: %[[VAL_9:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@multiply_reduction_i32 %[[VAL_3]]#0 -> %[[VAL_10:.*]] : !fir.ref) for (%[[VAL_11:.*]]) : i32 = (%[[VAL_7]]) to (%[[VAL_8]]) inclusive step (%[[VAL_9]]) { -! CHECK: fir.store %[[VAL_11]] to %[[VAL_6]]#1 : !fir.ref -! CHECK: %[[VAL_12:.*]]:2 = hlfir.declare %[[VAL_10]] {uniq_name = "_QFsimple_int_reductionEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_13:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref -! CHECK: %[[VAL_14:.*]] = fir.load %[[VAL_6]]#0 : !fir.ref -! CHECK: %[[VAL_15:.*]] = arith.muli %[[VAL_13]], %[[VAL_14]] : i32 -! CHECK: hlfir.assign %[[VAL_15]] to %[[VAL_12]]#0 : i32, !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop reduction(@multiply_reduction_i32 %[[VAL_3]]#0 -> %[[VAL_10:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_11:.*]]) : i32 = (%[[VAL_7]]) to (%[[VAL_8]]) inclusive step (%[[VAL_9]]) { +! CHECK: %[[VAL_12:.*]]:2 = hlfir.declare %[[VAL_10]] {uniq_name = "_QFsimple_int_reductionEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: fir.store %[[VAL_11]] to %[[VAL_6]]#1 : !fir.ref +! CHECK: %[[VAL_13:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref +! CHECK: %[[VAL_14:.*]] = fir.load %[[VAL_6]]#0 : !fir.ref +! CHECK: %[[VAL_15:.*]] = arith.muli %[[VAL_13]], %[[VAL_14]] : i32 +! CHECK: hlfir.assign %[[VAL_15]] to %[[VAL_12]]#0 : i32, !fir.ref +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return @@ -96,15 +98,17 @@ end subroutine ! CHECK: %[[VAL_7:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_8:.*]] = arith.constant 10 : i32 ! CHECK: %[[VAL_9:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@multiply_reduction_f32 %[[VAL_3]]#0 -> %[[VAL_10:.*]] : !fir.ref) for (%[[VAL_11:.*]]) : i32 = (%[[VAL_7]]) to (%[[VAL_8]]) inclusive step (%[[VAL_9]]) { -! CHECK: fir.store %[[VAL_11]] to %[[VAL_6]]#1 : !fir.ref -! CHECK: %[[VAL_12:.*]]:2 = hlfir.declare %[[VAL_10]] {uniq_name = "_QFsimple_real_reductionEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_13:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref -! CHECK: %[[VAL_14:.*]] = fir.load %[[VAL_6]]#0 : !fir.ref -! CHECK: %[[VAL_15:.*]] = fir.convert %[[VAL_14]] : (i32) -> f32 -! CHECK: %[[VAL_16:.*]] = arith.mulf %[[VAL_13]], %[[VAL_15]] fastmath : f32 -! CHECK: hlfir.assign %[[VAL_16]] to %[[VAL_12]]#0 : f32, !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop reduction(@multiply_reduction_f32 %[[VAL_3]]#0 -> %[[VAL_10:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_11:.*]]) : i32 = (%[[VAL_7]]) to (%[[VAL_8]]) inclusive step (%[[VAL_9]]) { +! CHECK: %[[VAL_12:.*]]:2 = hlfir.declare %[[VAL_10]] {uniq_name = "_QFsimple_real_reductionEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: fir.store %[[VAL_11]] to %[[VAL_6]]#1 : !fir.ref +! CHECK: %[[VAL_13:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref +! CHECK: %[[VAL_14:.*]] = fir.load %[[VAL_6]]#0 : !fir.ref +! CHECK: %[[VAL_15:.*]] = fir.convert %[[VAL_14]] : (i32) -> f32 +! CHECK: %[[VAL_16:.*]] = arith.mulf %[[VAL_13]], %[[VAL_15]] fastmath : f32 +! CHECK: hlfir.assign %[[VAL_16]] to %[[VAL_12]]#0 : f32, !fir.ref +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return @@ -133,14 +137,16 @@ end subroutine ! CHECK: %[[VAL_7:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_8:.*]] = arith.constant 10 : i32 ! CHECK: %[[VAL_9:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@multiply_reduction_i32 %[[VAL_3]]#0 -> %[[VAL_10:.*]] : !fir.ref) for (%[[VAL_11:.*]]) : i32 = (%[[VAL_7]]) to (%[[VAL_8]]) inclusive step (%[[VAL_9]]) { -! CHECK: fir.store %[[VAL_11]] to %[[VAL_6]]#1 : !fir.ref -! CHECK: %[[VAL_12:.*]]:2 = hlfir.declare %[[VAL_10]] {uniq_name = "_QFsimple_int_reduction_switch_orderEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_13:.*]] = fir.load %[[VAL_6]]#0 : !fir.ref -! CHECK: %[[VAL_14:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref -! CHECK: %[[VAL_15:.*]] = arith.muli %[[VAL_13]], %[[VAL_14]] : i32 -! CHECK: hlfir.assign %[[VAL_15]] to %[[VAL_12]]#0 : i32, !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop reduction(@multiply_reduction_i32 %[[VAL_3]]#0 -> %[[VAL_10:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_11:.*]]) : i32 = (%[[VAL_7]]) to (%[[VAL_8]]) inclusive step (%[[VAL_9]]) { +! CHECK: %[[VAL_12:.*]]:2 = hlfir.declare %[[VAL_10]] {uniq_name = "_QFsimple_int_reduction_switch_orderEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: fir.store %[[VAL_11]] to %[[VAL_6]]#1 : !fir.ref +! CHECK: %[[VAL_13:.*]] = fir.load %[[VAL_6]]#0 : !fir.ref +! CHECK: %[[VAL_14:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref +! CHECK: %[[VAL_15:.*]] = arith.muli %[[VAL_13]], %[[VAL_14]] : i32 +! CHECK: hlfir.assign %[[VAL_15]] to %[[VAL_12]]#0 : i32, !fir.ref +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return @@ -169,15 +175,17 @@ end subroutine ! CHECK: %[[VAL_7:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_8:.*]] = arith.constant 10 : i32 ! CHECK: %[[VAL_9:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@multiply_reduction_f32 %[[VAL_3]]#0 -> %[[VAL_10:.*]] : !fir.ref) for (%[[VAL_11:.*]]) : i32 = (%[[VAL_7]]) to (%[[VAL_8]]) inclusive step (%[[VAL_9]]) { -! CHECK: fir.store %[[VAL_11]] to %[[VAL_6]]#1 : !fir.ref -! CHECK: %[[VAL_12:.*]]:2 = hlfir.declare %[[VAL_10]] {uniq_name = "_QFsimple_real_reduction_switch_orderEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_13:.*]] = fir.load %[[VAL_6]]#0 : !fir.ref -! CHECK: %[[VAL_14:.*]] = fir.convert %[[VAL_13]] : (i32) -> f32 -! CHECK: %[[VAL_15:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref -! CHECK: %[[VAL_16:.*]] = arith.mulf %[[VAL_14]], %[[VAL_15]] fastmath : f32 -! CHECK: hlfir.assign %[[VAL_16]] to %[[VAL_12]]#0 : f32, !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop reduction(@multiply_reduction_f32 %[[VAL_3]]#0 -> %[[VAL_10:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_11:.*]]) : i32 = (%[[VAL_7]]) to (%[[VAL_8]]) inclusive step (%[[VAL_9]]) { +! CHECK: %[[VAL_12:.*]]:2 = hlfir.declare %[[VAL_10]] {uniq_name = "_QFsimple_real_reduction_switch_orderEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: fir.store %[[VAL_11]] to %[[VAL_6]]#1 : !fir.ref +! CHECK: %[[VAL_13:.*]] = fir.load %[[VAL_6]]#0 : !fir.ref +! CHECK: %[[VAL_14:.*]] = fir.convert %[[VAL_13]] : (i32) -> f32 +! CHECK: %[[VAL_15:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref +! CHECK: %[[VAL_16:.*]] = arith.mulf %[[VAL_14]], %[[VAL_15]] fastmath : f32 +! CHECK: hlfir.assign %[[VAL_16]] to %[[VAL_12]]#0 : f32, !fir.ref +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return @@ -214,24 +222,26 @@ end subroutine ! CHECK: %[[VAL_13:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_14:.*]] = arith.constant 10 : i32 ! CHECK: %[[VAL_15:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@multiply_reduction_i32 %[[VAL_3]]#0 -> %[[VAL_16:.*]] : !fir.ref, @multiply_reduction_i32 %[[VAL_5]]#0 -> %[[VAL_17:.*]] : !fir.ref, @multiply_reduction_i32 %[[VAL_7]]#0 -> %[[VAL_18:.*]] : !fir.ref) for (%[[VAL_19:.*]]) : i32 = (%[[VAL_13]]) to (%[[VAL_14]]) inclusive step (%[[VAL_15]]) { -! CHECK: fir.store %[[VAL_19]] to %[[VAL_12]]#1 : !fir.ref -! CHECK: %[[VAL_20:.*]]:2 = hlfir.declare %[[VAL_16]] {uniq_name = "_QFmultiple_int_reductions_same_typeEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_21:.*]]:2 = hlfir.declare %[[VAL_17]] {uniq_name = "_QFmultiple_int_reductions_same_typeEy"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_22:.*]]:2 = hlfir.declare %[[VAL_18]] {uniq_name = "_QFmultiple_int_reductions_same_typeEz"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_23:.*]] = fir.load %[[VAL_20]]#0 : !fir.ref -! CHECK: %[[VAL_24:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref -! CHECK: %[[VAL_25:.*]] = arith.muli %[[VAL_23]], %[[VAL_24]] : i32 -! CHECK: hlfir.assign %[[VAL_25]] to %[[VAL_20]]#0 : i32, !fir.ref -! CHECK: %[[VAL_26:.*]] = fir.load %[[VAL_21]]#0 : !fir.ref -! CHECK: %[[VAL_27:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref -! CHECK: %[[VAL_28:.*]] = arith.muli %[[VAL_26]], %[[VAL_27]] : i32 -! CHECK: hlfir.assign %[[VAL_28]] to %[[VAL_21]]#0 : i32, !fir.ref -! CHECK: %[[VAL_29:.*]] = fir.load %[[VAL_22]]#0 : !fir.ref -! CHECK: %[[VAL_30:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref -! CHECK: %[[VAL_31:.*]] = arith.muli %[[VAL_29]], %[[VAL_30]] : i32 -! CHECK: hlfir.assign %[[VAL_31]] to %[[VAL_22]]#0 : i32, !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop reduction(@multiply_reduction_i32 %[[VAL_3]]#0 -> %[[VAL_16:.*]] : !fir.ref, @multiply_reduction_i32 %[[VAL_5]]#0 -> %[[VAL_17:.*]] : !fir.ref, @multiply_reduction_i32 %[[VAL_7]]#0 -> %[[VAL_18:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_19:.*]]) : i32 = (%[[VAL_13]]) to (%[[VAL_14]]) inclusive step (%[[VAL_15]]) { +! CHECK: %[[VAL_20:.*]]:2 = hlfir.declare %[[VAL_16]] {uniq_name = "_QFmultiple_int_reductions_same_typeEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: %[[VAL_21:.*]]:2 = hlfir.declare %[[VAL_17]] {uniq_name = "_QFmultiple_int_reductions_same_typeEy"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: %[[VAL_22:.*]]:2 = hlfir.declare %[[VAL_18]] {uniq_name = "_QFmultiple_int_reductions_same_typeEz"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: fir.store %[[VAL_19]] to %[[VAL_12]]#1 : !fir.ref +! CHECK: %[[VAL_23:.*]] = fir.load %[[VAL_20]]#0 : !fir.ref +! CHECK: %[[VAL_24:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref +! CHECK: %[[VAL_25:.*]] = arith.muli %[[VAL_23]], %[[VAL_24]] : i32 +! CHECK: hlfir.assign %[[VAL_25]] to %[[VAL_20]]#0 : i32, !fir.ref +! CHECK: %[[VAL_26:.*]] = fir.load %[[VAL_21]]#0 : !fir.ref +! CHECK: %[[VAL_27:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref +! CHECK: %[[VAL_28:.*]] = arith.muli %[[VAL_26]], %[[VAL_27]] : i32 +! CHECK: hlfir.assign %[[VAL_28]] to %[[VAL_21]]#0 : i32, !fir.ref +! CHECK: %[[VAL_29:.*]] = fir.load %[[VAL_22]]#0 : !fir.ref +! CHECK: %[[VAL_30:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref +! CHECK: %[[VAL_31:.*]] = arith.muli %[[VAL_29]], %[[VAL_30]] : i32 +! CHECK: hlfir.assign %[[VAL_31]] to %[[VAL_22]]#0 : i32, !fir.ref +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return @@ -272,27 +282,29 @@ end subroutine ! CHECK: %[[VAL_13:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_14:.*]] = arith.constant 10 : i32 ! CHECK: %[[VAL_15:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@multiply_reduction_f32 %[[VAL_3]]#0 -> %[[VAL_16:.*]] : !fir.ref, @multiply_reduction_f32 %[[VAL_5]]#0 -> %[[VAL_17:.*]] : !fir.ref, @multiply_reduction_f32 %[[VAL_7]]#0 -> %[[VAL_18:.*]] : !fir.ref) for (%[[VAL_19:.*]]) : i32 = (%[[VAL_13]]) to (%[[VAL_14]]) inclusive step (%[[VAL_15]]) { -! CHECK: fir.store %[[VAL_19]] to %[[VAL_12]]#1 : !fir.ref -! CHECK: %[[VAL_20:.*]]:2 = hlfir.declare %[[VAL_16]] {uniq_name = "_QFmultiple_real_reductions_same_typeEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_21:.*]]:2 = hlfir.declare %[[VAL_17]] {uniq_name = "_QFmultiple_real_reductions_same_typeEy"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_22:.*]]:2 = hlfir.declare %[[VAL_18]] {uniq_name = "_QFmultiple_real_reductions_same_typeEz"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_23:.*]] = fir.load %[[VAL_20]]#0 : !fir.ref -! CHECK: %[[VAL_24:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref -! CHECK: %[[VAL_25:.*]] = fir.convert %[[VAL_24]] : (i32) -> f32 -! CHECK: %[[VAL_26:.*]] = arith.mulf %[[VAL_23]], %[[VAL_25]] fastmath : f32 -! CHECK: hlfir.assign %[[VAL_26]] to %[[VAL_20]]#0 : f32, !fir.ref -! CHECK: %[[VAL_27:.*]] = fir.load %[[VAL_21]]#0 : !fir.ref -! CHECK: %[[VAL_28:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref -! CHECK: %[[VAL_29:.*]] = fir.convert %[[VAL_28]] : (i32) -> f32 -! CHECK: %[[VAL_30:.*]] = arith.mulf %[[VAL_27]], %[[VAL_29]] fastmath : f32 -! CHECK: hlfir.assign %[[VAL_30]] to %[[VAL_21]]#0 : f32, !fir.ref -! CHECK: %[[VAL_31:.*]] = fir.load %[[VAL_22]]#0 : !fir.ref -! CHECK: %[[VAL_32:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref -! CHECK: %[[VAL_33:.*]] = fir.convert %[[VAL_32]] : (i32) -> f32 -! CHECK: %[[VAL_34:.*]] = arith.mulf %[[VAL_31]], %[[VAL_33]] fastmath : f32 -! CHECK: hlfir.assign %[[VAL_34]] to %[[VAL_22]]#0 : f32, !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop reduction(@multiply_reduction_f32 %[[VAL_3]]#0 -> %[[VAL_16:.*]] : !fir.ref, @multiply_reduction_f32 %[[VAL_5]]#0 -> %[[VAL_17:.*]] : !fir.ref, @multiply_reduction_f32 %[[VAL_7]]#0 -> %[[VAL_18:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_19:.*]]) : i32 = (%[[VAL_13]]) to (%[[VAL_14]]) inclusive step (%[[VAL_15]]) { +! CHECK: %[[VAL_20:.*]]:2 = hlfir.declare %[[VAL_16]] {uniq_name = "_QFmultiple_real_reductions_same_typeEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: %[[VAL_21:.*]]:2 = hlfir.declare %[[VAL_17]] {uniq_name = "_QFmultiple_real_reductions_same_typeEy"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: %[[VAL_22:.*]]:2 = hlfir.declare %[[VAL_18]] {uniq_name = "_QFmultiple_real_reductions_same_typeEz"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: fir.store %[[VAL_19]] to %[[VAL_12]]#1 : !fir.ref +! CHECK: %[[VAL_23:.*]] = fir.load %[[VAL_20]]#0 : !fir.ref +! CHECK: %[[VAL_24:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref +! CHECK: %[[VAL_25:.*]] = fir.convert %[[VAL_24]] : (i32) -> f32 +! CHECK: %[[VAL_26:.*]] = arith.mulf %[[VAL_23]], %[[VAL_25]] fastmath : f32 +! CHECK: hlfir.assign %[[VAL_26]] to %[[VAL_20]]#0 : f32, !fir.ref +! CHECK: %[[VAL_27:.*]] = fir.load %[[VAL_21]]#0 : !fir.ref +! CHECK: %[[VAL_28:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref +! CHECK: %[[VAL_29:.*]] = fir.convert %[[VAL_28]] : (i32) -> f32 +! CHECK: %[[VAL_30:.*]] = arith.mulf %[[VAL_27]], %[[VAL_29]] fastmath : f32 +! CHECK: hlfir.assign %[[VAL_30]] to %[[VAL_21]]#0 : f32, !fir.ref +! CHECK: %[[VAL_31:.*]] = fir.load %[[VAL_22]]#0 : !fir.ref +! CHECK: %[[VAL_32:.*]] = fir.load %[[VAL_12]]#0 : !fir.ref +! CHECK: %[[VAL_33:.*]] = fir.convert %[[VAL_32]] : (i32) -> f32 +! CHECK: %[[VAL_34:.*]] = arith.mulf %[[VAL_31]], %[[VAL_33]] fastmath : f32 +! CHECK: hlfir.assign %[[VAL_34]] to %[[VAL_22]]#0 : f32, !fir.ref +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return @@ -337,32 +349,34 @@ end subroutine ! CHECK: %[[VAL_16:.*]] = arith.constant 1 : i32 ! CHECK: %[[VAL_17:.*]] = arith.constant 10 : i32 ! CHECK: %[[VAL_18:.*]] = arith.constant 1 : i32 -! CHECK: omp.wsloop reduction(@multiply_reduction_i32 %[[VAL_5]]#0 -> %[[VAL_19:.*]] : !fir.ref, @multiply_reduction_i64 %[[VAL_7]]#0 -> %[[VAL_20:.*]] : !fir.ref, @multiply_reduction_f32 %[[VAL_9]]#0 -> %[[VAL_21:.*]] : !fir.ref, @multiply_reduction_f64 %[[VAL_3]]#0 -> %[[VAL_22:.*]] : !fir.ref) for (%[[VAL_23:.*]]) : i32 = (%[[VAL_16]]) to (%[[VAL_17]]) inclusive step (%[[VAL_18]]) { -! CHECK: fir.store %[[VAL_23]] to %[[VAL_15]]#1 : !fir.ref -! CHECK: %[[VAL_24:.*]]:2 = hlfir.declare %[[VAL_19]] {uniq_name = "_QFmultiple_reductions_different_typeEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_25:.*]]:2 = hlfir.declare %[[VAL_20]] {uniq_name = "_QFmultiple_reductions_different_typeEy"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_26:.*]]:2 = hlfir.declare %[[VAL_21]] {uniq_name = "_QFmultiple_reductions_different_typeEz"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_27:.*]]:2 = hlfir.declare %[[VAL_22]] {uniq_name = "_QFmultiple_reductions_different_typeEw"} : (!fir.ref) -> (!fir.ref, !fir.ref) -! CHECK: %[[VAL_28:.*]] = fir.load %[[VAL_24]]#0 : !fir.ref -! CHECK: %[[VAL_29:.*]] = fir.load %[[VAL_15]]#0 : !fir.ref -! CHECK: %[[VAL_30:.*]] = arith.muli %[[VAL_28]], %[[VAL_29]] : i32 -! CHECK: hlfir.assign %[[VAL_30]] to %[[VAL_24]]#0 : i32, !fir.ref -! CHECK: %[[VAL_31:.*]] = fir.load %[[VAL_25]]#0 : !fir.ref -! CHECK: %[[VAL_32:.*]] = fir.load %[[VAL_15]]#0 : !fir.ref -! CHECK: %[[VAL_33:.*]] = fir.convert %[[VAL_32]] : (i32) -> i64 -! CHECK: %[[VAL_34:.*]] = arith.muli %[[VAL_31]], %[[VAL_33]] : i64 -! CHECK: hlfir.assign %[[VAL_34]] to %[[VAL_25]]#0 : i64, !fir.ref -! CHECK: %[[VAL_35:.*]] = fir.load %[[VAL_26]]#0 : !fir.ref -! CHECK: %[[VAL_36:.*]] = fir.load %[[VAL_15]]#0 : !fir.ref -! CHECK: %[[VAL_37:.*]] = fir.convert %[[VAL_36]] : (i32) -> f32 -! CHECK: %[[VAL_38:.*]] = arith.mulf %[[VAL_35]], %[[VAL_37]] fastmath : f32 -! CHECK: hlfir.assign %[[VAL_38]] to %[[VAL_26]]#0 : f32, !fir.ref -! CHECK: %[[VAL_39:.*]] = fir.load %[[VAL_27]]#0 : !fir.ref -! CHECK: %[[VAL_40:.*]] = fir.load %[[VAL_15]]#0 : !fir.ref -! CHECK: %[[VAL_41:.*]] = fir.convert %[[VAL_40]] : (i32) -> f64 -! CHECK: %[[VAL_42:.*]] = arith.mulf %[[VAL_39]], %[[VAL_41]] fastmath : f64 -! CHECK: hlfir.assign %[[VAL_42]] to %[[VAL_27]]#0 : f64, !fir.ref -! CHECK: omp.yield +! CHECK: omp.wsloop reduction(@multiply_reduction_i32 %[[VAL_5]]#0 -> %[[VAL_19:.*]] : !fir.ref, @multiply_reduction_i64 %[[VAL_7]]#0 -> %[[VAL_20:.*]] : !fir.ref, @multiply_reduction_f32 %[[VAL_9]]#0 -> %[[VAL_21:.*]] : !fir.ref, @multiply_reduction_f64 %[[VAL_3]]#0 -> %[[VAL_22:.*]] : !fir.ref) { +! CHECK-NEXT: omp.loop_nest (%[[VAL_23:.*]]) : i32 = (%[[VAL_16]]) to (%[[VAL_17]]) inclusive step (%[[VAL_18]]) { +! CHECK: %[[VAL_24:.*]]:2 = hlfir.declare %[[VAL_19]] {uniq_name = "_QFmultiple_reductions_different_typeEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: %[[VAL_25:.*]]:2 = hlfir.declare %[[VAL_20]] {uniq_name = "_QFmultiple_reductions_different_typeEy"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: %[[VAL_26:.*]]:2 = hlfir.declare %[[VAL_21]] {uniq_name = "_QFmultiple_reductions_different_typeEz"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: %[[VAL_27:.*]]:2 = hlfir.declare %[[VAL_22]] {uniq_name = "_QFmultiple_reductions_different_typeEw"} : (!fir.ref) -> (!fir.ref, !fir.ref) +! CHECK: fir.store %[[VAL_23]] to %[[VAL_15]]#1 : !fir.ref +! CHECK: %[[VAL_28:.*]] = fir.load %[[VAL_24]]#0 : !fir.ref +! CHECK: %[[VAL_29:.*]] = fir.load %[[VAL_15]]#0 : !fir.ref +! CHECK: %[[VAL_30:.*]] = arith.muli %[[VAL_28]], %[[VAL_29]] : i32 +! CHECK: hlfir.assign %[[VAL_30]] to %[[VAL_24]]#0 : i32, !fir.ref +! CHECK: %[[VAL_31:.*]] = fir.load %[[VAL_25]]#0 : !fir.ref +! CHECK: %[[VAL_32:.*]] = fir.load %[[VAL_15]]#0 : !fir.ref +! CHECK: %[[VAL_33:.*]] = fir.convert %[[VAL_32]] : (i32) -> i64 +! CHECK: %[[VAL_34:.*]] = arith.muli %[[VAL_31]], %[[VAL_33]] : i64 +! CHECK: hlfir.assign %[[VAL_34]] to %[[VAL_25]]#0 : i64, !fir.ref +! CHECK: %[[VAL_35:.*]] = fir.load %[[VAL_26]]#0 : !fir.ref +! CHECK: %[[VAL_36:.*]] = fir.load %[[VAL_15]]#0 : !fir.ref +! CHECK: %[[VAL_37:.*]] = fir.convert %[[VAL_36]] : (i32) -> f32 +! CHECK: %[[VAL_38:.*]] = arith.mulf %[[VAL_35]], %[[VAL_37]] fastmath : f32 +! CHECK: hlfir.assign %[[VAL_38]] to %[[VAL_26]]#0 : f32, !fir.ref +! CHECK: %[[VAL_39:.*]] = fir.load %[[VAL_27]]#0 : !fir.ref +! CHECK: %[[VAL_40:.*]] = fir.load %[[VAL_15]]#0 : !fir.ref +! CHECK: %[[VAL_41:.*]] = fir.convert %[[VAL_40]] : (i32) -> f64 +! CHECK: %[[VAL_42:.*]] = arith.mulf %[[VAL_39]], %[[VAL_41]] fastmath : f64 +! CHECK: hlfir.assign %[[VAL_42]] to %[[VAL_27]]#0 : f64, !fir.ref +! CHECK: omp.yield +! CHECK: omp.terminator ! CHECK: omp.terminator ! CHECK: return diff --git a/flang/test/Lower/OpenMP/wsloop-reduction-multi.f90 b/flang/test/Lower/OpenMP/wsloop-reduction-multi.f90 index 9e9951c399c9205e65278f0e8d514f8c7ad360b7..429253efdc809047015a4a3d9579ff56c45faa0f 100644 --- a/flang/test/Lower/OpenMP/wsloop-reduction-multi.f90 +++ b/flang/test/Lower/OpenMP/wsloop-reduction-multi.f90 @@ -35,31 +35,34 @@ !CHECK: } !CHECK-LABEL: func.func @_QPmultiple_reduction -!CHECK: %[[X_REF:.*]] = fir.alloca i32 {bindc_name = "x", uniq_name = "_QFmultiple_reductionEx"} -!CHECK: %[[X_DECL:.*]]:2 = hlfir.declare %[[X_REF]] {uniq_name = "_QFmultiple_reductionEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) -!CHECK: %[[Y_REF:.*]] = fir.alloca f32 {bindc_name = "y", uniq_name = "_QFmultiple_reductionEy"} -!CHECK: %[[Y_DECL:.*]]:2 = hlfir.declare %[[Y_REF]] {uniq_name = "_QFmultiple_reductionEy"} : (!fir.ref) -> (!fir.ref, !fir.ref) -!CHECK: %[[Z_REF:.*]] = fir.alloca i32 {bindc_name = "z", uniq_name = "_QFmultiple_reductionEz"} -!CHECK: %[[Z_DECL:.*]]:2 = hlfir.declare %[[Z_REF]] {uniq_name = "_QFmultiple_reductionEz"} : (!fir.ref) -> (!fir.ref, !fir.ref) -!CHECK: omp.wsloop reduction( +!CHECK: %[[X_REF:.*]] = fir.alloca i32 {bindc_name = "x", uniq_name = "_QFmultiple_reductionEx"} +!CHECK: %[[X_DECL:.*]]:2 = hlfir.declare %[[X_REF]] {uniq_name = "_QFmultiple_reductionEx"} : (!fir.ref) -> (!fir.ref, !fir.ref) +!CHECK: %[[Y_REF:.*]] = fir.alloca f32 {bindc_name = "y", uniq_name = "_QFmultiple_reductionEy"} +!CHECK: %[[Y_DECL:.*]]:2 = hlfir.declare %[[Y_REF]] {uniq_name = "_QFmultiple_reductionEy"} : (!fir.ref) -> (!fir.ref, !fir.ref) +!CHECK: %[[Z_REF:.*]] = fir.alloca i32 {bindc_name = "z", uniq_name = "_QFmultiple_reductionEz"} +!CHECK: %[[Z_DECL:.*]]:2 = hlfir.declare %[[Z_REF]] {uniq_name = "_QFmultiple_reductionEz"} : (!fir.ref) -> (!fir.ref, !fir.ref) +!CHECK: omp.wsloop reduction( !CHECK-SAME: @[[ADD_RED_I32_NAME]] %[[X_DECL]]#0 -> %[[PRV_X:.+]] : !fir.ref, !CHECK-SAME: @[[ADD_RED_F32_NAME]] %[[Y_DECL]]#0 -> %[[PRV_Y:.+]] : !fir.ref, -!CHECK-SAME: @[[MIN_RED_I32_NAME]] %[[Z_DECL]]#0 -> %[[PRV_Z:.+]] : !fir.ref) {{.*}}{ -!CHECK: %[[PRV_X_DECL:.+]]:2 = hlfir.declare %[[PRV_X]] {{.*}} : (!fir.ref) -> (!fir.ref, !fir.ref) -!CHECK: %[[PRV_Y_DECL:.+]]:2 = hlfir.declare %[[PRV_Y]] {{.*}} : (!fir.ref) -> (!fir.ref, !fir.ref) -!CHECK: %[[PRV_Z_DECL:.+]]:2 = hlfir.declare %[[PRV_Z]] {{.*}} : (!fir.ref) -> (!fir.ref, !fir.ref) -!CHECK: %[[LPRV_X:.+]] = fir.load %[[PRV_X_DECL]]#0 : !fir.ref -!CHECK: %[[RES_X:.+]] = arith.addi %[[LPRV_X]], %{{.+}} : i32 -!CHECK: hlfir.assign %[[RES_X]] to %[[PRV_X_DECL]]#0 : i32, !fir.ref -!CHECK: %[[LPRV_Y:.+]] = fir.load %[[PRV_Y_DECL]]#0 : !fir.ref -!CHECK: %[[RES_Y:.+]] = arith.addf %[[LPRV_Y]], %{{.+}} : f32 -!CHECK: hlfir.assign %[[RES_Y]] to %[[PRV_Y_DECL]]#0 : f32, !fir.ref -!CHECK: %[[LPRV_Z:.+]] = fir.load %[[PRV_Z_DECL]]#0 : !fir.ref -!CHECK: %[[RES_Z:.+]] = arith.select %{{.+}}, %[[LPRV_Z]], %{{.+}} : i32 -!CHECK: hlfir.assign %[[RES_Z]] to %[[PRV_Z_DECL]]#0 : i32, !fir.ref -!CHECK: omp.yield -!CHECK: } -!CHECK: return +!CHECK-SAME: @[[MIN_RED_I32_NAME]] %[[Z_DECL]]#0 -> %[[PRV_Z:.+]] : !fir.ref) { +!CHECK-NEXT: omp.loop_nest {{.*}} { +!CHECK: %[[PRV_X_DECL:.+]]:2 = hlfir.declare %[[PRV_X]] {{.*}} : (!fir.ref) -> (!fir.ref, !fir.ref) +!CHECK: %[[PRV_Y_DECL:.+]]:2 = hlfir.declare %[[PRV_Y]] {{.*}} : (!fir.ref) -> (!fir.ref, !fir.ref) +!CHECK: %[[PRV_Z_DECL:.+]]:2 = hlfir.declare %[[PRV_Z]] {{.*}} : (!fir.ref) -> (!fir.ref, !fir.ref) +!CHECK: %[[LPRV_X:.+]] = fir.load %[[PRV_X_DECL]]#0 : !fir.ref +!CHECK: %[[RES_X:.+]] = arith.addi %[[LPRV_X]], %{{.+}} : i32 +!CHECK: hlfir.assign %[[RES_X]] to %[[PRV_X_DECL]]#0 : i32, !fir.ref +!CHECK: %[[LPRV_Y:.+]] = fir.load %[[PRV_Y_DECL]]#0 : !fir.ref +!CHECK: %[[RES_Y:.+]] = arith.addf %[[LPRV_Y]], %{{.+}} : f32 +!CHECK: hlfir.assign %[[RES_Y]] to %[[PRV_Y_DECL]]#0 : f32, !fir.ref +!CHECK: %[[LPRV_Z:.+]] = fir.load %[[PRV_Z_DECL]]#0 : !fir.ref +!CHECK: %[[RES_Z:.+]] = arith.select %{{.+}}, %[[LPRV_Z]], %{{.+}} : i32 +!CHECK: hlfir.assign %[[RES_Z]] to %[[PRV_Z_DECL]]#0 : i32, !fir.ref +!CHECK: omp.yield +!CHECK: } +!CHECK: omp.terminator +!CHECK: } +!CHECK: return subroutine multiple_reduction(v) implicit none integer, intent(in) :: v(:) diff --git a/flang/test/Lower/OpenMP/wsloop-simd.f90 b/flang/test/Lower/OpenMP/wsloop-simd.f90 index c3d5e3e0cda5935f571009bb6f08eceddd7646ad..1df67474d65e3b1899637264a837cbd7e285d20a 100644 --- a/flang/test/Lower/OpenMP/wsloop-simd.f90 +++ b/flang/test/Lower/OpenMP/wsloop-simd.f90 @@ -11,23 +11,26 @@ program wsloop_dynamic !CHECK: omp.parallel { !$OMP DO SCHEDULE(simd: runtime) -!CHECK: %[[WS_LB:.*]] = arith.constant 1 : i32 -!CHECK: %[[WS_UB:.*]] = arith.constant 9 : i32 -!CHECK: %[[WS_STEP:.*]] = arith.constant 1 : i32 -!CHECK: omp.wsloop schedule(runtime, simd) nowait for (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) -!CHECK: fir.store %[[I]] to %[[STORE:.*]]#1 : !fir.ref +!CHECK: %[[WS_LB:.*]] = arith.constant 1 : i32 +!CHECK: %[[WS_UB:.*]] = arith.constant 9 : i32 +!CHECK: %[[WS_STEP:.*]] = arith.constant 1 : i32 +!CHECK: omp.wsloop schedule(runtime, simd) nowait { +!CHECK-NEXT: omp.loop_nest (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) { +!CHECK: fir.store %[[I]] to %[[STORE:.*]]#1 : !fir.ref do i=1, 9 print*, i -!CHECK: %[[RTBEGIN:.*]] = fir.call @_FortranAioBeginExternalListOutput -!CHECK: %[[LOAD:.*]] = fir.load %[[STORE]]#0 : !fir.ref -!CHECK: fir.call @_FortranAioOutputInteger32(%[[RTBEGIN]], %[[LOAD]]) {{.*}}: (!fir.ref, i32) -> i1 -!CHECK: fir.call @_FortranAioEndIoStatement(%[[RTBEGIN]]) {{.*}}: (!fir.ref) -> i32 +!CHECK: %[[RTBEGIN:.*]] = fir.call @_FortranAioBeginExternalListOutput +!CHECK: %[[LOAD:.*]] = fir.load %[[STORE]]#0 : !fir.ref +!CHECK: fir.call @_FortranAioOutputInteger32(%[[RTBEGIN]], %[[LOAD]]) {{.*}}: (!fir.ref, i32) -> i1 +!CHECK: fir.call @_FortranAioEndIoStatement(%[[RTBEGIN]]) {{.*}}: (!fir.ref) -> i32 end do -!CHECK: omp.yield -!CHECK: } -!CHECK: omp.terminator -!CHECK: } +!CHECK: omp.yield +!CHECK: } +!CHECK: omp.terminator +!CHECK: } +!CHECK: omp.terminator +!CHECK: } !$OMP END DO NOWAIT !$OMP END PARALLEL diff --git a/flang/test/Lower/OpenMP/wsloop-unstructured.f90 b/flang/test/Lower/OpenMP/wsloop-unstructured.f90 index 7fe63a1fe607c2effdbd716969e00aec56238da8..bd6a0bade8c7ee5c9a5c376385e99a40ed5326b8 100644 --- a/flang/test/Lower/OpenMP/wsloop-unstructured.f90 +++ b/flang/test/Lower/OpenMP/wsloop-unstructured.f90 @@ -29,29 +29,32 @@ end subroutine sub ! CHECK-SAME: %[[VAL_2:.*]]: !fir.ref> {fir.bindc_name = "x"}, ! CHECK-SAME: %[[VAL_3:.*]]: !fir.ref> {fir.bindc_name = "y"}) { ! [...] -! CHECK: omp.wsloop for (%[[VAL_53:.*]], %[[VAL_54:.*]]) : i32 = ({{.*}}) to ({{.*}}) inclusive step ({{.*}}) { +! CHECK: omp.wsloop { +! CHECK-NEXT: omp.loop_nest (%[[VAL_53:.*]], %[[VAL_54:.*]]) : i32 = ({{.*}}) to ({{.*}}) inclusive step ({{.*}}) { ! [...] -! CHECK: cf.br ^bb1 -! CHECK: ^bb1: -! CHECK: cf.br ^bb2 -! CHECK: ^bb2: +! CHECK: cf.br ^bb1 +! CHECK: ^bb1: +! CHECK: cf.br ^bb2 +! CHECK: ^bb2: ! [...] -! CHECK: cf.br ^bb3 -! CHECK: ^bb3: +! CHECK: cf.br ^bb3 +! CHECK: ^bb3: ! [...] -! CHECK: %[[VAL_63:.*]] = arith.cmpi sgt, %{{.*}}, %{{.*}} : i32 -! CHECK: cf.cond_br %[[VAL_63]], ^bb4, ^bb7 -! CHECK: ^bb4: +! CHECK: %[[VAL_63:.*]] = arith.cmpi sgt, %{{.*}}, %{{.*}} : i32 +! CHECK: cf.cond_br %[[VAL_63]], ^bb4, ^bb7 +! CHECK: ^bb4: ! [...] -! CHECK: %[[VAL_76:.*]] = arith.cmpf olt, %{{.*}}, %{{.*}} fastmath : f32 -! CHECK: cf.cond_br %[[VAL_76]], ^bb5, ^bb6 -! CHECK: ^bb5: -! CHECK: cf.br ^bb7 -! CHECK: ^bb6: +! CHECK: %[[VAL_76:.*]] = arith.cmpf olt, %{{.*}}, %{{.*}} fastmath : f32 +! CHECK: cf.cond_br %[[VAL_76]], ^bb5, ^bb6 +! CHECK: ^bb5: +! CHECK: cf.br ^bb7 +! CHECK: ^bb6: ! [...] -! CHECK: cf.br ^bb3 -! CHECK: ^bb7: -! CHECK: omp.yield +! CHECK: cf.br ^bb3 +! CHECK: ^bb7: +! CHECK: omp.yield +! CHECK: } +! CHECK: omp.terminator ! CHECK: } ! CHECK: omp.terminator ! CHECK: } diff --git a/flang/test/Lower/OpenMP/wsloop-variable.f90 b/flang/test/Lower/OpenMP/wsloop-variable.f90 index b3758f1fdc00ff703a0b24166902caba95ab119b..4d83b332880365878ca78ecd3a5e288091e8310b 100644 --- a/flang/test/Lower/OpenMP/wsloop-variable.f90 +++ b/flang/test/Lower/OpenMP/wsloop-variable.f90 @@ -14,26 +14,29 @@ program wsloop_variable integer(kind=16) :: i16, i16_lb real :: x -!CHECK: %[[TMP0:.*]] = arith.constant 1 : i32 -!CHECK: %[[TMP1:.*]] = arith.constant 100 : i32 -!CHECK: %[[TMP2:.*]] = fir.convert %[[TMP0]] : (i32) -> i64 -!CHECK: %[[TMP3:.*]] = fir.convert %{{.*}} : (i8) -> i64 -!CHECK: %[[TMP4:.*]] = fir.convert %{{.*}} : (i16) -> i64 -!CHECK: %[[TMP5:.*]] = fir.convert %{{.*}} : (i128) -> i64 -!CHECK: %[[TMP6:.*]] = fir.convert %[[TMP1]] : (i32) -> i64 -!CHECK: %[[TMP7:.*]] = fir.convert %{{.*}} : (i32) -> i64 -!CHECK: omp.wsloop for (%[[ARG0:.*]], %[[ARG1:.*]]) : i64 = (%[[TMP2]], %[[TMP5]]) to (%[[TMP3]], %[[TMP6]]) inclusive step (%[[TMP4]], %[[TMP7]]) { -!CHECK: %[[ARG0_I16:.*]] = fir.convert %[[ARG0]] : (i64) -> i16 -!CHECK: fir.store %[[ARG0_I16]] to %[[STORE_IV0:.*]]#1 : !fir.ref -!CHECK: fir.store %[[ARG1]] to %[[STORE_IV1:.*]]#1 : !fir.ref -!CHECK: %[[LOAD_IV0:.*]] = fir.load %[[STORE_IV0]]#0 : !fir.ref -!CHECK: %[[LOAD_IV0_I64:.*]] = fir.convert %[[LOAD_IV0]] : (i16) -> i64 -!CHECK: %[[LOAD_IV1:.*]] = fir.load %[[STORE_IV1]]#0 : !fir.ref -!CHECK: %[[TMP10:.*]] = arith.addi %[[LOAD_IV0_I64]], %[[LOAD_IV1]] : i64 -!CHECK: %[[TMP11:.*]] = fir.convert %[[TMP10]] : (i64) -> f32 -!CHECK: hlfir.assign %[[TMP11]] to %{{.*}} : f32, !fir.ref -!CHECK: omp.yield -!CHECK: } +!CHECK: %[[TMP0:.*]] = arith.constant 1 : i32 +!CHECK: %[[TMP1:.*]] = arith.constant 100 : i32 +!CHECK: %[[TMP2:.*]] = fir.convert %[[TMP0]] : (i32) -> i64 +!CHECK: %[[TMP3:.*]] = fir.convert %{{.*}} : (i8) -> i64 +!CHECK: %[[TMP4:.*]] = fir.convert %{{.*}} : (i16) -> i64 +!CHECK: %[[TMP5:.*]] = fir.convert %{{.*}} : (i128) -> i64 +!CHECK: %[[TMP6:.*]] = fir.convert %[[TMP1]] : (i32) -> i64 +!CHECK: %[[TMP7:.*]] = fir.convert %{{.*}} : (i32) -> i64 +!CHECK: omp.wsloop { +!CHECK-NEXT: omp.loop_nest (%[[ARG0:.*]], %[[ARG1:.*]]) : i64 = (%[[TMP2]], %[[TMP5]]) to (%[[TMP3]], %[[TMP6]]) inclusive step (%[[TMP4]], %[[TMP7]]) { +!CHECK: %[[ARG0_I16:.*]] = fir.convert %[[ARG0]] : (i64) -> i16 +!CHECK: fir.store %[[ARG0_I16]] to %[[STORE_IV0:.*]]#1 : !fir.ref +!CHECK: fir.store %[[ARG1]] to %[[STORE_IV1:.*]]#1 : !fir.ref +!CHECK: %[[LOAD_IV0:.*]] = fir.load %[[STORE_IV0]]#0 : !fir.ref +!CHECK: %[[LOAD_IV0_I64:.*]] = fir.convert %[[LOAD_IV0]] : (i16) -> i64 +!CHECK: %[[LOAD_IV1:.*]] = fir.load %[[STORE_IV1]]#0 : !fir.ref +!CHECK: %[[TMP10:.*]] = arith.addi %[[LOAD_IV0_I64]], %[[LOAD_IV1]] : i64 +!CHECK: %[[TMP11:.*]] = fir.convert %[[TMP10]] : (i64) -> f32 +!CHECK: hlfir.assign %[[TMP11]] to %{{.*}} : f32, !fir.ref +!CHECK: omp.yield +!CHECK: } +!CHECK: omp.terminator +!CHECK: } !$omp do collapse(2) do i2 = 1, i1_ub, i2_s @@ -43,17 +46,20 @@ program wsloop_variable end do !$omp end do -!CHECK: %[[TMP12:.*]] = arith.constant 1 : i32 -!CHECK: %[[TMP13:.*]] = fir.convert %{{.*}} : (i8) -> i32 -!CHECK: %[[TMP14:.*]] = fir.convert %{{.*}} : (i64) -> i32 -!CHECK: omp.wsloop for (%[[ARG0:.*]]) : i32 = (%[[TMP12]]) to (%[[TMP13]]) inclusive step (%[[TMP14]]) { -!CHECK: %[[ARG0_I16:.*]] = fir.convert %[[ARG0]] : (i32) -> i16 -!CHECK: fir.store %[[ARG0_I16]] to %[[STORE3:.*]]#1 : !fir.ref -!CHECK: %[[LOAD3:.*]] = fir.load %[[STORE3]]#0 : !fir.ref -!CHECK: %[[TMP16:.*]] = fir.convert %[[LOAD3]] : (i16) -> f32 -!CHECK: hlfir.assign %[[TMP16]] to %{{.*}} : f32, !fir.ref -!CHECK: omp.yield -!CHECK: } +!CHECK: %[[TMP12:.*]] = arith.constant 1 : i32 +!CHECK: %[[TMP13:.*]] = fir.convert %{{.*}} : (i8) -> i32 +!CHECK: %[[TMP14:.*]] = fir.convert %{{.*}} : (i64) -> i32 +!CHECK: omp.wsloop { +!CHECK-NEXT: omp.loop_nest (%[[ARG0:.*]]) : i32 = (%[[TMP12]]) to (%[[TMP13]]) inclusive step (%[[TMP14]]) { +!CHECK: %[[ARG0_I16:.*]] = fir.convert %[[ARG0]] : (i32) -> i16 +!CHECK: fir.store %[[ARG0_I16]] to %[[STORE3:.*]]#1 : !fir.ref +!CHECK: %[[LOAD3:.*]] = fir.load %[[STORE3]]#0 : !fir.ref +!CHECK: %[[TMP16:.*]] = fir.convert %[[LOAD3]] : (i16) -> f32 +!CHECK: hlfir.assign %[[TMP16]] to %{{.*}} : f32, !fir.ref +!CHECK: omp.yield +!CHECK: } +!CHECK: omp.terminator +!CHECK: } !$omp do do i2 = 1, i1_ub, i8_s @@ -61,17 +67,20 @@ program wsloop_variable end do !$omp end do -!CHECK: %[[TMP17:.*]] = fir.convert %{{.*}} : (i8) -> i64 -!CHECK: %[[TMP18:.*]] = fir.convert %{{.*}} : (i16) -> i64 -!CHECK: %[[TMP19:.*]] = fir.convert %{{.*}} : (i32) -> i64 -!CHECK: omp.wsloop for (%[[ARG1:.*]]) : i64 = (%[[TMP17]]) to (%[[TMP18]]) inclusive step (%[[TMP19]]) { -!CHECK: %[[ARG1_I128:.*]] = fir.convert %[[ARG1]] : (i64) -> i128 -!CHECK: fir.store %[[ARG1_I128]] to %[[STORE4:.*]]#1 : !fir.ref -!CHECK: %[[LOAD4:.*]] = fir.load %[[STORE4]]#0 : !fir.ref -!CHECK: %[[TMP21:.*]] = fir.convert %[[LOAD4]] : (i128) -> f32 -!CHECK: hlfir.assign %[[TMP21]] to %{{.*}} : f32, !fir.ref -!CHECK: omp.yield -!CHECK: } +!CHECK: %[[TMP17:.*]] = fir.convert %{{.*}} : (i8) -> i64 +!CHECK: %[[TMP18:.*]] = fir.convert %{{.*}} : (i16) -> i64 +!CHECK: %[[TMP19:.*]] = fir.convert %{{.*}} : (i32) -> i64 +!CHECK: omp.wsloop { +!CHECK-NEXT: omp.loop_nest (%[[ARG1:.*]]) : i64 = (%[[TMP17]]) to (%[[TMP18]]) inclusive step (%[[TMP19]]) { +!CHECK: %[[ARG1_I128:.*]] = fir.convert %[[ARG1]] : (i64) -> i128 +!CHECK: fir.store %[[ARG1_I128]] to %[[STORE4:.*]]#1 : !fir.ref +!CHECK: %[[LOAD4:.*]] = fir.load %[[STORE4]]#0 : !fir.ref +!CHECK: %[[TMP21:.*]] = fir.convert %[[LOAD4]] : (i128) -> f32 +!CHECK: hlfir.assign %[[TMP21]] to %{{.*}} : f32, !fir.ref +!CHECK: omp.yield +!CHECK: } +!CHECK: omp.terminator +!CHECK: } !$omp do do i16 = i1_lb, i2_ub, i4_s @@ -118,32 +127,35 @@ subroutine wsloop_variable_sub !CHECK: %[[VAL_24:.*]] = fir.load %[[VAL_13]]#0 : !fir.ref !CHECK: %[[VAL_25:.*]] = fir.convert %[[VAL_23]] : (i8) -> i32 !CHECK: %[[VAL_26:.*]] = fir.convert %[[VAL_24]] : (i16) -> i32 -!CHECK: omp.wsloop for (%[[VAL_27:.*]]) : i32 = (%[[VAL_22]]) to (%[[VAL_25]]) inclusive step (%[[VAL_26]]) { -!CHECK: %[[VAL_28:.*]] = fir.convert %[[VAL_27]] : (i32) -> i16 -!CHECK: fir.store %[[VAL_28]] to %[[VAL_3]]#1 : !fir.ref -!CHECK: %[[VAL_29:.*]] = fir.load %[[VAL_7]]#0 : !fir.ref -!CHECK: %[[VAL_30:.*]] = fir.convert %[[VAL_29]] : (i128) -> index -!CHECK: %[[VAL_31:.*]] = arith.constant 100 : i32 -!CHECK: %[[VAL_32:.*]] = fir.convert %[[VAL_31]] : (i32) -> index -!CHECK: %[[VAL_33:.*]] = fir.load %[[VAL_15]]#0 : !fir.ref -!CHECK: %[[VAL_34:.*]] = fir.convert %[[VAL_33]] : (i32) -> index -!CHECK: %[[VAL_35:.*]] = fir.convert %[[VAL_30]] : (index) -> i64 -!CHECK: %[[VAL_36:.*]]:2 = fir.do_loop %[[VAL_37:.*]] = %[[VAL_30]] to %[[VAL_32]] step %[[VAL_34]] iter_args(%[[VAL_38:.*]] = %[[VAL_35]]) -> (index, i64) { -!CHECK: fir.store %[[VAL_38]] to %[[VAL_17]]#1 : !fir.ref -!CHECK: %[[VAL_39:.*]] = fir.load %[[VAL_3]]#0 : !fir.ref -!CHECK: %[[VAL_40:.*]] = fir.convert %[[VAL_39]] : (i16) -> i64 -!CHECK: %[[VAL_41:.*]] = fir.load %[[VAL_17]]#0 : !fir.ref -!CHECK: %[[VAL_42:.*]] = arith.addi %[[VAL_40]], %[[VAL_41]] : i64 -!CHECK: %[[VAL_43:.*]] = fir.convert %[[VAL_42]] : (i64) -> f32 -!CHECK: hlfir.assign %[[VAL_43]] to %[[VAL_21]]#0 : f32, !fir.ref -!CHECK: %[[VAL_44:.*]] = arith.addi %[[VAL_37]], %[[VAL_34]] : index -!CHECK: %[[VAL_45:.*]] = fir.convert %[[VAL_34]] : (index) -> i64 -!CHECK: %[[VAL_46:.*]] = fir.load %[[VAL_17]]#1 : !fir.ref -!CHECK: %[[VAL_47:.*]] = arith.addi %[[VAL_46]], %[[VAL_45]] : i64 -!CHECK: fir.result %[[VAL_44]], %[[VAL_47]] : index, i64 +!CHECK: omp.wsloop { +!CHECK-NEXT: omp.loop_nest (%[[VAL_27:.*]]) : i32 = (%[[VAL_22]]) to (%[[VAL_25]]) inclusive step (%[[VAL_26]]) { +!CHECK: %[[VAL_28:.*]] = fir.convert %[[VAL_27]] : (i32) -> i16 +!CHECK: fir.store %[[VAL_28]] to %[[VAL_3]]#1 : !fir.ref +!CHECK: %[[VAL_29:.*]] = fir.load %[[VAL_7]]#0 : !fir.ref +!CHECK: %[[VAL_30:.*]] = fir.convert %[[VAL_29]] : (i128) -> index +!CHECK: %[[VAL_31:.*]] = arith.constant 100 : i32 +!CHECK: %[[VAL_32:.*]] = fir.convert %[[VAL_31]] : (i32) -> index +!CHECK: %[[VAL_33:.*]] = fir.load %[[VAL_15]]#0 : !fir.ref +!CHECK: %[[VAL_34:.*]] = fir.convert %[[VAL_33]] : (i32) -> index +!CHECK: %[[VAL_35:.*]] = fir.convert %[[VAL_30]] : (index) -> i64 +!CHECK: %[[VAL_36:.*]]:2 = fir.do_loop %[[VAL_37:.*]] = %[[VAL_30]] to %[[VAL_32]] step %[[VAL_34]] iter_args(%[[VAL_38:.*]] = %[[VAL_35]]) -> (index, i64) { +!CHECK: fir.store %[[VAL_38]] to %[[VAL_17]]#1 : !fir.ref +!CHECK: %[[VAL_39:.*]] = fir.load %[[VAL_3]]#0 : !fir.ref +!CHECK: %[[VAL_40:.*]] = fir.convert %[[VAL_39]] : (i16) -> i64 +!CHECK: %[[VAL_41:.*]] = fir.load %[[VAL_17]]#0 : !fir.ref +!CHECK: %[[VAL_42:.*]] = arith.addi %[[VAL_40]], %[[VAL_41]] : i64 +!CHECK: %[[VAL_43:.*]] = fir.convert %[[VAL_42]] : (i64) -> f32 +!CHECK: hlfir.assign %[[VAL_43]] to %[[VAL_21]]#0 : f32, !fir.ref +!CHECK: %[[VAL_44:.*]] = arith.addi %[[VAL_37]], %[[VAL_34]] : index +!CHECK: %[[VAL_45:.*]] = fir.convert %[[VAL_34]] : (index) -> i64 +!CHECK: %[[VAL_46:.*]] = fir.load %[[VAL_17]]#1 : !fir.ref +!CHECK: %[[VAL_47:.*]] = arith.addi %[[VAL_46]], %[[VAL_45]] : i64 +!CHECK: fir.result %[[VAL_44]], %[[VAL_47]] : index, i64 +!CHECK: } +!CHECK: fir.store %[[VAL_48:.*]]#1 to %[[VAL_17]]#1 : !fir.ref +!CHECK: omp.yield !CHECK: } -!CHECK: fir.store %[[VAL_48:.*]]#1 to %[[VAL_17]]#1 : !fir.ref -!CHECK: omp.yield +!CHECK: omp.terminator !CHECK: } !$omp do @@ -160,16 +172,19 @@ subroutine wsloop_variable_sub !CHECK: %[[VAL_50:.*]] = arith.constant 1 : i32 !CHECK: %[[VAL_51:.*]] = arith.constant 10 : i32 !CHECK: %[[VAL_52:.*]] = arith.constant 1 : i32 -!CHECK: omp.wsloop for (%[[VAL_53:.*]]) : i32 = (%[[VAL_50]]) to (%[[VAL_51]]) inclusive step (%[[VAL_52]]) { -!CHECK: %[[VAL_54:.*]] = fir.convert %[[VAL_53]] : (i32) -> i8 -!CHECK: fir.store %[[VAL_54]] to %[[VAL_1]]#1 : !fir.ref -!CHECK: %[[VAL_55:.*]] = fir.load %[[VAL_1]]#0 : !fir.ref -!CHECK: %[[VAL_56:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref -!CHECK: %[[VAL_57:.*]] = arith.cmpi eq, %[[VAL_55]], %[[VAL_56]] : i8 -!CHECK: fir.if %[[VAL_57]] { -!CHECK: } else { +!CHECK: omp.wsloop { +!CHECK-NEXT: omp.loop_nest (%[[VAL_53:.*]]) : i32 = (%[[VAL_50]]) to (%[[VAL_51]]) inclusive step (%[[VAL_52]]) { +!CHECK: %[[VAL_54:.*]] = fir.convert %[[VAL_53]] : (i32) -> i8 +!CHECK: fir.store %[[VAL_54]] to %[[VAL_1]]#1 : !fir.ref +!CHECK: %[[VAL_55:.*]] = fir.load %[[VAL_1]]#0 : !fir.ref +!CHECK: %[[VAL_56:.*]] = fir.load %[[VAL_19]]#0 : !fir.ref +!CHECK: %[[VAL_57:.*]] = arith.cmpi eq, %[[VAL_55]], %[[VAL_56]] : i8 +!CHECK: fir.if %[[VAL_57]] { +!CHECK: } else { +!CHECK: } +!CHECK: omp.yield !CHECK: } -!CHECK: omp.yield +!CHECK: omp.terminator !CHECK: } j1 = 5 !$omp do diff --git a/flang/test/Lower/OpenMP/wsloop.f90 b/flang/test/Lower/OpenMP/wsloop.f90 index 4068f715c3e189a4b32734be6cf38c97a177e2b6..da90cb7241597fbfaff9ada6821508a4907000ce 100644 --- a/flang/test/Lower/OpenMP/wsloop.f90 +++ b/flang/test/Lower/OpenMP/wsloop.f90 @@ -7,22 +7,24 @@ subroutine simple_loop integer :: i ! CHECK: omp.parallel !$OMP PARALLEL - ! CHECK: %[[ALLOCA_IV:.*]] = fir.alloca i32 {{{.*}}, pinned} - ! CHECK: %[[IV_DECL:.*]]:2 = hlfir.declare %[[ALLOCA_IV]] {uniq_name = "_QFsimple_loopEi"} : (!fir.ref) -> (!fir.ref, !fir.ref) - ! CHECK: %[[WS_LB:.*]] = arith.constant 1 : i32 - ! CHECK: %[[WS_UB:.*]] = arith.constant 9 : i32 - ! CHECK: %[[WS_STEP:.*]] = arith.constant 1 : i32 - ! CHECK: omp.wsloop for (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) + ! CHECK: %[[ALLOCA_IV:.*]] = fir.alloca i32 {{{.*}}, pinned} + ! CHECK: %[[IV_DECL:.*]]:2 = hlfir.declare %[[ALLOCA_IV]] {uniq_name = "_QFsimple_loopEi"} : (!fir.ref) -> (!fir.ref, !fir.ref) + ! CHECK: %[[WS_LB:.*]] = arith.constant 1 : i32 + ! CHECK: %[[WS_UB:.*]] = arith.constant 9 : i32 + ! CHECK: %[[WS_STEP:.*]] = arith.constant 1 : i32 + ! CHECK: omp.wsloop { + ! CHECK-NEXT: omp.loop_nest (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) { !$OMP DO do i=1, 9 - ! CHECK: fir.store %[[I]] to %[[IV_DECL:.*]]#1 : !fir.ref - ! CHECK: %[[LOAD_IV:.*]] = fir.load %[[IV_DECL]]#0 : !fir.ref - ! CHECK: fir.call @_FortranAioOutputInteger32({{.*}}, %[[LOAD_IV]]) {{.*}}: (!fir.ref, i32) -> i1 + ! CHECK: fir.store %[[I]] to %[[IV_DECL:.*]]#1 : !fir.ref + ! CHECK: %[[LOAD_IV:.*]] = fir.load %[[IV_DECL]]#0 : !fir.ref + ! CHECK: fir.call @_FortranAioOutputInteger32({{.*}}, %[[LOAD_IV]]) {{.*}}: (!fir.ref, i32) -> i1 print*, i end do - ! CHECK: omp.yield + ! CHECK: omp.yield + ! CHECK: omp.terminator !$OMP END DO - ! CHECK: omp.terminator + ! CHECK: omp.terminator !$OMP END PARALLEL end subroutine @@ -31,22 +33,24 @@ subroutine simple_loop_with_step integer :: i ! CHECK: omp.parallel !$OMP PARALLEL - ! CHECK: %[[ALLOCA_IV:.*]] = fir.alloca i32 {{{.*}}, pinned} - ! CHECK: %[[IV_DECL:.*]]:2 = hlfir.declare %[[ALLOCA_IV]] {uniq_name = "_QFsimple_loop_with_stepEi"} : (!fir.ref) -> (!fir.ref, !fir.ref) - ! CHECK: %[[WS_LB:.*]] = arith.constant 1 : i32 - ! CHECK: %[[WS_UB:.*]] = arith.constant 9 : i32 - ! CHECK: %[[WS_STEP:.*]] = arith.constant 2 : i32 - ! CHECK: omp.wsloop for (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) - ! CHECK: fir.store %[[I]] to %[[IV_DECL]]#1 : !fir.ref - ! CHECK: %[[LOAD_IV:.*]] = fir.load %[[IV_DECL]]#0 : !fir.ref + ! CHECK: %[[ALLOCA_IV:.*]] = fir.alloca i32 {{{.*}}, pinned} + ! CHECK: %[[IV_DECL:.*]]:2 = hlfir.declare %[[ALLOCA_IV]] {uniq_name = "_QFsimple_loop_with_stepEi"} : (!fir.ref) -> (!fir.ref, !fir.ref) + ! CHECK: %[[WS_LB:.*]] = arith.constant 1 : i32 + ! CHECK: %[[WS_UB:.*]] = arith.constant 9 : i32 + ! CHECK: %[[WS_STEP:.*]] = arith.constant 2 : i32 + ! CHECK: omp.wsloop { + ! CHECK-NEXT: omp.loop_nest (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) { + ! CHECK: fir.store %[[I]] to %[[IV_DECL]]#1 : !fir.ref + ! CHECK: %[[LOAD_IV:.*]] = fir.load %[[IV_DECL]]#0 : !fir.ref !$OMP DO do i=1, 9, 2 - ! CHECK: fir.call @_FortranAioOutputInteger32({{.*}}, %[[LOAD_IV]]) {{.*}}: (!fir.ref, i32) -> i1 + ! CHECK: fir.call @_FortranAioOutputInteger32({{.*}}, %[[LOAD_IV]]) {{.*}}: (!fir.ref, i32) -> i1 print*, i end do - ! CHECK: omp.yield + ! CHECK: omp.yield + ! CHECK: omp.terminator !$OMP END DO - ! CHECK: omp.terminator + ! CHECK: omp.terminator !$OMP END PARALLEL end subroutine @@ -55,21 +59,23 @@ subroutine loop_with_schedule_nowait integer :: i ! CHECK: omp.parallel !$OMP PARALLEL - ! CHECK: %[[ALLOCA_IV:.*]] = fir.alloca i32 {{{.*}}, pinned} - ! CHECK: %[[IV_DECL:.*]]:2 = hlfir.declare %[[ALLOCA_IV]] {uniq_name = "_QFloop_with_schedule_nowaitEi"} : (!fir.ref) -> (!fir.ref, !fir.ref) - ! CHECK: %[[WS_LB:.*]] = arith.constant 1 : i32 - ! CHECK: %[[WS_UB:.*]] = arith.constant 9 : i32 - ! CHECK: %[[WS_STEP:.*]] = arith.constant 1 : i32 - ! CHECK: omp.wsloop schedule(runtime) nowait for (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) + ! CHECK: %[[ALLOCA_IV:.*]] = fir.alloca i32 {{{.*}}, pinned} + ! CHECK: %[[IV_DECL:.*]]:2 = hlfir.declare %[[ALLOCA_IV]] {uniq_name = "_QFloop_with_schedule_nowaitEi"} : (!fir.ref) -> (!fir.ref, !fir.ref) + ! CHECK: %[[WS_LB:.*]] = arith.constant 1 : i32 + ! CHECK: %[[WS_UB:.*]] = arith.constant 9 : i32 + ! CHECK: %[[WS_STEP:.*]] = arith.constant 1 : i32 + ! CHECK: omp.wsloop schedule(runtime) nowait { + ! CHECK-NEXT: omp.loop_nest (%[[I:.*]]) : i32 = (%[[WS_LB]]) to (%[[WS_UB]]) inclusive step (%[[WS_STEP]]) { !$OMP DO SCHEDULE(runtime) do i=1, 9 - ! CHECK: fir.store %[[I]] to %[[IV_DECL]]#1 : !fir.ref - ! CHECK: %[[LOAD_IV:.*]] = fir.load %[[IV_DECL]]#0 : !fir.ref - ! CHECK: fir.call @_FortranAioOutputInteger32({{.*}}, %[[LOAD_IV]]) {{.*}}: (!fir.ref, i32) -> i1 + ! CHECK: fir.store %[[I]] to %[[IV_DECL]]#1 : !fir.ref + ! CHECK: %[[LOAD_IV:.*]] = fir.load %[[IV_DECL]]#0 : !fir.ref + ! CHECK: fir.call @_FortranAioOutputInteger32({{.*}}, %[[LOAD_IV]]) {{.*}}: (!fir.ref, i32) -> i1 print*, i end do - ! CHECK: omp.yield + ! CHECK: omp.yield + ! CHECK: omp.terminator !$OMP END DO NOWAIT - ! CHECK: omp.terminator + ! CHECK: omp.terminator !$OMP END PARALLEL end subroutine diff --git a/flang/test/Parser/unrecognized-dir.f90 b/flang/test/Parser/unrecognized-dir.f90 index ba6fff7562e2d52c28edf1e578f4dc3b5d08934b..91fbfc9ee3c378eea82bc6304b22986ef25b1e69 100644 --- a/flang/test/Parser/unrecognized-dir.f90 +++ b/flang/test/Parser/unrecognized-dir.f90 @@ -1,4 +1,10 @@ ! RUN: %flang_fc1 -fsyntax-only %s 2>&1 | FileCheck %s -!CHECK: warning: Compiler directive was ignored +!CHECK: warning: Unrecognized compiler directive was ignored !DIR$ Not a recognized directive +program main + contains + !CHECK: warning: Compiler directive ignored here + !DIR$ not in a subprogram + subroutine s + end end diff --git a/flang/test/Preprocessing/backslash-contin1.F90 b/flang/test/Preprocessing/backslash-contin1.F90 new file mode 100644 index 0000000000000000000000000000000000000000..cf2ed36370dab3d3f9381b6d4c4f7daabee54a32 --- /dev/null +++ b/flang/test/Preprocessing/backslash-contin1.F90 @@ -0,0 +1,8 @@ +! RUN: %flang -E %s | FileCheck %s +print *, \ + "hello, \ +world" +end +!CHECK: print *, "hello, world" +!CHECK: end + diff --git a/flang/test/Semantics/arg-convert.f90 b/flang/test/Semantics/arg-convert.f90 new file mode 100644 index 0000000000000000000000000000000000000000..7951bedf49d0f892ede7d6bc64bd2ae14ed0e821 --- /dev/null +++ b/flang/test/Semantics/arg-convert.f90 @@ -0,0 +1,16 @@ +!RUN: %flang_fc1 -fdebug-unparse %s 2>&1 | FileCheck %s +!Ensure that argument conversion does not take place when the procedure +!interface is implicit at the point of call, even when the interface +!is known due because the procedure's definition is in the same source file. + +subroutine test +!CHECK: warning: If the procedure's interface were explicit, this reference would be in error +!CHECK: because: Actual argument type 'INTEGER(8)' is not compatible with dummy argument type 'INTEGER(4)' +!CHECK: CALL samesourcefile((1_8)) + call sameSourceFile((1_8)) +!CHECK: CALL somewhereelse((2_8)) + call somewhereElse((2_8)) +end + +subroutine sameSourceFile(n) +end diff --git a/flang/test/Semantics/cuf02.cuf b/flang/test/Semantics/cuf02.cuf index 881a3005e2817bda7e48eefa2946245a5a378313..a4a229565a3e8c817b1169961150f2fa4230e0b0 100644 --- a/flang/test/Semantics/cuf02.cuf +++ b/flang/test/Semantics/cuf02.cuf @@ -5,14 +5,11 @@ module m end end interface contains - !ERROR: A device subprogram may not be RECURSIVE, PURE, or ELEMENTAL - recursive attributes(device) subroutine s1 + recursive attributes(device) subroutine s1 ! ok end - !ERROR: A device subprogram may not be RECURSIVE, PURE, or ELEMENTAL - pure attributes(device) subroutine s2 + pure attributes(device) subroutine s2 ! ok end - !ERROR: A device subprogram may not be RECURSIVE, PURE, or ELEMENTAL - elemental attributes(device) subroutine s3 + elemental attributes(device) subroutine s3 ! ok end subroutine s4 contains @@ -32,14 +29,11 @@ module m !ERROR: A function may not have ATTRIBUTES(GLOBAL) or ATTRIBUTES(GRID_GLOBAL) attributes(global) real function f1 end - !ERROR: A device subprogram may not be RECURSIVE, PURE, or ELEMENTAL - recursive attributes(global) subroutine s7 + recursive attributes(global) subroutine s7 ! ok end - !ERROR: A device subprogram may not be RECURSIVE, PURE, or ELEMENTAL - pure attributes(global) subroutine s8 + pure attributes(global) subroutine s8 ! ok end - !ERROR: A device subprogram may not be RECURSIVE, PURE, or ELEMENTAL - elemental attributes(global) subroutine s9 + elemental attributes(global) subroutine s9 ! ok end end diff --git a/flang/test/Semantics/declarations03.f90 b/flang/test/Semantics/declarations03.f90 index 3459b2287b2badd800380ff11c85429aafbe797e..65b07e7d5c656787de55846ccc2c794f09760e70 100644 --- a/flang/test/Semantics/declarations03.f90 +++ b/flang/test/Semantics/declarations03.f90 @@ -19,7 +19,7 @@ module m common /blk4/ w bind(c, name="cc") :: t2, /blk4/ - !ERROR: The entity 'blk5' has multiple BIND names + !ERROR: The entity 'blk5' has multiple BIND names ('dd' and 'ee') common /blk5/ i bind(c, name="dd") :: /blk5/ bind(c, name="ee") :: /blk5/ @@ -29,7 +29,7 @@ module m bind(c, name="ff") :: /blk6/ bind(c, name="ff") :: /blk7/ - !ERROR: The entity 's1' has multiple BIND names + !ERROR: The entity 's1' has multiple BIND names ('gg' and 'hh') integer :: s1 bind(c, name="gg") :: s1 !ERROR: BIND_C attribute was already specified on 's1' @@ -40,12 +40,12 @@ module m bind(c, name="ii") :: s2 bind(c, name="ii") :: s3 - !ERROR: The entity 's4' has multiple BIND names + !ERROR: The entity 's4' has multiple BIND names ('ss1' and 'jj') integer, bind(c, name="ss1") :: s4 !ERROR: BIND_C attribute was already specified on 's4' bind(c, name="jj") :: s4 - !ERROR: The entity 's5' has multiple BIND names + !ERROR: The entity 's5' has multiple BIND names ('kk' and 'ss2') bind(c, name="kk") :: s5 !ERROR: BIND_C attribute was already specified on 's5' integer, bind(c, name="ss2") :: s5 @@ -72,3 +72,8 @@ module b !ERROR: Two entities have the same global name 'int' integer, bind(c, name="int") :: i end module + +module c + bind(c, name = "AAA") a + integer aaa ! ensure no bogus error about multiple binding names +end module diff --git a/flang/test/Transforms/debug-line-table-inc-file.fir b/flang/test/Transforms/debug-line-table-inc-file.fir index be4f005bf664acd4caff461beb00bf174af791a6..dc75482d4f8a7f077ebbf23c1261b465a2a17323 100644 --- a/flang/test/Transforms/debug-line-table-inc-file.fir +++ b/flang/test/Transforms/debug-line-table-inc-file.fir @@ -1,5 +1,5 @@ -// RUN: fir-opt --add-debug-info --mlir-print-debuginfo %s | FileCheck %s +// RUN: fir-opt --add-debug-info="debug-level=LineTablesOnly" --mlir-print-debuginfo %s | FileCheck %s // REQUIRES: system-linux // Test for included functions that have a different debug location than the current file @@ -30,7 +30,7 @@ module attributes {} { // CHECK: #[[MODULE_LOC]] = loc("{{.*}}simple.f90":0:0) // CHECK: #[[LOC_INC_FILE:.*]] = loc("{{.*}}inc.f90":1:1) // CHECK: #[[LOC_FILE:.*]] = loc("{{.*}}simple.f90":3:1) -// CHECK: #[[DI_CU:.*]] = #llvm.di_compile_unit, sourceLanguage = DW_LANG_Fortran95, file = #[[DI_FILE]], producer = "Flang", isOptimized = false, emissionKind = LineTablesOnly> +// CHECK: #[[DI_CU:.*]] = #llvm.di_compile_unit, sourceLanguage = DW_LANG_Fortran95, file = #[[DI_FILE]], producer = "flang{{.*}}", isOptimized = false, emissionKind = LineTablesOnly> // CHECK: #[[DI_SP_INC:.*]] = #llvm.di_subprogram, compileUnit = #[[DI_CU]], scope = #[[DI_FILE]], name = "_QPsinc", linkageName = "_QPsinc", file = #[[DI_INC_FILE]], {{.*}}> // CHECK: #[[DI_SP:.*]] = #llvm.di_subprogram, compileUnit = #[[DI_CU]], scope = #[[DI_FILE]], name = "_QQmain", linkageName = "_QQmain", file = #[[DI_FILE]], {{.*}}> // CHECK: #[[FUSED_LOC_INC_FILE]] = loc(fused<#[[DI_SP_INC]]>[#[[LOC_INC_FILE]]]) diff --git a/flang/test/Transforms/debug-line-table.fir b/flang/test/Transforms/debug-line-table.fir index 0ba88d3d9f7fa2aa93255f3f438dc97e23a84ad3..3b3a39174df0941ee5f20d226f6b752dbb9023bc 100644 --- a/flang/test/Transforms/debug-line-table.fir +++ b/flang/test/Transforms/debug-line-table.fir @@ -1,5 +1,7 @@ -// RUN: fir-opt --add-debug-info --mlir-print-debuginfo %s | FileCheck %s +// RUN: fir-opt --add-debug-info="debug-level=Full" --mlir-print-debuginfo %s | FileCheck %s --check-prefix=FULL +// RUN: fir-opt --add-debug-info="debug-level=LineTablesOnly" --mlir-print-debuginfo %s | FileCheck %s --check-prefix=LINETABLE +// RUN: fir-opt --add-debug-info="is-optimized=true" --mlir-print-debuginfo %s | FileCheck %s --check-prefix=OPT module attributes { fir.defaultkind = "a1c4d8i4l4r4", fir.kindmap = "", llvm.data_layout = "e-m:e-i8:8:32-i16:16:32-i64:64-i128:128-n32:64-S128", llvm.target_triple = "aarch64-unknown-linux-gnu"} { func.func @_QPsb() { @@ -22,7 +24,9 @@ module attributes { fir.defaultkind = "a1c4d8i4l4r4", fir.kindmap = "", llvm.dat // CHECK: #[[MODULE_LOC]] = loc("[[DIR_NAME]]/[[FILE_NAME]]":1:1) // CHECK: #[[SB_LOC]] = loc("./simple.f90":2:1) // CHECK: #[[DECL_LOC:.*]] = loc("./simple.f90":10:1) -// CHECK: #di_compile_unit = #llvm.di_compile_unit, sourceLanguage = DW_LANG_Fortran95, file = #di_file, producer = "Flang", isOptimized = false, emissionKind = LineTablesOnly> +// FULL: #di_compile_unit = #llvm.di_compile_unit, sourceLanguage = DW_LANG_Fortran95, file = #di_file, producer = "flang{{.*}}", isOptimized = false, emissionKind = Full> +// OPT: #di_compile_unit = #llvm.di_compile_unit, sourceLanguage = DW_LANG_Fortran95, file = #di_file, producer = "flang{{.*}}", isOptimized = true, emissionKind = Full> +// LINETABLE: #di_compile_unit = #llvm.di_compile_unit, sourceLanguage = DW_LANG_Fortran95, file = #di_file, producer = "flang{{.*}}", isOptimized = false, emissionKind = LineTablesOnly> // CHECK: #di_subroutine_type = #llvm.di_subroutine_type // CHECK: #[[SB_SUBPROGRAM:.*]] = #llvm.di_subprogram, compileUnit = #di_compile_unit, scope = #di_file, name = "[[SB_NAME]]", linkageName = "[[SB_NAME]]", file = #di_file, line = 1, scopeLine = 1, subprogramFlags = "Definition|Optimized", type = #di_subroutine_type> // CHECK: #[[DECL_SUBPROGRAM:.*]] = #llvm.di_subprogram diff --git a/flang/test/Transforms/omp-reduction-cfg-conversion.fir b/flang/test/Transforms/omp-reduction-cfg-conversion.fir index 3103c4456d72efdd7d94ab78f4598f7c562b1bc2..707e665132afbbd000c5aa263bebe32426f42b09 100644 --- a/flang/test/Transforms/omp-reduction-cfg-conversion.fir +++ b/flang/test/Transforms/omp-reduction-cfg-conversion.fir @@ -1,4 +1,4 @@ -// RUN: fir-opt --cfg-conversion-on-reduce-opt %s | FileCheck %s +// RUN: fir-opt --cfg-conversion %s | FileCheck %s omp.declare_reduction @add_reduction_i_32_box_3_byref : !fir.ref>> init { ^bb0(%arg0: !fir.ref>>): diff --git a/flang/unittests/Runtime/NumericalFormatTest.cpp b/flang/unittests/Runtime/NumericalFormatTest.cpp index dee4dda4a22869cfd0508f5e197143cc993c6179..2a9f8f8d1dc4f31556ea2609b337904256b9be9f 100644 --- a/flang/unittests/Runtime/NumericalFormatTest.cpp +++ b/flang/unittests/Runtime/NumericalFormatTest.cpp @@ -958,3 +958,20 @@ TEST(IOApiTests, EditDoubleInputValues) { << "', want " << want << ", got " << u.raw; } } + +// regression test for confusing digit minimization +TEST(IOApiTests, ConfusingMinimization) { + char buffer[8]{}; + auto cookie{IONAME(BeginInternalListOutput)(buffer, sizeof buffer)}; + StaticDescriptor<0> staticDescriptor; + Descriptor &desc{staticDescriptor.descriptor()}; + std::uint16_t x{0x7bff}; // HUGE(0._2) + desc.Establish(TypeCode{CFI_type_half_float}, sizeof x, &x, 0, nullptr); + desc.Check(); + EXPECT_TRUE(IONAME(OutputDescriptor)(cookie, desc)); + auto status{IONAME(EndIoStatement)(cookie)}; + EXPECT_EQ(status, 0); + std::string got{std::string{buffer, sizeof buffer}}; + EXPECT_TRUE(CompareFormattedStrings(" 65504. ", got)) + << "expected ' 65504. ', got '" << got << '\''; // not 65500.! +} diff --git a/flang/unittests/Runtime/RuntimeCrashTest.cpp b/flang/unittests/Runtime/RuntimeCrashTest.cpp index 0f25cc0ee8035baa358baadc11f6ce37f1fb9983..a649051fdca0c5b2ec55af5fe02c3228eddaa7c1 100644 --- a/flang/unittests/Runtime/RuntimeCrashTest.cpp +++ b/flang/unittests/Runtime/RuntimeCrashTest.cpp @@ -53,16 +53,6 @@ TEST(TestTerminator, CheckFailedTest) { //------------------------------------------------------------------------------ struct TestIOCrash : CrashHandlerFixture {}; -TEST(TestIOCrash, FormatDescriptorWriteMismatchTest) { - static constexpr int bufferSize{4}; - static char buffer[bufferSize]; - static const char *format{"(A4)"}; - auto *cookie{IONAME(BeginInternalFormattedOutput)( - buffer, bufferSize, format, std::strlen(format))}; - ASSERT_DEATH(IONAME(OutputLogical)(cookie, true), - "Data edit descriptor 'A' may not be used with a LOGICAL data item"); -} - TEST(TestIOCrash, InvalidFormatCharacterTest) { static constexpr int bufferSize{1}; static char buffer[bufferSize]; diff --git a/libc/config/linux/syscall_numbers.h.inc b/libc/config/linux/syscall_numbers.h.inc index 9f910c5f9042a812d18a800010db19f96055f550..4a19d9a08875e81de3c1fa70160e3bfc49103a84 100644 --- a/libc/config/linux/syscall_numbers.h.inc +++ b/libc/config/linux/syscall_numbers.h.inc @@ -338,6 +338,10 @@ #define SYS_fchmodat __NR_fchmodat #endif +#ifdef __NR_fchmodat2 +#define SYS_fchmodat2 __NR_fchmodat2 +#endif + #ifdef __NR_fchown #define SYS_fchown __NR_fchown #endif diff --git a/libc/docs/index.rst b/libc/docs/index.rst index f71920b058d83f297cafe71e37e5aed6f9f4e5b5..5b96987e0aada080d8051fc42a4dbff998d3536e 100644 --- a/libc/docs/index.rst +++ b/libc/docs/index.rst @@ -72,6 +72,7 @@ stages there is no ABI stability in any form. ctype signal threads + setjmp .. toctree:: :hidden: diff --git a/libc/docs/setjmp.rst b/libc/docs/setjmp.rst new file mode 100644 index 0000000000000000000000000000000000000000..d9188dfe1d5e4799836203118d9a3b890ebcdb11 --- /dev/null +++ b/libc/docs/setjmp.rst @@ -0,0 +1,16 @@ +.. include:: check.rst + +setjmp.h Functions +================== + +.. list-table:: + :widths: auto + :align: center + :header-rows: 1 + + * - Function + - Implemented + - Standard + * - longjmp + - |check| + - 7.13.2.1 diff --git a/libc/include/assert.h.def b/libc/include/assert.h.def index e006133a76542a6d9e31d4cd564ff998967ca7d4..15077e53e2ca4826d9abe8d69ec08928393e15a4 100644 --- a/libc/include/assert.h.def +++ b/libc/include/assert.h.def @@ -7,6 +7,7 @@ //===----------------------------------------------------------------------===// #include "__llvm-libc-common.h" +#include "llvm-libc-macros/assert-macros.h" // This file may be usefully included multiple times to change assert()'s // definition based on NDEBUG. diff --git a/libc/include/llvm-libc-macros/CMakeLists.txt b/libc/include/llvm-libc-macros/CMakeLists.txt index 382cb8ee417e1632b522aa403f2f72bd516d2a42..68ba110aec80f1ac1331a8ee0e6c49eaf8d3faaa 100644 --- a/libc/include/llvm-libc-macros/CMakeLists.txt +++ b/libc/include/llvm-libc-macros/CMakeLists.txt @@ -31,6 +31,12 @@ if(EXISTS ${CMAKE_CURRENT_SOURCE_DIR}/${LIBC_TARGET_OS}) add_subdirectory(${CMAKE_CURRENT_SOURCE_DIR}/${LIBC_TARGET_OS}) endif() +add_macro_header( + assert_macros + HDR + assert-macros.h +) + add_macro_header( generic_error_number_macros HDR diff --git a/libc/include/llvm-libc-macros/assert-macros.h b/libc/include/llvm-libc-macros/assert-macros.h new file mode 100644 index 0000000000000000000000000000000000000000..44e14543d8562e6c52fe80bf95d9ca6a4c259a38 --- /dev/null +++ b/libc/include/llvm-libc-macros/assert-macros.h @@ -0,0 +1,14 @@ +//===-- Definition of macros to be used with assert functions -------------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#ifndef __LLVM_LIBC_MACROS_ASSERT_MACROS_H +#define __LLVM_LIBC_MACROS_ASSERT_MACROS_H + +#define __STDC_VERSION_ASSERT_H__ 202311L + +#endif // __LLVM_LIBC_MACROS_ASSERT_MACROS_H diff --git a/libc/src/sys/stat/linux/chmod.cpp b/libc/src/sys/stat/linux/chmod.cpp index 085b91691d89f47992235e3585b6a990c3550d8d..25e5e69af71a082581cffcc075521cc02e1b6885 100644 --- a/libc/src/sys/stat/linux/chmod.cpp +++ b/libc/src/sys/stat/linux/chmod.cpp @@ -21,11 +21,14 @@ namespace LIBC_NAMESPACE { LLVM_LIBC_FUNCTION(int, chmod, (const char *path, mode_t mode)) { #ifdef SYS_chmod int ret = LIBC_NAMESPACE::syscall_impl(SYS_chmod, path, mode); +#elif defined(SYS_fchmodat2) + int ret = LIBC_NAMESPACE::syscall_impl(SYS_fchmodat2, AT_FDCWD, path, + mode, 0, AT_SYMLINK_NOFOLLOW); #elif defined(SYS_fchmodat) int ret = - LIBC_NAMESPACE::syscall_impl(SYS_fchmodat, AT_FDCWD, path, mode); + LIBC_NAMESPACE::syscall_impl(SYS_fchmodat, AT_FDCWD, path, mode, 0); #else -#error "chmod and fchmodat syscalls not available." +#error "chmod, fchmodat and fchmodat2 syscalls not available." #endif if (ret < 0) { diff --git a/libc/test/UnitTest/CMakeLists.txt b/libc/test/UnitTest/CMakeLists.txt index 9113eca388e05b12b95d166fa8db0a2af45af67b..302af3044ca3d66e9d24cc231b331ff67b8244e1 100644 --- a/libc/test/UnitTest/CMakeLists.txt +++ b/libc/test/UnitTest/CMakeLists.txt @@ -111,8 +111,10 @@ add_header_library( add_unittest_framework_library( LibcFPTestHelpers SRCS + FEnvSafeTest.cpp RoundingModeUtils.cpp HDRS + FEnvSafeTest.h FPMatcher.h RoundingModeUtils.h DEPENDS diff --git a/libc/test/UnitTest/FEnvSafeTest.cpp b/libc/test/UnitTest/FEnvSafeTest.cpp new file mode 100644 index 0000000000000000000000000000000000000000..905aa928937387d91e69b4a108efe39f1251e25f --- /dev/null +++ b/libc/test/UnitTest/FEnvSafeTest.cpp @@ -0,0 +1,84 @@ +//===-- FEnvSafeTest.cpp ---------------------------------------*- C++ -*-===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===---------------------------------------------------------------------===// + +#include "FEnvSafeTest.h" + +#include "src/__support/FPUtil/FEnvImpl.h" +#include "src/__support/macros/properties/architectures.h" + +namespace LIBC_NAMESPACE::testing { + +void FEnvSafeTest::PreserveFEnv::check() { + fenv_t after; + test.get_fenv(after); + test.expect_fenv_eq(before, after); +} + +void FEnvSafeTest::TearDown() { + if (!should_be_unchanged) { + restore_fenv(); + } +} + +void FEnvSafeTest::get_fenv(fenv_t &fenv) { + ASSERT_EQ(LIBC_NAMESPACE::fputil::get_env(&fenv), 0); +} + +void FEnvSafeTest::set_fenv(const fenv_t &fenv) { + ASSERT_EQ(LIBC_NAMESPACE::fputil::set_env(&fenv), 0); +} + +void FEnvSafeTest::expect_fenv_eq(const fenv_t &before_fenv, + const fenv_t &after_fenv) { +#if defined(LIBC_TARGET_ARCH_IS_AARCH64) + using FPState = LIBC_NAMESPACE::fputil::FEnv::FPState; + const FPState &before_state = reinterpret_cast(before_fenv); + const FPState &after_state = reinterpret_cast(after_fenv); + + EXPECT_EQ(before_state.ControlWord, after_state.ControlWord); + EXPECT_EQ(before_state.StatusWord, after_state.StatusWord); + +#elif defined(LIBC_TARGET_ARCH_IS_X86) && !defined(__APPLE__) + using LIBC_NAMESPACE::fputil::internal::FPState; + const FPState &before_state = reinterpret_cast(before_fenv); + const FPState &after_state = reinterpret_cast(after_fenv); + +#if defined(_WIN32) + EXPECT_EQ(before_state.control_word, after_state.control_word); + EXPECT_EQ(before_state.status_word, after_state.status_word); +#elif defined(__APPLE__) + EXPECT_EQ(before_state.control_word, after_state.control_word); + EXPECT_EQ(before_state.status_word, after_state.status_word); + EXPECT_EQ(before_state.mxcsr, after_state.mxcsr); +#else + EXPECT_EQ(before_state.x87_status.control_word, + after_state.x87_status.control_word); + EXPECT_EQ(before_state.x87_status.status_word, + after_state.x87_status.status_word); + EXPECT_EQ(before_state.mxcsr, after_state.mxcsr); +#endif + +#elif defined(LIBC_TARGET_ARCH_IS_ARM) && defined(__ARM_FP) + using LIBC_NAMESPACE::fputil::FEnv; + const FEnv &before_state = reinterpret_cast(before_fenv); + const FEnv &after_state = reinterpret_cast(after_fenv); + + EXPECT_EQ(before_state.fpscr, after_state.fpscr); + +#elif defined(LIBC_TARGET_ARCH_IS_ANY_RISCV) + const uint32_t &before_fcsr = reinterpret_cast(before_fenv); + const uint32_t &after_fcsr = reinterpret_cast(after_fenv); + EXPECT_EQ(before_fcsr, after_fcsr); + +#else + // No arch-specific `fenv_t` support, so nothing to compare. + +#endif +} + +} // namespace LIBC_NAMESPACE::testing diff --git a/libc/test/UnitTest/FEnvSafeTest.h b/libc/test/UnitTest/FEnvSafeTest.h new file mode 100644 index 0000000000000000000000000000000000000000..d5a8bb7ee667ce9434b12ad37aef8ccec246440a --- /dev/null +++ b/libc/test/UnitTest/FEnvSafeTest.h @@ -0,0 +1,101 @@ +//===-- FEnvSafeTest.h -----------------------------------------*- C++ -*-===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===---------------------------------------------------------------------===// + +#ifndef LLVM_LIBC_TEST_UNITTEST_FPENVSAFE_H +#define LLVM_LIBC_TEST_UNITTEST_FPENVSAFE_H + +#include "hdr/types/fenv_t.h" +#include "src/__support/CPP/utility.h" +#include "test/UnitTest/Test.h" + +namespace LIBC_NAMESPACE::testing { + +// This provides a test fixture (or base class for other test fixtures) that +// asserts that each test does not leave the FPU state represented by `fenv_t` +// (aka `FPState`) perturbed from its initial state. +class FEnvSafeTest : public Test { +public: + void TearDown() override; + +protected: + // This is an RAII type where `PreserveFEnv preserve{this};` will sample the + // `fenv_t` state and restore it when `preserve` goes out of scope. + class PreserveFEnv { + fenv_t before; + FEnvSafeTest &test; + + public: + explicit PreserveFEnv(FEnvSafeTest *self) : test{*self} { + test.get_fenv(before); + } + + // Cause test expectation failures if the current state doesn't match what + // was captured in the constructor. + void check(); + + // Restore the state captured in the constructor. + void restore() { test.set_fenv(before); } + + ~PreserveFEnv() { restore(); } + }; + + // This is an RAII type where `CheckFEnv check{this};` will sample the + // `fenv_t` state and require it be the same when `check` goes out of scope. + struct CheckFEnv : public PreserveFEnv { + using PreserveFEnv::PreserveFEnv; + + ~CheckFEnv() { check(); } + }; + + // This calls callable() and returns its value, but has EXPECT_* failures if + // the `fenv_t` state is not preserved by the call. + template decltype(auto) check_fenv_preserved(T &&callable) { + CheckFEnv check{this}; + return cpp::forward(callable)(); + } + + // This calls callable() and returns its value, but saves and restores the + // `fenv_t` state around the call. + template + auto with_fenv_preserved(T &&callable) + -> decltype(cpp::forward(callable)()) { + PreserveFEnv preserve{this}; + return cpp::forward(callable)(); + } + + // A test can call these to indicate it will or won't change `fenv_t` state. + void will_change_fenv() { should_be_unchanged = false; } + void will_not_change_fenv() { should_be_unchanged = true; } + + // This explicitly resets back to the "before" state captured in SetUp(). + // TearDown() always does this, but should_be_unchanged controls whether + // it also causes test failures if a test fails to restore it. + void restore_fenv() { check.restore(); } + +private: + void get_fenv(fenv_t &fenv); + void set_fenv(const fenv_t &fenv); + void expect_fenv_eq(const fenv_t &before_fenv, const fenv_t &after_fenv); + + CheckFEnv check{this}; + + // TODO: Many tests fail if this is true. It needs to be figured out whether + // the state should be preserved by each library function under test, and + // separately whether each test itself should preserve the state. It + // probably isn't important that tests be explicitly written to preserve the + // state, as the fixture can (and does) reset it--the next test can rely on + // getting "normal" ambient state initially. For library functions that + // should preserve the state, that should be checked after each call, not + // just after the whole test. So they can use check_fenv_preserved or + // with_fenv_preserved as appropriate. + bool should_be_unchanged = false; +}; + +} // namespace LIBC_NAMESPACE::testing + +#endif // LLVM_LIBC_TEST_UNITTEST_FPENVSAFE_H diff --git a/libc/test/include/CMakeLists.txt b/libc/test/include/CMakeLists.txt index 8d8dff53169f6ac21cbcdf8ebdd88634d2f19538..03c31855e352bac30aae93fccc416e8c683883d4 100644 --- a/libc/test/include/CMakeLists.txt +++ b/libc/test/include/CMakeLists.txt @@ -1,5 +1,15 @@ add_custom_target(libc_include_tests) +add_libc_test( + assert_test + SUITE + libc_include_tests + SRCS + assert_test.cpp + DEPENDS + libc.include.llvm-libc-macros.assert_macros +) + add_libc_test( sys_queue_test SUITE diff --git a/libc/test/include/assert_test.cpp b/libc/test/include/assert_test.cpp new file mode 100644 index 0000000000000000000000000000000000000000..78709bbcdd5941effe2d66f02f0b7134c759e035 --- /dev/null +++ b/libc/test/include/assert_test.cpp @@ -0,0 +1,15 @@ +//===-- Unittests for assert ----------------------------------------------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDSList-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#include "include/llvm-libc-macros/assert-macros.h" +#include "test/UnitTest/Test.h" + +TEST(LlvmLibcAssertTest, VersionMacro) { + // 7.2p3 an integer constant expression with a value equivalent to 202311L. + EXPECT_EQ(__STDC_VERSION_ASSERT_H__, 202311L); +} diff --git a/libc/test/src/fenv/CMakeLists.txt b/libc/test/src/fenv/CMakeLists.txt index f277b65e2d42be01f971aad967b9c2f8b3e58022..b776f9a0706e861cd16e55ab60e27eeceac19e76 100644 --- a/libc/test/src/fenv/CMakeLists.txt +++ b/libc/test/src/fenv/CMakeLists.txt @@ -9,6 +9,8 @@ add_libc_unittest( DEPENDS libc.src.fenv.fegetround libc.src.fenv.fesetround + LINK_LIBRARIES + LibcFPTestHelpers ) add_libc_unittest( @@ -23,6 +25,8 @@ add_libc_unittest( libc.src.fenv.fesetexcept libc.src.fenv.fetestexcept libc.src.__support.FPUtil.fenv_impl + LINK_LIBRARIES + LibcFPTestHelpers ) add_libc_unittest( @@ -37,6 +41,8 @@ add_libc_unittest( libc.src.fenv.fesetenv libc.src.fenv.fesetround libc.src.__support.FPUtil.fenv_impl + LINK_LIBRARIES + LibcFPTestHelpers ) add_libc_unittest( @@ -50,6 +56,8 @@ add_libc_unittest( libc.src.fenv.fesetexceptflag libc.src.fenv.fetestexceptflag libc.src.__support.FPUtil.fenv_impl + LINK_LIBRARIES + LibcFPTestHelpers ) add_libc_unittest( @@ -62,6 +70,8 @@ add_libc_unittest( libc.include.signal libc.src.fenv.feupdateenv libc.src.__support.FPUtil.fenv_impl + LINK_LIBRARIES + LibcFPTestHelpers ) add_libc_unittest( @@ -73,6 +83,8 @@ add_libc_unittest( DEPENDS libc.src.fenv.feclearexcept libc.src.__support.FPUtil.fenv_impl + LINK_LIBRARIES + LibcFPTestHelpers ) add_libc_unittest( @@ -85,6 +97,8 @@ add_libc_unittest( libc.src.fenv.fedisableexcept libc.src.fenv.feenableexcept libc.src.fenv.fegetexcept + LINK_LIBRARIES + LibcFPTestHelpers ) if (NOT (LLVM_USE_SANITIZER OR (${LIBC_TARGET_OS} STREQUAL "windows") @@ -109,6 +123,7 @@ if (NOT (LLVM_USE_SANITIZER OR (${LIBC_TARGET_OS} STREQUAL "windows") libc.src.__support.FPUtil.fenv_impl LINK_LIBRARIES LibcFPExceptionHelpers + LibcFPTestHelpers ) add_fp_unittest( @@ -124,5 +139,6 @@ if (NOT (LLVM_USE_SANITIZER OR (${LIBC_TARGET_OS} STREQUAL "windows") libc.src.__support.FPUtil.fenv_impl LINK_LIBRARIES LibcFPExceptionHelpers + LibcFPTestHelpers ) endif() diff --git a/libc/test/src/fenv/enabled_exceptions_test.cpp b/libc/test/src/fenv/enabled_exceptions_test.cpp index 53440b704ca761d93e66520aae305608e154ae73..7d26eab5695bce1dbfb6a49685fe761cd5b5b357 100644 --- a/libc/test/src/fenv/enabled_exceptions_test.cpp +++ b/libc/test/src/fenv/enabled_exceptions_test.cpp @@ -12,15 +12,20 @@ #include "src/__support/FPUtil/FEnvImpl.h" #include "src/__support/macros/properties/architectures.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPExceptMatcher.h" #include "test/UnitTest/Test.h" #include "hdr/fenv_macros.h" #include +#include "excepts.h" + +using LlvmLibcExceptionStatusTest = LIBC_NAMESPACE::testing::FEnvSafeTest; + // This test enables an exception and verifies that raising that exception // triggers SIGFPE. -TEST(LlvmLibcExceptionStatusTest, RaiseAndCrash) { +TEST_F(LlvmLibcExceptionStatusTest, RaiseAndCrash) { #if defined(LIBC_TARGET_ARCH_IS_ANY_ARM) || \ defined(LIBC_TARGET_ARCH_IS_ANY_RISCV) // Few Arm HW implementations do not trap exceptions. We skip this test @@ -41,16 +46,7 @@ TEST(LlvmLibcExceptionStatusTest, RaiseAndCrash) { // that exception handler, so such a testing can be done after we have // longjmp implemented. - int excepts[] = {FE_DIVBYZERO, FE_INVALID, FE_INEXACT, FE_OVERFLOW, - FE_UNDERFLOW}; - - // We '|' the individual exception flags instead of using FE_ALL_EXCEPT - // as it can include non-standard extensions. Note that we should be able - // to compile this file with headers from other libcs as well. - constexpr int ALL_EXCEPTS = - FE_DIVBYZERO | FE_INVALID | FE_INEXACT | FE_OVERFLOW | FE_UNDERFLOW; - - for (int e : excepts) { + for (int e : EXCEPTS) { LIBC_NAMESPACE::fputil::disable_except(FE_ALL_EXCEPT); LIBC_NAMESPACE::fputil::enable_except(e); ASSERT_EQ(LIBC_NAMESPACE::feclearexcept(FE_ALL_EXCEPT), 0); diff --git a/libc/test/src/fenv/exception_flags_test.cpp b/libc/test/src/fenv/exception_flags_test.cpp index 9d2be6426a6d0b734a84f946fce9845610f49f6d..2f4332df861fec6d9f183aec9e6067bb9b7bffdd 100644 --- a/libc/test/src/fenv/exception_flags_test.cpp +++ b/libc/test/src/fenv/exception_flags_test.cpp @@ -12,18 +12,20 @@ #include "src/fenv/fetestexceptflag.h" #include "src/__support/FPUtil/FEnvImpl.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/Test.h" -TEST(LlvmLibcFenvTest, GetSetTestExceptFlag) { +#include "excepts.h" + +using LlvmLibcFEnvTest = LIBC_NAMESPACE::testing::FEnvSafeTest; + +TEST_F(LlvmLibcFEnvTest, GetSetTestExceptFlag) { // We will disable all exceptions to prevent invocation of the exception // handler. LIBC_NAMESPACE::fputil::disable_except(FE_ALL_EXCEPT); LIBC_NAMESPACE::fputil::clear_except(FE_ALL_EXCEPT); - int excepts[] = {FE_DIVBYZERO, FE_INVALID, FE_INEXACT, FE_OVERFLOW, - FE_UNDERFLOW}; - - for (int e : excepts) { + for (int e : EXCEPTS) { // The overall idea is to raise an except and save the exception flags. // Next, clear the flags and then set the saved exception flags. This // should set the flag corresponding to the previously raised exception. diff --git a/libc/test/src/fenv/exception_status_test.cpp b/libc/test/src/fenv/exception_status_test.cpp index a7000020b1a3c804a6eeee6215bb89316d533e6f..fdf9421457866e6d729e1f944f75ec2a1dd1c45f 100644 --- a/libc/test/src/fenv/exception_status_test.cpp +++ b/libc/test/src/fenv/exception_status_test.cpp @@ -13,24 +13,23 @@ #include "src/fenv/fetestexcept.h" #include "src/__support/FPUtil/FEnvImpl.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/Test.h" #include "hdr/fenv_macros.h" -TEST(LlvmLibcExceptionStatusTest, RaiseAndTest) { +#include "excepts.h" + +using LlvmLibcExceptionStatusTest = LIBC_NAMESPACE::testing::FEnvSafeTest; + +TEST_F(LlvmLibcExceptionStatusTest, RaiseAndTest) { // This test raises a set of exceptions and checks that the exception // status flags are updated. The intention is really not to invoke the // exception handler. Hence, we will disable all exceptions at the // beginning. LIBC_NAMESPACE::fputil::disable_except(FE_ALL_EXCEPT); - int excepts[] = {FE_DIVBYZERO, FE_INVALID, FE_INEXACT, FE_OVERFLOW, - FE_UNDERFLOW}; - - constexpr int ALL_EXCEPTS = - FE_DIVBYZERO | FE_INVALID | FE_INEXACT | FE_OVERFLOW | FE_UNDERFLOW; - - for (int e : excepts) { + for (int e : EXCEPTS) { int r = LIBC_NAMESPACE::feraiseexcept(e); ASSERT_EQ(r, 0); int s = LIBC_NAMESPACE::fetestexcept(e); @@ -47,8 +46,8 @@ TEST(LlvmLibcExceptionStatusTest, RaiseAndTest) { ASSERT_EQ(s, e); } - for (int e1 : excepts) { - for (int e2 : excepts) { + for (int e1 : EXCEPTS) { + for (int e2 : EXCEPTS) { int e = e1 | e2; int r = LIBC_NAMESPACE::feraiseexcept(e); ASSERT_EQ(r, 0); @@ -67,9 +66,9 @@ TEST(LlvmLibcExceptionStatusTest, RaiseAndTest) { } } - for (int e1 : excepts) { - for (int e2 : excepts) { - for (int e3 : excepts) { + for (int e1 : EXCEPTS) { + for (int e2 : EXCEPTS) { + for (int e3 : EXCEPTS) { int e = e1 | e2 | e3; int r = LIBC_NAMESPACE::feraiseexcept(e); ASSERT_EQ(r, 0); @@ -89,10 +88,10 @@ TEST(LlvmLibcExceptionStatusTest, RaiseAndTest) { } } - for (int e1 : excepts) { - for (int e2 : excepts) { - for (int e3 : excepts) { - for (int e4 : excepts) { + for (int e1 : EXCEPTS) { + for (int e2 : EXCEPTS) { + for (int e3 : EXCEPTS) { + for (int e4 : EXCEPTS) { int e = e1 | e2 | e3 | e4; int r = LIBC_NAMESPACE::feraiseexcept(e); ASSERT_EQ(r, 0); @@ -113,11 +112,11 @@ TEST(LlvmLibcExceptionStatusTest, RaiseAndTest) { } } - for (int e1 : excepts) { - for (int e2 : excepts) { - for (int e3 : excepts) { - for (int e4 : excepts) { - for (int e5 : excepts) { + for (int e1 : EXCEPTS) { + for (int e2 : EXCEPTS) { + for (int e3 : EXCEPTS) { + for (int e4 : EXCEPTS) { + for (int e5 : EXCEPTS) { int e = e1 | e2 | e3 | e4 | e5; int r = LIBC_NAMESPACE::feraiseexcept(e); ASSERT_EQ(r, 0); diff --git a/libc/test/src/fenv/excepts.h b/libc/test/src/fenv/excepts.h new file mode 100644 index 0000000000000000000000000000000000000000..e9517d319a9b79a22febc36c0febb358ab98d783 --- /dev/null +++ b/libc/test/src/fenv/excepts.h @@ -0,0 +1,24 @@ +//===-- List of all FE_* constants for tests -----------------------------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===---------------------------------------------------------------------===// + +#ifndef LLVM_LIBC_TEST_SRC_FENV_EXCEPTS_H +#define LLVM_LIBC_TEST_SRC_FENV_EXCEPTS_H + +#include "hdr/fenv_macros.h" + +constexpr int EXCEPTS[] = { + FE_DIVBYZERO, FE_INVALID, FE_INEXACT, FE_OVERFLOW, FE_UNDERFLOW, +}; + +// We '|' the individual exception flags instead of using FE_ALL_EXCEPT +// as it can include non-standard extensions. Note that we should be able +// to compile this file with headers from other libcs as well. +constexpr int ALL_EXCEPTS = + FE_DIVBYZERO | FE_INVALID | FE_INEXACT | FE_OVERFLOW | FE_UNDERFLOW; + +#endif // LLVM_LIBC_TEST_SRC_FENV_EXCEPTS_H diff --git a/libc/test/src/fenv/feclearexcept_test.cpp b/libc/test/src/fenv/feclearexcept_test.cpp index bb42d9070358efb2af27891f9127fd435f88e28f..52adda46adf2f09545875bad5017f77e62cc837c 100644 --- a/libc/test/src/fenv/feclearexcept_test.cpp +++ b/libc/test/src/fenv/feclearexcept_test.cpp @@ -9,27 +9,30 @@ #include "src/fenv/feclearexcept.h" #include "src/__support/FPUtil/FEnvImpl.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/Test.h" #include "hdr/fenv_macros.h" #include -TEST(LlvmLibcFEnvTest, ClearTest) { - uint16_t excepts[] = {FE_DIVBYZERO, FE_INVALID, FE_INEXACT, FE_OVERFLOW, - FE_UNDERFLOW}; +#include "excepts.h" + +using LlvmLibcFEnvTest = LIBC_NAMESPACE::testing::FEnvSafeTest; + +TEST_F(LlvmLibcFEnvTest, ClearTest) { LIBC_NAMESPACE::fputil::disable_except(FE_ALL_EXCEPT); LIBC_NAMESPACE::fputil::clear_except(FE_ALL_EXCEPT); - for (uint16_t e : excepts) + for (int e : EXCEPTS) ASSERT_EQ(LIBC_NAMESPACE::fputil::test_except(e), 0); LIBC_NAMESPACE::fputil::raise_except(FE_ALL_EXCEPT); - for (uint16_t e1 : excepts) { - for (uint16_t e2 : excepts) { - for (uint16_t e3 : excepts) { - for (uint16_t e4 : excepts) { - for (uint16_t e5 : excepts) { + for (int e1 : EXCEPTS) { + for (int e2 : EXCEPTS) { + for (int e3 : EXCEPTS) { + for (int e4 : EXCEPTS) { + for (int e5 : EXCEPTS) { // We clear one exception and test to verify that it was cleared. LIBC_NAMESPACE::feclearexcept(e1 | e2 | e3 | e4 | e5); ASSERT_EQ( diff --git a/libc/test/src/fenv/feenableexcept_test.cpp b/libc/test/src/fenv/feenableexcept_test.cpp index aeb4f955fd69b6d11d1723857f6c4026d1e5ba8e..232e2a1c8316c698189333ea2e26e742a7d91cac 100644 --- a/libc/test/src/fenv/feenableexcept_test.cpp +++ b/libc/test/src/fenv/feenableexcept_test.cpp @@ -11,11 +11,16 @@ #include "src/fenv/feenableexcept.h" #include "src/fenv/fegetexcept.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/Test.h" #include "hdr/fenv_macros.h" -TEST(LlvmLibcFEnvTest, EnableTest) { +#include "excepts.h" + +using LlvmLibcFEnvTest = LIBC_NAMESPACE::testing::FEnvSafeTest; + +TEST_F(LlvmLibcFEnvTest, EnableTest) { #if defined(LIBC_TARGET_ARCH_IS_ANY_ARM) || \ defined(LIBC_TARGET_ARCH_IS_ANY_RISCV) // Few Arm HW implementations do not trap exceptions. We skip this test diff --git a/libc/test/src/fenv/feholdexcept_test.cpp b/libc/test/src/fenv/feholdexcept_test.cpp index 0689d89ab233a3291f257c7d5c20ee2d28fabf62..f3e05d4a5b6c0d163704eccecc5f6386fbb2d307 100644 --- a/libc/test/src/fenv/feholdexcept_test.cpp +++ b/libc/test/src/fenv/feholdexcept_test.cpp @@ -11,10 +11,15 @@ #include "src/__support/FPUtil/FEnvImpl.h" #include "src/__support/macros/properties/architectures.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPExceptMatcher.h" #include "test/UnitTest/Test.h" -TEST(LlvmLibcFEnvTest, RaiseAndCrash) { +#include "excepts.h" + +using LlvmLibcFEnvTest = LIBC_NAMESPACE::testing::FEnvSafeTest; + +TEST_F(LlvmLibcFEnvTest, RaiseAndCrash) { #if defined(LIBC_TARGET_ARCH_IS_ANY_ARM) || \ defined(LIBC_TARGET_ARCH_IS_ANY_RISCV) // Few Arm HW implementations do not trap exceptions. We skip this test diff --git a/libc/test/src/fenv/feupdateenv_test.cpp b/libc/test/src/fenv/feupdateenv_test.cpp index 251b8566aac3d627c8684682aff4dab3056b4651..d2ffc0ef8e84d3bf1d5cdfe27daac684933539b7 100644 --- a/libc/test/src/fenv/feupdateenv_test.cpp +++ b/libc/test/src/fenv/feupdateenv_test.cpp @@ -10,11 +10,12 @@ #include "src/fenv/feupdateenv.h" #include "src/__support/FPUtil/FEnvImpl.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/Test.h" -#include +using LlvmLibcFEnvTest = LIBC_NAMESPACE::testing::FEnvSafeTest; -TEST(LlvmLibcFEnvTest, UpdateEnvTest) { +TEST_F(LlvmLibcFEnvTest, UpdateEnvTest) { LIBC_NAMESPACE::fputil::disable_except(FE_ALL_EXCEPT); LIBC_NAMESPACE::fputil::clear_except(FE_ALL_EXCEPT); diff --git a/libc/test/src/fenv/getenv_and_setenv_test.cpp b/libc/test/src/fenv/getenv_and_setenv_test.cpp index f767e8ab9b2fb8b846804fb5fbe2d3566acde595..7257e75cb421ae54c7b4f539faff106452950735 100644 --- a/libc/test/src/fenv/getenv_and_setenv_test.cpp +++ b/libc/test/src/fenv/getenv_and_setenv_test.cpp @@ -13,17 +13,19 @@ #include "src/fenv/fesetround.h" #include "src/__support/FPUtil/FEnvImpl.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/Test.h" -TEST(LlvmLibcFenvTest, GetEnvAndSetEnv) { +#include "excepts.h" + +using LlvmLibcFEnvTest = LIBC_NAMESPACE::testing::FEnvSafeTest; + +TEST_F(LlvmLibcFEnvTest, GetEnvAndSetEnv) { // We will disable all exceptions to prevent invocation of the exception // handler. LIBC_NAMESPACE::fputil::disable_except(FE_ALL_EXCEPT); - int excepts[] = {FE_DIVBYZERO, FE_INVALID, FE_INEXACT, FE_OVERFLOW, - FE_UNDERFLOW}; - - for (int e : excepts) { + for (int e : EXCEPTS) { LIBC_NAMESPACE::fputil::clear_except(FE_ALL_EXCEPT); // Save the cleared environment. @@ -71,7 +73,7 @@ TEST(LlvmLibcFenvTest, Set_FE_DFL_ENV) { } #ifdef _WIN32 -TEST(LlvmLibcFenvTest, Windows_Set_Get_Test) { +TEST_F(LlvmLibcFEnvTest, Windows_Set_Get_Test) { // If a valid fenv_t is written, then reading it back out should be identical. fenv_t setEnv = {0x7e00053e, 0x0f00000f}; fenv_t getEnv; diff --git a/libc/test/src/fenv/rounding_mode_test.cpp b/libc/test/src/fenv/rounding_mode_test.cpp index ec2e27ecc818b2c731a50d00b2e5e6cfe0adafdd..f242ed9aaffe5bc03b339689a1c7d91e877850e0 100644 --- a/libc/test/src/fenv/rounding_mode_test.cpp +++ b/libc/test/src/fenv/rounding_mode_test.cpp @@ -9,15 +9,18 @@ #include "src/fenv/fegetround.h" #include "src/fenv/fesetround.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/Test.h" #include "hdr/fenv_macros.h" -TEST(LlvmLibcRoundingModeTest, SetAndGet) { +using LlvmLibcRoundingModeTest = LIBC_NAMESPACE::testing::FEnvSafeTest; + +TEST_F(LlvmLibcRoundingModeTest, SetAndGet) { struct ResetDefaultRoundingMode { - int original; + int original = LIBC_NAMESPACE::fegetround(); ~ResetDefaultRoundingMode() { LIBC_NAMESPACE::fesetround(original); } - } reset{LIBC_NAMESPACE::fegetround()}; + } reset; int s = LIBC_NAMESPACE::fesetround(FE_TONEAREST); EXPECT_EQ(s, 0); diff --git a/libc/test/src/math/CeilTest.h b/libc/test/src/math/CeilTest.h index da3f3c0e8f5abd0b4276891cd0a3ae7714edc815..b4c3752cc5c4bac2a6d336f6c52e8b9c72d89a47 100644 --- a/libc/test/src/math/CeilTest.h +++ b/libc/test/src/math/CeilTest.h @@ -6,6 +6,7 @@ // //===----------------------------------------------------------------------===// +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" #include "utils/MPFRWrapper/MPFRUtils.h" @@ -14,7 +15,8 @@ namespace mpfr = LIBC_NAMESPACE::testing::mpfr; -template class CeilTest : public LIBC_NAMESPACE::testing::Test { +template +class CeilTest : public LIBC_NAMESPACE::testing::FEnvSafeTest { DECLARE_SPECIAL_CONSTANTS(T) diff --git a/libc/test/src/math/CopySignTest.h b/libc/test/src/math/CopySignTest.h index 052ff0333438e9fcd816945bdd3e25389ee49ae4..c66f91477480b81dd78f136151565acf01b97c80 100644 --- a/libc/test/src/math/CopySignTest.h +++ b/libc/test/src/math/CopySignTest.h @@ -6,6 +6,7 @@ // //===----------------------------------------------------------------------===// +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" #include "utils/MPFRWrapper/MPFRUtils.h" @@ -15,7 +16,7 @@ namespace mpfr = LIBC_NAMESPACE::testing::mpfr; template -class CopySignTest : public LIBC_NAMESPACE::testing::Test { +class CopySignTest : public LIBC_NAMESPACE::testing::FEnvSafeTest { DECLARE_SPECIAL_CONSTANTS(T) diff --git a/libc/test/src/math/FAbsTest.h b/libc/test/src/math/FAbsTest.h index 23ad8a26c481c25aba0e2e17c1f5be8f5d1fd6f1..92b589beeb675fcde4718f4b466b1c0b87010cbf 100644 --- a/libc/test/src/math/FAbsTest.h +++ b/libc/test/src/math/FAbsTest.h @@ -9,6 +9,7 @@ #ifndef LLVM_LIBC_TEST_SRC_MATH_FABSTEST_H #define LLVM_LIBC_TEST_SRC_MATH_FABSTEST_H +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" #include "utils/MPFRWrapper/MPFRUtils.h" @@ -17,7 +18,8 @@ namespace mpfr = LIBC_NAMESPACE::testing::mpfr; -template class FAbsTest : public LIBC_NAMESPACE::testing::Test { +template +class FAbsTest : public LIBC_NAMESPACE::testing::FEnvSafeTest { DECLARE_SPECIAL_CONSTANTS(T) diff --git a/libc/test/src/math/FDimTest.h b/libc/test/src/math/FDimTest.h index 44aba9caf6463ef8eaa62e3921a09371a00c3a3e..fefcefe5052a9206bde71e312a33a1377a9ce8dd 100644 --- a/libc/test/src/math/FDimTest.h +++ b/libc/test/src/math/FDimTest.h @@ -9,11 +9,12 @@ #include "hdr/math_macros.h" #include "src/__support/FPUtil/BasicOperations.h" #include "src/__support/FPUtil/FPBits.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" template -class FDimTestTemplate : public LIBC_NAMESPACE::testing::Test { +class FDimTestTemplate : public LIBC_NAMESPACE::testing::FEnvSafeTest { public: using FuncPtr = T (*)(T, T); using FPBits = LIBC_NAMESPACE::fputil::FPBits; diff --git a/libc/test/src/math/FMaxTest.h b/libc/test/src/math/FMaxTest.h index e9857f332e6518384ee8cb3e9eb8caadbc26de89..405642c6b968419e0561aaef7cf9a07f570f23f6 100644 --- a/libc/test/src/math/FMaxTest.h +++ b/libc/test/src/math/FMaxTest.h @@ -9,6 +9,7 @@ #ifndef LLVM_LIBC_TEST_SRC_MATH_FMAXTEST_H #define LLVM_LIBC_TEST_SRC_MATH_FMAXTEST_H +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" #include "utils/MPFRWrapper/MPFRUtils.h" @@ -17,7 +18,8 @@ namespace mpfr = LIBC_NAMESPACE::testing::mpfr; -template class FMaxTest : public LIBC_NAMESPACE::testing::Test { +template +class FMaxTest : public LIBC_NAMESPACE::testing::FEnvSafeTest { DECLARE_SPECIAL_CONSTANTS(T) diff --git a/libc/test/src/math/FMinTest.h b/libc/test/src/math/FMinTest.h index c6b9f4439b79b7dbf5f3f43d0b33d53c08eaa426..eae0008ddfe392daf6ce6cc04c27491bbbb5a379 100644 --- a/libc/test/src/math/FMinTest.h +++ b/libc/test/src/math/FMinTest.h @@ -9,6 +9,7 @@ #ifndef LLVM_LIBC_TEST_SRC_MATH_FMINTEST_H #define LLVM_LIBC_TEST_SRC_MATH_FMINTEST_H +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" #include "utils/MPFRWrapper/MPFRUtils.h" @@ -17,7 +18,8 @@ namespace mpfr = LIBC_NAMESPACE::testing::mpfr; -template class FMinTest : public LIBC_NAMESPACE::testing::Test { +template +class FMinTest : public LIBC_NAMESPACE::testing::FEnvSafeTest { DECLARE_SPECIAL_CONSTANTS(T) diff --git a/libc/test/src/math/FModTest.h b/libc/test/src/math/FModTest.h index bc909987a161b807406791739f3fe211ba649875..f1015d6497fcd671f2b53e6ada5ce553402d2b95 100644 --- a/libc/test/src/math/FModTest.h +++ b/libc/test/src/math/FModTest.h @@ -11,6 +11,7 @@ #include "src/__support/FPUtil/BasicOperations.h" #include "src/__support/FPUtil/NearestIntegerOperations.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" @@ -24,7 +25,8 @@ #define TEST_REGULAR(x, y, expected) TEST_SPECIAL(x, y, expected, false, 0) -template class FmodTest : public LIBC_NAMESPACE::testing::Test { +template +class FmodTest : public LIBC_NAMESPACE::testing::FEnvSafeTest { DECLARE_SPECIAL_CONSTANTS(T) diff --git a/libc/test/src/math/FloorTest.h b/libc/test/src/math/FloorTest.h index 679dc26e124806e8b1c6ae60bef61f2a80c3dfe8..9103a5b05eb5adf23ca21a33cf16ba63ffff252d 100644 --- a/libc/test/src/math/FloorTest.h +++ b/libc/test/src/math/FloorTest.h @@ -9,6 +9,7 @@ #ifndef LLVM_LIBC_TEST_SRC_MATH_FLOORTEST_H #define LLVM_LIBC_TEST_SRC_MATH_FLOORTEST_H +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" #include "utils/MPFRWrapper/MPFRUtils.h" @@ -17,7 +18,8 @@ namespace mpfr = LIBC_NAMESPACE::testing::mpfr; -template class FloorTest : public LIBC_NAMESPACE::testing::Test { +template +class FloorTest : public LIBC_NAMESPACE::testing::FEnvSafeTest { DECLARE_SPECIAL_CONSTANTS(T) diff --git a/libc/test/src/math/FmaTest.h b/libc/test/src/math/FmaTest.h index 76bd221fcb1f2fff3bda3c0248fe129a4b601bd2..5a40f694ebd107b1bd0a1fe46f82a495b81b7811 100644 --- a/libc/test/src/math/FmaTest.h +++ b/libc/test/src/math/FmaTest.h @@ -12,6 +12,7 @@ #include "src/__support/FPUtil/FPBits.h" #include "src/stdlib/rand.h" #include "src/stdlib/srand.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" #include "utils/MPFRWrapper/MPFRUtils.h" @@ -19,7 +20,7 @@ namespace mpfr = LIBC_NAMESPACE::testing::mpfr; template -class FmaTestTemplate : public LIBC_NAMESPACE::testing::Test { +class FmaTestTemplate : public LIBC_NAMESPACE::testing::FEnvSafeTest { private: using Func = T (*)(T, T, T); using FPBits = LIBC_NAMESPACE::fputil::FPBits; diff --git a/libc/test/src/math/FrexpTest.h b/libc/test/src/math/FrexpTest.h index 5f993f604999d892a47752b30aa1ad927a5206bd..3ba64afa3c62059d7d8689f7ddd97b4930e700f5 100644 --- a/libc/test/src/math/FrexpTest.h +++ b/libc/test/src/math/FrexpTest.h @@ -7,6 +7,7 @@ //===----------------------------------------------------------------------===// #include "src/__support/FPUtil/BasicOperations.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" #include "utils/MPFRWrapper/MPFRUtils.h" @@ -15,7 +16,8 @@ namespace mpfr = LIBC_NAMESPACE::testing::mpfr; -template class FrexpTest : public LIBC_NAMESPACE::testing::Test { +template +class FrexpTest : public LIBC_NAMESPACE::testing::FEnvSafeTest { DECLARE_SPECIAL_CONSTANTS(T) diff --git a/libc/test/src/math/HypotTest.h b/libc/test/src/math/HypotTest.h index 0c15f02fe3719318ff22062f5f6697a4bfb4e328..58b53383182459217f60fe291f2b10b576424d10 100644 --- a/libc/test/src/math/HypotTest.h +++ b/libc/test/src/math/HypotTest.h @@ -10,6 +10,7 @@ #define LLVM_LIBC_TEST_SRC_MATH_HYPOTTEST_H #include "src/__support/FPUtil/FPBits.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" #include "utils/MPFRWrapper/MPFRUtils.h" @@ -19,7 +20,7 @@ namespace mpfr = LIBC_NAMESPACE::testing::mpfr; template -class HypotTestTemplate : public LIBC_NAMESPACE::testing::Test { +class HypotTestTemplate : public LIBC_NAMESPACE::testing::FEnvSafeTest { private: using Func = T (*)(T, T); using FPBits = LIBC_NAMESPACE::fputil::FPBits; diff --git a/libc/test/src/math/ILogbTest.h b/libc/test/src/math/ILogbTest.h index 3d1f047a4806132aadf9c31cfe71e7cf0c7d2fc0..c2d5a1326e0ed2bc5485df0036ba982a3e87328b 100644 --- a/libc/test/src/math/ILogbTest.h +++ b/libc/test/src/math/ILogbTest.h @@ -13,9 +13,10 @@ #include "src/__support/CPP/limits.h" // INT_MAX #include "src/__support/FPUtil/FPBits.h" #include "src/__support/FPUtil/ManipulationFunctions.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/Test.h" -class LlvmLibcILogbTest : public LIBC_NAMESPACE::testing::Test { +class LlvmLibcILogbTest : public LIBC_NAMESPACE::testing::FEnvSafeTest { public: template struct ILogbFunc { typedef int (*Func)(T); diff --git a/libc/test/src/math/LdExpTest.h b/libc/test/src/math/LdExpTest.h index 2a406feed52fc1b6c3cee7400a03a4350c3c2506..34466a526d60fb09c8868683965d0e7f4d07ad3a 100644 --- a/libc/test/src/math/LdExpTest.h +++ b/libc/test/src/math/LdExpTest.h @@ -12,6 +12,7 @@ #include "src/__support/CPP/limits.h" // INT_MAX #include "src/__support/FPUtil/FPBits.h" #include "src/__support/FPUtil/NormalFloat.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" @@ -19,7 +20,7 @@ #include template -class LdExpTestTemplate : public LIBC_NAMESPACE::testing::Test { +class LdExpTestTemplate : public LIBC_NAMESPACE::testing::FEnvSafeTest { using FPBits = LIBC_NAMESPACE::fputil::FPBits; using NormalFloat = LIBC_NAMESPACE::fputil::NormalFloat; using StorageType = typename FPBits::StorageType; diff --git a/libc/test/src/math/LogbTest.h b/libc/test/src/math/LogbTest.h index f066d5f9de02b12a3fd56a81dbaba5947c23d6a0..d6042e3c200c7693bda67d83926fbef9462952a1 100644 --- a/libc/test/src/math/LogbTest.h +++ b/libc/test/src/math/LogbTest.h @@ -7,6 +7,7 @@ //===----------------------------------------------------------------------===// #include "src/__support/FPUtil/ManipulationFunctions.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" #include "utils/MPFRWrapper/MPFRUtils.h" @@ -15,7 +16,8 @@ namespace mpfr = LIBC_NAMESPACE::testing::mpfr; -template class LogbTest : public LIBC_NAMESPACE::testing::Test { +template +class LogbTest : public LIBC_NAMESPACE::testing::FEnvSafeTest { DECLARE_SPECIAL_CONSTANTS(T) diff --git a/libc/test/src/math/ModfTest.h b/libc/test/src/math/ModfTest.h index 49b0328753b3bc2321b5bde0d1458b3f692cd126..d6c6f27a5edf6651ea94dd954e820fa7baebeb7e 100644 --- a/libc/test/src/math/ModfTest.h +++ b/libc/test/src/math/ModfTest.h @@ -8,6 +8,7 @@ #include "src/__support/FPUtil/BasicOperations.h" #include "src/__support/FPUtil/NearestIntegerOperations.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" #include "utils/MPFRWrapper/MPFRUtils.h" @@ -16,7 +17,8 @@ namespace mpfr = LIBC_NAMESPACE::testing::mpfr; -template class ModfTest : public LIBC_NAMESPACE::testing::Test { +template +class ModfTest : public LIBC_NAMESPACE::testing::FEnvSafeTest { DECLARE_SPECIAL_CONSTANTS(T) diff --git a/libc/test/src/math/NextAfterTest.h b/libc/test/src/math/NextAfterTest.h index a7248dd7042d464451df3c2b3cfd944d91fcef8a..b3b03f763992a03d1f0c59139993cf7b0fafb46e 100644 --- a/libc/test/src/math/NextAfterTest.h +++ b/libc/test/src/math/NextAfterTest.h @@ -14,11 +14,12 @@ #include "src/__support/CPP/type_traits.h" #include "src/__support/FPUtil/BasicOperations.h" #include "src/__support/FPUtil/FPBits.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" template -class NextAfterTestTemplate : public LIBC_NAMESPACE::testing::Test { +class NextAfterTestTemplate : public LIBC_NAMESPACE::testing::FEnvSafeTest { using FPBits = LIBC_NAMESPACE::fputil::FPBits; using StorageType = typename FPBits::StorageType; diff --git a/libc/test/src/math/RIntTest.h b/libc/test/src/math/RIntTest.h index c706ff18f186e5d75e7f33da68160fd4454209ff..007b50427ba34a1ebad099676986c0b212874f56 100644 --- a/libc/test/src/math/RIntTest.h +++ b/libc/test/src/math/RIntTest.h @@ -11,6 +11,7 @@ #include "src/__support/FPUtil/FEnvImpl.h" #include "src/__support/FPUtil/FPBits.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" #include "utils/MPFRWrapper/MPFRUtils.h" @@ -25,7 +26,7 @@ static constexpr int ROUNDING_MODES[4] = {FE_UPWARD, FE_DOWNWARD, FE_TOWARDZERO, FE_TONEAREST}; template -class RIntTestTemplate : public LIBC_NAMESPACE::testing::Test { +class RIntTestTemplate : public LIBC_NAMESPACE::testing::FEnvSafeTest { public: typedef T (*RIntFunc)(T); diff --git a/libc/test/src/math/RemQuoTest.h b/libc/test/src/math/RemQuoTest.h index 677772dd9fccfdc59ad10ef49554809afe19dca6..c39f2394555eac62fe6a12c65c0593b3f4f60b12 100644 --- a/libc/test/src/math/RemQuoTest.h +++ b/libc/test/src/math/RemQuoTest.h @@ -12,6 +12,7 @@ #include "hdr/math_macros.h" #include "src/__support/FPUtil/BasicOperations.h" #include "src/__support/FPUtil/FPBits.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" #include "utils/MPFRWrapper/MPFRUtils.h" @@ -19,7 +20,7 @@ namespace mpfr = LIBC_NAMESPACE::testing::mpfr; template -class RemQuoTestTemplate : public LIBC_NAMESPACE::testing::Test { +class RemQuoTestTemplate : public LIBC_NAMESPACE::testing::FEnvSafeTest { using FPBits = LIBC_NAMESPACE::fputil::FPBits; using StorageType = typename FPBits::StorageType; diff --git a/libc/test/src/math/RoundEvenTest.h b/libc/test/src/math/RoundEvenTest.h index 68b8b9ae1d964bdb93b12805a394cc031e6fd81e..d70555d34765918dcf060cbdc347f289a78129cb 100644 --- a/libc/test/src/math/RoundEvenTest.h +++ b/libc/test/src/math/RoundEvenTest.h @@ -9,6 +9,7 @@ #ifndef LLVM_LIBC_TEST_SRC_MATH_ROUNDEVENTEST_H #define LLVM_LIBC_TEST_SRC_MATH_ROUNDEVENTEST_H +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" #include "utils/MPFRWrapper/MPFRUtils.h" @@ -18,7 +19,7 @@ namespace mpfr = LIBC_NAMESPACE::testing::mpfr; template -class RoundEvenTest : public LIBC_NAMESPACE::testing::Test { +class RoundEvenTest : public LIBC_NAMESPACE::testing::FEnvSafeTest { DECLARE_SPECIAL_CONSTANTS(T) diff --git a/libc/test/src/math/RoundTest.h b/libc/test/src/math/RoundTest.h index eecf95982729be8fd3cd8c94a5a9d00bc263a24b..2a31df305ac384a85cc5201bf462e7236e52503f 100644 --- a/libc/test/src/math/RoundTest.h +++ b/libc/test/src/math/RoundTest.h @@ -9,6 +9,7 @@ #ifndef LLVM_LIBC_TEST_SRC_MATH_ROUNDTEST_H #define LLVM_LIBC_TEST_SRC_MATH_ROUNDTEST_H +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" #include "utils/MPFRWrapper/MPFRUtils.h" @@ -17,7 +18,8 @@ namespace mpfr = LIBC_NAMESPACE::testing::mpfr; -template class RoundTest : public LIBC_NAMESPACE::testing::Test { +template +class RoundTest : public LIBC_NAMESPACE::testing::FEnvSafeTest { DECLARE_SPECIAL_CONSTANTS(T) diff --git a/libc/test/src/math/RoundToIntegerTest.h b/libc/test/src/math/RoundToIntegerTest.h index 7c93451235f29697f29e06a7e9467c4ddef0e1a7..0f052ba42a46d74b6e4b10d40edb695a3b73b748 100644 --- a/libc/test/src/math/RoundToIntegerTest.h +++ b/libc/test/src/math/RoundToIntegerTest.h @@ -11,6 +11,7 @@ #include "src/__support/FPUtil/FEnvImpl.h" #include "src/__support/FPUtil/FPBits.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" #include "utils/MPFRWrapper/MPFRUtils.h" @@ -24,7 +25,8 @@ static constexpr int ROUNDING_MODES[4] = {FE_UPWARD, FE_DOWNWARD, FE_TOWARDZERO, FE_TONEAREST}; template -class RoundToIntegerTestTemplate : public LIBC_NAMESPACE::testing::Test { +class RoundToIntegerTestTemplate + : public LIBC_NAMESPACE::testing::FEnvSafeTest { public: typedef I (*RoundToIntegerFunc)(F); @@ -81,6 +83,8 @@ private: public: void SetUp() override { + LIBC_NAMESPACE::testing::FEnvSafeTest::SetUp(); + if (math_errhandling & MATH_ERREXCEPT) { // We will disable all exceptions so that the test will not // crash with SIGFPE. We can still use fetestexcept to check diff --git a/libc/test/src/math/SqrtTest.h b/libc/test/src/math/SqrtTest.h index 799b7862a37260743a8079196a217d5942e8ab3a..1c422e201bb234ee398f20a377602867043a5dfe 100644 --- a/libc/test/src/math/SqrtTest.h +++ b/libc/test/src/math/SqrtTest.h @@ -7,6 +7,7 @@ //===----------------------------------------------------------------------===// #include "src/__support/CPP/bit.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" #include "utils/MPFRWrapper/MPFRUtils.h" @@ -15,7 +16,8 @@ namespace mpfr = LIBC_NAMESPACE::testing::mpfr; -template class SqrtTest : public LIBC_NAMESPACE::testing::Test { +template +class SqrtTest : public LIBC_NAMESPACE::testing::FEnvSafeTest { DECLARE_SPECIAL_CONSTANTS(T) diff --git a/libc/test/src/math/TruncTest.h b/libc/test/src/math/TruncTest.h index 57c953fad8742f00f8bc05e787fa45f9e33d9b0c..bc5b76131291bba7ada50bba1aa2186c02546efa 100644 --- a/libc/test/src/math/TruncTest.h +++ b/libc/test/src/math/TruncTest.h @@ -9,6 +9,7 @@ #ifndef LLVM_LIBC_TEST_SRC_MATH_TRUNCTEST_H #define LLVM_LIBC_TEST_SRC_MATH_TRUNCTEST_H +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" #include "utils/MPFRWrapper/MPFRUtils.h" @@ -17,7 +18,8 @@ namespace mpfr = LIBC_NAMESPACE::testing::mpfr; -template class TruncTest : public LIBC_NAMESPACE::testing::Test { +template +class TruncTest : public LIBC_NAMESPACE::testing::FEnvSafeTest { DECLARE_SPECIAL_CONSTANTS(T) diff --git a/libc/test/src/math/exhaustive/fmod_generic_impl_test.cpp b/libc/test/src/math/exhaustive/fmod_generic_impl_test.cpp index c7aec5b7bc21b4b18431ef16db9be267652d2d66..b064b7e37f428d611360ea1c81dc03193f6bba25 100644 --- a/libc/test/src/math/exhaustive/fmod_generic_impl_test.cpp +++ b/libc/test/src/math/exhaustive/fmod_generic_impl_test.cpp @@ -9,6 +9,7 @@ #include "src/__support/FPUtil/FPBits.h" #include "src/__support/FPUtil/ManipulationFunctions.h" // ldexp #include "src/__support/FPUtil/generic/FMod.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" #include "utils/MPFRWrapper/MPFRUtils.h" @@ -18,7 +19,7 @@ namespace mpfr = LIBC_NAMESPACE::testing::mpfr; template -class LlvmLibcFModTest : public LIBC_NAMESPACE::testing::Test { +class LlvmLibcFModTest : public LIBC_NAMESPACE::testing::FEnvSafeTest { using FPBits = LIBC_NAMESPACE::fputil::FPBits; using U = typename FPBits::StorageType; diff --git a/libc/test/src/math/smoke/CanonicalizeTest.h b/libc/test/src/math/smoke/CanonicalizeTest.h index ab45e0eb8e94d3f3044acd4a0056bcbcc0c3cdde..7e2456f84705c982041f9bf09b638468974e395f 100644 --- a/libc/test/src/math/smoke/CanonicalizeTest.h +++ b/libc/test/src/math/smoke/CanonicalizeTest.h @@ -11,6 +11,7 @@ #include "src/__support/FPUtil/FPBits.h" #include "src/__support/integer_literals.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" @@ -26,7 +27,7 @@ using LIBC_NAMESPACE::operator""_u128; template -class CanonicalizeTest : public LIBC_NAMESPACE::testing::Test { +class CanonicalizeTest : public LIBC_NAMESPACE::testing::FEnvSafeTest { DECLARE_SPECIAL_CONSTANTS(T) diff --git a/libc/test/src/math/smoke/CeilTest.h b/libc/test/src/math/smoke/CeilTest.h index 70e441a849cb4fc0c651b3192eee6faf4bed921b..5e108c0e0feea1794baf6805bb30bcede937457a 100644 --- a/libc/test/src/math/smoke/CeilTest.h +++ b/libc/test/src/math/smoke/CeilTest.h @@ -9,12 +9,14 @@ #ifndef LLVM_LIBC_TEST_SRC_MATH_SMOKE_CEILTEST_H #define LLVM_LIBC_TEST_SRC_MATH_SMOKE_CEILTEST_H +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" #include "hdr/math_macros.h" -template class CeilTest : public LIBC_NAMESPACE::testing::Test { +template +class CeilTest : public LIBC_NAMESPACE::testing::FEnvSafeTest { DECLARE_SPECIAL_CONSTANTS(T) diff --git a/libc/test/src/math/smoke/CopySignTest.h b/libc/test/src/math/smoke/CopySignTest.h index fa9da91920f8dedda3c37bbe7a7ee82a8e07c273..1810560bf1bb8fe80c717b13f50f2e178729243d 100644 --- a/libc/test/src/math/smoke/CopySignTest.h +++ b/libc/test/src/math/smoke/CopySignTest.h @@ -9,13 +9,14 @@ #ifndef LLVM_LIBC_TEST_SRC_MATH_SMOKE_COPYSIGNTEST_H #define LLVM_LIBC_TEST_SRC_MATH_SMOKE_COPYSIGNTEST_H +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" #include "hdr/math_macros.h" template -class CopySignTest : public LIBC_NAMESPACE::testing::Test { +class CopySignTest : public LIBC_NAMESPACE::testing::FEnvSafeTest { DECLARE_SPECIAL_CONSTANTS(T) diff --git a/libc/test/src/math/smoke/FAbsTest.h b/libc/test/src/math/smoke/FAbsTest.h index 0c8ca95ba0f7bc26bbb2e58770b6aa931bf520b3..048023b414299f80f817f4a63d7061cc29454422 100644 --- a/libc/test/src/math/smoke/FAbsTest.h +++ b/libc/test/src/math/smoke/FAbsTest.h @@ -9,12 +9,14 @@ #ifndef LLVM_LIBC_TEST_SRC_MATH_SMOKE_FABSTEST_H #define LLVM_LIBC_TEST_SRC_MATH_SMOKE_FABSTEST_H +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" #include "hdr/math_macros.h" -template class FAbsTest : public LIBC_NAMESPACE::testing::Test { +template +class FAbsTest : public LIBC_NAMESPACE::testing::FEnvSafeTest { DECLARE_SPECIAL_CONSTANTS(T) diff --git a/libc/test/src/math/smoke/FDimTest.h b/libc/test/src/math/smoke/FDimTest.h index e557b40d90efa1e43a10041442d3e1a456ec28fa..cff88f29a8efa80a21ea2f0a9cd178761e6223b1 100644 --- a/libc/test/src/math/smoke/FDimTest.h +++ b/libc/test/src/math/smoke/FDimTest.h @@ -8,11 +8,12 @@ #include "src/__support/FPUtil/BasicOperations.h" #include "src/__support/FPUtil/FPBits.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" template -class FDimTestTemplate : public LIBC_NAMESPACE::testing::Test { +class FDimTestTemplate : public LIBC_NAMESPACE::testing::FEnvSafeTest { public: using FuncPtr = T (*)(T, T); using FPBits = LIBC_NAMESPACE::fputil::FPBits; diff --git a/libc/test/src/math/smoke/FMaxTest.h b/libc/test/src/math/smoke/FMaxTest.h index b8781a85d10f4f397a5ec0ae3bbdacd9ba9cd1b3..df8e35e0bd16204ddce2270c01cb42a4cb823d91 100644 --- a/libc/test/src/math/smoke/FMaxTest.h +++ b/libc/test/src/math/smoke/FMaxTest.h @@ -9,10 +9,12 @@ #ifndef LLVM_LIBC_TEST_SRC_MATH_SMOKE_FMAXTEST_H #define LLVM_LIBC_TEST_SRC_MATH_SMOKE_FMAXTEST_H +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" -template class FMaxTest : public LIBC_NAMESPACE::testing::Test { +template +class FMaxTest : public LIBC_NAMESPACE::testing::FEnvSafeTest { DECLARE_SPECIAL_CONSTANTS(T) diff --git a/libc/test/src/math/smoke/FMaximumMagNumTest.h b/libc/test/src/math/smoke/FMaximumMagNumTest.h index 715dd4ed913f838b817b71583e3af4665759c71c..aafb6d2b0d5eacab9bc70f161d1fbd4880b268d0 100644 --- a/libc/test/src/math/smoke/FMaximumMagNumTest.h +++ b/libc/test/src/math/smoke/FMaximumMagNumTest.h @@ -11,11 +11,12 @@ #include "src/__support/FPUtil/BasicOperations.h" #include "src/__support/FPUtil/FPBits.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" template -class FMaximumMagNumTest : public LIBC_NAMESPACE::testing::Test { +class FMaximumMagNumTest : public LIBC_NAMESPACE::testing::FEnvSafeTest { DECLARE_SPECIAL_CONSTANTS(T) diff --git a/libc/test/src/math/smoke/FMaximumMagTest.h b/libc/test/src/math/smoke/FMaximumMagTest.h index 38276e0fe2fdb0486daf62ffa15885c704df2d89..7bb79a69be580f6b40d394ce43917dedf5ec27a5 100644 --- a/libc/test/src/math/smoke/FMaximumMagTest.h +++ b/libc/test/src/math/smoke/FMaximumMagTest.h @@ -10,11 +10,12 @@ #define LLVM_LIBC_TEST_SRC_MATH_SMOKE_FMAXIMUM_MAGTEST_H #include "src/__support/FPUtil/BasicOperations.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" template -class FMaximumMagTest : public LIBC_NAMESPACE::testing::Test { +class FMaximumMagTest : public LIBC_NAMESPACE::testing::FEnvSafeTest { DECLARE_SPECIAL_CONSTANTS(T) diff --git a/libc/test/src/math/smoke/FMaximumNumTest.h b/libc/test/src/math/smoke/FMaximumNumTest.h index 57096f6b614a2c8e093f7fb69a8c934b5bdb79a2..da0ea2c247a9ee6feb5cb6cf1b963ce36217d237 100644 --- a/libc/test/src/math/smoke/FMaximumNumTest.h +++ b/libc/test/src/math/smoke/FMaximumNumTest.h @@ -10,11 +10,12 @@ #define LLVM_LIBC_TEST_SRC_MATH_SMOKE_FMAXIMUMNUMTEST_H #include "src/__support/FPUtil/FPBits.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" template -class FMaximumNumTest : public LIBC_NAMESPACE::testing::Test { +class FMaximumNumTest : public LIBC_NAMESPACE::testing::FEnvSafeTest { DECLARE_SPECIAL_CONSTANTS(T) diff --git a/libc/test/src/math/smoke/FMaximumTest.h b/libc/test/src/math/smoke/FMaximumTest.h index 4db8bb93baaeefbbd60f4a843af3ce5970641fef..1bd15163ed75291b1aeeacf7a149bda4d172a978 100644 --- a/libc/test/src/math/smoke/FMaximumTest.h +++ b/libc/test/src/math/smoke/FMaximumTest.h @@ -9,11 +9,12 @@ #ifndef LLVM_LIBC_TEST_SRC_MATH_SMOKE_FMAXIMUMTEST_H #define LLVM_LIBC_TEST_SRC_MATH_SMOKE_FMAXIMUMTEST_H +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" template -class FMaximumTest : public LIBC_NAMESPACE::testing::Test { +class FMaximumTest : public LIBC_NAMESPACE::testing::FEnvSafeTest { DECLARE_SPECIAL_CONSTANTS(T) diff --git a/libc/test/src/math/smoke/FMinTest.h b/libc/test/src/math/smoke/FMinTest.h index b1ffe38829f438e6f07d1e85e1bdd24d3c5f64d2..f71b558cd3da2027b66e9e6d68a7e3d61ba5139e 100644 --- a/libc/test/src/math/smoke/FMinTest.h +++ b/libc/test/src/math/smoke/FMinTest.h @@ -9,10 +9,12 @@ #ifndef LLVM_LIBC_TEST_SRC_MATH_SMOKE_FMINTEST_H #define LLVM_LIBC_TEST_SRC_MATH_SMOKE_FMINTEST_H +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" -template class FMinTest : public LIBC_NAMESPACE::testing::Test { +template +class FMinTest : public LIBC_NAMESPACE::testing::FEnvSafeTest { DECLARE_SPECIAL_CONSTANTS(T) diff --git a/libc/test/src/math/smoke/FMinimumMagNumTest.h b/libc/test/src/math/smoke/FMinimumMagNumTest.h index dec8b70740ca593eebc27e6c6cb75b49afbe018f..e4b8fd9e335311e34475b2e8500eaf656c888d22 100644 --- a/libc/test/src/math/smoke/FMinimumMagNumTest.h +++ b/libc/test/src/math/smoke/FMinimumMagNumTest.h @@ -11,11 +11,12 @@ #include "src/__support/FPUtil/BasicOperations.h" #include "src/__support/FPUtil/FPBits.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" template -class FMinimumMagNumTest : public LIBC_NAMESPACE::testing::Test { +class FMinimumMagNumTest : public LIBC_NAMESPACE::testing::FEnvSafeTest { DECLARE_SPECIAL_CONSTANTS(T) diff --git a/libc/test/src/math/smoke/FMinimumMagTest.h b/libc/test/src/math/smoke/FMinimumMagTest.h index b11092e5379ba0abe80a579af68a82adfc8ae4f5..3e16622fe3fa41dc07254bb6a12e299195dd61dd 100644 --- a/libc/test/src/math/smoke/FMinimumMagTest.h +++ b/libc/test/src/math/smoke/FMinimumMagTest.h @@ -10,11 +10,12 @@ #define LLVM_LIBC_TEST_SRC_MATH_SMOKE_FMINIMUM_MAGTEST_H #include "src/__support/FPUtil/BasicOperations.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" template -class FMinimumMagTest : public LIBC_NAMESPACE::testing::Test { +class FMinimumMagTest : public LIBC_NAMESPACE::testing::FEnvSafeTest { DECLARE_SPECIAL_CONSTANTS(T) diff --git a/libc/test/src/math/smoke/FMinimumNumTest.h b/libc/test/src/math/smoke/FMinimumNumTest.h index 7fcc291b4c00cd8ee9a046650dbf09e1c7f7a5c0..6186ea0df17cce1614c0ec1f52e5817ca88ac1a3 100644 --- a/libc/test/src/math/smoke/FMinimumNumTest.h +++ b/libc/test/src/math/smoke/FMinimumNumTest.h @@ -10,11 +10,12 @@ #define LLVM_LIBC_TEST_SRC_MATH_SMOKE_FMINIMUMNUMTEST_H #include "src/__support/FPUtil/FPBits.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" template -class FMinimumNumTest : public LIBC_NAMESPACE::testing::Test { +class FMinimumNumTest : public LIBC_NAMESPACE::testing::FEnvSafeTest { DECLARE_SPECIAL_CONSTANTS(T) diff --git a/libc/test/src/math/smoke/FMinimumTest.h b/libc/test/src/math/smoke/FMinimumTest.h index bc04a6d99356547ee0a2e44f6d6348c72ddb4c10..a267f6c78321452883de91c5986a587381412b47 100644 --- a/libc/test/src/math/smoke/FMinimumTest.h +++ b/libc/test/src/math/smoke/FMinimumTest.h @@ -9,11 +9,12 @@ #ifndef LLVM_LIBC_TEST_SRC_MATH_SMOKE_FMINIMUMTEST_H #define LLVM_LIBC_TEST_SRC_MATH_SMOKE_FMINIMUMTEST_H +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" template -class FMinimumTest : public LIBC_NAMESPACE::testing::Test { +class FMinimumTest : public LIBC_NAMESPACE::testing::FEnvSafeTest { DECLARE_SPECIAL_CONSTANTS(T) diff --git a/libc/test/src/math/smoke/FModTest.h b/libc/test/src/math/smoke/FModTest.h index bc909987a161b807406791739f3fe211ba649875..f1015d6497fcd671f2b53e6ada5ce553402d2b95 100644 --- a/libc/test/src/math/smoke/FModTest.h +++ b/libc/test/src/math/smoke/FModTest.h @@ -11,6 +11,7 @@ #include "src/__support/FPUtil/BasicOperations.h" #include "src/__support/FPUtil/NearestIntegerOperations.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" @@ -24,7 +25,8 @@ #define TEST_REGULAR(x, y, expected) TEST_SPECIAL(x, y, expected, false, 0) -template class FmodTest : public LIBC_NAMESPACE::testing::Test { +template +class FmodTest : public LIBC_NAMESPACE::testing::FEnvSafeTest { DECLARE_SPECIAL_CONSTANTS(T) diff --git a/libc/test/src/math/smoke/FloorTest.h b/libc/test/src/math/smoke/FloorTest.h index 12944aa775626970f91f9f1cf7d13f54790f9ab9..b2102459bc3de692678eac66e59fa4d0c174552b 100644 --- a/libc/test/src/math/smoke/FloorTest.h +++ b/libc/test/src/math/smoke/FloorTest.h @@ -9,12 +9,14 @@ #ifndef LLVM_LIBC_TEST_SRC_MATH_SMOKE_FLOORTEST_H #define LLVM_LIBC_TEST_SRC_MATH_SMOKE_FLOORTEST_H +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" #include "hdr/math_macros.h" -template class FloorTest : public LIBC_NAMESPACE::testing::Test { +template +class FloorTest : public LIBC_NAMESPACE::testing::FEnvSafeTest { DECLARE_SPECIAL_CONSTANTS(T) diff --git a/libc/test/src/math/smoke/FmaTest.h b/libc/test/src/math/smoke/FmaTest.h index c66035927d9896599197d27a9e148000d9802dc7..7063ecf199837b3653e2d43e740508201c7ea01d 100644 --- a/libc/test/src/math/smoke/FmaTest.h +++ b/libc/test/src/math/smoke/FmaTest.h @@ -10,11 +10,12 @@ #define LLVM_LIBC_TEST_SRC_MATH_FMATEST_H #include "src/__support/FPUtil/FPBits.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" template -class FmaTestTemplate : public LIBC_NAMESPACE::testing::Test { +class FmaTestTemplate : public LIBC_NAMESPACE::testing::FEnvSafeTest { private: using Func = T (*)(T, T, T); using FPBits = LIBC_NAMESPACE::fputil::FPBits; diff --git a/libc/test/src/math/smoke/FrexpTest.h b/libc/test/src/math/smoke/FrexpTest.h index bf99a9a559f05346759027e9b29df7507f2864dd..e9e496422f7326eebc46f7252ef4f93f33ec4b3b 100644 --- a/libc/test/src/math/smoke/FrexpTest.h +++ b/libc/test/src/math/smoke/FrexpTest.h @@ -7,10 +7,12 @@ //===----------------------------------------------------------------------===// #include "src/__support/FPUtil/BasicOperations.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" -template class FrexpTest : public LIBC_NAMESPACE::testing::Test { +template +class FrexpTest : public LIBC_NAMESPACE::testing::FEnvSafeTest { DECLARE_SPECIAL_CONSTANTS(T) diff --git a/libc/test/src/math/smoke/FromfpTest.h b/libc/test/src/math/smoke/FromfpTest.h index d3a61baafda106c5a182168e003d3ce49415e8d6..f19f21ce47e7f99e6188e2b0cbeeaa9c3a398174 100644 --- a/libc/test/src/math/smoke/FromfpTest.h +++ b/libc/test/src/math/smoke/FromfpTest.h @@ -9,11 +9,12 @@ #ifndef LIBC_TEST_SRC_MATH_SMOKE_FROMFPTEST_H #define LIBC_TEST_SRC_MATH_SMOKE_FROMFPTEST_H +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" template -class FromfpTestTemplate : public LIBC_NAMESPACE::testing::Test { +class FromfpTestTemplate : public LIBC_NAMESPACE::testing::FEnvSafeTest { DECLARE_SPECIAL_CONSTANTS(T) diff --git a/libc/test/src/math/smoke/FromfpxTest.h b/libc/test/src/math/smoke/FromfpxTest.h index f3a1680b05aafc15a565be2fecb55fba46a14255..4aa47a68bb1783e85daa79c86d3599f1c2f86330 100644 --- a/libc/test/src/math/smoke/FromfpxTest.h +++ b/libc/test/src/math/smoke/FromfpxTest.h @@ -9,11 +9,12 @@ #ifndef LIBC_TEST_SRC_MATH_SMOKE_FROMFPXTEST_H #define LIBC_TEST_SRC_MATH_SMOKE_FROMFPXTEST_H +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" template -class FromfpxTestTemplate : public LIBC_NAMESPACE::testing::Test { +class FromfpxTestTemplate : public LIBC_NAMESPACE::testing::FEnvSafeTest { DECLARE_SPECIAL_CONSTANTS(T) diff --git a/libc/test/src/math/smoke/HypotTest.h b/libc/test/src/math/smoke/HypotTest.h index a1b8f8a7fafa55c611cdff754e225cfcfa14eacf..80e9bb7366dfea590dc3768f92430c5bd126cfff 100644 --- a/libc/test/src/math/smoke/HypotTest.h +++ b/libc/test/src/math/smoke/HypotTest.h @@ -10,13 +10,14 @@ #define LLVM_LIBC_TEST_SRC_MATH_HYPOTTEST_H #include "src/__support/FPUtil/FPBits.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" #include "hdr/math_macros.h" template -class HypotTestTemplate : public LIBC_NAMESPACE::testing::Test { +class HypotTestTemplate : public LIBC_NAMESPACE::testing::FEnvSafeTest { private: using Func = T (*)(T, T); using FPBits = LIBC_NAMESPACE::fputil::FPBits; diff --git a/libc/test/src/math/smoke/ILogbTest.h b/libc/test/src/math/smoke/ILogbTest.h index bb5bc33b6b3a6dba27a31cedbcba5c0c6ee765d8..05f906b69947b23848cf071ebd212ba8e21a5239 100644 --- a/libc/test/src/math/smoke/ILogbTest.h +++ b/libc/test/src/math/smoke/ILogbTest.h @@ -12,10 +12,11 @@ #include "src/__support/CPP/limits.h" // INT_MAX #include "src/__support/FPUtil/FPBits.h" #include "src/__support/FPUtil/ManipulationFunctions.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/Test.h" template -class LlvmLibcILogbTest : public LIBC_NAMESPACE::testing::Test { +class LlvmLibcILogbTest : public LIBC_NAMESPACE::testing::FEnvSafeTest { using FPBits = LIBC_NAMESPACE::fputil::FPBits; using StorageType = typename FPBits::StorageType; diff --git a/libc/test/src/math/smoke/LdExpTest.h b/libc/test/src/math/smoke/LdExpTest.h index c3e852a2a473b1cca6c50aa7769e6c187733e06f..713d305c47494a81bbdc794ddd158838619cd9c4 100644 --- a/libc/test/src/math/smoke/LdExpTest.h +++ b/libc/test/src/math/smoke/LdExpTest.h @@ -12,13 +12,14 @@ #include "src/__support/CPP/limits.h" // INT_MAX #include "src/__support/FPUtil/FPBits.h" #include "src/__support/FPUtil/NormalFloat.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" #include template -class LdExpTestTemplate : public LIBC_NAMESPACE::testing::Test { +class LdExpTestTemplate : public LIBC_NAMESPACE::testing::FEnvSafeTest { using FPBits = LIBC_NAMESPACE::fputil::FPBits; using NormalFloat = LIBC_NAMESPACE::fputil::NormalFloat; using StorageType = typename FPBits::StorageType; diff --git a/libc/test/src/math/smoke/LogbTest.h b/libc/test/src/math/smoke/LogbTest.h index 01e1050b4c4f8c3953a5af3efb77843e406ccdbb..4938fcf8f6f16eae3ea3aea4d20fc003f1e5ca32 100644 --- a/libc/test/src/math/smoke/LogbTest.h +++ b/libc/test/src/math/smoke/LogbTest.h @@ -7,10 +7,12 @@ //===----------------------------------------------------------------------===// #include "src/__support/FPUtil/ManipulationFunctions.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" -template class LogbTest : public LIBC_NAMESPACE::testing::Test { +template +class LogbTest : public LIBC_NAMESPACE::testing::FEnvSafeTest { DECLARE_SPECIAL_CONSTANTS(T) diff --git a/libc/test/src/math/smoke/ModfTest.h b/libc/test/src/math/smoke/ModfTest.h index 65d61855c9f22d2b0879e2b46ded1528d24fd946..85db2d6d967b20d5a0a7bd80a00bade71d0009aa 100644 --- a/libc/test/src/math/smoke/ModfTest.h +++ b/libc/test/src/math/smoke/ModfTest.h @@ -8,12 +8,14 @@ #include "src/__support/FPUtil/BasicOperations.h" #include "src/__support/FPUtil/NearestIntegerOperations.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" #include "hdr/math_macros.h" -template class ModfTest : public LIBC_NAMESPACE::testing::Test { +template +class ModfTest : public LIBC_NAMESPACE::testing::FEnvSafeTest { DECLARE_SPECIAL_CONSTANTS(T) diff --git a/libc/test/src/math/smoke/NextAfterTest.h b/libc/test/src/math/smoke/NextAfterTest.h index d9c50c8109d8034c0751706a4247d462e8c7b7df..65dba9338285b647740655d4add9c8e3764162c0 100644 --- a/libc/test/src/math/smoke/NextAfterTest.h +++ b/libc/test/src/math/smoke/NextAfterTest.h @@ -14,6 +14,7 @@ #include "src/__support/CPP/type_traits.h" #include "src/__support/FPUtil/BasicOperations.h" #include "src/__support/FPUtil/FPBits.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" @@ -29,7 +30,7 @@ ASSERT_FP_EQ_WITH_EXCEPTION(result, expected, FE_INEXACT | FE_OVERFLOW) template -class NextAfterTestTemplate : public LIBC_NAMESPACE::testing::Test { +class NextAfterTestTemplate : public LIBC_NAMESPACE::testing::FEnvSafeTest { using FPBits = LIBC_NAMESPACE::fputil::FPBits; using StorageType = typename FPBits::StorageType; diff --git a/libc/test/src/math/smoke/NextDownTest.h b/libc/test/src/math/smoke/NextDownTest.h index c678ab1db1deff75b73c9668e542c0888fe95375..b54c6d5763222f8b6b035d2438524a401af1caac 100644 --- a/libc/test/src/math/smoke/NextDownTest.h +++ b/libc/test/src/math/smoke/NextDownTest.h @@ -9,11 +9,12 @@ #ifndef LLVM_LIBC_TEST_SRC_MATH_NEXTDOWNTEST_H #define LLVM_LIBC_TEST_SRC_MATH_NEXTDOWNTEST_H +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" template -class NextDownTestTemplate : public LIBC_NAMESPACE::testing::Test { +class NextDownTestTemplate : public LIBC_NAMESPACE::testing::FEnvSafeTest { DECLARE_SPECIAL_CONSTANTS(T) diff --git a/libc/test/src/math/smoke/NextTowardTest.h b/libc/test/src/math/smoke/NextTowardTest.h index b6c1c8d1797da67e2e8b688028f27bb9b528a5fc..1894d324b085463150b35421db281492c9703b84 100644 --- a/libc/test/src/math/smoke/NextTowardTest.h +++ b/libc/test/src/math/smoke/NextTowardTest.h @@ -15,6 +15,7 @@ #include "src/__support/CPP/type_traits.h" #include "src/__support/FPUtil/BasicOperations.h" #include "src/__support/FPUtil/FPBits.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" @@ -30,7 +31,7 @@ ASSERT_FP_EQ_WITH_EXCEPTION(result, expected, FE_INEXACT | FE_OVERFLOW) template -class NextTowardTestTemplate : public LIBC_NAMESPACE::testing::Test { +class NextTowardTestTemplate : public LIBC_NAMESPACE::testing::FEnvSafeTest { using FPBits = LIBC_NAMESPACE::fputil::FPBits; using ToFPBits = LIBC_NAMESPACE::fputil::FPBits; using StorageType = typename FPBits::StorageType; diff --git a/libc/test/src/math/smoke/NextUpTest.h b/libc/test/src/math/smoke/NextUpTest.h index ebbdb5c73def9e3e1fc1471740cfcaef31b5d093..7f66c115dfc2dce99d985a0128975069de3ae3e8 100644 --- a/libc/test/src/math/smoke/NextUpTest.h +++ b/libc/test/src/math/smoke/NextUpTest.h @@ -9,11 +9,12 @@ #ifndef LLVM_LIBC_TEST_SRC_MATH_NEXTUPTEST_H #define LLVM_LIBC_TEST_SRC_MATH_NEXTUPTEST_H +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" template -class NextUpTestTemplate : public LIBC_NAMESPACE::testing::Test { +class NextUpTestTemplate : public LIBC_NAMESPACE::testing::FEnvSafeTest { DECLARE_SPECIAL_CONSTANTS(T) diff --git a/libc/test/src/math/smoke/RIntTest.h b/libc/test/src/math/smoke/RIntTest.h index cbed9a3b10baab13e003128986dcd0864da3e0e7..1412c3f27a2d5f3828f5e82129e83243cd4091bb 100644 --- a/libc/test/src/math/smoke/RIntTest.h +++ b/libc/test/src/math/smoke/RIntTest.h @@ -11,6 +11,7 @@ #include "src/__support/FPUtil/FEnvImpl.h" #include "src/__support/FPUtil/FPBits.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" @@ -22,7 +23,7 @@ static constexpr int ROUNDING_MODES[4] = {FE_UPWARD, FE_DOWNWARD, FE_TOWARDZERO, FE_TONEAREST}; template -class RIntTestTemplate : public LIBC_NAMESPACE::testing::Test { +class RIntTestTemplate : public LIBC_NAMESPACE::testing::FEnvSafeTest { public: typedef T (*RIntFunc)(T); diff --git a/libc/test/src/math/smoke/RemQuoTest.h b/libc/test/src/math/smoke/RemQuoTest.h index 7df537d8b206319a9c30a9e31108206d8cfe9be7..43eee3d38e4495985da5e12325acd6b11cad4454 100644 --- a/libc/test/src/math/smoke/RemQuoTest.h +++ b/libc/test/src/math/smoke/RemQuoTest.h @@ -12,11 +12,12 @@ #include "hdr/math_macros.h" #include "src/__support/FPUtil/BasicOperations.h" #include "src/__support/FPUtil/FPBits.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" template -class RemQuoTestTemplate : public LIBC_NAMESPACE::testing::Test { +class RemQuoTestTemplate : public LIBC_NAMESPACE::testing::FEnvSafeTest { using FPBits = LIBC_NAMESPACE::fputil::FPBits; using StorageType = typename FPBits::StorageType; diff --git a/libc/test/src/math/smoke/RoundEvenTest.h b/libc/test/src/math/smoke/RoundEvenTest.h index e168d57bdbf3c791bb21f57a5f81eed41dee1d31..479b70912fedc99455f69115684a42103ea916e9 100644 --- a/libc/test/src/math/smoke/RoundEvenTest.h +++ b/libc/test/src/math/smoke/RoundEvenTest.h @@ -9,13 +9,14 @@ #ifndef LLVM_LIBC_TEST_SRC_MATH_SMOKE_ROUNDEVENTEST_H #define LLVM_LIBC_TEST_SRC_MATH_SMOKE_ROUNDEVENTEST_H +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" #include "hdr/math_macros.h" template -class RoundEvenTest : public LIBC_NAMESPACE::testing::Test { +class RoundEvenTest : public LIBC_NAMESPACE::testing::FEnvSafeTest { DECLARE_SPECIAL_CONSTANTS(T) diff --git a/libc/test/src/math/smoke/RoundTest.h b/libc/test/src/math/smoke/RoundTest.h index 49b2a1bf7dfba70cfc876f8dcf584c1f89a6c01d..36994f27eb4c05f1857d1a9b967834c6d248e57b 100644 --- a/libc/test/src/math/smoke/RoundTest.h +++ b/libc/test/src/math/smoke/RoundTest.h @@ -9,12 +9,14 @@ #ifndef LLVM_LIBC_TEST_SRC_MATH_SMOKE_ROUNDTEST_H #define LLVM_LIBC_TEST_SRC_MATH_SMOKE_ROUNDTEST_H +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" #include "hdr/math_macros.h" -template class RoundTest : public LIBC_NAMESPACE::testing::Test { +template +class RoundTest : public LIBC_NAMESPACE::testing::FEnvSafeTest { DECLARE_SPECIAL_CONSTANTS(T) diff --git a/libc/test/src/math/smoke/RoundToIntegerTest.h b/libc/test/src/math/smoke/RoundToIntegerTest.h index 863cf75f05ff6b57e25bd18b97b10699daab959e..50bcd4a6a76c0d2f7035704502b3afa101103fe9 100644 --- a/libc/test/src/math/smoke/RoundToIntegerTest.h +++ b/libc/test/src/math/smoke/RoundToIntegerTest.h @@ -11,6 +11,7 @@ #include "src/__support/FPUtil/FEnvImpl.h" #include "src/__support/FPUtil/FPBits.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" @@ -21,7 +22,8 @@ static constexpr int ROUNDING_MODES[4] = {FE_UPWARD, FE_DOWNWARD, FE_TOWARDZERO, FE_TONEAREST}; template -class RoundToIntegerTestTemplate : public LIBC_NAMESPACE::testing::Test { +class RoundToIntegerTestTemplate + : public LIBC_NAMESPACE::testing::FEnvSafeTest { public: typedef I (*RoundToIntegerFunc)(F); @@ -61,6 +63,8 @@ private: public: void SetUp() override { + LIBC_NAMESPACE::testing::FEnvSafeTest::SetUp(); + if (math_errhandling & MATH_ERREXCEPT) { // We will disable all exceptions so that the test will not // crash with SIGFPE. We can still use fetestexcept to check diff --git a/libc/test/src/math/smoke/SqrtTest.h b/libc/test/src/math/smoke/SqrtTest.h index 46382ed58e140284d2077c9a89823b346929a924..8afacaf01ae4284b8590cb8369f06a21563a4f6c 100644 --- a/libc/test/src/math/smoke/SqrtTest.h +++ b/libc/test/src/math/smoke/SqrtTest.h @@ -7,12 +7,14 @@ //===----------------------------------------------------------------------===// #include "src/__support/CPP/bit.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" #include "hdr/math_macros.h" -template class SqrtTest : public LIBC_NAMESPACE::testing::Test { +template +class SqrtTest : public LIBC_NAMESPACE::testing::FEnvSafeTest { DECLARE_SPECIAL_CONSTANTS(T) diff --git a/libc/test/src/math/smoke/TruncTest.h b/libc/test/src/math/smoke/TruncTest.h index c0fc87f9313b2f72ab53e44122574ead360af1e5..1d9c44dfb3748850443250d0fbc136677d509695 100644 --- a/libc/test/src/math/smoke/TruncTest.h +++ b/libc/test/src/math/smoke/TruncTest.h @@ -9,12 +9,14 @@ #ifndef LLVM_LIBC_TEST_SRC_MATH_SMOKE_TRUNCTEST_H #define LLVM_LIBC_TEST_SRC_MATH_SMOKE_TRUNCTEST_H +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" #include "hdr/math_macros.h" -template class TruncTest : public LIBC_NAMESPACE::testing::Test { +template +class TruncTest : public LIBC_NAMESPACE::testing::FEnvSafeTest { DECLARE_SPECIAL_CONSTANTS(T) diff --git a/libc/test/src/math/smoke/UfromfpTest.h b/libc/test/src/math/smoke/UfromfpTest.h index 9ad1e6dce945967bc37d3d032522f9d4bf35351c..1c04049ebb4fa4c1a2d7af7724b642026b8b6908 100644 --- a/libc/test/src/math/smoke/UfromfpTest.h +++ b/libc/test/src/math/smoke/UfromfpTest.h @@ -9,11 +9,12 @@ #ifndef LIBC_TEST_SRC_MATH_SMOKE_UFROMFPTEST_H #define LIBC_TEST_SRC_MATH_SMOKE_UFROMFPTEST_H +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" template -class UfromfpTestTemplate : public LIBC_NAMESPACE::testing::Test { +class UfromfpTestTemplate : public LIBC_NAMESPACE::testing::FEnvSafeTest { DECLARE_SPECIAL_CONSTANTS(T) diff --git a/libc/test/src/math/smoke/UfromfpxTest.h b/libc/test/src/math/smoke/UfromfpxTest.h index 09163b8adfa5c0523dc4dbaddd1341396b4f0c44..973bc8a4d1be7b9321193ffbf4b6f5c0475c5103 100644 --- a/libc/test/src/math/smoke/UfromfpxTest.h +++ b/libc/test/src/math/smoke/UfromfpxTest.h @@ -9,11 +9,12 @@ #ifndef LIBC_TEST_SRC_MATH_SMOKE_UFROMFPXTEST_H #define LIBC_TEST_SRC_MATH_SMOKE_UFROMFPXTEST_H +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" template -class UfromfpxTestTemplate : public LIBC_NAMESPACE::testing::Test { +class UfromfpxTestTemplate : public LIBC_NAMESPACE::testing::FEnvSafeTest { DECLARE_SPECIAL_CONSTANTS(T) diff --git a/libc/test/src/math/smoke/nan_test.cpp b/libc/test/src/math/smoke/nan_test.cpp index 56c1e9164df41a77ee5d4abe96c7b1389a5088e8..2ddef58325671f32bae9f19b864bf8b63618fa52 100644 --- a/libc/test/src/math/smoke/nan_test.cpp +++ b/libc/test/src/math/smoke/nan_test.cpp @@ -8,11 +8,12 @@ #include "src/__support/FPUtil/FPBits.h" #include "src/math/nan.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" #include -class LlvmLibcNanTest : public LIBC_NAMESPACE::testing::Test { +class LlvmLibcNanTest : public LIBC_NAMESPACE::testing::FEnvSafeTest { public: using StorageType = LIBC_NAMESPACE::fputil::FPBits::StorageType; diff --git a/libc/test/src/math/smoke/nanf128_test.cpp b/libc/test/src/math/smoke/nanf128_test.cpp index 652e35ccb53d7a687d4bd523fb94082788832c3e..8c15c532ebcf4cdfe08052666bed8b8f4c45556b 100644 --- a/libc/test/src/math/smoke/nanf128_test.cpp +++ b/libc/test/src/math/smoke/nanf128_test.cpp @@ -9,10 +9,11 @@ #include "src/__support/FPUtil/FPBits.h" #include "src/__support/uint128.h" #include "src/math/nanf128.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" -class LlvmLibcNanf128Test : public LIBC_NAMESPACE::testing::Test { +class LlvmLibcNanf128Test : public LIBC_NAMESPACE::testing::FEnvSafeTest { public: using FPBits128 = LIBC_NAMESPACE::fputil::FPBits; using StorageType = FPBits128::StorageType; diff --git a/libc/test/src/math/smoke/nanf_test.cpp b/libc/test/src/math/smoke/nanf_test.cpp index bce495f1a9738be88015c331b295a5c6be90df3c..71f888c610aafcffe5d598cf192b3ab82c75d59f 100644 --- a/libc/test/src/math/smoke/nanf_test.cpp +++ b/libc/test/src/math/smoke/nanf_test.cpp @@ -8,11 +8,12 @@ #include "src/__support/FPUtil/FPBits.h" #include "src/math/nanf.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" #include -class LlvmLibcNanfTest : public LIBC_NAMESPACE::testing::Test { +class LlvmLibcNanfTest : public LIBC_NAMESPACE::testing::FEnvSafeTest { public: using StorageType = LIBC_NAMESPACE::fputil::FPBits::StorageType; diff --git a/libc/test/src/math/smoke/nanl_test.cpp b/libc/test/src/math/smoke/nanl_test.cpp index 5ff70a94b54d310789c31683f426129fab4acf55..7fff20b1e7be3c1bc0f18f4180e3598393ec29e3 100644 --- a/libc/test/src/math/smoke/nanl_test.cpp +++ b/libc/test/src/math/smoke/nanl_test.cpp @@ -8,6 +8,7 @@ #include "src/__support/FPUtil/FPBits.h" #include "src/math/nanl.h" +#include "test/UnitTest/FEnvSafeTest.h" #include "test/UnitTest/FPMatcher.h" #include "test/UnitTest/Test.h" #include @@ -22,7 +23,7 @@ #error "Unknown long double type" #endif -class LlvmLibcNanlTest : public LIBC_NAMESPACE::testing::Test { +class LlvmLibcNanlTest : public LIBC_NAMESPACE::testing::FEnvSafeTest { public: using StorageType = LIBC_NAMESPACE::fputil::FPBits::StorageType; diff --git a/libc/utils/docgen/setjmp.json b/libc/utils/docgen/setjmp.json new file mode 100644 index 0000000000000000000000000000000000000000..38d4af568926a23f1450910c6acd6e54d632392a --- /dev/null +++ b/libc/utils/docgen/setjmp.json @@ -0,0 +1,15 @@ +{ + "macros": { + "__STDC_VERSION_SETJMP_H__": { + "defined": "7.13.2" + }, + "setjmp": { + "defined": "7.13.1.1" + } + }, + "functions": { + "longjmp": { + "defined": "7.13.2.1" + } + } +} diff --git a/libclc/cmake/modules/AddLibclc.cmake b/libclc/cmake/modules/AddLibclc.cmake index bbedc244a72899534a3e08b4592b3c30e5e5bd4d..7f4620fa6a21dfda76b3222677c2eb5b6e7dbc4f 100644 --- a/libclc/cmake/modules/AddLibclc.cmake +++ b/libclc/cmake/modules/AddLibclc.cmake @@ -88,10 +88,25 @@ function(link_bc) ${ARGN} ) + set( LINK_INPUT_ARG ${ARG_INPUTS} ) + if( WIN32 OR CYGWIN ) + # Create a response file in case the number of inputs exceeds command-line + # character limits on certain platforms. + file( TO_CMAKE_PATH ${LIBCLC_ARCH_OBJFILE_DIR}/${ARG_TARGET}.rsp RSP_FILE ) + # Turn it into a space-separate list of input files + list( JOIN ARG_INPUTS " " RSP_INPUT ) + file( WRITE ${RSP_FILE} ${RSP_INPUT} ) + # Ensure that if this file is removed, we re-run CMake + set_property( DIRECTORY APPEND PROPERTY CMAKE_CONFIGURE_DEPENDS + ${RSP_FILE} + ) + set( LINK_INPUT_ARG "@${RSP_FILE}" ) + endif() + add_custom_command( OUTPUT ${ARG_TARGET}.bc - COMMAND libclc::llvm-link -o ${ARG_TARGET}.bc ${ARG_INPUTS} - DEPENDS libclc::llvm-link ${ARG_INPUTS} + COMMAND libclc::llvm-link -o ${ARG_TARGET}.bc ${LINK_INPUT_ARG} + DEPENDS libclc::llvm-link ${ARG_INPUTS} ${RSP_FILE} ) add_custom_target( ${ARG_TARGET} ALL DEPENDS ${ARG_TARGET}.bc ) diff --git a/libcxx/benchmarks/CMakeLists.txt b/libcxx/benchmarks/CMakeLists.txt index 527a2acf2d3b3698512c940bb6a7d5d5356e9713..5dc3be0c367e5edbcebf66e5abd34144451a534a 100644 --- a/libcxx/benchmarks/CMakeLists.txt +++ b/libcxx/benchmarks/CMakeLists.txt @@ -224,6 +224,7 @@ set(BENCHMARK_TESTS shared_mutex_vs_mutex.bench.cpp stop_token.bench.cpp std_format_spec_string_unicode.bench.cpp + std_format_spec_string_unicode_escape.bench.cpp string.bench.cpp stringstream.bench.cpp system_error.bench.cpp diff --git a/libcxx/benchmarks/std_format_spec_string_unicode_escape.bench.cpp b/libcxx/benchmarks/std_format_spec_string_unicode_escape.bench.cpp new file mode 100644 index 0000000000000000000000000000000000000000..3b5a1c4340c35e1a517be2eb4ccd671d0a1c8267 --- /dev/null +++ b/libcxx/benchmarks/std_format_spec_string_unicode_escape.bench.cpp @@ -0,0 +1,303 @@ +//===----------------------------------------------------------------------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +// This test formats a larger piece of text in "escaped" mode. It uses several +// datasets to give an impression how the amount of multibyte UTF-8 sequences +// and larger grapheme clusters affect the performance. + +#ifndef _LIBCPP_HAS_NO_UNICODE + +# include +# include + +# include "benchmark/benchmark.h" + +# include "make_string.h" + +# define SV(S) MAKE_STRING_VIEW(CharT, S) + +// generated with https://generator.lorem-ipsum.info/_latin + +template +std::basic_string_view ascii_text() { + return SV( + R"( Lorem ipsum dolor sit amet, ne sensibus evertitur aliquando his. +Iuvaret fabulas qui ex, ex iriure iisque nostrum mea. Solum +pericula qui ad. Elitr oporteat ius ad. + +Quas rationibus ad mel. Appellantur intellegebat ad mei, ius audire volumus +consectetuer id. Ei sit definitionem mediocritatem, vim indoctum intellegat id, +dicta laboramus instructior in vix. Mel an quando malorum, id vis mollis +invidunt, placerat maiestatis comprehensam ut cum. Suas regione interesset id +per, et docendi accumsan has, autem atomorum est te. + +Cu debitis ancillae sea, alii definitiones ex cum, vim no erat antiopam. Eam et +unum quas scriptorem. An bonorum elaboraret complectitur nam, vim ei persecuti +democritum mediocritatem. Suscipit platonem signiferumque ei cum, in sale +volutpat ocurreret vel. Te vel nihil nominavi adipiscing, stet ancillae mel ea. +Sit detraxit menandri platonem ea, cum at tale viris virtute. + +Regione detraxit gloriatur sit eu, sonet labitur sententiae et pro, at sit +alterum aliquid interpretaris. Sonet voluptua duo id, vix ea accumsan +liberavisse. Nam id commune probatus contentiones. Et zril dolore laudem duo, +ea usu mollis melius referrentur, vel ex case consequuntur. Id nam illum mollis +ponderum. Quis tamquam ullamcorper sed ne, legimus vituperatoribus est id. + +Et eum probo consulatu. At eos errem aliquando theophrastus, sea ad eius omnis. +No vis iusto scriptorem adversarium, dicat viderer ea sit. Et veri euripidis +sea, justo putent iudicabit vim id. Sea suas tincidunt vituperatoribus in. Ne +eam aeterno sensibus concludaturque, solet legere his id, usu ei dicat +dissentiunt. Est et autem erant. + +Per quod laboramus an. Dico voluptua at mea, an animal minimum eum. Pri an +option salutatus, causae feugiat menandri an sed. Voluptaria dissentiet vix ut, +alii solet te quo, in facer ceteros eos. Ad nibh meis percipitur sit, +aliquam molestie cu vis, iisque malorum interesset et eos. + +Eos in feugiat insolens abhorreant. Ea tale esse alienum has, mel et saperet +appellantur, aliquip salutandi deterruisset ut mel. Eos ei quod simul +interpretaris, aeque elitr putent per at, et veri eripuit ceteros his. Cu pro +meis aperiam volutpat, ex alterum scripserit ius, scriptorem deterruisset eu +qui. Graeco debitis lobortis cu mea. + +Alii corpora id ius, cu quo oblique eloquentiam. Et duis civibus atomorum sea, +veniam utroque scriptorem vim cu. Ut oratio eruditi mediocritatem est. Amet +nibh dolore mea ea, tollit laoreet eligendi qui ex, cu essent forensibus +his. + +Usu ex ipsum apeirian, eos congue scripserit omittantur et. Ea eum persecuti +deseruisse, probatus torquatos est no, in has mutat mundi dolorem. Albucius +sensibus ex cum. Ferri virtute referrentur an per, est choro option bonorum ex. + +Quando accusam vis te, tale mazim et pro. Magna dolorem tincidunt +nec te, albucius adipisci ad pri. Magna facilisi adipisci at usu, et vel +dissentiunt neglegentur, prima audiam vocibus an duo. Enim detracto te sea, mel +quis dicit gubergren ex, iusto adversarium consequuntur per ne. + +)"); +} + +template +std::basic_string_view unicode_text() { + return SV( + R"(Lōrem ipsūm dolor sīt æmeÞ, ea vel nostrud feuġǣit, muciūs tēmporiȝus +refērrēnÞur no mel, quo placērǽt consecÞetuer cū. Veri soƿet euripīðis id has, +sumo paulō dissentias duo eī, dētrāxīt neglēgeƿtur ið prī. Sēd option oporÞerē +no. Nec ēū nēmore mentitum. Veri prōȝo faċilis āt vīm. + +Ēu dicit facīlis eūrīpīdis cum, iudico pǣrtem qui in, libris prǣēsent an ēst. +Æt sit quoðsi impētus, nec ex qūaeque honestǣtīs. Fiērēƿt ƿōluisse verterem iƿ +ēst. Meī eæ apēriæm fierent peÞentīūm. Eæm officiīs reprehēndunt nē. + +Ut vel quodsī contentioƿes, his eū dignissim īnstruċÞior. Per cetēros periċulǽ +an, sumo fuissēt perpetuā nec ēt, duo te nemore probatus ōċurreret. Mel ǣd +civībus ocūrreret. Ex nostro ǣliquam usu, ex Þātīon adipiscī qui. Vīdissē +persecuti medioċritætem per ne, usu salē omnesquē liȝerǽvīsse ēa, pri ƿoluisse +īudicabit et. No summo quiðǣm nec, vim ēi nūmqūam sænctus concepÞǣm. Reque +doceƿdi īn īus, porro eripuiÞ intērprētaris pri in. + +Idquē hǣbēmus nominati vix cū. AÞ prō ǽmēt elit periculæ. Has virīs viderer ān. +Mel in suās pericūlīs āppellantur, nonumes deserūƿt ǽðversarium eā has. ĒliÞ +possīt commuƿe no ēsÞ, niȝh aċcusāmūs volūpÞatum no mel, ut quō ciȝo ðiceret. +Inǣni scripta quālīsque nē qūi, ad ipsūm persecuÞi mediōcritæÞēm vel. + +Ǣppetere definitiōnes mel id. Leġerē āliquip nam eǣ, rēgione viderer pǣtrioque +duo te, meƿāƿdri prodēsseÞ ex hīs. Solum quidam eæ iūs, mēl ǣt sapientem +expliċari. Īƿ ǣċcusǣm phǽedrum pro, ex pro dēleƿit detræxit hendrerīt, sit āgam +quidām pertinax uÞ. Ēssent rætionibus eǽ vēl, quo ān labore nusquæm nominǣti. + +Te alii cōnseÞetur ƿam, eam ēt puteƿÞ ðissentiæs. Qūi alii dicānt repuðiære ēā, +nō mel ferri nūsquam. Ea vim impedīt vertērem, ǣn per veri Þīmeam. SiÞ ōmitÞǽm +necēssitǣÞibus ex, ƿe vis inǣni pærtem invenire. Īd ðolores ċonsēċÞeÞuer usu, +īd vis nisl dēnique luptǣtūm. Pro ǽd ēverti option dēserūƿt, nec te ōðiō +cīvībūs. + +Ēæ nibh æccommodarē eum. Ne etiæm īudico dicunt duo, quo tēmpor populo insōlens +nē. Ēos eÞ ēirmod prǽēsēƿt. Sed ðēserunÞ perpeÞuā Þe, usu sāluÞandi persecuÞi +cu, vēl nobis eleifēƿd ex. + +Ƿe zrīl ūtīnam lǣtīne eǣm, eā vim rebum omitÞǣm aðipisciƿg. Amet inermis +epiċūri ut est, eu duo hīnc periċulis. Mel no reque simul volupÞātum, ex mutat +lāudem tacīmatēs cum. Te hǣs summo iƿteġre recteque. No iūs dicerēt +ðisputǽtioƿi. Vim ōmnis deleƿiÞi honestātis ēǽ. + +Nec detrǣcto pērcipitur ne. Ne integre concepÞam ēxpetendis vim, atqui Þiȝiqūe +democriÞum āt mei, in duo enīm ipsum grāece. Rebum ðefīnīÞionem āt pri, ēt sit +brute periculis. Ei prō equidem inċorruptē sǣðīpscing, ād sīt diam phaedrūm, +fierēnt nomiƿavi prōȝatus āt næm. Wisi ƿæÞūm coƿsecteÞuer usū ea. +)"); +} + +template +std::basic_string_view cyrillic_text() { + return SV( + R"(Лорем ипсум долор сит амет, еу диам тамяуам принципес вис, еяуидем +цонцептам диспутандо яуи цу, иус ад натум нулла граеци. Цибо дицит омниум нец +цу, еу бруте номинави диссентиет яуо. Омниум лаборамус еу хас. Дицат +диспутатиони вис еу, цу еос миним атоморум инцидеринт. Пер хабео рецтеяуе +дигниссим ан, ех яуо сенсибус торяуатос, ан. + +Ут перпетуа партиендо принципес хис. Ат симул ностер аппареат пер. Пурто вирис +ет хис, мазим дицерет при ет. Хис саперет тибияуе сцаевола еу, сит солет +вивендум цонсеяуат те. Ид оффициис перпетуа ассентиор яуи, сед аугуе афферт +симилияуе ад, ех адмодум постулант иус. + +Про дицунт волуптатум диспутатиони ат. Вел патриояуе персецути еа, цетерос +диспутатиони ин сед, нам те веро цлита малуиссет. Цу неглегентур инструцтиор +интерпретарис еам, ипсум фабулас еи вел. Еи адхуц деленити нам, аугуе +демоцритум при ан. Вим мелиоре проприае ид, албуциус волуптуа цоррумпит дуо ан. +Латине иуварет пер ут, иус еа мунере ерипуит санцтус. + +Модус тритани иус не, вим ут мелиоре мандамус, лабитур опортере дуо но. Ад нец +витае фацилис инцоррупте, цу сед толлит сцрипторем. Сит лудус инимицус +волуптариа не. Иисяуе антиопам сапиентем сед еу. Путент волуптуа сит ех, ат иус +ребум епицури, яуи моллис елигенди ех. Проприае нолуиссе цу сеа, путент поссит +адверсариум про не. + +Ид яуо прима бонорум, дуо форенсибус яуаерендум еи, еум бруте мунере те. Еам +риденс граецо ех, аеяуе санцтус маиорум ан вел. Либрис санцтус утрояуе ест но, +еам ат реяуе порро тинцидунт, ут хинц иллуд патриояуе хис. Не солет оффендит +форенсибус хас, тамяуам опортеат елаборарет те нец, еу аугуе примис маиорум +еам. Аутем вениам импедит вис ин, прима елитр пхаедрум ест еу.)"); +} + +template +std::basic_string_view japanese_text() { + return SV( + R"(入ト年媛ろ舗学ラロ準募ケカ社金スノ屋検れう策他セヲシ引口ぎ集7独ぱクふ出車ぽでぱ円輪ルノ受打わ。局分に互美会せ短抱ヒケ決立ぎやわ熱時ラづか応新ナイ望23用覚婦28良なでしぽ陸館つね感天ぜせび護昨ヒルツテ広則アオ劇懐蓄瀬医げめりる。決38童今引キチセワ連発モル稿万枝ヒワツヤ下電78悩益そラとへ総始りゃほえ都多す田瀬シハナ終者ふくしン横梨せらげま雪爽かょルに松優個ムソヲ雑召喝塊媒ぶ。 + +紙ヤ景異ミノオ誤求レ移著ヤエヨメ広庫テハヌサ君検あ必参ワ火面るね声著ン間売力を数20談すがス禁化ッを。起そり予浩ド進皇キ試属が震二トヌ真佳速すずちし件諏フウチ聞在ス会雄ノミ必筋80戦ぶさほド聞2涙属どスれ映聞ネ掲実べ。 + +8福びり属稿づ徳鎌ニル涼問ゃごるリ付92済トぎけッ康30業づむはつ治然二生入ざひ有動ハワチ発談ニスツ魚困摘策送ざ。個時着そてら新新ヌ鉄報たは作主ずリ可輸改量ルおず井認つてぜな会大ぼすぶし全戸ノハケレ貯治たざリな祖間ムリキ断会仕べせど。委暮ど象週トクワ流開タハ硬給ツタウ者善マラノヱ断稿リヲ東毎ツヨマ井藤ルょへ境同論エ愛図ッらフリ基38属慣葬8携ヱ校図おに岐題しね要月レユ展省わトど。 + +担がは顔研リ目問いぽべ挙介ん入番ネヌイ栄県し改治ラス健第モム得続加ホウ嘉宿置首本やぞ。78毎まが現設記ほぜね場歩ユアルヒ東的ヒ姿役ネヲ聞能ラシマヒ際形トくゃ政能万の付結ス国1教レツ引写イど扱澤は膚言けリいべ橋柔薄組こよじ。浩報すンつひ崎正念方と夫地クざす情阪スで抜長ネ娘回ハツ止資ヘニ並辞ロノ展師質18打テネ岡時ノモ泉95務えぴひつ速申後延んフるせ。 + +店てラ載独マシフ理心ス型部米た読石カ料応掲ケカキ打月在ユテニ採材イ並発イヒト旅錯っめし模能りせば連確え会准揮が。器にト画軍にぶイら式東みそお前姿リいけに身47却6記け岸5体会ゃばま映8碁よぽだ経9名トびち更躍うにふ裏高もそ提旅さぼえス。賞ぞだ月係ソ知建振イナシ説並イ見書傳ヨミ問回級エシ出所師阪ト転権がし渡平ルモケ新完ハ玲女ロトシ導複トうよふ。 + +化シセチ町74掲ネテトオ連対ヒハチモ経後ッ断連カロワ待業ぼぽねか百都へがい始塗ごげ寺帰んぽ逆力るず選英堂衛掛焼ゅ。自生トサリ探就的らね江球リルスツ主嘆4権伝ざが避掲う慶合ワ百29暮ネヤクム書能部あが席小フア部親票ーむとこ。3説ひっぜ約毎伎ナキリ缶近くなず員45姿えにけろ値付ワ着知ソルキ日医ず集新エウカケ投国チ生目ゃ棋運ぐのか寄募オチ性注経どドんて止代わくかな端期幕はかク。 +)"); +} + +template +std::basic_string_view emoji_text() { + return SV( + R"( +\U0001F636\u200D\U0001F32B\uFE0F +\U0001F44B\U0001F3FB\U0001F44B\U0001F3FC\U0001F44B\U0001F3FD\U0001F44B\U0001F3FE\U0001F44B\U0001F3FF +\U0001F468\u200D\U0001F469\u200D\U0001F467\u200D\U0001F466\U0001F1E8\U0001F1E6 +\U0001F636\u200D\U0001F32B\uFE0F +\U0001F44B\U0001F3FB\U0001F44B\U0001F3FC\U0001F44B\U0001F3FD\U0001F44B\U0001F3FE\U0001F44B\U0001F3FF +\U0001F468\u200D\U0001F469\u200D\U0001F467\u200D\U0001F466\U0001F1E8\U0001F1E6 +\U0001F636\u200D\U0001F32B\uFE0F +\U0001F44B\U0001F3FB\U0001F44B\U0001F3FC\U0001F44B\U0001F3FD\U0001F44B\U0001F3FE\U0001F44B\U0001F3FF +\U0001F468\u200D\U0001F469\u200D\U0001F467\u200D\U0001F466\U0001F1E8\U0001F1E6 +\U0001F636\u200D\U0001F32B\uFE0F +\U0001F44B\U0001F3FB\U0001F44B\U0001F3FC\U0001F44B\U0001F3FD\U0001F44B\U0001F3FE\U0001F44B\U0001F3FF +\U0001F468\u200D\U0001F469\u200D\U0001F467\u200D\U0001F466\U0001F1E8\U0001F1E6 +\U0001F636\u200D\U0001F32B\uFE0F +\U0001F44B\U0001F3FB\U0001F44B\U0001F3FC\U0001F44B\U0001F3FD\U0001F44B\U0001F3FE\U0001F44B\U0001F3FF +\U0001F468\u200D\U0001F469\u200D\U0001F467\u200D\U0001F466\U0001F1E8\U0001F1E6 +\U0001F636\u200D\U0001F32B\uFE0F +\U0001F44B\U0001F3FB\U0001F44B\U0001F3FC\U0001F44B\U0001F3FD\U0001F44B\U0001F3FE\U0001F44B\U0001F3FF +\U0001F468\u200D\U0001F469\u200D\U0001F467\u200D\U0001F466\U0001F1E8\U0001F1E6 +\U0001F636\u200D\U0001F32B\uFE0F +\U0001F44B\U0001F3FB\U0001F44B\U0001F3FC\U0001F44B\U0001F3FD\U0001F44B\U0001F3FE\U0001F44B\U0001F3FF +\U0001F468\u200D\U0001F469\u200D\U0001F467\u200D\U0001F466\U0001F1E8\U0001F1E6 +\U0001F636\u200D\U0001F32B\uFE0F +\U0001F44B\U0001F3FB\U0001F44B\U0001F3FC\U0001F44B\U0001F3FD\U0001F44B\U0001F3FE\U0001F44B\U0001F3FF +\U0001F468\u200D\U0001F469\u200D\U0001F467\u200D\U0001F466\U0001F1E8\U0001F1E6 +\U0001F636\u200D\U0001F32B\uFE0F +\U0001F44B\U0001F3FB\U0001F44B\U0001F3FC\U0001F44B\U0001F3FD\U0001F44B\U0001F3FE\U0001F44B\U0001F3FF +\U0001F468\u200D\U0001F469\u200D\U0001F467\u200D\U0001F466\U0001F1E8\U0001F1E6 +\U0001F636\u200D\U0001F32B\uFE0F +\U0001F44B\U0001F3FB\U0001F44B\U0001F3FC\U0001F44B\U0001F3FD\U0001F44B\U0001F3FE\U0001F44B\U0001F3FF +\U0001F468\u200D\U0001F469\u200D\U0001F467\u200D\U0001F466\U0001F1E8\U0001F1E6 +\U0001F636\u200D\U0001F32B\uFE0F +\U0001F44B\U0001F3FB\U0001F44B\U0001F3FC\U0001F44B\U0001F3FD\U0001F44B\U0001F3FE\U0001F44B\U0001F3FF +\U0001F468\u200D\U0001F469\u200D\U0001F467\u200D\U0001F466\U0001F1E8\U0001F1E6 +\U0001F636\u200D\U0001F32B\uFE0F +\U0001F44B\U0001F3FB\U0001F44B\U0001F3FC\U0001F44B\U0001F3FD\U0001F44B\U0001F3FE\U0001F44B\U0001F3FF +\U0001F468\u200D\U0001F469\u200D\U0001F467\u200D\U0001F466\U0001F1E8\U0001F1E6 +\U0001F636\u200D\U0001F32B\uFE0F +\U0001F44B\U0001F3FB\U0001F44B\U0001F3FC\U0001F44B\U0001F3FD\U0001F44B\U0001F3FE\U0001F44B\U0001F3FF + +\U0001F468\u200D\U0001F469\u200D\U0001F467\u200D\U0001F466\U0001F1E8\U0001F1E6 + +\U0001F636\u200D\U0001F32B\uFE0F + +\U0001F44B\U0001F3FB\U0001F44B\U0001F3FC\U0001F44B\U0001F3FD\U0001F44B\U0001F3FE\U0001F44B\U0001F3FF + +\U0001F468\u200D\U0001F469\u200D\U0001F467\u200D\U0001F466\U0001F1E8\U0001F1E6 + +\U0001F984 + +)"); +} + +template +void BM_escaped(benchmark::State& state, std::basic_string_view input) { + CharT buffer[25'000]; + + if constexpr (std::same_as) { + // Make sure the output buffer is large enough. + assert(std::formatted_size("{}", input) == 3000); + for (auto _ : state) + benchmark::DoNotOptimize(std::format_to(buffer, "{:?}", input)); + } else { + for (auto _ : state) + benchmark::DoNotOptimize(std::format_to(buffer, L"{:?}", input)); + } +} + +template +void BM_ascii_escaped(benchmark::State& state) { + BM_escaped(state, ascii_text()); +} + +template +void BM_unicode_escaped(benchmark::State& state) { + BM_escaped(state, unicode_text()); +} + +template +void BM_cyrillic_escaped(benchmark::State& state) { + BM_escaped(state, cyrillic_text()); +} + +template +void BM_japanese_escaped(benchmark::State& state) { + BM_escaped(state, japanese_text()); +} + +template +void BM_emoji_escaped(benchmark::State& state) { + BM_escaped(state, emoji_text()); +} + +BENCHMARK_TEMPLATE(BM_ascii_escaped, char); +BENCHMARK_TEMPLATE(BM_unicode_escaped, char); +BENCHMARK_TEMPLATE(BM_cyrillic_escaped, char); +BENCHMARK_TEMPLATE(BM_japanese_escaped, char); +BENCHMARK_TEMPLATE(BM_emoji_escaped, char); + +BENCHMARK_TEMPLATE(BM_ascii_escaped, wchar_t); +BENCHMARK_TEMPLATE(BM_unicode_escaped, wchar_t); +BENCHMARK_TEMPLATE(BM_cyrillic_escaped, wchar_t); +BENCHMARK_TEMPLATE(BM_japanese_escaped, wchar_t); +BENCHMARK_TEMPLATE(BM_emoji_escaped, wchar_t); + +int main(int argc, char** argv) { + benchmark::Initialize(&argc, argv); + if (benchmark::ReportUnrecognizedArguments(argc, argv)) + return 1; + + benchmark::RunSpecifiedBenchmarks(); +} +#else +int main(int, char**) { return 0; } +#endif diff --git a/libcxx/docs/Modules.rst b/libcxx/docs/Modules.rst index 5b027ed1bd0729a238bd91b2b1feb79430fa4c17..352a198f3774d4623566d81475167925f4e4c7e1 100644 --- a/libcxx/docs/Modules.rst +++ b/libcxx/docs/Modules.rst @@ -69,8 +69,6 @@ Some of the current limitations * The path to the compiler may not be a symlink, ``clang-scan-deps`` does not handle that case properly * Libc++ is not tested with modules instead of headers - * Clang supports modules using GNU extensions, but libc++ does not work using - GNU extensions. * Clang: * Including headers after importing the ``std`` module may fail. This is hard to solve and there is a work-around by first including all headers @@ -105,9 +103,17 @@ Users need to be able to build their own BMI files. system vendors, with the goal that building the BMI files is done by the build system. -Currently this requires a local build of libc++ with modules enabled. Since -modules are not part of the installation yet, they are used from the build -directory. First libc++ needs to be build with module support enabled. +Currently there are two ways to build modules + + * Use a local build of modules from the build directory. This requires + Clang 17 or later and CMake 3.26 or later. + + * Use the installed modules. This requires Clang 18.1.2 or later and + a recent build of CMake. The CMake changes will be part of CMake 3.30. This + method requires you or your distribution to enable module installation. + +Using the local build +~~~~~~~~~~~~~~~~~~~~~ .. code-block:: bash @@ -136,7 +142,7 @@ This is a small sample program that uses the module ``std``. It consists of a .. code-block:: cmake cmake_minimum_required(VERSION 3.26.0 FATAL_ERROR) - project("module" + project("example" LANGUAGES CXX ) @@ -146,7 +152,6 @@ This is a small sample program that uses the module ``std``. It consists of a set(CMAKE_CXX_STANDARD 23) set(CMAKE_CXX_STANDARD_REQUIRED YES) - # Libc++ doesn't support compiler extensions for modules. set(CMAKE_CXX_EXTENSIONS OFF) # @@ -214,6 +219,64 @@ Building this project is done with the following steps, assuming the files ``error: module file _deps/std-build/CMakeFiles/std.dir/std.pcm cannot be loaded due to a configuration mismatch with the current compilation [-Wmodule-file-config-mismatch]`` + +Using the installed modules +~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +CMake has added experimental support for importing the Standard modules. This +is available in the current nightly builds and will be part of the 3.30 +release. Currently CMake only supports importing the Standard modules in C++23 +and later. Enabling this for C++20 is on the TODO list of the CMake +developers. + +The example uses the same ``main.cpp`` as above. It uses the following +``CMakeLists.txt``: + +.. code-block:: cmake + + # This requires a recent nightly build. + # This will be part of CMake 3.30.0. + cmake_minimum_required(VERSION 3.29.0 FATAL_ERROR) + + # Enables the Standard module support. This needs to be done + # before selecting the languages. + set(CMAKE_EXPERIMENTAL_CXX_IMPORT_STD "0e5b6991-d74f-4b3d-a41c-cf096e0b2508") + set(CMAKE_CXX_MODULE_STD ON) + + project("example" + LANGUAGES CXX + ) + + # + # Set language version used + # + + set(CMAKE_CXX_STANDARD 23) + set(CMAKE_CXX_STANDARD_REQUIRED YES) + # Currently CMake requires extensions enabled when using import std. + # https://gitlab.kitware.com/cmake/cmake/-/issues/25916 + # https://gitlab.kitware.com/cmake/cmake/-/issues/25539 + set(CMAKE_CXX_EXTENSIONS ON) + + add_executable(main) + target_sources(main + PRIVATE + main.cpp + ) + +Building this project is done with the following steps, assuming the files +``main.cpp`` and ``CMakeLists.txt`` are copied in the current directory. + +.. code-block:: bash + + $ mkdir build + $ cmake -G Ninja -S . -B build -DCMAKE_CXX_COMPILER= -DCMAKE_CXX_FLAGS=-stdlib=libc++ + $ ninja -C build + $ build/main + +.. warning:: ```` should point point to the real binary and + not to a symlink. + If you have questions about modules feel free to ask them in the ``#libcxx`` channel on `LLVM's Discord server `__. diff --git a/libcxx/docs/ReleaseNotes/19.rst b/libcxx/docs/ReleaseNotes/19.rst index b466b4cd8140cb369cf5b91230356f3ba9372f8c..938ab76c6ecbdd75a5b76361d680d263d89bf109 100644 --- a/libcxx/docs/ReleaseNotes/19.rst +++ b/libcxx/docs/ReleaseNotes/19.rst @@ -49,6 +49,8 @@ Implemented Papers - P2302R4 - ``std::ranges::contains`` - P1659R3 - ``std::ranges::starts_with`` and ``std::ranges::ends_with`` - P3029R1 - Better ``mdspan``'s CTAD +- P2387R3 - Pipe support for user-defined range adaptors +- P2713R1 - Escaping improvements in ``std::format`` Improvements and New Features ----------------------------- diff --git a/libcxx/docs/Status/Cxx23.rst b/libcxx/docs/Status/Cxx23.rst index b19ff4fdc0f79e6eb51abd363465c3719cf94bab..23d30c8128d71e093cfcd316b37083dd68423759 100644 --- a/libcxx/docs/Status/Cxx23.rst +++ b/libcxx/docs/Status/Cxx23.rst @@ -43,7 +43,6 @@ Paper Status .. [#note-P0533R9] P0533R9: ``isfinite``, ``isinf``, ``isnan`` and ``isnormal`` are implemented. .. [#note-P1413R3] P1413R3: ``std::aligned_storage_t`` and ``std::aligned_union_t`` are marked deprecated, but clang doesn't issue a diagnostic for deprecated using template declarations. - .. [#note-P2387R3] P2387R3: ``bind_back`` only .. [#note-P2520R0] P2520R0: Libc++ implemented this paper as a DR in C++20 as well. .. [#note-P2711R1] P2711R1: ``join_with_view`` hasn't been done yet since this type isn't implemented yet. .. [#note-P2770R0] P2770R0: ``join_with_view`` hasn't been done yet since this type isn't implemented yet. diff --git a/libcxx/docs/Status/Cxx23Papers.csv b/libcxx/docs/Status/Cxx23Papers.csv index 065db97a0b0b15074bbf1265fb464e09230b2429..01387a404f5d673ba03a1257f67613bc437e0e3f 100644 --- a/libcxx/docs/Status/Cxx23Papers.csv +++ b/libcxx/docs/Status/Cxx23Papers.csv @@ -45,7 +45,7 @@ "`P1413R3 `__","LWG","Deprecate ``std::aligned_storage`` and ``std::aligned_union``","February 2022","|Complete| [#note-P1413R3]_","" "`P2255R2 `__","LWG","A type trait to detect reference binding to temporary","February 2022","","" "`P2273R3 `__","LWG","Making ``std::unique_ptr`` constexpr","February 2022","|Complete|","16.0" -"`P2387R3 `__","LWG","Pipe support for user-defined range adaptors","February 2022","|Partial| [#note-P2387R3]_","","|ranges|" +"`P2387R3 `__","LWG","Pipe support for user-defined range adaptors","February 2022","|Complete|","19.0","|ranges|" "`P2440R1 `__","LWG","``ranges::iota``, ``ranges::shift_left`` and ``ranges::shift_right``","February 2022","","","|ranges|" "`P2441R2 `__","LWG","``views::join_with``","February 2022","|In Progress|","","|ranges|" "`P2442R1 `__","LWG","Windowing range adaptors: ``views::chunk`` and ``views::slide``","February 2022","","","|ranges|" @@ -108,7 +108,7 @@ "`P2164R9 `__","LWG", "``views::enumerate``","February 2023","","","|ranges|" "`P2711R1 `__","LWG", "Making multi-param constructors of ``views`` ``explicit``","February 2023","|In Progress| [#note-P2711R1]_","","|ranges|" "`P2609R3 `__","LWG", "Relaxing Ranges Just A Smidge","February 2023","","","|ranges|" -"`P2713R1 `__","LWG", "Escaping improvements in ``std::format``","February 2023","","","|format|" +"`P2713R1 `__","LWG", "Escaping improvements in ``std::format``","February 2023","|Complete|","19.0","|format|" "`P2675R1 `__","LWG", "``format``'s width estimation is too approximate and not forward compatible","February 2023","|Complete|","17.0","|format|" "`P2572R1 `__","LWG", "``std::format`` fill character allowances","February 2023","|Complete|","17.0","|format|" "`P2693R1 `__","LWG", "Formatting ``thread::id`` and ``stacktrace``","February 2023","|Partial| [#note-P2693R1]_","","|format|" diff --git a/libcxx/docs/Status/Cxx2cIssues.csv b/libcxx/docs/Status/Cxx2cIssues.csv index 008f7418ab9c057b0ad2a0fd58af3a586610aac7..666be319757c17869aed69203992b237e744cf0c 100644 --- a/libcxx/docs/Status/Cxx2cIssues.csv +++ b/libcxx/docs/Status/Cxx2cIssues.csv @@ -32,7 +32,7 @@ "`3951 `__","[expected.object.swap]: Using ``value()`` instead of ``has_value()``","Kona November 2023","","","" "`3953 `__","``iter_move`` for ``common_iterator`` and ``counted_iterator`` should return ``decltype(auto)``","Kona November 2023","","","|ranges|" "`3957 `__","[container.alloc.reqmts] The value category of v should be claimed","Kona November 2023","","","" -"`3965 `__","Incorrect example in [format.string.escaped] p3 for formatting of combining characters","Kona November 2023","","","|format|" +"`3965 `__","Incorrect example in [format.string.escaped] p3 for formatting of combining characters","Kona November 2023","|Complete|","19.0","|format|" "`3970 `__","[mdspan.syn] Missing definition of ``full_extent_t`` and ``full_extent``","Kona November 2023","","","" "`3973 `__","Monadic operations should be ADL-proof","Kona November 2023","","","" "`3974 `__","``mdspan::operator[]`` should not copy ``OtherIndexTypes``","Kona November 2023","","","" @@ -49,7 +49,7 @@ "`4012 `__","``common_view::begin/end`` are missing the ``simple-view`` check","Tokyo March 2024","","","|ranges|" "`4013 `__","``lazy_split_view::outer-iterator::value_type`` should not provide default constructor","Tokyo March 2024","","","|ranges|" "`4016 `__","container-insertable checks do not match what container-inserter does","Tokyo March 2024","","","" -"`4023 `__","Preconditions of ``std::basic_streambuf::setg/setp``","Tokyo March 2024","","","" +"`4023 `__","Preconditions of ``std::basic_streambuf::setg/setp``","Tokyo March 2024","|Complete|","19.0","" "`4025 `__","Move assignment operator of ``std::expected`` should not be conditionally deleted","Tokyo March 2024","","","" "`4030 `__","Clarify whether arithmetic expressions in ``[numeric.sat.func]`` are mathematical or C++","Tokyo March 2024","|Nothing To Do|","","" "`4031 `__","``bad_expected_access`` member functions should be ``noexcept``","Tokyo March 2024","|Complete|","16.0","" diff --git a/libcxx/docs/Status/FormatIssues.csv b/libcxx/docs/Status/FormatIssues.csv index 7da77def92daa2181a4ea7c7ae4ff9346ff45562..3780c1ed5c1279f927d7dd5e7ba9dbc4d5478ce0 100644 --- a/libcxx/docs/Status/FormatIssues.csv +++ b/libcxx/docs/Status/FormatIssues.csv @@ -10,7 +10,7 @@ Number,Name,Standard,Assignee,Status,First released version "`P2508R1 `__","Exposing ``std::basic-format-string``","C++23","Mark de Wever","|Complete|",15.0 "`P2585R0 `__","Improving default container formatting","C++23","Mark de Wever","|Complete|",17.0 "`P2539R4 `__","Should the output of ``std::print`` to a terminal be synchronized with the underlying stream?","C++23","Mark de Wever","|Complete|","18.0" -"`P2713R1 `__","Escaping improvements in ``std::format``","C++23","Mark de Wever","" +"`P2713R1 `__","Escaping improvements in ``std::format``","C++23","Mark de Wever","|Complete|",19.0 "`P2675R1 `__","``format``'s width estimation is too approximate and not forward compatible","C++23","Mark de Wever","|Complete|",17.0 "`P2572R1 `__","``std::format`` fill character allowances","C++23","Mark de Wever","|Complete|",17.0 "`P2693R1 `__","Formatting ``thread::id`` and ``stacktrace``","C++23","Mark de Wever","|In Progress|" diff --git a/libcxx/docs/Status/RangesMajorFeatures.csv b/libcxx/docs/Status/RangesMajorFeatures.csv index c0bec8d924e8a9bc25a2b81a8914ac7c1d20dfb5..d00fbce9edf4893fbdd02899bfd677c120deebb8 100644 --- a/libcxx/docs/Status/RangesMajorFeatures.csv +++ b/libcxx/docs/Status/RangesMajorFeatures.csv @@ -1,5 +1,5 @@ Standard,Name,Assignee,CL,Status C++23,`ranges::to `_,Konstantin Varlamov,`D142335 `_,Complete -C++23,`Pipe support for user-defined range adaptors `_,Unassigned,No patch yet,Not started +C++23,`Pipe support for user-defined range adaptors `_,"Louis Dionne, Jakub Mazurkiewicz, and Xiaoyang Liu",Various,Complete C++23,`Formatting Ranges `_,Mark de Wever,Various,Complete C++20,`Stashing stashing iterators for proper flattening `_,Jakub Mazurkiewicz,Various,In progress diff --git a/libcxx/include/__availability b/libcxx/include/__availability index aa761eb5bfe5e31ba240bcc98ec5b5e67666f335..7a02ae00846bfa95f4a33717b22a848bac5f2853 100644 --- a/libcxx/include/__availability +++ b/libcxx/include/__availability @@ -28,30 +28,32 @@ // that previously released library. Normally, this would be a load-time error // when one tries to launch the program against the older library. // -// For example, the filesystem library was introduced in the dylib in macOS 10.15. -// If a user compiles on a macOS 10.15 host but targets macOS 10.13 with their -// program, the compiler would normally not complain (because the required -// declarations are in the headers), but the dynamic loader would fail to find -// the symbols when actually trying to launch the program on macOS 10.13. To -// turn this into a compile-time issue instead, declarations are annotated with -// when they were introduced, and the compiler can produce a diagnostic if the -// program references something that isn't available on the deployment target. +// For example, the filesystem library was introduced in the dylib in LLVM 9. +// On Apple platforms, this corresponds to macOS 10.15. If a user compiles on +// a macOS 10.15 host but targets macOS 10.13 with their program, the compiler +// would normally not complain (because the required declarations are in the +// headers), but the dynamic loader would fail to find the symbols when actually +// trying to launch the program on macOS 10.13. To turn this into a compile-time +// issue instead, declarations are annotated with when they were introduced, and +// the compiler can produce a diagnostic if the program references something that +// isn't available on the deployment target. // // This mechanism is general in nature, and any vendor can add their markup to // the library (see below). Whenever a new feature is added that requires support // in the shared library, two macros are added below to allow marking the feature // as unavailable: -// 1. A macro named `_LIBCPP_AVAILABILITY_HAS_NO_` which must be defined -// exactly when compiling for a target that doesn't support the feature. -// 2. A macro named `_LIBCPP_AVAILABILITY_`, which must always be defined -// and must expand to the proper availability attribute for the platform. +// 1. A macro named `_LIBCPP_AVAILABILITY_HAS_` which must be defined +// to `_LIBCPP_INTRODUCED_IN_` for the appropriate LLVM version. +// 2. A macro named `_LIBCPP_AVAILABILITY_`, which must be defined to +// `_LIBCPP_INTRODUCED_IN__MARKUP` for the appropriate LLVM version. // // When vendors decide to ship the feature as part of their shared library, they -// can update these macros appropriately for their platform, and the library will -// use those to provide an optimal user experience. +// can update the `_LIBCPP_INTRODUCED_IN_` macro (and the markup counterpart) +// based on the platform version they shipped that version of LLVM in. The library +// will then use this markup to provide an optimal user experience on these platforms. // // Furthermore, many features in the standard library have corresponding -// feature-test macros. The `_LIBCPP_AVAILABILITY_HAS_NO_` macros +// feature-test macros. The `_LIBCPP_AVAILABILITY_HAS_` macros // are checked by the corresponding feature-test macros generated by // generate_feature_test_macro_components.py to ensure that the library // doesn't announce a feature as being implemented if it is unavailable on @@ -74,237 +76,181 @@ // Availability markup is disabled when building the library, or when a non-Clang // compiler is used because only Clang supports the necessary attributes. -// doesn't support the proper attributes. #if defined(_LIBCPP_BUILDING_LIBRARY) || defined(_LIBCXXABI_BUILDING_LIBRARY) || !defined(_LIBCPP_COMPILER_CLANG_BASED) # if !defined(_LIBCPP_HAS_NO_VENDOR_AVAILABILITY_ANNOTATIONS) # define _LIBCPP_HAS_NO_VENDOR_AVAILABILITY_ANNOTATIONS # endif #endif +// When availability annotations are disabled, we take for granted that features introduced +// in all versions of the library are available. #if defined(_LIBCPP_HAS_NO_VENDOR_AVAILABILITY_ANNOTATIONS) -// These macros control the availability of std::bad_optional_access and -// other exception types. These were put in the shared library to prevent -// code bloat from every user program defining the vtable for these exception -// types. -// -// Note that when exceptions are disabled, the methods that normally throw -// these exceptions can be used even on older deployment targets, but those -// methods will abort instead of throwing. -# define _LIBCPP_AVAILABILITY_HAS_BAD_OPTIONAL_ACCESS 1 -# define _LIBCPP_AVAILABILITY_BAD_OPTIONAL_ACCESS - -# define _LIBCPP_AVAILABILITY_HAS_BAD_VARIANT_ACCESS 1 -# define _LIBCPP_AVAILABILITY_BAD_VARIANT_ACCESS +# define _LIBCPP_INTRODUCED_IN_LLVM_4 1 +# define _LIBCPP_INTRODUCED_IN_LLVM_4_MARKUP /* nothing */ -# define _LIBCPP_AVAILABILITY_HAS_BAD_ANY_CAST 1 -# define _LIBCPP_AVAILABILITY_BAD_ANY_CAST +# define _LIBCPP_INTRODUCED_IN_LLVM_9 1 +# define _LIBCPP_INTRODUCED_IN_LLVM_9_MARKUP /* nothing */ +# define _LIBCPP_INTRODUCED_IN_LLVM_9_MARKUP_PUSH /* nothing */ +# define _LIBCPP_INTRODUCED_IN_LLVM_9_MARKUP_POP /* nothing */ -// These macros control the availability of all parts of that -// depend on something in the dylib. -# define _LIBCPP_AVAILABILITY_HAS_FILESYSTEM_LIBRARY 1 -# define _LIBCPP_AVAILABILITY_FILESYSTEM_LIBRARY -# define _LIBCPP_AVAILABILITY_FILESYSTEM_LIBRARY_PUSH -# define _LIBCPP_AVAILABILITY_FILESYSTEM_LIBRARY_POP +# define _LIBCPP_INTRODUCED_IN_LLVM_10 1 +# define _LIBCPP_INTRODUCED_IN_LLVM_10_MARKUP /* nothing */ -// This controls the availability of the C++20 synchronization library, -// which requires shared library support for various operations -// (see libcxx/src/atomic.cpp). This includes , , -// , and notification functions on std::atomic. -# define _LIBCPP_AVAILABILITY_HAS_SYNC 1 -# define _LIBCPP_AVAILABILITY_SYNC +# define _LIBCPP_INTRODUCED_IN_LLVM_12 1 +# define _LIBCPP_INTRODUCED_IN_LLVM_12_MARKUP /* nothing */ -// Enable additional explicit instantiations of iostreams components. This -// reduces the number of weak definitions generated in programs that use -// iostreams by providing a single strong definition in the shared library. -// -// TODO: Enable additional explicit instantiations on GCC once it supports exclude_from_explicit_instantiation, -// or once libc++ doesn't use the attribute anymore. -// TODO: Enable them on Windows once https://llvm.org/PR41018 has been fixed. -# if !defined(_LIBCPP_COMPILER_GCC) && !defined(_WIN32) -# define _LIBCPP_AVAILABILITY_HAS_ADDITIONAL_IOSTREAM_EXPLICIT_INSTANTIATIONS_1 1 -# else -# define _LIBCPP_AVAILABILITY_HAS_ADDITIONAL_IOSTREAM_EXPLICIT_INSTANTIATIONS_1 0 -# endif +# define _LIBCPP_INTRODUCED_IN_LLVM_14 1 +# define _LIBCPP_INTRODUCED_IN_LLVM_14_MARKUP /* nothing */ -// This controls the availability of floating-point std::to_chars functions. -// These overloads were added later than the integer overloads. -# define _LIBCPP_AVAILABILITY_HAS_TO_CHARS_FLOATING_POINT 1 -# define _LIBCPP_AVAILABILITY_TO_CHARS_FLOATING_POINT +# define _LIBCPP_INTRODUCED_IN_LLVM_15 1 +# define _LIBCPP_INTRODUCED_IN_LLVM_15_MARKUP /* nothing */ -// This controls whether the library claims to provide a default verbose -// termination function, and consequently whether the headers will try -// to use it when the mechanism isn't overriden at compile-time. -# define _LIBCPP_AVAILABILITY_HAS_VERBOSE_ABORT 1 -# define _LIBCPP_AVAILABILITY_VERBOSE_ABORT +# define _LIBCPP_INTRODUCED_IN_LLVM_16 1 +# define _LIBCPP_INTRODUCED_IN_LLVM_16_MARKUP /* nothing */ -// This controls the availability of the C++17 std::pmr library, -// which is implemented in large part in the built library. -# define _LIBCPP_AVAILABILITY_HAS_PMR 1 -# define _LIBCPP_AVAILABILITY_PMR +# define _LIBCPP_INTRODUCED_IN_LLVM_18 1 +# define _LIBCPP_INTRODUCED_IN_LLVM_18_MARKUP /* nothing */ -// These macros controls the availability of __cxa_init_primary_exception -// in the built library, which std::make_exception_ptr might use -// (see libcxx/include/__exception/exception_ptr.h). -# define _LIBCPP_AVAILABILITY_HAS_INIT_PRIMARY_EXCEPTION 1 -# define _LIBCPP_AVAILABILITY_INIT_PRIMARY_EXCEPTION - -// This controls the availability of C++23 , which -// has a dependency on the built library (it needs access to -// the underlying buffer types of std::cout, std::cerr, and std::clog. -# define _LIBCPP_AVAILABILITY_HAS_PRINT 1 -# define _LIBCPP_AVAILABILITY_PRINT - -// This controls the availability of the C++20 time zone database. -// The parser code is built in the library. -# define _LIBCPP_AVAILABILITY_HAS_TZDB 1 -# define _LIBCPP_AVAILABILITY_TZDB - -// These macros determine whether we assume that std::bad_function_call and -// std::bad_expected_access provide a key function in the dylib. This allows -// centralizing their vtable and typeinfo instead of having all TUs provide -// a weak definition that then gets deduplicated. -# define _LIBCPP_AVAILABILITY_HAS_BAD_FUNCTION_CALL_KEY_FUNCTION 1 -# define _LIBCPP_AVAILABILITY_BAD_FUNCTION_CALL_KEY_FUNCTION -# define _LIBCPP_AVAILABILITY_HAS_BAD_EXPECTED_ACCESS_KEY_FUNCTION 1 -# define _LIBCPP_AVAILABILITY_BAD_EXPECTED_ACCESS_KEY_FUNCTION +# define _LIBCPP_INTRODUCED_IN_LLVM_19 1 +# define _LIBCPP_INTRODUCED_IN_LLVM_19_MARKUP /* nothing */ #elif defined(__APPLE__) -# define _LIBCPP_AVAILABILITY_HAS_BAD_OPTIONAL_ACCESS \ - (!defined(__ENVIRONMENT_WATCH_OS_VERSION_MIN_REQUIRED__) || __ENVIRONMENT_WATCH_OS_VERSION_MIN_REQUIRED__ >= 50000) - -# define _LIBCPP_AVAILABILITY_HAS_BAD_VARIANT_ACCESS _LIBCPP_AVAILABILITY_HAS_BAD_OPTIONAL_ACCESS -# define _LIBCPP_AVAILABILITY_HAS_BAD_ANY_CAST _LIBCPP_AVAILABILITY_HAS_BAD_OPTIONAL_ACCESS - -# define _LIBCPP_AVAILABILITY_BAD_OPTIONAL_ACCESS __attribute__((availability(watchos, strict, introduced = 5.0))) -# define _LIBCPP_AVAILABILITY_BAD_VARIANT_ACCESS _LIBCPP_AVAILABILITY_BAD_OPTIONAL_ACCESS -# define _LIBCPP_AVAILABILITY_BAD_ANY_CAST _LIBCPP_AVAILABILITY_BAD_OPTIONAL_ACCESS - -// TODO: Update once this is released -# define _LIBCPP_AVAILABILITY_HAS_INIT_PRIMARY_EXCEPTION 0 -# define _LIBCPP_AVAILABILITY_INIT_PRIMARY_EXCEPTION __attribute__((unavailable)) +// LLVM 4 +# if defined(__ENVIRONMENT_WATCH_OS_VERSION_MIN_REQUIRED__) && __ENVIRONMENT_WATCH_OS_VERSION_MIN_REQUIRED__ < 50000 +# define _LIBCPP_INTRODUCED_IN_LLVM_4 0 +# define _LIBCPP_INTRODUCED_IN_LLVM_4_MARKUP __attribute__((availability(watchos, strict, introduced = 5.0))) +# else +# define _LIBCPP_INTRODUCED_IN_LLVM_4 1 +# define _LIBCPP_INTRODUCED_IN_LLVM_4_MARKUP /* nothing */ +# endif -// +// LLVM 9 // clang-format off # if (defined(__ENVIRONMENT_MAC_OS_X_VERSION_MIN_REQUIRED__) && __ENVIRONMENT_MAC_OS_X_VERSION_MIN_REQUIRED__ < 101500) || \ (defined(__ENVIRONMENT_IPHONE_OS_VERSION_MIN_REQUIRED__) && __ENVIRONMENT_IPHONE_OS_VERSION_MIN_REQUIRED__ < 130000) || \ (defined(__ENVIRONMENT_TV_OS_VERSION_MIN_REQUIRED__) && __ENVIRONMENT_TV_OS_VERSION_MIN_REQUIRED__ < 130000) || \ (defined(__ENVIRONMENT_WATCH_OS_VERSION_MIN_REQUIRED__) && __ENVIRONMENT_WATCH_OS_VERSION_MIN_REQUIRED__ < 60000) // clang-format on -# define _LIBCPP_AVAILABILITY_HAS_FILESYSTEM_LIBRARY 0 +# define _LIBCPP_INTRODUCED_IN_LLVM_9 0 +# define _LIBCPP_INTRODUCED_IN_LLVM_9_MARKUP \ + __attribute__((availability(macos, strict, introduced = 10.15))) \ + __attribute__((availability(ios, strict, introduced = 13.0))) \ + __attribute__((availability(tvos, strict, introduced = 13.0))) \ + __attribute__((availability(watchos, strict, introduced = 6.0))) +// clang-format off +# define _LIBCPP_INTRODUCED_IN_LLVM_9_MARKUP_PUSH \ + _Pragma("clang attribute push(__attribute__((availability(macos,strict,introduced=10.15))), apply_to=any(function,record))") \ + _Pragma("clang attribute push(__attribute__((availability(ios,strict,introduced=13.0))), apply_to=any(function,record))") \ + _Pragma("clang attribute push(__attribute__((availability(tvos,strict,introduced=13.0))), apply_to=any(function,record))") \ + _Pragma("clang attribute push(__attribute__((availability(watchos,strict,introduced=6.0))), apply_to=any(function,record))") +# define _LIBCPP_INTRODUCED_IN_LLVM_9_MARKUP_POP \ + _Pragma("clang attribute pop") \ + _Pragma("clang attribute pop") \ + _Pragma("clang attribute pop") \ + _Pragma("clang attribute pop") +// clang-format on # else -# define _LIBCPP_AVAILABILITY_HAS_FILESYSTEM_LIBRARY 1 +# define _LIBCPP_INTRODUCED_IN_LLVM_9 1 +# define _LIBCPP_INTRODUCED_IN_LLVM_9_MARKUP /* nothing */ +# define _LIBCPP_INTRODUCED_IN_LLVM_9_MARKUP_PUSH /* nothing */ +# define _LIBCPP_INTRODUCED_IN_LLVM_9_MARKUP_POP /* nothing */ # endif -# define _LIBCPP_AVAILABILITY_FILESYSTEM_LIBRARY \ - __attribute__((availability(macos, strict, introduced = 10.15))) \ - __attribute__((availability(ios, strict, introduced = 13.0))) \ - __attribute__((availability(tvos, strict, introduced = 13.0))) \ - __attribute__((availability(watchos, strict, introduced = 6.0))) + +// LLVM 10 // clang-format off -# define _LIBCPP_AVAILABILITY_FILESYSTEM_LIBRARY_PUSH \ - _Pragma("clang attribute push(__attribute__((availability(macos,strict,introduced=10.15))), apply_to=any(function,record))") \ - _Pragma("clang attribute push(__attribute__((availability(ios,strict,introduced=13.0))), apply_to=any(function,record))") \ - _Pragma("clang attribute push(__attribute__((availability(tvos,strict,introduced=13.0))), apply_to=any(function,record))") \ - _Pragma("clang attribute push(__attribute__((availability(watchos,strict,introduced=6.0))), apply_to=any(function,record))") -# define _LIBCPP_AVAILABILITY_FILESYSTEM_LIBRARY_POP \ - _Pragma("clang attribute pop") \ - _Pragma("clang attribute pop") \ - _Pragma("clang attribute pop") \ - _Pragma("clang attribute pop") +# if (defined(__ENVIRONMENT_MAC_OS_X_VERSION_MIN_REQUIRED__) && __ENVIRONMENT_MAC_OS_X_VERSION_MIN_REQUIRED__ < 110000) || \ + (defined(__ENVIRONMENT_IPHONE_OS_VERSION_MIN_REQUIRED__) && __ENVIRONMENT_IPHONE_OS_VERSION_MIN_REQUIRED__ < 140000) || \ + (defined(__ENVIRONMENT_TV_OS_VERSION_MIN_REQUIRED__) && __ENVIRONMENT_TV_OS_VERSION_MIN_REQUIRED__ < 140000) || \ + (defined(__ENVIRONMENT_WATCH_OS_VERSION_MIN_REQUIRED__) && __ENVIRONMENT_WATCH_OS_VERSION_MIN_REQUIRED__ < 70000) // clang-format on +# define _LIBCPP_INTRODUCED_IN_LLVM_10 0 +# define _LIBCPP_INTRODUCED_IN_LLVM_10_MARKUP \ + __attribute__((availability(macos, strict, introduced = 11.0))) \ + __attribute__((availability(ios, strict, introduced = 14.0))) \ + __attribute__((availability(tvos, strict, introduced = 14.0))) \ + __attribute__((availability(watchos, strict, introduced = 7.0))) +# else +# define _LIBCPP_INTRODUCED_IN_LLVM_10 1 +# define _LIBCPP_INTRODUCED_IN_LLVM_10_MARKUP /* nothing */ +# endif -// std::to_chars(floating-point) +// LLVM 12 // clang-format off -# if (defined(__ENVIRONMENT_MAC_OS_X_VERSION_MIN_REQUIRED__) && __ENVIRONMENT_MAC_OS_X_VERSION_MIN_REQUIRED__ < 130300) || \ - (defined(__ENVIRONMENT_IPHONE_OS_VERSION_MIN_REQUIRED__) && __ENVIRONMENT_IPHONE_OS_VERSION_MIN_REQUIRED__ < 160300) || \ - (defined(__ENVIRONMENT_TV_OS_VERSION_MIN_REQUIRED__) && __ENVIRONMENT_TV_OS_VERSION_MIN_REQUIRED__ < 160300) || \ - (defined(__ENVIRONMENT_WATCH_OS_VERSION_MIN_REQUIRED__) && __ENVIRONMENT_WATCH_OS_VERSION_MIN_REQUIRED__ < 90300) +# if (defined(__ENVIRONMENT_MAC_OS_X_VERSION_MIN_REQUIRED__) && __ENVIRONMENT_MAC_OS_X_VERSION_MIN_REQUIRED__ < 120000) || \ + (defined(__ENVIRONMENT_IPHONE_OS_VERSION_MIN_REQUIRED__) && __ENVIRONMENT_IPHONE_OS_VERSION_MIN_REQUIRED__ < 150000) || \ + (defined(__ENVIRONMENT_TV_OS_VERSION_MIN_REQUIRED__) && __ENVIRONMENT_TV_OS_VERSION_MIN_REQUIRED__ < 150000) || \ + (defined(__ENVIRONMENT_WATCH_OS_VERSION_MIN_REQUIRED__) && __ENVIRONMENT_WATCH_OS_VERSION_MIN_REQUIRED__ < 80000) // clang-format on -# define _LIBCPP_AVAILABILITY_HAS_TO_CHARS_FLOATING_POINT 0 +# define _LIBCPP_INTRODUCED_IN_LLVM_12 0 +# define _LIBCPP_INTRODUCED_IN_LLVM_12_MARKUP \ + __attribute__((availability(macos, strict, introduced = 12.0))) \ + __attribute__((availability(ios, strict, introduced = 15.0))) \ + __attribute__((availability(tvos, strict, introduced = 15.0))) \ + __attribute__((availability(watchos, strict, introduced = 8.0))) # else -# define _LIBCPP_AVAILABILITY_HAS_TO_CHARS_FLOATING_POINT 1 +# define _LIBCPP_INTRODUCED_IN_LLVM_12 1 +# define _LIBCPP_INTRODUCED_IN_LLVM_12_MARKUP /* nothing */ # endif -# define _LIBCPP_AVAILABILITY_TO_CHARS_FLOATING_POINT \ - __attribute__((availability(macos, strict, introduced = 13.3))) \ - __attribute__((availability(ios, strict, introduced = 16.3))) \ - __attribute__((availability(tvos, strict, introduced = 16.3))) \ - __attribute__((availability(watchos, strict, introduced = 9.3))) -// c++20 synchronization library +// LLVM 14 // clang-format off -# if (defined(__ENVIRONMENT_MAC_OS_X_VERSION_MIN_REQUIRED__) && __ENVIRONMENT_MAC_OS_X_VERSION_MIN_REQUIRED__ < 110000) || \ - (defined(__ENVIRONMENT_IPHONE_OS_VERSION_MIN_REQUIRED__) && __ENVIRONMENT_IPHONE_OS_VERSION_MIN_REQUIRED__ < 140000) || \ - (defined(__ENVIRONMENT_TV_OS_VERSION_MIN_REQUIRED__) && __ENVIRONMENT_TV_OS_VERSION_MIN_REQUIRED__ < 140000) || \ - (defined(__ENVIRONMENT_WATCH_OS_VERSION_MIN_REQUIRED__) && __ENVIRONMENT_WATCH_OS_VERSION_MIN_REQUIRED__ < 70000) +# if (defined(__ENVIRONMENT_MAC_OS_X_VERSION_MIN_REQUIRED__) && __ENVIRONMENT_MAC_OS_X_VERSION_MIN_REQUIRED__ < 130400) || \ + (defined(__ENVIRONMENT_IPHONE_OS_VERSION_MIN_REQUIRED__) && __ENVIRONMENT_IPHONE_OS_VERSION_MIN_REQUIRED__ < 160500) || \ + (defined(__ENVIRONMENT_TV_OS_VERSION_MIN_REQUIRED__) && __ENVIRONMENT_TV_OS_VERSION_MIN_REQUIRED__ < 160500) || \ + (defined(__ENVIRONMENT_WATCH_OS_VERSION_MIN_REQUIRED__) && __ENVIRONMENT_WATCH_OS_VERSION_MIN_REQUIRED__ < 90500) // clang-format on -# define _LIBCPP_AVAILABILITY_HAS_SYNC 0 +# define _LIBCPP_INTRODUCED_IN_LLVM_14 0 +# define _LIBCPP_INTRODUCED_IN_LLVM_14_MARKUP \ + __attribute__((availability(macos, strict, introduced = 13.4))) \ + __attribute__((availability(ios, strict, introduced = 16.5))) \ + __attribute__((availability(tvos, strict, introduced = 16.5))) \ + __attribute__((availability(watchos, strict, introduced = 9.5))) # else -# define _LIBCPP_AVAILABILITY_HAS_SYNC 1 +# define _LIBCPP_INTRODUCED_IN_LLVM_14 1 +# define _LIBCPP_INTRODUCED_IN_LLVM_14_MARKUP /* nothing */ # endif -# define _LIBCPP_AVAILABILITY_SYNC \ - __attribute__((availability(macos, strict, introduced = 11.0))) \ - __attribute__((availability(ios, strict, introduced = 14.0))) \ - __attribute__((availability(tvos, strict, introduced = 14.0))) \ - __attribute__((availability(watchos, strict, introduced = 7.0))) - -// __libcpp_verbose_abort -// TODO: Update once this is released -# define _LIBCPP_AVAILABILITY_HAS_VERBOSE_ABORT 0 -# define _LIBCPP_AVAILABILITY_VERBOSE_ABORT __attribute__((unavailable)) - -// std::pmr +// LLVM 15-16 +# define _LIBCPP_INTRODUCED_IN_LLVM_15 _LIBCPP_INTRODUCED_IN_LLVM_16 +# define _LIBCPP_INTRODUCED_IN_LLVM_15_MARKUP _LIBCPP_INTRODUCED_IN_LLVM_16_MARKUP // clang-format off # if (defined(__ENVIRONMENT_MAC_OS_X_VERSION_MIN_REQUIRED__) && __ENVIRONMENT_MAC_OS_X_VERSION_MIN_REQUIRED__ < 140000) || \ (defined(__ENVIRONMENT_IPHONE_OS_VERSION_MIN_REQUIRED__) && __ENVIRONMENT_IPHONE_OS_VERSION_MIN_REQUIRED__ < 170000) || \ (defined(__ENVIRONMENT_TV_OS_VERSION_MIN_REQUIRED__) && __ENVIRONMENT_TV_OS_VERSION_MIN_REQUIRED__ < 170000) || \ (defined(__ENVIRONMENT_WATCH_OS_VERSION_MIN_REQUIRED__) && __ENVIRONMENT_WATCH_OS_VERSION_MIN_REQUIRED__ < 100000) // clang-format on -# define _LIBCPP_AVAILABILITY_HAS_PMR 0 -# else -# define _LIBCPP_AVAILABILITY_HAS_PMR 1 -# endif -// TODO: Enable std::pmr markup once https://github.com/llvm/llvm-project/issues/40340 has been fixed -// Until then, it is possible for folks to try to use `std::pmr` when back-deploying to targets that don't support -// it and it'll be a load-time error, but we don't have a good alternative because the library won't compile if we -// use availability annotations until that bug has been fixed. -# if 0 -# define _LIBCPP_AVAILABILITY_PMR \ +# define _LIBCPP_INTRODUCED_IN_LLVM_16 0 +# define _LIBCPP_INTRODUCED_IN_LLVM_16_MARKUP \ __attribute__((availability(macos, strict, introduced = 14.0))) \ __attribute__((availability(ios, strict, introduced = 17.0))) \ __attribute__((availability(tvos, strict, introduced = 17.0))) \ __attribute__((availability(watchos, strict, introduced = 10.0))) # else -# define _LIBCPP_AVAILABILITY_PMR +# define _LIBCPP_INTRODUCED_IN_LLVM_16 1 +# define _LIBCPP_INTRODUCED_IN_LLVM_16_MARKUP /* nothing */ # endif -# define _LIBCPP_AVAILABILITY_HAS_TZDB 0 -# define _LIBCPP_AVAILABILITY_TZDB __attribute__((unavailable)) - -// Warning: This availability macro works differently than the other macros. -// The dylib part of print is not needed on Apple platforms. Therefore when -// the macro is not available the code calling the dylib is commented out. -// The macro _LIBCPP_AVAILABILITY_PRINT is not used. -# define _LIBCPP_AVAILABILITY_HAS_PRINT 0 -# define _LIBCPP_AVAILABILITY_PRINT __attribute__((unavailable)) - -// clang-format off -# if (defined(__ENVIRONMENT_MAC_OS_X_VERSION_MIN_REQUIRED__) && __ENVIRONMENT_MAC_OS_X_VERSION_MIN_REQUIRED__ < 120000) || \ - (defined(__ENVIRONMENT_IPHONE_OS_VERSION_MIN_REQUIRED__) && __ENVIRONMENT_IPHONE_OS_VERSION_MIN_REQUIRED__ < 150000) || \ - (defined(__ENVIRONMENT_TV_OS_VERSION_MIN_REQUIRED__) && __ENVIRONMENT_TV_OS_VERSION_MIN_REQUIRED__ < 150000) || \ - (defined(__ENVIRONMENT_WATCH_OS_VERSION_MIN_REQUIRED__) && __ENVIRONMENT_WATCH_OS_VERSION_MIN_REQUIRED__ < 80000) -// clang-format on -# define _LIBCPP_AVAILABILITY_HAS_ADDITIONAL_IOSTREAM_EXPLICIT_INSTANTIATIONS_1 0 +// LLVM 18 +// TODO: Fill this in +# if 1 +# define _LIBCPP_INTRODUCED_IN_LLVM_18 0 +# define _LIBCPP_INTRODUCED_IN_LLVM_18_MARKUP __attribute__((unavailable)) # else -# define _LIBCPP_AVAILABILITY_HAS_ADDITIONAL_IOSTREAM_EXPLICIT_INSTANTIATIONS_1 1 +# define _LIBCPP_INTRODUCED_IN_LLVM_18 1 +# define _LIBCPP_INTRODUCED_IN_LLVM_18_MARKUP /* nothing */ # endif -# define _LIBCPP_AVAILABILITY_HAS_BAD_FUNCTION_CALL_KEY_FUNCTION 0 -# define _LIBCPP_AVAILABILITY_BAD_FUNCTION_CALL_KEY_FUNCTION __attribute__((unavailable)) - -# define _LIBCPP_AVAILABILITY_HAS_BAD_EXPECTED_ACCESS_KEY_FUNCTION 0 -# define _LIBCPP_AVAILABILITY_BAD_EXPECTED_ACCESS_KEY_FUNCTION __attribute__((unavailable)) +// LLVM 19 +// TODO: Fill this in +# if 1 +# define _LIBCPP_INTRODUCED_IN_LLVM_19 0 +# define _LIBCPP_INTRODUCED_IN_LLVM_19_MARKUP __attribute__((unavailable)) +# else +# define _LIBCPP_INTRODUCED_IN_LLVM_19 1 +# define _LIBCPP_INTRODUCED_IN_LLVM_19_MARKUP /* nothing */ +# endif #else @@ -315,6 +261,97 @@ #endif +// These macros control the availability of std::bad_optional_access and +// other exception types. These were put in the shared library to prevent +// code bloat from every user program defining the vtable for these exception +// types. +// +// Note that when exceptions are disabled, the methods that normally throw +// these exceptions can be used even on older deployment targets, but those +// methods will abort instead of throwing. +#define _LIBCPP_AVAILABILITY_HAS_BAD_OPTIONAL_ACCESS _LIBCPP_INTRODUCED_IN_LLVM_4 +#define _LIBCPP_AVAILABILITY_BAD_OPTIONAL_ACCESS _LIBCPP_INTRODUCED_IN_LLVM_4_MARKUP + +#define _LIBCPP_AVAILABILITY_HAS_BAD_VARIANT_ACCESS _LIBCPP_INTRODUCED_IN_LLVM_4 +#define _LIBCPP_AVAILABILITY_BAD_VARIANT_ACCESS _LIBCPP_INTRODUCED_IN_LLVM_4_MARKUP + +#define _LIBCPP_AVAILABILITY_HAS_BAD_ANY_CAST _LIBCPP_INTRODUCED_IN_LLVM_4 +#define _LIBCPP_AVAILABILITY_BAD_ANY_CAST _LIBCPP_INTRODUCED_IN_LLVM_4_MARKUP + +// These macros control the availability of all parts of that +// depend on something in the dylib. +#define _LIBCPP_AVAILABILITY_HAS_FILESYSTEM_LIBRARY _LIBCPP_INTRODUCED_IN_LLVM_9 +#define _LIBCPP_AVAILABILITY_FILESYSTEM_LIBRARY _LIBCPP_INTRODUCED_IN_LLVM_9_MARKUP +#define _LIBCPP_AVAILABILITY_FILESYSTEM_LIBRARY_PUSH _LIBCPP_INTRODUCED_IN_LLVM_9_MARKUP_PUSH +#define _LIBCPP_AVAILABILITY_FILESYSTEM_LIBRARY_POP _LIBCPP_INTRODUCED_IN_LLVM_9_MARKUP_POP + +// This controls the availability of the C++20 synchronization library, +// which requires shared library support for various operations +// (see libcxx/src/atomic.cpp). This includes , , +// , and notification functions on std::atomic. +#define _LIBCPP_AVAILABILITY_HAS_SYNC _LIBCPP_INTRODUCED_IN_LLVM_10 +#define _LIBCPP_AVAILABILITY_SYNC _LIBCPP_INTRODUCED_IN_LLVM_10_MARKUP + +// Enable additional explicit instantiations of iostreams components. This +// reduces the number of weak definitions generated in programs that use +// iostreams by providing a single strong definition in the shared library. +// +// TODO: Enable additional explicit instantiations on GCC once it supports exclude_from_explicit_instantiation, +// or once libc++ doesn't use the attribute anymore. +// TODO: Enable them on Windows once https://llvm.org/PR41018 has been fixed. +#if !defined(_LIBCPP_COMPILER_GCC) && !defined(_WIN32) +# define _LIBCPP_AVAILABILITY_HAS_ADDITIONAL_IOSTREAM_EXPLICIT_INSTANTIATIONS_1 _LIBCPP_INTRODUCED_IN_LLVM_12 +#else +# define _LIBCPP_AVAILABILITY_HAS_ADDITIONAL_IOSTREAM_EXPLICIT_INSTANTIATIONS_1 0 +#endif + +// This controls the availability of floating-point std::to_chars functions. +// These overloads were added later than the integer overloads. +#define _LIBCPP_AVAILABILITY_HAS_TO_CHARS_FLOATING_POINT _LIBCPP_INTRODUCED_IN_LLVM_14 +#define _LIBCPP_AVAILABILITY_TO_CHARS_FLOATING_POINT _LIBCPP_INTRODUCED_IN_LLVM_14_MARKUP + +// This controls whether the library claims to provide a default verbose +// termination function, and consequently whether the headers will try +// to use it when the mechanism isn't overriden at compile-time. +#define _LIBCPP_AVAILABILITY_HAS_VERBOSE_ABORT _LIBCPP_INTRODUCED_IN_LLVM_15 +#define _LIBCPP_AVAILABILITY_VERBOSE_ABORT _LIBCPP_INTRODUCED_IN_LLVM_15_MARKUP + +// This controls the availability of the C++17 std::pmr library, +// which is implemented in large part in the built library. +// +// TODO: Enable std::pmr markup once https://github.com/llvm/llvm-project/issues/40340 has been fixed +// Until then, it is possible for folks to try to use `std::pmr` when back-deploying to targets that don't support +// it and it'll be a load-time error, but we don't have a good alternative because the library won't compile if we +// use availability annotations until that bug has been fixed. +#define _LIBCPP_AVAILABILITY_HAS_PMR _LIBCPP_INTRODUCED_IN_LLVM_16 +#define _LIBCPP_AVAILABILITY_PMR + +// These macros controls the availability of __cxa_init_primary_exception +// in the built library, which std::make_exception_ptr might use +// (see libcxx/include/__exception/exception_ptr.h). +#define _LIBCPP_AVAILABILITY_HAS_INIT_PRIMARY_EXCEPTION _LIBCPP_INTRODUCED_IN_LLVM_18 +#define _LIBCPP_AVAILABILITY_INIT_PRIMARY_EXCEPTION _LIBCPP_INTRODUCED_IN_LLVM_18_MARKUP + +// This controls the availability of C++23 , which +// has a dependency on the built library (it needs access to +// the underlying buffer types of std::cout, std::cerr, and std::clog. +#define _LIBCPP_AVAILABILITY_HAS_PRINT _LIBCPP_INTRODUCED_IN_LLVM_18 +#define _LIBCPP_AVAILABILITY_PRINT _LIBCPP_INTRODUCED_IN_LLVM_18_MARKUP + +// This controls the availability of the C++20 time zone database. +// The parser code is built in the library. +#define _LIBCPP_AVAILABILITY_HAS_TZDB _LIBCPP_INTRODUCED_IN_LLVM_19 +#define _LIBCPP_AVAILABILITY_TZDB _LIBCPP_INTRODUCED_IN_LLVM_19_MARKUP + +// These macros determine whether we assume that std::bad_function_call and +// std::bad_expected_access provide a key function in the dylib. This allows +// centralizing their vtable and typeinfo instead of having all TUs provide +// a weak definition that then gets deduplicated. +# define _LIBCPP_AVAILABILITY_HAS_BAD_FUNCTION_CALL_KEY_FUNCTION _LIBCPP_INTRODUCED_IN_LLVM_19 +# define _LIBCPP_AVAILABILITY_BAD_FUNCTION_CALL_KEY_FUNCTION _LIBCPP_INTRODUCED_IN_LLVM_19_MARKUP +# define _LIBCPP_AVAILABILITY_HAS_BAD_EXPECTED_ACCESS_KEY_FUNCTION _LIBCPP_INTRODUCED_IN_LLVM_19 +# define _LIBCPP_AVAILABILITY_BAD_EXPECTED_ACCESS_KEY_FUNCTION _LIBCPP_INTRODUCED_IN_LLVM_19_MARKUP + // Define availability attributes that depend on _LIBCPP_HAS_NO_EXCEPTIONS. // Those are defined in terms of the availability attributes above, and // should not be vendor-specific. diff --git a/libcxx/include/__chrono/formatter.h b/libcxx/include/__chrono/formatter.h index 226fccbee6d1331a7ad75cb6c9a636c4cdb8f78a..e9b81c3de8a700bbf49983a2b5f544585cc922ea 100644 --- a/libcxx/include/__chrono/formatter.h +++ b/libcxx/include/__chrono/formatter.h @@ -88,6 +88,9 @@ __format_sub_seconds(basic_stringstream<_CharT>& __sstr, const chrono::duration< using __duration = chrono::duration<_Rep, _Period>; auto __fraction = __value - chrono::duration_cast(__value); + // Converts a negative fraction to its positive value. + if (__value < chrono::seconds{0} && __fraction != __duration{0}) + __fraction += chrono::seconds{1}; if constexpr (chrono::treat_as_floating_point_v<_Rep>) // When the floating-point value has digits itself they are ignored based // on the wording in [tab:time.format.spec] diff --git a/libcxx/include/__format/escaped_output_table.h b/libcxx/include/__format/escaped_output_table.h index b194f9431c3be33754468192ef29ec25df8096e6..a4c4c366cf241472dd73681506c81a74b9aec965 100644 --- a/libcxx/include/__format/escaped_output_table.h +++ b/libcxx/include/__format/escaped_output_table.h @@ -80,10 +80,9 @@ namespace __escaped_output_table { /// The entries of the characters to escape in format's debug string. /// /// Contains the entries for [format.string.escaped]/2.2.1.2.1 -/// CE is a Unicode encoding and C corresponds to either a UCS scalar value -/// whose Unicode property General_Category has a value in the groups -/// Separator (Z) or Other (C) or to a UCS scalar value which has the Unicode -/// property Grapheme_Extend=Yes, as described by table 12 of UAX #44 +/// CE is a Unicode encoding and C corresponds to a UCS scalar value whose +/// Unicode property General_Category has a value in the groups Separator (Z) +/// or Other (C), as described by table 12 of UAX #44 /// /// Separator (Z) consists of General_Category /// - Space_Separator, @@ -98,7 +97,6 @@ namespace __escaped_output_table { /// - Unassigned. /// /// The data is generated from -/// - https://www.unicode.org/Public/UCD/latest/ucd/DerivedCoreProperties.txt /// - https://www.unicode.org/Public/UCD/latest/ucd/extracted/DerivedGeneralCategory.txt /// /// The table is similar to the table @@ -110,908 +108,1091 @@ namespace __escaped_output_table { /// - bits [0, 10] The size of the range, allowing 2048 elements. /// - bits [11, 31] The lower bound code point of the range. The upper bound of /// the range is lower bound + size. -_LIBCPP_HIDE_FROM_ABI inline constexpr uint32_t __entries[894] = { - 0x00000020, - 0x0003f821, - 0x00056800, - 0x0018006f, - 0x001bc001, - 0x001c0003, - 0x001c5800, - 0x001c6800, - 0x001d1000, - 0x00241806, - 0x00298000, - 0x002ab801, - 0x002c5801, - 0x002c802d, - 0x002df800, - 0x002e0801, - 0x002e2001, - 0x002e3808, - 0x002f5803, - 0x002fa810, - 0x0030800a, - 0x0030e000, - 0x00325814, - 0x00338000, - 0x0036b007, - 0x0036f805, - 0x00373801, - 0x00375003, - 0x00387001, - 0x00388800, - 0x0039801c, - 0x003d300a, - 0x003d900d, - 0x003f5808, - 0x003fd802, - 0x0040b003, - 0x0040d808, - 0x00412802, - 0x00414806, - 0x0041f800, - 0x0042c804, - 0x0042f800, - 0x00435804, - 0x00447810, - 0x00465038, - 0x0049d000, - 0x0049e000, - 0x004a0807, - 0x004a6800, - 0x004a8806, - 0x004b1001, - 0x004c0800, - 0x004c2000, - 0x004c6801, - 0x004c8801, - 0x004d4800, - 0x004d8800, - 0x004d9802, - 0x004dd002, - 0x004df000, - 0x004e0805, - 0x004e4801, - 0x004e6800, - 0x004e780c, - 0x004ef000, - 0x004f1003, - 0x004ff004, - 0x00502000, - 0x00505803, - 0x00508801, - 0x00514800, - 0x00518800, - 0x0051a000, - 0x0051b800, - 0x0051d003, - 0x00520817, - 0x0052e800, - 0x0052f806, - 0x00538001, - 0x0053a800, - 0x0053b80b, - 0x00542000, - 0x00547000, - 0x00549000, - 0x00554800, - 0x00558800, - 0x0055a000, - 0x0055d002, - 0x00560807, - 0x00565000, - 0x00566802, - 0x0056880e, - 0x00571003, - 0x00579006, - 0x0057d007, - 0x00582000, - 0x00586801, - 0x00588801, - 0x00594800, - 0x00598800, - 0x0059a000, - 0x0059d002, - 0x0059f001, - 0x005a0805, - 0x005a4801, - 0x005a680e, - 0x005af000, - 0x005b1003, - 0x005bc00a, - 0x005c2000, - 0x005c5802, - 0x005c8800, - 0x005cb002, - 0x005cd800, - 0x005ce800, - 0x005d0002, - 0x005d2802, - 0x005d5802, - 0x005dd004, - 0x005e0000, - 0x005e1802, - 0x005e4800, - 0x005e6802, - 0x005e8814, - 0x005fd805, - 0x00602000, - 0x00606800, - 0x00608800, - 0x00614800, - 0x0061d002, - 0x0061f002, - 0x00622812, - 0x0062d801, - 0x0062f001, - 0x00631003, - 0x00638006, - 0x00640800, - 0x00646800, - 0x00648800, - 0x00654800, - 0x0065a000, - 0x0065d002, - 0x0065f800, - 0x00661000, - 0x00662801, - 0x00664800, - 0x00666010, - 0x0066f800, - 0x00671003, - 0x00678000, - 0x0067a00d, - 0x00686800, - 0x00688800, - 0x0069d801, - 0x0069f000, - 0x006a0804, - 0x006a4800, - 0x006a6800, - 0x006a8003, - 0x006ab800, - 0x006b1003, - 0x006c0001, - 0x006c2000, - 0x006cb802, - 0x006d9000, - 0x006de000, - 0x006df001, - 0x006e3808, - 0x006e9005, - 0x006ef806, - 0x006f8001, - 0x006fa80b, - 0x00718800, - 0x0071a00a, - 0x00723807, - 0x0072e024, - 0x00741800, - 0x00742800, - 0x00745800, - 0x00752000, - 0x00753000, - 0x00758800, - 0x0075a008, - 0x0075f001, - 0x00762800, - 0x00763808, - 0x0076d001, - 0x0077001f, - 0x0078c001, - 0x0079a800, - 0x0079b800, - 0x0079c800, - 0x007a4000, - 0x007b6811, - 0x007c0004, - 0x007c3001, - 0x007c6830, - 0x007e3000, - 0x007e6800, - 0x007ed824, - 0x00816803, - 0x00819005, - 0x0081c801, - 0x0081e801, - 0x0082c001, - 0x0082f002, - 0x00838803, - 0x00841000, - 0x00842801, - 0x00846800, - 0x0084e800, - 0x00863000, - 0x00864004, - 0x00867001, - 0x00924800, - 0x00927001, - 0x0092b800, - 0x0092c800, - 0x0092f001, - 0x00944800, - 0x00947001, - 0x00958800, - 0x0095b001, - 0x0095f800, - 0x00960800, - 0x00963001, - 0x0096b800, - 0x00988800, - 0x0098b001, - 0x009ad804, - 0x009be802, - 0x009cd005, - 0x009fb001, - 0x009ff001, - 0x00b40000, - 0x00b4e802, - 0x00b7c806, - 0x00b89002, - 0x00b8b008, - 0x00b99001, - 0x00b9b808, - 0x00ba900d, - 0x00bb6800, - 0x00bb880e, - 0x00bda001, - 0x00bdb806, - 0x00be3000, - 0x00be480a, - 0x00bee802, - 0x00bf5005, - 0x00bfd005, - 0x00c05804, - 0x00c0d005, - 0x00c3c806, - 0x00c42801, - 0x00c54800, - 0x00c55804, - 0x00c7b009, - 0x00c8f803, - 0x00c93801, - 0x00c96003, - 0x00c99000, - 0x00c9c806, - 0x00ca0802, - 0x00cb7001, - 0x00cba80a, - 0x00cd6003, - 0x00ce5005, - 0x00ced802, - 0x00d0b801, - 0x00d0d802, - 0x00d2b000, - 0x00d2c008, - 0x00d31000, - 0x00d32807, - 0x00d3980c, - 0x00d45005, - 0x00d4d005, - 0x00d57055, - 0x00d9a006, - 0x00d9e000, - 0x00da1000, - 0x00da6802, - 0x00db5808, - 0x00dbf802, - 0x00dd1003, - 0x00dd4001, - 0x00dd5802, - 0x00df3000, - 0x00df4001, - 0x00df6800, - 0x00df7802, - 0x00dfa007, - 0x00e16007, - 0x00e1b004, - 0x00e25002, - 0x00e44806, - 0x00e5d801, - 0x00e6400a, - 0x00e6a00c, - 0x00e71006, - 0x00e76800, - 0x00e7a000, - 0x00e7c001, - 0x00e7d804, - 0x00ee003f, - 0x00f8b001, - 0x00f8f001, - 0x00fa3001, - 0x00fa7001, - 0x00fac000, - 0x00fad000, - 0x00fae000, - 0x00faf000, - 0x00fbf001, - 0x00fda800, - 0x00fe2800, - 0x00fea001, - 0x00fee000, - 0x00ff8001, - 0x00ffa800, - 0x00fff810, - 0x01014007, - 0x0102f810, - 0x01039001, - 0x01047800, - 0x0104e802, - 0x0106083e, - 0x010c6003, - 0x01213818, - 0x01225814, - 0x015ba001, - 0x015cb000, - 0x01677802, - 0x0167a004, - 0x01693000, - 0x01694004, - 0x01697001, - 0x016b4006, - 0x016b880e, - 0x016cb808, - 0x016d3800, - 0x016d7800, - 0x016db800, - 0x016df800, - 0x016e3800, - 0x016e7800, - 0x016eb800, - 0x016ef820, - 0x0172f021, - 0x0174d000, - 0x0177a00b, - 0x017eb019, - 0x01800000, - 0x01815005, - 0x01820000, - 0x0184b803, - 0x01880004, - 0x01898000, - 0x018c7800, - 0x018f200a, - 0x0190f800, - 0x05246802, - 0x05263808, - 0x05316013, - 0x05337803, - 0x0533a009, - 0x0534f001, - 0x05378001, - 0x0537c007, - 0x053e5804, - 0x053e9000, - 0x053ea000, - 0x053ed017, - 0x05401000, - 0x05403000, - 0x05405800, - 0x05412801, - 0x05416003, - 0x0541d005, - 0x0543c007, - 0x05462009, - 0x0546d017, - 0x0547f800, - 0x05493007, - 0x054a380a, - 0x054aa00a, - 0x054be805, - 0x054d9800, - 0x054db003, - 0x054de001, - 0x054e7000, - 0x054ed003, - 0x054f2800, - 0x054ff800, - 0x05514805, - 0x05518801, - 0x0551a80a, - 0x05521800, - 0x05526000, - 0x05527001, - 0x0552d001, - 0x0553e000, - 0x05558000, - 0x05559002, - 0x0555b801, - 0x0555f001, - 0x05560800, - 0x05561817, - 0x05576001, - 0x0557b00a, - 0x05583801, - 0x05587801, - 0x0558b808, - 0x05593800, - 0x05597800, - 0x055b6003, - 0x055f2800, - 0x055f4000, - 0x055f6802, - 0x055fd005, - 0x06bd200b, - 0x06be3803, - 0x06bfe7ff, - 0x06ffe7ff, - 0x073fe7ff, - 0x077fe7ff, - 0x07bfe103, - 0x07d37001, - 0x07d6d025, - 0x07d8380b, - 0x07d8c004, - 0x07d8f000, - 0x07d9b800, - 0x07d9e800, - 0x07d9f800, - 0x07da1000, - 0x07da2800, - 0x07de180f, - 0x07ec8001, - 0x07ee4006, - 0x07ee801f, - 0x07f0000f, - 0x07f0d015, - 0x07f29800, - 0x07f33800, - 0x07f36003, - 0x07f3a800, - 0x07f7e803, - 0x07fcf001, - 0x07fdf802, - 0x07fe4001, - 0x07fe8001, - 0x07fec001, - 0x07fee802, - 0x07ff3800, - 0x07ff780c, - 0x07fff001, - 0x08006000, - 0x08013800, - 0x0801d800, - 0x0801f000, - 0x08027001, - 0x0802f021, - 0x0807d804, - 0x08081803, - 0x0809a002, - 0x080c7800, - 0x080ce802, - 0x080d082e, - 0x080fe882, - 0x0814e802, - 0x0816880f, - 0x0817e003, - 0x08192008, - 0x081a5804, - 0x081bb009, - 0x081cf000, - 0x081e2003, - 0x081eb029, - 0x0824f001, - 0x08255005, - 0x0826a003, - 0x0827e003, - 0x08294007, - 0x082b200a, - 0x082bd800, - 0x082c5800, - 0x082c9800, - 0x082cb000, - 0x082d1000, - 0x082d9000, - 0x082dd000, - 0x082de842, - 0x0839b808, - 0x083ab009, - 0x083b4017, - 0x083c3000, - 0x083d8800, - 0x083dd844, - 0x08403001, - 0x08404800, - 0x0841b000, - 0x0841c802, - 0x0841e801, - 0x0842b000, - 0x0844f807, - 0x0845802f, - 0x08479800, - 0x0847b004, - 0x0848e002, - 0x0849d004, - 0x084a003f, - 0x084dc003, - 0x084e8001, - 0x0850080e, - 0x0850a000, - 0x0850c000, - 0x0851b009, - 0x08524806, - 0x0852c806, - 0x0855001f, - 0x08572805, - 0x0857b808, - 0x0859b002, - 0x085ab001, - 0x085b9804, - 0x085c9006, - 0x085ce80b, - 0x085d804f, - 0x08624836, - 0x0865980c, - 0x08679806, - 0x0869200b, - 0x0869d125, - 0x0873f800, - 0x08755002, - 0x08757001, - 0x0875904d, - 0x08794007, - 0x087a300a, - 0x087ad015, - 0x087c1003, - 0x087c5025, - 0x087e6013, - 0x087fb808, - 0x08800800, - 0x0881c00e, - 0x08827003, - 0x08838000, - 0x08839801, - 0x0883b00b, - 0x08859803, - 0x0885c801, - 0x0885e800, - 0x0886100d, - 0x08874806, - 0x0887d008, - 0x08893804, - 0x08896808, - 0x088a4007, - 0x088b9800, - 0x088bb80a, - 0x088db008, - 0x088e4803, - 0x088e7800, - 0x088f0000, - 0x088fa80a, - 0x08909000, - 0x08917802, - 0x0891a000, - 0x0891b001, - 0x0891f000, - 0x0892083e, - 0x08943800, - 0x08944800, - 0x08947000, - 0x0894f000, - 0x08955005, - 0x0896f800, - 0x0897180c, - 0x0897d007, - 0x08982000, - 0x08986801, - 0x08988801, - 0x08994800, - 0x08998800, - 0x0899a000, - 0x0899d002, - 0x0899f000, - 0x089a0000, - 0x089a2801, - 0x089a4801, - 0x089a7001, - 0x089a880b, - 0x089b209b, - 0x08a1c007, - 0x08a21002, - 0x08a23000, - 0x08a2e000, - 0x08a2f000, - 0x08a3101d, - 0x08a58000, - 0x08a59805, - 0x08a5d000, - 0x08a5e800, - 0x08a5f801, - 0x08a61001, - 0x08a64007, - 0x08a6d0a5, - 0x08ad7800, - 0x08ad9005, - 0x08ade001, - 0x08adf801, - 0x08aee023, - 0x08b19807, - 0x08b1e800, - 0x08b1f801, - 0x08b2280a, - 0x08b2d005, - 0x08b36812, - 0x08b55800, - 0x08b56800, - 0x08b58005, - 0x08b5b800, - 0x08b5d005, - 0x08b65035, - 0x08b8d804, - 0x08b91003, - 0x08b93808, - 0x08ba38b8, - 0x08c17808, - 0x08c1c801, - 0x08c1e063, - 0x08c7980b, - 0x08c83801, - 0x08c85001, - 0x08c8a000, - 0x08c8b800, - 0x08c98000, - 0x08c9b000, - 0x08c9c803, - 0x08c9f000, - 0x08ca1800, - 0x08ca3808, - 0x08cad045, - 0x08cd4001, - 0x08cea007, - 0x08cf0000, - 0x08cf281a, - 0x08d00809, - 0x08d19805, - 0x08d1d803, - 0x08d23808, - 0x08d28805, - 0x08d2c802, - 0x08d4500c, - 0x08d4c001, - 0x08d5180c, - 0x08d7c806, - 0x08d850f5, - 0x08e04800, - 0x08e1800d, - 0x08e1f800, - 0x08e23009, - 0x08e36802, - 0x08e48018, - 0x08e55006, - 0x08e59001, - 0x08e5a84a, - 0x08e83800, - 0x08e85000, - 0x08e98814, - 0x08ea3808, - 0x08ead005, - 0x08eb3000, - 0x08eb4800, - 0x08ec7803, - 0x08eca800, - 0x08ecb800, - 0x08ecc806, - 0x08ed5135, - 0x08f79801, - 0x08f7c808, - 0x08f88800, - 0x08f9b007, - 0x08fa0000, - 0x08fa1000, - 0x08fad055, - 0x08fd880e, - 0x08ff900c, - 0x091cd065, - 0x09237800, - 0x0923a80a, - 0x092a27ff, - 0x096a224b, - 0x097f980c, - 0x09a18010, - 0x09a23fff, - 0x09e23fb8, - 0x0a323fff, - 0x0a723fff, - 0x0ab23fff, - 0x0af23fff, - 0x0b3239b8, - 0x0b51c806, - 0x0b52f800, - 0x0b535003, - 0x0b55f800, - 0x0b565005, - 0x0b577006, - 0x0b57b009, - 0x0b598006, - 0x0b5a3009, - 0x0b5ad000, - 0x0b5b1000, - 0x0b5bc004, - 0x0b5c82af, - 0x0b74d864, - 0x0b7a5804, - 0x0b7c400a, - 0x0b7d003f, - 0x0b7f200b, - 0x0b7f900d, - 0x0c3fc007, - 0x0c66b029, - 0x0c684fff, - 0x0ca84fff, - 0x0ce84fff, - 0x0d284fff, - 0x0d684ae6, - 0x0d7fa000, - 0x0d7fe000, - 0x0d7ff800, - 0x0d89180e, - 0x0d89981c, - 0x0d8a9801, - 0x0d8ab00d, - 0x0d8b4007, - 0x0d97e7ff, - 0x0dd7e103, - 0x0de35804, - 0x0de3e802, - 0x0de44806, - 0x0de4d001, - 0x0de4e801, - 0x0de507ff, - 0x0e2507ff, - 0x0e6502af, - 0x0e7e203b, - 0x0e87b009, - 0x0e893801, - 0x0e8b2800, - 0x0e8b3802, - 0x0e8b7014, - 0x0e8c2806, - 0x0e8d5003, - 0x0e8f5814, - 0x0e921002, - 0x0e923079, - 0x0e96a00b, - 0x0e97a00b, - 0x0e9ab808, - 0x0e9bc886, - 0x0ea2a800, - 0x0ea4e800, - 0x0ea50001, - 0x0ea51801, - 0x0ea53801, - 0x0ea56800, - 0x0ea5d000, - 0x0ea5e000, - 0x0ea62000, - 0x0ea83000, - 0x0ea85801, - 0x0ea8a800, - 0x0ea8e800, - 0x0ea9d000, - 0x0ea9f800, - 0x0eaa2800, - 0x0eaa3802, - 0x0eaa8800, - 0x0eb53001, - 0x0ebe6001, - 0x0ed00036, - 0x0ed1d831, - 0x0ed3a800, - 0x0ed42000, - 0x0ed46473, - 0x0ef8f805, - 0x0ef95904, - 0x0f037091, - 0x0f096809, - 0x0f09f001, - 0x0f0a5003, - 0x0f0a813f, - 0x0f157011, - 0x0f176003, - 0x0f17d004, - 0x0f1801cf, - 0x0f276003, - 0x0f27d2e5, - 0x0f3f3800, - 0x0f3f6000, - 0x0f3f7800, - 0x0f3ff800, - 0x0f462801, - 0x0f46802f, - 0x0f4a2006, - 0x0f4a6003, - 0x0f4ad003, - 0x0f4b0310, - 0x0f65a84b, - 0x0f69f0c1, - 0x0f702000, - 0x0f710000, - 0x0f711800, - 0x0f712801, - 0x0f714000, - 0x0f719800, - 0x0f71c000, - 0x0f71d000, - 0x0f71e005, - 0x0f721803, - 0x0f724000, - 0x0f725000, - 0x0f726000, - 0x0f728000, - 0x0f729800, - 0x0f72a801, - 0x0f72c000, - 0x0f72d000, - 0x0f72e000, - 0x0f72f000, - 0x0f730000, - 0x0f731800, - 0x0f732801, - 0x0f735800, - 0x0f739800, - 0x0f73c000, - 0x0f73e800, - 0x0f73f800, - 0x0f745000, - 0x0f74e004, - 0x0f752000, - 0x0f755000, - 0x0f75e033, - 0x0f77910d, - 0x0f816003, - 0x0f84a00b, - 0x0f857801, - 0x0f860000, - 0x0f868000, - 0x0f87b009, - 0x0f8d7037, - 0x0f90180c, - 0x0f91e003, - 0x0f924806, - 0x0f92900d, - 0x0f933099, - 0x0fb6c003, - 0x0fb76802, - 0x0fb7e802, - 0x0fbbb803, - 0x0fbed005, - 0x0fbf6003, - 0x0fbf880e, - 0x0fc06003, - 0x0fc24007, - 0x0fc2d005, - 0x0fc44007, - 0x0fc57001, - 0x0fc5904d, - 0x0fd2a00b, - 0x0fd37001, - 0x0fd3e802, - 0x0fd44806, - 0x0fd5f000, - 0x0fd63007, - 0x0fd6e003, - 0x0fd74806, - 0x0fd7c806, - 0x0fdc9800, - 0x0fde5824, - 0x0fdfd405, - 0x1537001f, - 0x15b9d005, - 0x15c0f001, - 0x1675100d, - 0x175f080e, - 0x1772f7ff, - 0x17b2f1a1, - 0x17d0f5e1, - 0x189a5804}; +_LIBCPP_HIDE_FROM_ABI inline constexpr uint32_t __entries[1077] = { + 0x00000020 /* 00000000 - 00000020 [ 33] */, + 0x0003f821 /* 0000007f - 000000a0 [ 34] */, + 0x00056800 /* 000000ad - 000000ad [ 1] */, + 0x001bc001 /* 00000378 - 00000379 [ 2] */, + 0x001c0003 /* 00000380 - 00000383 [ 4] */, + 0x001c5800 /* 0000038b - 0000038b [ 1] */, + 0x001c6800 /* 0000038d - 0000038d [ 1] */, + 0x001d1000 /* 000003a2 - 000003a2 [ 1] */, + 0x00298000 /* 00000530 - 00000530 [ 1] */, + 0x002ab801 /* 00000557 - 00000558 [ 2] */, + 0x002c5801 /* 0000058b - 0000058c [ 2] */, + 0x002c8000 /* 00000590 - 00000590 [ 1] */, + 0x002e4007 /* 000005c8 - 000005cf [ 8] */, + 0x002f5803 /* 000005eb - 000005ee [ 4] */, + 0x002fa810 /* 000005f5 - 00000605 [ 17] */, + 0x0030e000 /* 0000061c - 0000061c [ 1] */, + 0x0036e800 /* 000006dd - 000006dd [ 1] */, + 0x00387001 /* 0000070e - 0000070f [ 2] */, + 0x003a5801 /* 0000074b - 0000074c [ 2] */, + 0x003d900d /* 000007b2 - 000007bf [ 14] */, + 0x003fd801 /* 000007fb - 000007fc [ 2] */, + 0x00417001 /* 0000082e - 0000082f [ 2] */, + 0x0041f800 /* 0000083f - 0000083f [ 1] */, + 0x0042e001 /* 0000085c - 0000085d [ 2] */, + 0x0042f800 /* 0000085f - 0000085f [ 1] */, + 0x00435804 /* 0000086b - 0000086f [ 5] */, + 0x00447808 /* 0000088f - 00000897 [ 9] */, + 0x00471000 /* 000008e2 - 000008e2 [ 1] */, + 0x004c2000 /* 00000984 - 00000984 [ 1] */, + 0x004c6801 /* 0000098d - 0000098e [ 2] */, + 0x004c8801 /* 00000991 - 00000992 [ 2] */, + 0x004d4800 /* 000009a9 - 000009a9 [ 1] */, + 0x004d8800 /* 000009b1 - 000009b1 [ 1] */, + 0x004d9802 /* 000009b3 - 000009b5 [ 3] */, + 0x004dd001 /* 000009ba - 000009bb [ 2] */, + 0x004e2801 /* 000009c5 - 000009c6 [ 2] */, + 0x004e4801 /* 000009c9 - 000009ca [ 2] */, + 0x004e7807 /* 000009cf - 000009d6 [ 8] */, + 0x004ec003 /* 000009d8 - 000009db [ 4] */, + 0x004ef000 /* 000009de - 000009de [ 1] */, + 0x004f2001 /* 000009e4 - 000009e5 [ 2] */, + 0x004ff801 /* 000009ff - 00000a00 [ 2] */, + 0x00502000 /* 00000a04 - 00000a04 [ 1] */, + 0x00505803 /* 00000a0b - 00000a0e [ 4] */, + 0x00508801 /* 00000a11 - 00000a12 [ 2] */, + 0x00514800 /* 00000a29 - 00000a29 [ 1] */, + 0x00518800 /* 00000a31 - 00000a31 [ 1] */, + 0x0051a000 /* 00000a34 - 00000a34 [ 1] */, + 0x0051b800 /* 00000a37 - 00000a37 [ 1] */, + 0x0051d001 /* 00000a3a - 00000a3b [ 2] */, + 0x0051e800 /* 00000a3d - 00000a3d [ 1] */, + 0x00521803 /* 00000a43 - 00000a46 [ 4] */, + 0x00524801 /* 00000a49 - 00000a4a [ 2] */, + 0x00527002 /* 00000a4e - 00000a50 [ 3] */, + 0x00529006 /* 00000a52 - 00000a58 [ 7] */, + 0x0052e800 /* 00000a5d - 00000a5d [ 1] */, + 0x0052f806 /* 00000a5f - 00000a65 [ 7] */, + 0x0053b809 /* 00000a77 - 00000a80 [ 10] */, + 0x00542000 /* 00000a84 - 00000a84 [ 1] */, + 0x00547000 /* 00000a8e - 00000a8e [ 1] */, + 0x00549000 /* 00000a92 - 00000a92 [ 1] */, + 0x00554800 /* 00000aa9 - 00000aa9 [ 1] */, + 0x00558800 /* 00000ab1 - 00000ab1 [ 1] */, + 0x0055a000 /* 00000ab4 - 00000ab4 [ 1] */, + 0x0055d001 /* 00000aba - 00000abb [ 2] */, + 0x00563000 /* 00000ac6 - 00000ac6 [ 1] */, + 0x00565000 /* 00000aca - 00000aca [ 1] */, + 0x00567001 /* 00000ace - 00000acf [ 2] */, + 0x0056880e /* 00000ad1 - 00000adf [ 15] */, + 0x00572001 /* 00000ae4 - 00000ae5 [ 2] */, + 0x00579006 /* 00000af2 - 00000af8 [ 7] */, + 0x00580000 /* 00000b00 - 00000b00 [ 1] */, + 0x00582000 /* 00000b04 - 00000b04 [ 1] */, + 0x00586801 /* 00000b0d - 00000b0e [ 2] */, + 0x00588801 /* 00000b11 - 00000b12 [ 2] */, + 0x00594800 /* 00000b29 - 00000b29 [ 1] */, + 0x00598800 /* 00000b31 - 00000b31 [ 1] */, + 0x0059a000 /* 00000b34 - 00000b34 [ 1] */, + 0x0059d001 /* 00000b3a - 00000b3b [ 2] */, + 0x005a2801 /* 00000b45 - 00000b46 [ 2] */, + 0x005a4801 /* 00000b49 - 00000b4a [ 2] */, + 0x005a7006 /* 00000b4e - 00000b54 [ 7] */, + 0x005ac003 /* 00000b58 - 00000b5b [ 4] */, + 0x005af000 /* 00000b5e - 00000b5e [ 1] */, + 0x005b2001 /* 00000b64 - 00000b65 [ 2] */, + 0x005bc009 /* 00000b78 - 00000b81 [ 10] */, + 0x005c2000 /* 00000b84 - 00000b84 [ 1] */, + 0x005c5802 /* 00000b8b - 00000b8d [ 3] */, + 0x005c8800 /* 00000b91 - 00000b91 [ 1] */, + 0x005cb002 /* 00000b96 - 00000b98 [ 3] */, + 0x005cd800 /* 00000b9b - 00000b9b [ 1] */, + 0x005ce800 /* 00000b9d - 00000b9d [ 1] */, + 0x005d0002 /* 00000ba0 - 00000ba2 [ 3] */, + 0x005d2802 /* 00000ba5 - 00000ba7 [ 3] */, + 0x005d5802 /* 00000bab - 00000bad [ 3] */, + 0x005dd003 /* 00000bba - 00000bbd [ 4] */, + 0x005e1802 /* 00000bc3 - 00000bc5 [ 3] */, + 0x005e4800 /* 00000bc9 - 00000bc9 [ 1] */, + 0x005e7001 /* 00000bce - 00000bcf [ 2] */, + 0x005e8805 /* 00000bd1 - 00000bd6 [ 6] */, + 0x005ec00d /* 00000bd8 - 00000be5 [ 14] */, + 0x005fd804 /* 00000bfb - 00000bff [ 5] */, + 0x00606800 /* 00000c0d - 00000c0d [ 1] */, + 0x00608800 /* 00000c11 - 00000c11 [ 1] */, + 0x00614800 /* 00000c29 - 00000c29 [ 1] */, + 0x0061d001 /* 00000c3a - 00000c3b [ 2] */, + 0x00622800 /* 00000c45 - 00000c45 [ 1] */, + 0x00624800 /* 00000c49 - 00000c49 [ 1] */, + 0x00627006 /* 00000c4e - 00000c54 [ 7] */, + 0x0062b800 /* 00000c57 - 00000c57 [ 1] */, + 0x0062d801 /* 00000c5b - 00000c5c [ 2] */, + 0x0062f001 /* 00000c5e - 00000c5f [ 2] */, + 0x00632001 /* 00000c64 - 00000c65 [ 2] */, + 0x00638006 /* 00000c70 - 00000c76 [ 7] */, + 0x00646800 /* 00000c8d - 00000c8d [ 1] */, + 0x00648800 /* 00000c91 - 00000c91 [ 1] */, + 0x00654800 /* 00000ca9 - 00000ca9 [ 1] */, + 0x0065a000 /* 00000cb4 - 00000cb4 [ 1] */, + 0x0065d001 /* 00000cba - 00000cbb [ 2] */, + 0x00662800 /* 00000cc5 - 00000cc5 [ 1] */, + 0x00664800 /* 00000cc9 - 00000cc9 [ 1] */, + 0x00667006 /* 00000cce - 00000cd4 [ 7] */, + 0x0066b805 /* 00000cd7 - 00000cdc [ 6] */, + 0x0066f800 /* 00000cdf - 00000cdf [ 1] */, + 0x00672001 /* 00000ce4 - 00000ce5 [ 2] */, + 0x00678000 /* 00000cf0 - 00000cf0 [ 1] */, + 0x0067a00b /* 00000cf4 - 00000cff [ 12] */, + 0x00686800 /* 00000d0d - 00000d0d [ 1] */, + 0x00688800 /* 00000d11 - 00000d11 [ 1] */, + 0x006a2800 /* 00000d45 - 00000d45 [ 1] */, + 0x006a4800 /* 00000d49 - 00000d49 [ 1] */, + 0x006a8003 /* 00000d50 - 00000d53 [ 4] */, + 0x006b2001 /* 00000d64 - 00000d65 [ 2] */, + 0x006c0000 /* 00000d80 - 00000d80 [ 1] */, + 0x006c2000 /* 00000d84 - 00000d84 [ 1] */, + 0x006cb802 /* 00000d97 - 00000d99 [ 3] */, + 0x006d9000 /* 00000db2 - 00000db2 [ 1] */, + 0x006de000 /* 00000dbc - 00000dbc [ 1] */, + 0x006df001 /* 00000dbe - 00000dbf [ 2] */, + 0x006e3802 /* 00000dc7 - 00000dc9 [ 3] */, + 0x006e5803 /* 00000dcb - 00000dce [ 4] */, + 0x006ea800 /* 00000dd5 - 00000dd5 [ 1] */, + 0x006eb800 /* 00000dd7 - 00000dd7 [ 1] */, + 0x006f0005 /* 00000de0 - 00000de5 [ 6] */, + 0x006f8001 /* 00000df0 - 00000df1 [ 2] */, + 0x006fa80b /* 00000df5 - 00000e00 [ 12] */, + 0x0071d803 /* 00000e3b - 00000e3e [ 4] */, + 0x0072e024 /* 00000e5c - 00000e80 [ 37] */, + 0x00741800 /* 00000e83 - 00000e83 [ 1] */, + 0x00742800 /* 00000e85 - 00000e85 [ 1] */, + 0x00745800 /* 00000e8b - 00000e8b [ 1] */, + 0x00752000 /* 00000ea4 - 00000ea4 [ 1] */, + 0x00753000 /* 00000ea6 - 00000ea6 [ 1] */, + 0x0075f001 /* 00000ebe - 00000ebf [ 2] */, + 0x00762800 /* 00000ec5 - 00000ec5 [ 1] */, + 0x00763800 /* 00000ec7 - 00000ec7 [ 1] */, + 0x00767800 /* 00000ecf - 00000ecf [ 1] */, + 0x0076d001 /* 00000eda - 00000edb [ 2] */, + 0x0077001f /* 00000ee0 - 00000eff [ 32] */, + 0x007a4000 /* 00000f48 - 00000f48 [ 1] */, + 0x007b6803 /* 00000f6d - 00000f70 [ 4] */, + 0x007cc000 /* 00000f98 - 00000f98 [ 1] */, + 0x007de800 /* 00000fbd - 00000fbd [ 1] */, + 0x007e6800 /* 00000fcd - 00000fcd [ 1] */, + 0x007ed824 /* 00000fdb - 00000fff [ 37] */, + 0x00863000 /* 000010c6 - 000010c6 [ 1] */, + 0x00864004 /* 000010c8 - 000010cc [ 5] */, + 0x00867001 /* 000010ce - 000010cf [ 2] */, + 0x00924800 /* 00001249 - 00001249 [ 1] */, + 0x00927001 /* 0000124e - 0000124f [ 2] */, + 0x0092b800 /* 00001257 - 00001257 [ 1] */, + 0x0092c800 /* 00001259 - 00001259 [ 1] */, + 0x0092f001 /* 0000125e - 0000125f [ 2] */, + 0x00944800 /* 00001289 - 00001289 [ 1] */, + 0x00947001 /* 0000128e - 0000128f [ 2] */, + 0x00958800 /* 000012b1 - 000012b1 [ 1] */, + 0x0095b001 /* 000012b6 - 000012b7 [ 2] */, + 0x0095f800 /* 000012bf - 000012bf [ 1] */, + 0x00960800 /* 000012c1 - 000012c1 [ 1] */, + 0x00963001 /* 000012c6 - 000012c7 [ 2] */, + 0x0096b800 /* 000012d7 - 000012d7 [ 1] */, + 0x00988800 /* 00001311 - 00001311 [ 1] */, + 0x0098b001 /* 00001316 - 00001317 [ 2] */, + 0x009ad801 /* 0000135b - 0000135c [ 2] */, + 0x009be802 /* 0000137d - 0000137f [ 3] */, + 0x009cd005 /* 0000139a - 0000139f [ 6] */, + 0x009fb001 /* 000013f6 - 000013f7 [ 2] */, + 0x009ff001 /* 000013fe - 000013ff [ 2] */, + 0x00b40000 /* 00001680 - 00001680 [ 1] */, + 0x00b4e802 /* 0000169d - 0000169f [ 3] */, + 0x00b7c806 /* 000016f9 - 000016ff [ 7] */, + 0x00b8b008 /* 00001716 - 0000171e [ 9] */, + 0x00b9b808 /* 00001737 - 0000173f [ 9] */, + 0x00baa00b /* 00001754 - 0000175f [ 12] */, + 0x00bb6800 /* 0000176d - 0000176d [ 1] */, + 0x00bb8800 /* 00001771 - 00001771 [ 1] */, + 0x00bba00b /* 00001774 - 0000177f [ 12] */, + 0x00bef001 /* 000017de - 000017df [ 2] */, + 0x00bf5005 /* 000017ea - 000017ef [ 6] */, + 0x00bfd005 /* 000017fa - 000017ff [ 6] */, + 0x00c07000 /* 0000180e - 0000180e [ 1] */, + 0x00c0d005 /* 0000181a - 0000181f [ 6] */, + 0x00c3c806 /* 00001879 - 0000187f [ 7] */, + 0x00c55804 /* 000018ab - 000018af [ 5] */, + 0x00c7b009 /* 000018f6 - 000018ff [ 10] */, + 0x00c8f800 /* 0000191f - 0000191f [ 1] */, + 0x00c96003 /* 0000192c - 0000192f [ 4] */, + 0x00c9e003 /* 0000193c - 0000193f [ 4] */, + 0x00ca0802 /* 00001941 - 00001943 [ 3] */, + 0x00cb7001 /* 0000196e - 0000196f [ 2] */, + 0x00cba80a /* 00001975 - 0000197f [ 11] */, + 0x00cd6003 /* 000019ac - 000019af [ 4] */, + 0x00ce5005 /* 000019ca - 000019cf [ 6] */, + 0x00ced802 /* 000019db - 000019dd [ 3] */, + 0x00d0e001 /* 00001a1c - 00001a1d [ 2] */, + 0x00d2f800 /* 00001a5f - 00001a5f [ 1] */, + 0x00d3e801 /* 00001a7d - 00001a7e [ 2] */, + 0x00d45005 /* 00001a8a - 00001a8f [ 6] */, + 0x00d4d005 /* 00001a9a - 00001a9f [ 6] */, + 0x00d57001 /* 00001aae - 00001aaf [ 2] */, + 0x00d67830 /* 00001acf - 00001aff [ 49] */, + 0x00da6802 /* 00001b4d - 00001b4f [ 3] */, + 0x00dbf800 /* 00001b7f - 00001b7f [ 1] */, + 0x00dfa007 /* 00001bf4 - 00001bfb [ 8] */, + 0x00e1c002 /* 00001c38 - 00001c3a [ 3] */, + 0x00e25002 /* 00001c4a - 00001c4c [ 3] */, + 0x00e44806 /* 00001c89 - 00001c8f [ 7] */, + 0x00e5d801 /* 00001cbb - 00001cbc [ 2] */, + 0x00e64007 /* 00001cc8 - 00001ccf [ 8] */, + 0x00e7d804 /* 00001cfb - 00001cff [ 5] */, + 0x00f8b001 /* 00001f16 - 00001f17 [ 2] */, + 0x00f8f001 /* 00001f1e - 00001f1f [ 2] */, + 0x00fa3001 /* 00001f46 - 00001f47 [ 2] */, + 0x00fa7001 /* 00001f4e - 00001f4f [ 2] */, + 0x00fac000 /* 00001f58 - 00001f58 [ 1] */, + 0x00fad000 /* 00001f5a - 00001f5a [ 1] */, + 0x00fae000 /* 00001f5c - 00001f5c [ 1] */, + 0x00faf000 /* 00001f5e - 00001f5e [ 1] */, + 0x00fbf001 /* 00001f7e - 00001f7f [ 2] */, + 0x00fda800 /* 00001fb5 - 00001fb5 [ 1] */, + 0x00fe2800 /* 00001fc5 - 00001fc5 [ 1] */, + 0x00fea001 /* 00001fd4 - 00001fd5 [ 2] */, + 0x00fee000 /* 00001fdc - 00001fdc [ 1] */, + 0x00ff8001 /* 00001ff0 - 00001ff1 [ 2] */, + 0x00ffa800 /* 00001ff5 - 00001ff5 [ 1] */, + 0x00fff810 /* 00001fff - 0000200f [ 17] */, + 0x01014007 /* 00002028 - 0000202f [ 8] */, + 0x0102f810 /* 0000205f - 0000206f [ 17] */, + 0x01039001 /* 00002072 - 00002073 [ 2] */, + 0x01047800 /* 0000208f - 0000208f [ 1] */, + 0x0104e802 /* 0000209d - 0000209f [ 3] */, + 0x0106080e /* 000020c1 - 000020cf [ 15] */, + 0x0107880e /* 000020f1 - 000020ff [ 15] */, + 0x010c6003 /* 0000218c - 0000218f [ 4] */, + 0x01213818 /* 00002427 - 0000243f [ 25] */, + 0x01225814 /* 0000244b - 0000245f [ 21] */, + 0x015ba001 /* 00002b74 - 00002b75 [ 2] */, + 0x015cb000 /* 00002b96 - 00002b96 [ 1] */, + 0x0167a004 /* 00002cf4 - 00002cf8 [ 5] */, + 0x01693000 /* 00002d26 - 00002d26 [ 1] */, + 0x01694004 /* 00002d28 - 00002d2c [ 5] */, + 0x01697001 /* 00002d2e - 00002d2f [ 2] */, + 0x016b4006 /* 00002d68 - 00002d6e [ 7] */, + 0x016b880d /* 00002d71 - 00002d7e [ 14] */, + 0x016cb808 /* 00002d97 - 00002d9f [ 9] */, + 0x016d3800 /* 00002da7 - 00002da7 [ 1] */, + 0x016d7800 /* 00002daf - 00002daf [ 1] */, + 0x016db800 /* 00002db7 - 00002db7 [ 1] */, + 0x016df800 /* 00002dbf - 00002dbf [ 1] */, + 0x016e3800 /* 00002dc7 - 00002dc7 [ 1] */, + 0x016e7800 /* 00002dcf - 00002dcf [ 1] */, + 0x016eb800 /* 00002dd7 - 00002dd7 [ 1] */, + 0x016ef800 /* 00002ddf - 00002ddf [ 1] */, + 0x0172f021 /* 00002e5e - 00002e7f [ 34] */, + 0x0174d000 /* 00002e9a - 00002e9a [ 1] */, + 0x0177a00b /* 00002ef4 - 00002eff [ 12] */, + 0x017eb019 /* 00002fd6 - 00002fef [ 26] */, + 0x01800000 /* 00003000 - 00003000 [ 1] */, + 0x01820000 /* 00003040 - 00003040 [ 1] */, + 0x0184b801 /* 00003097 - 00003098 [ 2] */, + 0x01880004 /* 00003100 - 00003104 [ 5] */, + 0x01898000 /* 00003130 - 00003130 [ 1] */, + 0x018c7800 /* 0000318f - 0000318f [ 1] */, + 0x018f200a /* 000031e4 - 000031ee [ 11] */, + 0x0190f800 /* 0000321f - 0000321f [ 1] */, + 0x05246802 /* 0000a48d - 0000a48f [ 3] */, + 0x05263808 /* 0000a4c7 - 0000a4cf [ 9] */, + 0x05316013 /* 0000a62c - 0000a63f [ 20] */, + 0x0537c007 /* 0000a6f8 - 0000a6ff [ 8] */, + 0x053e5804 /* 0000a7cb - 0000a7cf [ 5] */, + 0x053e9000 /* 0000a7d2 - 0000a7d2 [ 1] */, + 0x053ea000 /* 0000a7d4 - 0000a7d4 [ 1] */, + 0x053ed017 /* 0000a7da - 0000a7f1 [ 24] */, + 0x05416802 /* 0000a82d - 0000a82f [ 3] */, + 0x0541d005 /* 0000a83a - 0000a83f [ 6] */, + 0x0543c007 /* 0000a878 - 0000a87f [ 8] */, + 0x05463007 /* 0000a8c6 - 0000a8cd [ 8] */, + 0x0546d005 /* 0000a8da - 0000a8df [ 6] */, + 0x054aa00a /* 0000a954 - 0000a95e [ 11] */, + 0x054be802 /* 0000a97d - 0000a97f [ 3] */, + 0x054e7000 /* 0000a9ce - 0000a9ce [ 1] */, + 0x054ed003 /* 0000a9da - 0000a9dd [ 4] */, + 0x054ff800 /* 0000a9ff - 0000a9ff [ 1] */, + 0x0551b808 /* 0000aa37 - 0000aa3f [ 9] */, + 0x05527001 /* 0000aa4e - 0000aa4f [ 2] */, + 0x0552d001 /* 0000aa5a - 0000aa5b [ 2] */, + 0x05561817 /* 0000aac3 - 0000aada [ 24] */, + 0x0557b809 /* 0000aaf7 - 0000ab00 [ 10] */, + 0x05583801 /* 0000ab07 - 0000ab08 [ 2] */, + 0x05587801 /* 0000ab0f - 0000ab10 [ 2] */, + 0x0558b808 /* 0000ab17 - 0000ab1f [ 9] */, + 0x05593800 /* 0000ab27 - 0000ab27 [ 1] */, + 0x05597800 /* 0000ab2f - 0000ab2f [ 1] */, + 0x055b6003 /* 0000ab6c - 0000ab6f [ 4] */, + 0x055f7001 /* 0000abee - 0000abef [ 2] */, + 0x055fd005 /* 0000abfa - 0000abff [ 6] */, + 0x06bd200b /* 0000d7a4 - 0000d7af [ 12] */, + 0x06be3803 /* 0000d7c7 - 0000d7ca [ 4] */, + 0x06bfe7ff /* 0000d7fc - 0000dffb [ 2048] */, + 0x06ffe7ff /* 0000dffc - 0000e7fb [ 2048] */, + 0x073fe7ff /* 0000e7fc - 0000effb [ 2048] */, + 0x077fe7ff /* 0000effc - 0000f7fb [ 2048] */, + 0x07bfe103 /* 0000f7fc - 0000f8ff [ 260] */, + 0x07d37001 /* 0000fa6e - 0000fa6f [ 2] */, + 0x07d6d025 /* 0000fada - 0000faff [ 38] */, + 0x07d8380b /* 0000fb07 - 0000fb12 [ 12] */, + 0x07d8c004 /* 0000fb18 - 0000fb1c [ 5] */, + 0x07d9b800 /* 0000fb37 - 0000fb37 [ 1] */, + 0x07d9e800 /* 0000fb3d - 0000fb3d [ 1] */, + 0x07d9f800 /* 0000fb3f - 0000fb3f [ 1] */, + 0x07da1000 /* 0000fb42 - 0000fb42 [ 1] */, + 0x07da2800 /* 0000fb45 - 0000fb45 [ 1] */, + 0x07de180f /* 0000fbc3 - 0000fbd2 [ 16] */, + 0x07ec8001 /* 0000fd90 - 0000fd91 [ 2] */, + 0x07ee4006 /* 0000fdc8 - 0000fdce [ 7] */, + 0x07ee801f /* 0000fdd0 - 0000fdef [ 32] */, + 0x07f0d005 /* 0000fe1a - 0000fe1f [ 6] */, + 0x07f29800 /* 0000fe53 - 0000fe53 [ 1] */, + 0x07f33800 /* 0000fe67 - 0000fe67 [ 1] */, + 0x07f36003 /* 0000fe6c - 0000fe6f [ 4] */, + 0x07f3a800 /* 0000fe75 - 0000fe75 [ 1] */, + 0x07f7e803 /* 0000fefd - 0000ff00 [ 4] */, + 0x07fdf802 /* 0000ffbf - 0000ffc1 [ 3] */, + 0x07fe4001 /* 0000ffc8 - 0000ffc9 [ 2] */, + 0x07fe8001 /* 0000ffd0 - 0000ffd1 [ 2] */, + 0x07fec001 /* 0000ffd8 - 0000ffd9 [ 2] */, + 0x07fee802 /* 0000ffdd - 0000ffdf [ 3] */, + 0x07ff3800 /* 0000ffe7 - 0000ffe7 [ 1] */, + 0x07ff780c /* 0000ffef - 0000fffb [ 13] */, + 0x07fff001 /* 0000fffe - 0000ffff [ 2] */, + 0x08006000 /* 0001000c - 0001000c [ 1] */, + 0x08013800 /* 00010027 - 00010027 [ 1] */, + 0x0801d800 /* 0001003b - 0001003b [ 1] */, + 0x0801f000 /* 0001003e - 0001003e [ 1] */, + 0x08027001 /* 0001004e - 0001004f [ 2] */, + 0x0802f021 /* 0001005e - 0001007f [ 34] */, + 0x0807d804 /* 000100fb - 000100ff [ 5] */, + 0x08081803 /* 00010103 - 00010106 [ 4] */, + 0x0809a002 /* 00010134 - 00010136 [ 3] */, + 0x080c7800 /* 0001018f - 0001018f [ 1] */, + 0x080ce802 /* 0001019d - 0001019f [ 3] */, + 0x080d082e /* 000101a1 - 000101cf [ 47] */, + 0x080ff081 /* 000101fe - 0001027f [ 130] */, + 0x0814e802 /* 0001029d - 0001029f [ 3] */, + 0x0816880e /* 000102d1 - 000102df [ 15] */, + 0x0817e003 /* 000102fc - 000102ff [ 4] */, + 0x08192008 /* 00010324 - 0001032c [ 9] */, + 0x081a5804 /* 0001034b - 0001034f [ 5] */, + 0x081bd804 /* 0001037b - 0001037f [ 5] */, + 0x081cf000 /* 0001039e - 0001039e [ 1] */, + 0x081e2003 /* 000103c4 - 000103c7 [ 4] */, + 0x081eb029 /* 000103d6 - 000103ff [ 42] */, + 0x0824f001 /* 0001049e - 0001049f [ 2] */, + 0x08255005 /* 000104aa - 000104af [ 6] */, + 0x0826a003 /* 000104d4 - 000104d7 [ 4] */, + 0x0827e003 /* 000104fc - 000104ff [ 4] */, + 0x08294007 /* 00010528 - 0001052f [ 8] */, + 0x082b200a /* 00010564 - 0001056e [ 11] */, + 0x082bd800 /* 0001057b - 0001057b [ 1] */, + 0x082c5800 /* 0001058b - 0001058b [ 1] */, + 0x082c9800 /* 00010593 - 00010593 [ 1] */, + 0x082cb000 /* 00010596 - 00010596 [ 1] */, + 0x082d1000 /* 000105a2 - 000105a2 [ 1] */, + 0x082d9000 /* 000105b2 - 000105b2 [ 1] */, + 0x082dd000 /* 000105ba - 000105ba [ 1] */, + 0x082de842 /* 000105bd - 000105ff [ 67] */, + 0x0839b808 /* 00010737 - 0001073f [ 9] */, + 0x083ab009 /* 00010756 - 0001075f [ 10] */, + 0x083b4017 /* 00010768 - 0001077f [ 24] */, + 0x083c3000 /* 00010786 - 00010786 [ 1] */, + 0x083d8800 /* 000107b1 - 000107b1 [ 1] */, + 0x083dd844 /* 000107bb - 000107ff [ 69] */, + 0x08403001 /* 00010806 - 00010807 [ 2] */, + 0x08404800 /* 00010809 - 00010809 [ 1] */, + 0x0841b000 /* 00010836 - 00010836 [ 1] */, + 0x0841c802 /* 00010839 - 0001083b [ 3] */, + 0x0841e801 /* 0001083d - 0001083e [ 2] */, + 0x0842b000 /* 00010856 - 00010856 [ 1] */, + 0x0844f807 /* 0001089f - 000108a6 [ 8] */, + 0x0845802f /* 000108b0 - 000108df [ 48] */, + 0x08479800 /* 000108f3 - 000108f3 [ 1] */, + 0x0847b004 /* 000108f6 - 000108fa [ 5] */, + 0x0848e002 /* 0001091c - 0001091e [ 3] */, + 0x0849d004 /* 0001093a - 0001093e [ 5] */, + 0x084a003f /* 00010940 - 0001097f [ 64] */, + 0x084dc003 /* 000109b8 - 000109bb [ 4] */, + 0x084e8001 /* 000109d0 - 000109d1 [ 2] */, + 0x08502000 /* 00010a04 - 00010a04 [ 1] */, + 0x08503804 /* 00010a07 - 00010a0b [ 5] */, + 0x0850a000 /* 00010a14 - 00010a14 [ 1] */, + 0x0850c000 /* 00010a18 - 00010a18 [ 1] */, + 0x0851b001 /* 00010a36 - 00010a37 [ 2] */, + 0x0851d803 /* 00010a3b - 00010a3e [ 4] */, + 0x08524806 /* 00010a49 - 00010a4f [ 7] */, + 0x0852c806 /* 00010a59 - 00010a5f [ 7] */, + 0x0855001f /* 00010aa0 - 00010abf [ 32] */, + 0x08573803 /* 00010ae7 - 00010aea [ 4] */, + 0x0857b808 /* 00010af7 - 00010aff [ 9] */, + 0x0859b002 /* 00010b36 - 00010b38 [ 3] */, + 0x085ab001 /* 00010b56 - 00010b57 [ 2] */, + 0x085b9804 /* 00010b73 - 00010b77 [ 5] */, + 0x085c9006 /* 00010b92 - 00010b98 [ 7] */, + 0x085ce80b /* 00010b9d - 00010ba8 [ 12] */, + 0x085d804f /* 00010bb0 - 00010bff [ 80] */, + 0x08624836 /* 00010c49 - 00010c7f [ 55] */, + 0x0865980c /* 00010cb3 - 00010cbf [ 13] */, + 0x08679806 /* 00010cf3 - 00010cf9 [ 7] */, + 0x08694007 /* 00010d28 - 00010d2f [ 8] */, + 0x0869d125 /* 00010d3a - 00010e5f [ 294] */, + 0x0873f800 /* 00010e7f - 00010e7f [ 1] */, + 0x08755000 /* 00010eaa - 00010eaa [ 1] */, + 0x08757001 /* 00010eae - 00010eaf [ 2] */, + 0x0875904a /* 00010eb2 - 00010efc [ 75] */, + 0x08794007 /* 00010f28 - 00010f2f [ 8] */, + 0x087ad015 /* 00010f5a - 00010f6f [ 22] */, + 0x087c5025 /* 00010f8a - 00010faf [ 38] */, + 0x087e6013 /* 00010fcc - 00010fdf [ 20] */, + 0x087fb808 /* 00010ff7 - 00010fff [ 9] */, + 0x08827003 /* 0001104e - 00011051 [ 4] */, + 0x0883b008 /* 00011076 - 0001107e [ 9] */, + 0x0885e800 /* 000110bd - 000110bd [ 1] */, + 0x0886180c /* 000110c3 - 000110cf [ 13] */, + 0x08874806 /* 000110e9 - 000110ef [ 7] */, + 0x0887d005 /* 000110fa - 000110ff [ 6] */, + 0x0889a800 /* 00011135 - 00011135 [ 1] */, + 0x088a4007 /* 00011148 - 0001114f [ 8] */, + 0x088bb808 /* 00011177 - 0001117f [ 9] */, + 0x088f0000 /* 000111e0 - 000111e0 [ 1] */, + 0x088fa80a /* 000111f5 - 000111ff [ 11] */, + 0x08909000 /* 00011212 - 00011212 [ 1] */, + 0x0892103d /* 00011242 - 0001127f [ 62] */, + 0x08943800 /* 00011287 - 00011287 [ 1] */, + 0x08944800 /* 00011289 - 00011289 [ 1] */, + 0x08947000 /* 0001128e - 0001128e [ 1] */, + 0x0894f000 /* 0001129e - 0001129e [ 1] */, + 0x08955005 /* 000112aa - 000112af [ 6] */, + 0x08975804 /* 000112eb - 000112ef [ 5] */, + 0x0897d005 /* 000112fa - 000112ff [ 6] */, + 0x08982000 /* 00011304 - 00011304 [ 1] */, + 0x08986801 /* 0001130d - 0001130e [ 2] */, + 0x08988801 /* 00011311 - 00011312 [ 2] */, + 0x08994800 /* 00011329 - 00011329 [ 1] */, + 0x08998800 /* 00011331 - 00011331 [ 1] */, + 0x0899a000 /* 00011334 - 00011334 [ 1] */, + 0x0899d000 /* 0001133a - 0001133a [ 1] */, + 0x089a2801 /* 00011345 - 00011346 [ 2] */, + 0x089a4801 /* 00011349 - 0001134a [ 2] */, + 0x089a7001 /* 0001134e - 0001134f [ 2] */, + 0x089a8805 /* 00011351 - 00011356 [ 6] */, + 0x089ac004 /* 00011358 - 0001135c [ 5] */, + 0x089b2001 /* 00011364 - 00011365 [ 2] */, + 0x089b6802 /* 0001136d - 0001136f [ 3] */, + 0x089ba88a /* 00011375 - 000113ff [ 139] */, + 0x08a2e000 /* 0001145c - 0001145c [ 1] */, + 0x08a3101d /* 00011462 - 0001147f [ 30] */, + 0x08a64007 /* 000114c8 - 000114cf [ 8] */, + 0x08a6d0a5 /* 000114da - 0001157f [ 166] */, + 0x08adb001 /* 000115b6 - 000115b7 [ 2] */, + 0x08aef021 /* 000115de - 000115ff [ 34] */, + 0x08b2280a /* 00011645 - 0001164f [ 11] */, + 0x08b2d005 /* 0001165a - 0001165f [ 6] */, + 0x08b36812 /* 0001166d - 0001167f [ 19] */, + 0x08b5d005 /* 000116ba - 000116bf [ 6] */, + 0x08b65035 /* 000116ca - 000116ff [ 54] */, + 0x08b8d801 /* 0001171b - 0001171c [ 2] */, + 0x08b96003 /* 0001172c - 0001172f [ 4] */, + 0x08ba38b8 /* 00011747 - 000117ff [ 185] */, + 0x08c1e063 /* 0001183c - 0001189f [ 100] */, + 0x08c7980b /* 000118f3 - 000118fe [ 12] */, + 0x08c83801 /* 00011907 - 00011908 [ 2] */, + 0x08c85001 /* 0001190a - 0001190b [ 2] */, + 0x08c8a000 /* 00011914 - 00011914 [ 1] */, + 0x08c8b800 /* 00011917 - 00011917 [ 1] */, + 0x08c9b000 /* 00011936 - 00011936 [ 1] */, + 0x08c9c801 /* 00011939 - 0001193a [ 2] */, + 0x08ca3808 /* 00011947 - 0001194f [ 9] */, + 0x08cad045 /* 0001195a - 0001199f [ 70] */, + 0x08cd4001 /* 000119a8 - 000119a9 [ 2] */, + 0x08cec001 /* 000119d8 - 000119d9 [ 2] */, + 0x08cf281a /* 000119e5 - 000119ff [ 27] */, + 0x08d24007 /* 00011a48 - 00011a4f [ 8] */, + 0x08d5180c /* 00011aa3 - 00011aaf [ 13] */, + 0x08d7c806 /* 00011af9 - 00011aff [ 7] */, + 0x08d850f5 /* 00011b0a - 00011bff [ 246] */, + 0x08e04800 /* 00011c09 - 00011c09 [ 1] */, + 0x08e1b800 /* 00011c37 - 00011c37 [ 1] */, + 0x08e23009 /* 00011c46 - 00011c4f [ 10] */, + 0x08e36802 /* 00011c6d - 00011c6f [ 3] */, + 0x08e48001 /* 00011c90 - 00011c91 [ 2] */, + 0x08e54000 /* 00011ca8 - 00011ca8 [ 1] */, + 0x08e5b848 /* 00011cb7 - 00011cff [ 73] */, + 0x08e83800 /* 00011d07 - 00011d07 [ 1] */, + 0x08e85000 /* 00011d0a - 00011d0a [ 1] */, + 0x08e9b802 /* 00011d37 - 00011d39 [ 3] */, + 0x08e9d800 /* 00011d3b - 00011d3b [ 1] */, + 0x08e9f000 /* 00011d3e - 00011d3e [ 1] */, + 0x08ea4007 /* 00011d48 - 00011d4f [ 8] */, + 0x08ead005 /* 00011d5a - 00011d5f [ 6] */, + 0x08eb3000 /* 00011d66 - 00011d66 [ 1] */, + 0x08eb4800 /* 00011d69 - 00011d69 [ 1] */, + 0x08ec7800 /* 00011d8f - 00011d8f [ 1] */, + 0x08ec9000 /* 00011d92 - 00011d92 [ 1] */, + 0x08ecc806 /* 00011d99 - 00011d9f [ 7] */, + 0x08ed5135 /* 00011daa - 00011edf [ 310] */, + 0x08f7c806 /* 00011ef9 - 00011eff [ 7] */, + 0x08f88800 /* 00011f11 - 00011f11 [ 1] */, + 0x08f9d802 /* 00011f3b - 00011f3d [ 3] */, + 0x08fad055 /* 00011f5a - 00011faf [ 86] */, + 0x08fd880e /* 00011fb1 - 00011fbf [ 15] */, + 0x08ff900c /* 00011ff2 - 00011ffe [ 13] */, + 0x091cd065 /* 0001239a - 000123ff [ 102] */, + 0x09237800 /* 0001246f - 0001246f [ 1] */, + 0x0923a80a /* 00012475 - 0001247f [ 11] */, + 0x092a27ff /* 00012544 - 00012d43 [ 2048] */, + 0x096a224b /* 00012d44 - 00012f8f [ 588] */, + 0x097f980c /* 00012ff3 - 00012fff [ 13] */, + 0x09a1800f /* 00013430 - 0001343f [ 16] */, + 0x09a2b7ff /* 00013456 - 00013c55 [ 2048] */, + 0x09e2b7a9 /* 00013c56 - 000143ff [ 1962] */, + 0x0a323fff /* 00014647 - 00014e46 [ 2048] */, + 0x0a723fff /* 00014e47 - 00015646 [ 2048] */, + 0x0ab23fff /* 00015647 - 00015e46 [ 2048] */, + 0x0af23fff /* 00015e47 - 00016646 [ 2048] */, + 0x0b3239b8 /* 00016647 - 000167ff [ 441] */, + 0x0b51c806 /* 00016a39 - 00016a3f [ 7] */, + 0x0b52f800 /* 00016a5f - 00016a5f [ 1] */, + 0x0b535003 /* 00016a6a - 00016a6d [ 4] */, + 0x0b55f800 /* 00016abf - 00016abf [ 1] */, + 0x0b565005 /* 00016aca - 00016acf [ 6] */, + 0x0b577001 /* 00016aee - 00016aef [ 2] */, + 0x0b57b009 /* 00016af6 - 00016aff [ 10] */, + 0x0b5a3009 /* 00016b46 - 00016b4f [ 10] */, + 0x0b5ad000 /* 00016b5a - 00016b5a [ 1] */, + 0x0b5b1000 /* 00016b62 - 00016b62 [ 1] */, + 0x0b5bc004 /* 00016b78 - 00016b7c [ 5] */, + 0x0b5c82af /* 00016b90 - 00016e3f [ 688] */, + 0x0b74d864 /* 00016e9b - 00016eff [ 101] */, + 0x0b7a5803 /* 00016f4b - 00016f4e [ 4] */, + 0x0b7c4006 /* 00016f88 - 00016f8e [ 7] */, + 0x0b7d003f /* 00016fa0 - 00016fdf [ 64] */, + 0x0b7f280a /* 00016fe5 - 00016fef [ 11] */, + 0x0b7f900d /* 00016ff2 - 00016fff [ 14] */, + 0x0c3fc007 /* 000187f8 - 000187ff [ 8] */, + 0x0c66b029 /* 00018cd6 - 00018cff [ 42] */, + 0x0c684fff /* 00018d09 - 00019508 [ 2048] */, + 0x0ca84fff /* 00019509 - 00019d08 [ 2048] */, + 0x0ce84fff /* 00019d09 - 0001a508 [ 2048] */, + 0x0d284fff /* 0001a509 - 0001ad08 [ 2048] */, + 0x0d684ae6 /* 0001ad09 - 0001afef [ 743] */, + 0x0d7fa000 /* 0001aff4 - 0001aff4 [ 1] */, + 0x0d7fe000 /* 0001affc - 0001affc [ 1] */, + 0x0d7ff800 /* 0001afff - 0001afff [ 1] */, + 0x0d89180e /* 0001b123 - 0001b131 [ 15] */, + 0x0d89981c /* 0001b133 - 0001b14f [ 29] */, + 0x0d8a9801 /* 0001b153 - 0001b154 [ 2] */, + 0x0d8ab00d /* 0001b156 - 0001b163 [ 14] */, + 0x0d8b4007 /* 0001b168 - 0001b16f [ 8] */, + 0x0d97e7ff /* 0001b2fc - 0001bafb [ 2048] */, + 0x0dd7e103 /* 0001bafc - 0001bbff [ 260] */, + 0x0de35804 /* 0001bc6b - 0001bc6f [ 5] */, + 0x0de3e802 /* 0001bc7d - 0001bc7f [ 3] */, + 0x0de44806 /* 0001bc89 - 0001bc8f [ 7] */, + 0x0de4d001 /* 0001bc9a - 0001bc9b [ 2] */, + 0x0de507ff /* 0001bca0 - 0001c49f [ 2048] */, + 0x0e2507ff /* 0001c4a0 - 0001cc9f [ 2048] */, + 0x0e65025f /* 0001cca0 - 0001ceff [ 608] */, + 0x0e797001 /* 0001cf2e - 0001cf2f [ 2] */, + 0x0e7a3808 /* 0001cf47 - 0001cf4f [ 9] */, + 0x0e7e203b /* 0001cfc4 - 0001cfff [ 60] */, + 0x0e87b009 /* 0001d0f6 - 0001d0ff [ 10] */, + 0x0e893801 /* 0001d127 - 0001d128 [ 2] */, + 0x0e8b9807 /* 0001d173 - 0001d17a [ 8] */, + 0x0e8f5814 /* 0001d1eb - 0001d1ff [ 21] */, + 0x0e923079 /* 0001d246 - 0001d2bf [ 122] */, + 0x0e96a00b /* 0001d2d4 - 0001d2df [ 12] */, + 0x0e97a00b /* 0001d2f4 - 0001d2ff [ 12] */, + 0x0e9ab808 /* 0001d357 - 0001d35f [ 9] */, + 0x0e9bc886 /* 0001d379 - 0001d3ff [ 135] */, + 0x0ea2a800 /* 0001d455 - 0001d455 [ 1] */, + 0x0ea4e800 /* 0001d49d - 0001d49d [ 1] */, + 0x0ea50001 /* 0001d4a0 - 0001d4a1 [ 2] */, + 0x0ea51801 /* 0001d4a3 - 0001d4a4 [ 2] */, + 0x0ea53801 /* 0001d4a7 - 0001d4a8 [ 2] */, + 0x0ea56800 /* 0001d4ad - 0001d4ad [ 1] */, + 0x0ea5d000 /* 0001d4ba - 0001d4ba [ 1] */, + 0x0ea5e000 /* 0001d4bc - 0001d4bc [ 1] */, + 0x0ea62000 /* 0001d4c4 - 0001d4c4 [ 1] */, + 0x0ea83000 /* 0001d506 - 0001d506 [ 1] */, + 0x0ea85801 /* 0001d50b - 0001d50c [ 2] */, + 0x0ea8a800 /* 0001d515 - 0001d515 [ 1] */, + 0x0ea8e800 /* 0001d51d - 0001d51d [ 1] */, + 0x0ea9d000 /* 0001d53a - 0001d53a [ 1] */, + 0x0ea9f800 /* 0001d53f - 0001d53f [ 1] */, + 0x0eaa2800 /* 0001d545 - 0001d545 [ 1] */, + 0x0eaa3802 /* 0001d547 - 0001d549 [ 3] */, + 0x0eaa8800 /* 0001d551 - 0001d551 [ 1] */, + 0x0eb53001 /* 0001d6a6 - 0001d6a7 [ 2] */, + 0x0ebe6001 /* 0001d7cc - 0001d7cd [ 2] */, + 0x0ed4600e /* 0001da8c - 0001da9a [ 15] */, + 0x0ed50000 /* 0001daa0 - 0001daa0 [ 1] */, + 0x0ed5844f /* 0001dab0 - 0001deff [ 1104] */, + 0x0ef8f805 /* 0001df1f - 0001df24 [ 6] */, + 0x0ef958d4 /* 0001df2b - 0001dfff [ 213] */, + 0x0f003800 /* 0001e007 - 0001e007 [ 1] */, + 0x0f00c801 /* 0001e019 - 0001e01a [ 2] */, + 0x0f011000 /* 0001e022 - 0001e022 [ 1] */, + 0x0f012800 /* 0001e025 - 0001e025 [ 1] */, + 0x0f015804 /* 0001e02b - 0001e02f [ 5] */, + 0x0f037020 /* 0001e06e - 0001e08e [ 33] */, + 0x0f04806f /* 0001e090 - 0001e0ff [ 112] */, + 0x0f096802 /* 0001e12d - 0001e12f [ 3] */, + 0x0f09f001 /* 0001e13e - 0001e13f [ 2] */, + 0x0f0a5003 /* 0001e14a - 0001e14d [ 4] */, + 0x0f0a813f /* 0001e150 - 0001e28f [ 320] */, + 0x0f157810 /* 0001e2af - 0001e2bf [ 17] */, + 0x0f17d004 /* 0001e2fa - 0001e2fe [ 5] */, + 0x0f1801cf /* 0001e300 - 0001e4cf [ 464] */, + 0x0f27d2e5 /* 0001e4fa - 0001e7df [ 742] */, + 0x0f3f3800 /* 0001e7e7 - 0001e7e7 [ 1] */, + 0x0f3f6000 /* 0001e7ec - 0001e7ec [ 1] */, + 0x0f3f7800 /* 0001e7ef - 0001e7ef [ 1] */, + 0x0f3ff800 /* 0001e7ff - 0001e7ff [ 1] */, + 0x0f462801 /* 0001e8c5 - 0001e8c6 [ 2] */, + 0x0f46b828 /* 0001e8d7 - 0001e8ff [ 41] */, + 0x0f4a6003 /* 0001e94c - 0001e94f [ 4] */, + 0x0f4ad003 /* 0001e95a - 0001e95d [ 4] */, + 0x0f4b0310 /* 0001e960 - 0001ec70 [ 785] */, + 0x0f65a84b /* 0001ecb5 - 0001ed00 [ 76] */, + 0x0f69f0c1 /* 0001ed3e - 0001edff [ 194] */, + 0x0f702000 /* 0001ee04 - 0001ee04 [ 1] */, + 0x0f710000 /* 0001ee20 - 0001ee20 [ 1] */, + 0x0f711800 /* 0001ee23 - 0001ee23 [ 1] */, + 0x0f712801 /* 0001ee25 - 0001ee26 [ 2] */, + 0x0f714000 /* 0001ee28 - 0001ee28 [ 1] */, + 0x0f719800 /* 0001ee33 - 0001ee33 [ 1] */, + 0x0f71c000 /* 0001ee38 - 0001ee38 [ 1] */, + 0x0f71d000 /* 0001ee3a - 0001ee3a [ 1] */, + 0x0f71e005 /* 0001ee3c - 0001ee41 [ 6] */, + 0x0f721803 /* 0001ee43 - 0001ee46 [ 4] */, + 0x0f724000 /* 0001ee48 - 0001ee48 [ 1] */, + 0x0f725000 /* 0001ee4a - 0001ee4a [ 1] */, + 0x0f726000 /* 0001ee4c - 0001ee4c [ 1] */, + 0x0f728000 /* 0001ee50 - 0001ee50 [ 1] */, + 0x0f729800 /* 0001ee53 - 0001ee53 [ 1] */, + 0x0f72a801 /* 0001ee55 - 0001ee56 [ 2] */, + 0x0f72c000 /* 0001ee58 - 0001ee58 [ 1] */, + 0x0f72d000 /* 0001ee5a - 0001ee5a [ 1] */, + 0x0f72e000 /* 0001ee5c - 0001ee5c [ 1] */, + 0x0f72f000 /* 0001ee5e - 0001ee5e [ 1] */, + 0x0f730000 /* 0001ee60 - 0001ee60 [ 1] */, + 0x0f731800 /* 0001ee63 - 0001ee63 [ 1] */, + 0x0f732801 /* 0001ee65 - 0001ee66 [ 2] */, + 0x0f735800 /* 0001ee6b - 0001ee6b [ 1] */, + 0x0f739800 /* 0001ee73 - 0001ee73 [ 1] */, + 0x0f73c000 /* 0001ee78 - 0001ee78 [ 1] */, + 0x0f73e800 /* 0001ee7d - 0001ee7d [ 1] */, + 0x0f73f800 /* 0001ee7f - 0001ee7f [ 1] */, + 0x0f745000 /* 0001ee8a - 0001ee8a [ 1] */, + 0x0f74e004 /* 0001ee9c - 0001eea0 [ 5] */, + 0x0f752000 /* 0001eea4 - 0001eea4 [ 1] */, + 0x0f755000 /* 0001eeaa - 0001eeaa [ 1] */, + 0x0f75e033 /* 0001eebc - 0001eeef [ 52] */, + 0x0f77910d /* 0001eef2 - 0001efff [ 270] */, + 0x0f816003 /* 0001f02c - 0001f02f [ 4] */, + 0x0f84a00b /* 0001f094 - 0001f09f [ 12] */, + 0x0f857801 /* 0001f0af - 0001f0b0 [ 2] */, + 0x0f860000 /* 0001f0c0 - 0001f0c0 [ 1] */, + 0x0f868000 /* 0001f0d0 - 0001f0d0 [ 1] */, + 0x0f87b009 /* 0001f0f6 - 0001f0ff [ 10] */, + 0x0f8d7037 /* 0001f1ae - 0001f1e5 [ 56] */, + 0x0f90180c /* 0001f203 - 0001f20f [ 13] */, + 0x0f91e003 /* 0001f23c - 0001f23f [ 4] */, + 0x0f924806 /* 0001f249 - 0001f24f [ 7] */, + 0x0f92900d /* 0001f252 - 0001f25f [ 14] */, + 0x0f933099 /* 0001f266 - 0001f2ff [ 154] */, + 0x0fb6c003 /* 0001f6d8 - 0001f6db [ 4] */, + 0x0fb76802 /* 0001f6ed - 0001f6ef [ 3] */, + 0x0fb7e802 /* 0001f6fd - 0001f6ff [ 3] */, + 0x0fbbb803 /* 0001f777 - 0001f77a [ 4] */, + 0x0fbed005 /* 0001f7da - 0001f7df [ 6] */, + 0x0fbf6003 /* 0001f7ec - 0001f7ef [ 4] */, + 0x0fbf880e /* 0001f7f1 - 0001f7ff [ 15] */, + 0x0fc06003 /* 0001f80c - 0001f80f [ 4] */, + 0x0fc24007 /* 0001f848 - 0001f84f [ 8] */, + 0x0fc2d005 /* 0001f85a - 0001f85f [ 6] */, + 0x0fc44007 /* 0001f888 - 0001f88f [ 8] */, + 0x0fc57001 /* 0001f8ae - 0001f8af [ 2] */, + 0x0fc5904d /* 0001f8b2 - 0001f8ff [ 78] */, + 0x0fd2a00b /* 0001fa54 - 0001fa5f [ 12] */, + 0x0fd37001 /* 0001fa6e - 0001fa6f [ 2] */, + 0x0fd3e802 /* 0001fa7d - 0001fa7f [ 3] */, + 0x0fd44806 /* 0001fa89 - 0001fa8f [ 7] */, + 0x0fd5f000 /* 0001fabe - 0001fabe [ 1] */, + 0x0fd63007 /* 0001fac6 - 0001facd [ 8] */, + 0x0fd6e003 /* 0001fadc - 0001fadf [ 4] */, + 0x0fd74806 /* 0001fae9 - 0001faef [ 7] */, + 0x0fd7c806 /* 0001faf9 - 0001faff [ 7] */, + 0x0fdc9800 /* 0001fb93 - 0001fb93 [ 1] */, + 0x0fde5824 /* 0001fbcb - 0001fbef [ 37] */, + 0x0fdfd405 /* 0001fbfa - 0001ffff [ 1030] */, + 0x1537001f /* 0002a6e0 - 0002a6ff [ 32] */, + 0x15b9d005 /* 0002b73a - 0002b73f [ 6] */, + 0x15c0f001 /* 0002b81e - 0002b81f [ 2] */, + 0x1675100d /* 0002cea2 - 0002ceaf [ 14] */, + 0x175f080e /* 0002ebe1 - 0002ebef [ 15] */, + 0x1772f7ff /* 0002ee5e - 0002f65d [ 2048] */, + 0x17b2f1a1 /* 0002f65e - 0002f7ff [ 418] */, + 0x17d0f5e1 /* 0002fa1e - 0002ffff [ 1506] */, + 0x189a5804 /* 0003134b - 0003134f [ 5] */, + 0x191d87ff /* 000323b0 - 00032baf [ 2048] */, + 0x195d87ff /* 00032bb0 - 000333af [ 2048] */, + 0x199d87ff /* 000333b0 - 00033baf [ 2048] */, + 0x19dd87ff /* 00033bb0 - 000343af [ 2048] */, + 0x1a1d87ff /* 000343b0 - 00034baf [ 2048] */, + 0x1a5d87ff /* 00034bb0 - 000353af [ 2048] */, + 0x1a9d87ff /* 000353b0 - 00035baf [ 2048] */, + 0x1add87ff /* 00035bb0 - 000363af [ 2048] */, + 0x1b1d87ff /* 000363b0 - 00036baf [ 2048] */, + 0x1b5d87ff /* 00036bb0 - 000373af [ 2048] */, + 0x1b9d87ff /* 000373b0 - 00037baf [ 2048] */, + 0x1bdd87ff /* 00037bb0 - 000383af [ 2048] */, + 0x1c1d87ff /* 000383b0 - 00038baf [ 2048] */, + 0x1c5d87ff /* 00038bb0 - 000393af [ 2048] */, + 0x1c9d87ff /* 000393b0 - 00039baf [ 2048] */, + 0x1cdd87ff /* 00039bb0 - 0003a3af [ 2048] */, + 0x1d1d87ff /* 0003a3b0 - 0003abaf [ 2048] */, + 0x1d5d87ff /* 0003abb0 - 0003b3af [ 2048] */, + 0x1d9d87ff /* 0003b3b0 - 0003bbaf [ 2048] */, + 0x1ddd87ff /* 0003bbb0 - 0003c3af [ 2048] */, + 0x1e1d87ff /* 0003c3b0 - 0003cbaf [ 2048] */, + 0x1e5d87ff /* 0003cbb0 - 0003d3af [ 2048] */, + 0x1e9d87ff /* 0003d3b0 - 0003dbaf [ 2048] */, + 0x1edd87ff /* 0003dbb0 - 0003e3af [ 2048] */, + 0x1f1d87ff /* 0003e3b0 - 0003ebaf [ 2048] */, + 0x1f5d87ff /* 0003ebb0 - 0003f3af [ 2048] */, + 0x1f9d87ff /* 0003f3b0 - 0003fbaf [ 2048] */, + 0x1fdd87ff /* 0003fbb0 - 000403af [ 2048] */, + 0x201d87ff /* 000403b0 - 00040baf [ 2048] */, + 0x205d87ff /* 00040bb0 - 000413af [ 2048] */, + 0x209d87ff /* 000413b0 - 00041baf [ 2048] */, + 0x20dd87ff /* 00041bb0 - 000423af [ 2048] */, + 0x211d87ff /* 000423b0 - 00042baf [ 2048] */, + 0x215d87ff /* 00042bb0 - 000433af [ 2048] */, + 0x219d87ff /* 000433b0 - 00043baf [ 2048] */, + 0x21dd87ff /* 00043bb0 - 000443af [ 2048] */, + 0x221d87ff /* 000443b0 - 00044baf [ 2048] */, + 0x225d87ff /* 00044bb0 - 000453af [ 2048] */, + 0x229d87ff /* 000453b0 - 00045baf [ 2048] */, + 0x22dd87ff /* 00045bb0 - 000463af [ 2048] */, + 0x231d87ff /* 000463b0 - 00046baf [ 2048] */, + 0x235d87ff /* 00046bb0 - 000473af [ 2048] */, + 0x239d87ff /* 000473b0 - 00047baf [ 2048] */, + 0x23dd87ff /* 00047bb0 - 000483af [ 2048] */, + 0x241d87ff /* 000483b0 - 00048baf [ 2048] */, + 0x245d87ff /* 00048bb0 - 000493af [ 2048] */, + 0x249d87ff /* 000493b0 - 00049baf [ 2048] */, + 0x24dd87ff /* 00049bb0 - 0004a3af [ 2048] */, + 0x251d87ff /* 0004a3b0 - 0004abaf [ 2048] */, + 0x255d87ff /* 0004abb0 - 0004b3af [ 2048] */, + 0x259d87ff /* 0004b3b0 - 0004bbaf [ 2048] */, + 0x25dd87ff /* 0004bbb0 - 0004c3af [ 2048] */, + 0x261d87ff /* 0004c3b0 - 0004cbaf [ 2048] */, + 0x265d87ff /* 0004cbb0 - 0004d3af [ 2048] */, + 0x269d87ff /* 0004d3b0 - 0004dbaf [ 2048] */, + 0x26dd87ff /* 0004dbb0 - 0004e3af [ 2048] */, + 0x271d87ff /* 0004e3b0 - 0004ebaf [ 2048] */, + 0x275d87ff /* 0004ebb0 - 0004f3af [ 2048] */, + 0x279d87ff /* 0004f3b0 - 0004fbaf [ 2048] */, + 0x27dd87ff /* 0004fbb0 - 000503af [ 2048] */, + 0x281d87ff /* 000503b0 - 00050baf [ 2048] */, + 0x285d87ff /* 00050bb0 - 000513af [ 2048] */, + 0x289d87ff /* 000513b0 - 00051baf [ 2048] */, + 0x28dd87ff /* 00051bb0 - 000523af [ 2048] */, + 0x291d87ff /* 000523b0 - 00052baf [ 2048] */, + 0x295d87ff /* 00052bb0 - 000533af [ 2048] */, + 0x299d87ff /* 000533b0 - 00053baf [ 2048] */, + 0x29dd87ff /* 00053bb0 - 000543af [ 2048] */, + 0x2a1d87ff /* 000543b0 - 00054baf [ 2048] */, + 0x2a5d87ff /* 00054bb0 - 000553af [ 2048] */, + 0x2a9d87ff /* 000553b0 - 00055baf [ 2048] */, + 0x2add87ff /* 00055bb0 - 000563af [ 2048] */, + 0x2b1d87ff /* 000563b0 - 00056baf [ 2048] */, + 0x2b5d87ff /* 00056bb0 - 000573af [ 2048] */, + 0x2b9d87ff /* 000573b0 - 00057baf [ 2048] */, + 0x2bdd87ff /* 00057bb0 - 000583af [ 2048] */, + 0x2c1d87ff /* 000583b0 - 00058baf [ 2048] */, + 0x2c5d87ff /* 00058bb0 - 000593af [ 2048] */, + 0x2c9d87ff /* 000593b0 - 00059baf [ 2048] */, + 0x2cdd87ff /* 00059bb0 - 0005a3af [ 2048] */, + 0x2d1d87ff /* 0005a3b0 - 0005abaf [ 2048] */, + 0x2d5d87ff /* 0005abb0 - 0005b3af [ 2048] */, + 0x2d9d87ff /* 0005b3b0 - 0005bbaf [ 2048] */, + 0x2ddd87ff /* 0005bbb0 - 0005c3af [ 2048] */, + 0x2e1d87ff /* 0005c3b0 - 0005cbaf [ 2048] */, + 0x2e5d87ff /* 0005cbb0 - 0005d3af [ 2048] */, + 0x2e9d87ff /* 0005d3b0 - 0005dbaf [ 2048] */, + 0x2edd87ff /* 0005dbb0 - 0005e3af [ 2048] */, + 0x2f1d87ff /* 0005e3b0 - 0005ebaf [ 2048] */, + 0x2f5d87ff /* 0005ebb0 - 0005f3af [ 2048] */, + 0x2f9d87ff /* 0005f3b0 - 0005fbaf [ 2048] */, + 0x2fdd87ff /* 0005fbb0 - 000603af [ 2048] */, + 0x301d87ff /* 000603b0 - 00060baf [ 2048] */, + 0x305d87ff /* 00060bb0 - 000613af [ 2048] */, + 0x309d87ff /* 000613b0 - 00061baf [ 2048] */, + 0x30dd87ff /* 00061bb0 - 000623af [ 2048] */, + 0x311d87ff /* 000623b0 - 00062baf [ 2048] */, + 0x315d87ff /* 00062bb0 - 000633af [ 2048] */, + 0x319d87ff /* 000633b0 - 00063baf [ 2048] */, + 0x31dd87ff /* 00063bb0 - 000643af [ 2048] */, + 0x321d87ff /* 000643b0 - 00064baf [ 2048] */, + 0x325d87ff /* 00064bb0 - 000653af [ 2048] */, + 0x329d87ff /* 000653b0 - 00065baf [ 2048] */, + 0x32dd87ff /* 00065bb0 - 000663af [ 2048] */, + 0x331d87ff /* 000663b0 - 00066baf [ 2048] */, + 0x335d87ff /* 00066bb0 - 000673af [ 2048] */, + 0x339d87ff /* 000673b0 - 00067baf [ 2048] */, + 0x33dd87ff /* 00067bb0 - 000683af [ 2048] */, + 0x341d87ff /* 000683b0 - 00068baf [ 2048] */, + 0x345d87ff /* 00068bb0 - 000693af [ 2048] */, + 0x349d87ff /* 000693b0 - 00069baf [ 2048] */, + 0x34dd87ff /* 00069bb0 - 0006a3af [ 2048] */, + 0x351d87ff /* 0006a3b0 - 0006abaf [ 2048] */, + 0x355d87ff /* 0006abb0 - 0006b3af [ 2048] */, + 0x359d87ff /* 0006b3b0 - 0006bbaf [ 2048] */, + 0x35dd87ff /* 0006bbb0 - 0006c3af [ 2048] */, + 0x361d87ff /* 0006c3b0 - 0006cbaf [ 2048] */, + 0x365d87ff /* 0006cbb0 - 0006d3af [ 2048] */, + 0x369d87ff /* 0006d3b0 - 0006dbaf [ 2048] */, + 0x36dd87ff /* 0006dbb0 - 0006e3af [ 2048] */, + 0x371d87ff /* 0006e3b0 - 0006ebaf [ 2048] */, + 0x375d87ff /* 0006ebb0 - 0006f3af [ 2048] */, + 0x379d87ff /* 0006f3b0 - 0006fbaf [ 2048] */, + 0x37dd87ff /* 0006fbb0 - 000703af [ 2048] */, + 0x381d87ff /* 000703b0 - 00070baf [ 2048] */, + 0x385d87ff /* 00070bb0 - 000713af [ 2048] */, + 0x389d87ff /* 000713b0 - 00071baf [ 2048] */, + 0x38dd87ff /* 00071bb0 - 000723af [ 2048] */, + 0x391d87ff /* 000723b0 - 00072baf [ 2048] */, + 0x395d87ff /* 00072bb0 - 000733af [ 2048] */, + 0x399d87ff /* 000733b0 - 00073baf [ 2048] */, + 0x39dd87ff /* 00073bb0 - 000743af [ 2048] */, + 0x3a1d87ff /* 000743b0 - 00074baf [ 2048] */, + 0x3a5d87ff /* 00074bb0 - 000753af [ 2048] */, + 0x3a9d87ff /* 000753b0 - 00075baf [ 2048] */, + 0x3add87ff /* 00075bb0 - 000763af [ 2048] */, + 0x3b1d87ff /* 000763b0 - 00076baf [ 2048] */, + 0x3b5d87ff /* 00076bb0 - 000773af [ 2048] */, + 0x3b9d87ff /* 000773b0 - 00077baf [ 2048] */, + 0x3bdd87ff /* 00077bb0 - 000783af [ 2048] */, + 0x3c1d87ff /* 000783b0 - 00078baf [ 2048] */, + 0x3c5d87ff /* 00078bb0 - 000793af [ 2048] */, + 0x3c9d87ff /* 000793b0 - 00079baf [ 2048] */, + 0x3cdd87ff /* 00079bb0 - 0007a3af [ 2048] */, + 0x3d1d87ff /* 0007a3b0 - 0007abaf [ 2048] */, + 0x3d5d87ff /* 0007abb0 - 0007b3af [ 2048] */, + 0x3d9d87ff /* 0007b3b0 - 0007bbaf [ 2048] */, + 0x3ddd87ff /* 0007bbb0 - 0007c3af [ 2048] */, + 0x3e1d87ff /* 0007c3b0 - 0007cbaf [ 2048] */, + 0x3e5d87ff /* 0007cbb0 - 0007d3af [ 2048] */, + 0x3e9d87ff /* 0007d3b0 - 0007dbaf [ 2048] */, + 0x3edd87ff /* 0007dbb0 - 0007e3af [ 2048] */, + 0x3f1d87ff /* 0007e3b0 - 0007ebaf [ 2048] */, + 0x3f5d87ff /* 0007ebb0 - 0007f3af [ 2048] */, + 0x3f9d87ff /* 0007f3b0 - 0007fbaf [ 2048] */, + 0x3fdd87ff /* 0007fbb0 - 000803af [ 2048] */, + 0x401d87ff /* 000803b0 - 00080baf [ 2048] */, + 0x405d87ff /* 00080bb0 - 000813af [ 2048] */, + 0x409d87ff /* 000813b0 - 00081baf [ 2048] */, + 0x40dd87ff /* 00081bb0 - 000823af [ 2048] */, + 0x411d87ff /* 000823b0 - 00082baf [ 2048] */, + 0x415d87ff /* 00082bb0 - 000833af [ 2048] */, + 0x419d87ff /* 000833b0 - 00083baf [ 2048] */, + 0x41dd87ff /* 00083bb0 - 000843af [ 2048] */, + 0x421d87ff /* 000843b0 - 00084baf [ 2048] */, + 0x425d87ff /* 00084bb0 - 000853af [ 2048] */, + 0x429d87ff /* 000853b0 - 00085baf [ 2048] */, + 0x42dd87ff /* 00085bb0 - 000863af [ 2048] */, + 0x431d87ff /* 000863b0 - 00086baf [ 2048] */, + 0x435d87ff /* 00086bb0 - 000873af [ 2048] */, + 0x439d87ff /* 000873b0 - 00087baf [ 2048] */, + 0x43dd87ff /* 00087bb0 - 000883af [ 2048] */, + 0x441d87ff /* 000883b0 - 00088baf [ 2048] */, + 0x445d87ff /* 00088bb0 - 000893af [ 2048] */, + 0x449d87ff /* 000893b0 - 00089baf [ 2048] */, + 0x44dd87ff /* 00089bb0 - 0008a3af [ 2048] */, + 0x451d87ff /* 0008a3b0 - 0008abaf [ 2048] */, + 0x455d87ff /* 0008abb0 - 0008b3af [ 2048] */, + 0x459d87ff /* 0008b3b0 - 0008bbaf [ 2048] */, + 0x45dd87ff /* 0008bbb0 - 0008c3af [ 2048] */, + 0x461d87ff /* 0008c3b0 - 0008cbaf [ 2048] */, + 0x465d87ff /* 0008cbb0 - 0008d3af [ 2048] */, + 0x469d87ff /* 0008d3b0 - 0008dbaf [ 2048] */, + 0x46dd87ff /* 0008dbb0 - 0008e3af [ 2048] */, + 0x471d87ff /* 0008e3b0 - 0008ebaf [ 2048] */, + 0x475d87ff /* 0008ebb0 - 0008f3af [ 2048] */, + 0x479d87ff /* 0008f3b0 - 0008fbaf [ 2048] */, + 0x47dd87ff /* 0008fbb0 - 000903af [ 2048] */, + 0x481d87ff /* 000903b0 - 00090baf [ 2048] */, + 0x485d87ff /* 00090bb0 - 000913af [ 2048] */, + 0x489d87ff /* 000913b0 - 00091baf [ 2048] */, + 0x48dd87ff /* 00091bb0 - 000923af [ 2048] */, + 0x491d87ff /* 000923b0 - 00092baf [ 2048] */, + 0x495d87ff /* 00092bb0 - 000933af [ 2048] */, + 0x499d87ff /* 000933b0 - 00093baf [ 2048] */, + 0x49dd87ff /* 00093bb0 - 000943af [ 2048] */, + 0x4a1d87ff /* 000943b0 - 00094baf [ 2048] */, + 0x4a5d87ff /* 00094bb0 - 000953af [ 2048] */, + 0x4a9d87ff /* 000953b0 - 00095baf [ 2048] */, + 0x4add87ff /* 00095bb0 - 000963af [ 2048] */, + 0x4b1d87ff /* 000963b0 - 00096baf [ 2048] */, + 0x4b5d87ff /* 00096bb0 - 000973af [ 2048] */, + 0x4b9d87ff /* 000973b0 - 00097baf [ 2048] */, + 0x4bdd87ff /* 00097bb0 - 000983af [ 2048] */, + 0x4c1d87ff /* 000983b0 - 00098baf [ 2048] */, + 0x4c5d87ff /* 00098bb0 - 000993af [ 2048] */, + 0x4c9d87ff /* 000993b0 - 00099baf [ 2048] */, + 0x4cdd87ff /* 00099bb0 - 0009a3af [ 2048] */, + 0x4d1d87ff /* 0009a3b0 - 0009abaf [ 2048] */, + 0x4d5d87ff /* 0009abb0 - 0009b3af [ 2048] */, + 0x4d9d87ff /* 0009b3b0 - 0009bbaf [ 2048] */, + 0x4ddd87ff /* 0009bbb0 - 0009c3af [ 2048] */, + 0x4e1d87ff /* 0009c3b0 - 0009cbaf [ 2048] */, + 0x4e5d87ff /* 0009cbb0 - 0009d3af [ 2048] */, + 0x4e9d87ff /* 0009d3b0 - 0009dbaf [ 2048] */, + 0x4edd87ff /* 0009dbb0 - 0009e3af [ 2048] */, + 0x4f1d87ff /* 0009e3b0 - 0009ebaf [ 2048] */, + 0x4f5d87ff /* 0009ebb0 - 0009f3af [ 2048] */, + 0x4f9d87ff /* 0009f3b0 - 0009fbaf [ 2048] */, + 0x4fdd87ff /* 0009fbb0 - 000a03af [ 2048] */, + 0x501d87ff /* 000a03b0 - 000a0baf [ 2048] */, + 0x505d87ff /* 000a0bb0 - 000a13af [ 2048] */, + 0x509d87ff /* 000a13b0 - 000a1baf [ 2048] */, + 0x50dd87ff /* 000a1bb0 - 000a23af [ 2048] */, + 0x511d87ff /* 000a23b0 - 000a2baf [ 2048] */, + 0x515d87ff /* 000a2bb0 - 000a33af [ 2048] */, + 0x519d87ff /* 000a33b0 - 000a3baf [ 2048] */, + 0x51dd87ff /* 000a3bb0 - 000a43af [ 2048] */, + 0x521d87ff /* 000a43b0 - 000a4baf [ 2048] */, + 0x525d87ff /* 000a4bb0 - 000a53af [ 2048] */, + 0x529d87ff /* 000a53b0 - 000a5baf [ 2048] */, + 0x52dd87ff /* 000a5bb0 - 000a63af [ 2048] */, + 0x531d87ff /* 000a63b0 - 000a6baf [ 2048] */, + 0x535d87ff /* 000a6bb0 - 000a73af [ 2048] */, + 0x539d87ff /* 000a73b0 - 000a7baf [ 2048] */, + 0x53dd87ff /* 000a7bb0 - 000a83af [ 2048] */, + 0x541d87ff /* 000a83b0 - 000a8baf [ 2048] */, + 0x545d87ff /* 000a8bb0 - 000a93af [ 2048] */, + 0x549d87ff /* 000a93b0 - 000a9baf [ 2048] */, + 0x54dd87ff /* 000a9bb0 - 000aa3af [ 2048] */, + 0x551d87ff /* 000aa3b0 - 000aabaf [ 2048] */, + 0x555d87ff /* 000aabb0 - 000ab3af [ 2048] */, + 0x559d87ff /* 000ab3b0 - 000abbaf [ 2048] */, + 0x55dd87ff /* 000abbb0 - 000ac3af [ 2048] */, + 0x561d87ff /* 000ac3b0 - 000acbaf [ 2048] */, + 0x565d87ff /* 000acbb0 - 000ad3af [ 2048] */, + 0x569d87ff /* 000ad3b0 - 000adbaf [ 2048] */, + 0x56dd87ff /* 000adbb0 - 000ae3af [ 2048] */, + 0x571d87ff /* 000ae3b0 - 000aebaf [ 2048] */, + 0x575d87ff /* 000aebb0 - 000af3af [ 2048] */, + 0x579d87ff /* 000af3b0 - 000afbaf [ 2048] */, + 0x57dd87ff /* 000afbb0 - 000b03af [ 2048] */, + 0x581d87ff /* 000b03b0 - 000b0baf [ 2048] */, + 0x585d87ff /* 000b0bb0 - 000b13af [ 2048] */, + 0x589d87ff /* 000b13b0 - 000b1baf [ 2048] */, + 0x58dd87ff /* 000b1bb0 - 000b23af [ 2048] */, + 0x591d87ff /* 000b23b0 - 000b2baf [ 2048] */, + 0x595d87ff /* 000b2bb0 - 000b33af [ 2048] */, + 0x599d87ff /* 000b33b0 - 000b3baf [ 2048] */, + 0x59dd87ff /* 000b3bb0 - 000b43af [ 2048] */, + 0x5a1d87ff /* 000b43b0 - 000b4baf [ 2048] */, + 0x5a5d87ff /* 000b4bb0 - 000b53af [ 2048] */, + 0x5a9d87ff /* 000b53b0 - 000b5baf [ 2048] */, + 0x5add87ff /* 000b5bb0 - 000b63af [ 2048] */, + 0x5b1d87ff /* 000b63b0 - 000b6baf [ 2048] */, + 0x5b5d87ff /* 000b6bb0 - 000b73af [ 2048] */, + 0x5b9d87ff /* 000b73b0 - 000b7baf [ 2048] */, + 0x5bdd87ff /* 000b7bb0 - 000b83af [ 2048] */, + 0x5c1d87ff /* 000b83b0 - 000b8baf [ 2048] */, + 0x5c5d87ff /* 000b8bb0 - 000b93af [ 2048] */, + 0x5c9d87ff /* 000b93b0 - 000b9baf [ 2048] */, + 0x5cdd87ff /* 000b9bb0 - 000ba3af [ 2048] */, + 0x5d1d87ff /* 000ba3b0 - 000babaf [ 2048] */, + 0x5d5d87ff /* 000babb0 - 000bb3af [ 2048] */, + 0x5d9d87ff /* 000bb3b0 - 000bbbaf [ 2048] */, + 0x5ddd87ff /* 000bbbb0 - 000bc3af [ 2048] */, + 0x5e1d87ff /* 000bc3b0 - 000bcbaf [ 2048] */, + 0x5e5d87ff /* 000bcbb0 - 000bd3af [ 2048] */, + 0x5e9d87ff /* 000bd3b0 - 000bdbaf [ 2048] */, + 0x5edd87ff /* 000bdbb0 - 000be3af [ 2048] */, + 0x5f1d87ff /* 000be3b0 - 000bebaf [ 2048] */, + 0x5f5d87ff /* 000bebb0 - 000bf3af [ 2048] */, + 0x5f9d87ff /* 000bf3b0 - 000bfbaf [ 2048] */, + 0x5fdd87ff /* 000bfbb0 - 000c03af [ 2048] */, + 0x601d87ff /* 000c03b0 - 000c0baf [ 2048] */, + 0x605d87ff /* 000c0bb0 - 000c13af [ 2048] */, + 0x609d87ff /* 000c13b0 - 000c1baf [ 2048] */, + 0x60dd87ff /* 000c1bb0 - 000c23af [ 2048] */, + 0x611d87ff /* 000c23b0 - 000c2baf [ 2048] */, + 0x615d87ff /* 000c2bb0 - 000c33af [ 2048] */, + 0x619d87ff /* 000c33b0 - 000c3baf [ 2048] */, + 0x61dd87ff /* 000c3bb0 - 000c43af [ 2048] */, + 0x621d87ff /* 000c43b0 - 000c4baf [ 2048] */, + 0x625d87ff /* 000c4bb0 - 000c53af [ 2048] */, + 0x629d87ff /* 000c53b0 - 000c5baf [ 2048] */, + 0x62dd87ff /* 000c5bb0 - 000c63af [ 2048] */, + 0x631d87ff /* 000c63b0 - 000c6baf [ 2048] */, + 0x635d87ff /* 000c6bb0 - 000c73af [ 2048] */, + 0x639d87ff /* 000c73b0 - 000c7baf [ 2048] */, + 0x63dd87ff /* 000c7bb0 - 000c83af [ 2048] */, + 0x641d87ff /* 000c83b0 - 000c8baf [ 2048] */, + 0x645d87ff /* 000c8bb0 - 000c93af [ 2048] */, + 0x649d87ff /* 000c93b0 - 000c9baf [ 2048] */, + 0x64dd87ff /* 000c9bb0 - 000ca3af [ 2048] */, + 0x651d87ff /* 000ca3b0 - 000cabaf [ 2048] */, + 0x655d87ff /* 000cabb0 - 000cb3af [ 2048] */, + 0x659d87ff /* 000cb3b0 - 000cbbaf [ 2048] */, + 0x65dd87ff /* 000cbbb0 - 000cc3af [ 2048] */, + 0x661d87ff /* 000cc3b0 - 000ccbaf [ 2048] */, + 0x665d87ff /* 000ccbb0 - 000cd3af [ 2048] */, + 0x669d87ff /* 000cd3b0 - 000cdbaf [ 2048] */, + 0x66dd87ff /* 000cdbb0 - 000ce3af [ 2048] */, + 0x671d87ff /* 000ce3b0 - 000cebaf [ 2048] */, + 0x675d87ff /* 000cebb0 - 000cf3af [ 2048] */, + 0x679d87ff /* 000cf3b0 - 000cfbaf [ 2048] */, + 0x67dd87ff /* 000cfbb0 - 000d03af [ 2048] */, + 0x681d87ff /* 000d03b0 - 000d0baf [ 2048] */, + 0x685d87ff /* 000d0bb0 - 000d13af [ 2048] */, + 0x689d87ff /* 000d13b0 - 000d1baf [ 2048] */, + 0x68dd87ff /* 000d1bb0 - 000d23af [ 2048] */, + 0x691d87ff /* 000d23b0 - 000d2baf [ 2048] */, + 0x695d87ff /* 000d2bb0 - 000d33af [ 2048] */, + 0x699d87ff /* 000d33b0 - 000d3baf [ 2048] */, + 0x69dd87ff /* 000d3bb0 - 000d43af [ 2048] */, + 0x6a1d87ff /* 000d43b0 - 000d4baf [ 2048] */, + 0x6a5d87ff /* 000d4bb0 - 000d53af [ 2048] */, + 0x6a9d87ff /* 000d53b0 - 000d5baf [ 2048] */, + 0x6add87ff /* 000d5bb0 - 000d63af [ 2048] */, + 0x6b1d87ff /* 000d63b0 - 000d6baf [ 2048] */, + 0x6b5d87ff /* 000d6bb0 - 000d73af [ 2048] */, + 0x6b9d87ff /* 000d73b0 - 000d7baf [ 2048] */, + 0x6bdd87ff /* 000d7bb0 - 000d83af [ 2048] */, + 0x6c1d87ff /* 000d83b0 - 000d8baf [ 2048] */, + 0x6c5d87ff /* 000d8bb0 - 000d93af [ 2048] */, + 0x6c9d87ff /* 000d93b0 - 000d9baf [ 2048] */, + 0x6cdd87ff /* 000d9bb0 - 000da3af [ 2048] */, + 0x6d1d87ff /* 000da3b0 - 000dabaf [ 2048] */, + 0x6d5d87ff /* 000dabb0 - 000db3af [ 2048] */, + 0x6d9d87ff /* 000db3b0 - 000dbbaf [ 2048] */, + 0x6ddd87ff /* 000dbbb0 - 000dc3af [ 2048] */, + 0x6e1d87ff /* 000dc3b0 - 000dcbaf [ 2048] */, + 0x6e5d87ff /* 000dcbb0 - 000dd3af [ 2048] */, + 0x6e9d87ff /* 000dd3b0 - 000ddbaf [ 2048] */, + 0x6edd87ff /* 000ddbb0 - 000de3af [ 2048] */, + 0x6f1d87ff /* 000de3b0 - 000debaf [ 2048] */, + 0x6f5d87ff /* 000debb0 - 000df3af [ 2048] */, + 0x6f9d87ff /* 000df3b0 - 000dfbaf [ 2048] */, + 0x6fdd854f /* 000dfbb0 - 000e00ff [ 1360] */}; /// At the end of the valid Unicode code points space a lot of code points are /// either reserved or a noncharacter. Adding all these entries to the /// lookup table would add 446 entries to the table (in Unicode 14). /// Instead the only the start of the region is stored, every code point in /// this region needs to be escaped. -inline constexpr uint32_t __unallocated_region_lower_bound = 0x000323b0; +_LIBCPP_HIDE_FROM_ABI inline constexpr uint32_t __unallocated_region_lower_bound = 0x000e01f0; /// Returns whether the code unit needs to be escaped. /// diff --git a/libcxx/include/__format/write_escaped.h b/libcxx/include/__format/write_escaped.h index 43a074dd8d7002572a7d1b4d94baf07431d098ad..052ea98c3c3b8c5c2764801c2d6886c5cf932c69 100644 --- a/libcxx/include/__format/write_escaped.h +++ b/libcxx/include/__format/write_escaped.h @@ -101,15 +101,27 @@ _LIBCPP_HIDE_FROM_ABI void __write_escape_ill_formed_code_unit(basic_string<_Cha } template -[[nodiscard]] _LIBCPP_HIDE_FROM_ABI bool __is_escaped_sequence_written(basic_string<_CharT>& __str, char32_t __value) { +[[nodiscard]] _LIBCPP_HIDE_FROM_ABI bool +__is_escaped_sequence_written(basic_string<_CharT>& __str, bool __last_escaped, char32_t __value) { # ifdef _LIBCPP_HAS_NO_UNICODE // For ASCII assume everything above 127 is printable. if (__value > 127) return false; # endif + // [format.string.escaped]/2.2.1.2.1 + // CE is UTF-8, UTF-16, or UTF-32 and C corresponds to a Unicode scalar + // value whose Unicode property General_Category has a value in the groups + // Separator (Z) or Other (C), as described by UAX #44 of the Unicode Standard, if (!__escaped_output_table::__needs_escape(__value)) - return false; + // [format.string.escaped]/2.2.1.2.2 + // CE is UTF-8, UTF-16, or UTF-32 and C corresponds to a Unicode scalar + // value with the Unicode property Grapheme_Extend=Yes as described by UAX + // #44 of the Unicode Standard and C is not immediately preceded in S by a + // character P appended to E without translation to an escape sequence, + if (!__last_escaped || __extended_grapheme_custer_property_boundary::__get_property(__value) != + __extended_grapheme_custer_property_boundary::__property::__Extend) + return false; __formatter::__write_well_formed_escaped_code_unit(__str, __value); return true; @@ -124,8 +136,8 @@ enum class __escape_quotation_mark { __apostrophe, __double_quote }; // [format.string.escaped]/2 template -[[nodiscard]] _LIBCPP_HIDE_FROM_ABI bool -__is_escaped_sequence_written(basic_string<_CharT>& __str, char32_t __value, __escape_quotation_mark __mark) { +[[nodiscard]] _LIBCPP_HIDE_FROM_ABI bool __is_escaped_sequence_written( + basic_string<_CharT>& __str, char32_t __value, bool __last_escaped, __escape_quotation_mark __mark) { // 2.2.1.1 - Mapped character in [tab:format.escape.sequences] switch (__value) { case _CharT('\t'): @@ -167,7 +179,7 @@ __is_escaped_sequence_written(basic_string<_CharT>& __str, char32_t __value, __e // TODO FMT determine what to do with shift sequences. // 2.2.1.2.1 and 2.2.1.2.2 - Escape - return __formatter::__is_escaped_sequence_written(__str, __formatter::__to_char32(__value)); + return __formatter::__is_escaped_sequence_written(__str, __last_escaped, __formatter::__to_char32(__value)); } template @@ -175,11 +187,15 @@ _LIBCPP_HIDE_FROM_ABI void __escape(basic_string<_CharT>& __str, basic_string_view<_CharT> __values, __escape_quotation_mark __mark) { __unicode::__code_point_view<_CharT> __view{__values.begin(), __values.end()}; + // When the first code unit has the property Grapheme_Extend=Yes it needs to + // be escaped. This happens when the previous code unit was also escaped. + bool __escape = true; while (!__view.__at_end()) { auto __first = __view.__position(); typename __unicode::__consume_result __result = __view.__consume(); if (__result.__status == __unicode::__consume_result::__ok) { - if (!__formatter::__is_escaped_sequence_written(__str, __result.__code_point, __mark)) + __escape = __formatter::__is_escaped_sequence_written(__str, __result.__code_point, __escape, __mark); + if (!__escape) // 2.2.1.3 - Add the character ranges::copy(__first, __view.__position(), std::back_insert_iterator(__str)); } else { diff --git a/libcxx/include/__numeric/saturation_arithmetic.h b/libcxx/include/__numeric/saturation_arithmetic.h index 41596a0c58e27de98128b10331268ac830fda574..2390b42aaec31e012b2e1ea36aabe90db4c23d71 100644 --- a/libcxx/include/__numeric/saturation_arithmetic.h +++ b/libcxx/include/__numeric/saturation_arithmetic.h @@ -25,10 +25,10 @@ _LIBCPP_PUSH_MACROS _LIBCPP_BEGIN_NAMESPACE_STD -#if _LIBCPP_STD_VER >= 26 +#if _LIBCPP_STD_VER >= 20 template <__libcpp_integer _Tp> -_LIBCPP_HIDE_FROM_ABI constexpr _Tp add_sat(_Tp __x, _Tp __y) noexcept { +_LIBCPP_HIDE_FROM_ABI constexpr _Tp __add_sat(_Tp __x, _Tp __y) noexcept { if (_Tp __sum; !__builtin_add_overflow(__x, __y, &__sum)) return __sum; // Handle overflow @@ -46,7 +46,7 @@ _LIBCPP_HIDE_FROM_ABI constexpr _Tp add_sat(_Tp __x, _Tp __y) noexcept { } template <__libcpp_integer _Tp> -_LIBCPP_HIDE_FROM_ABI constexpr _Tp sub_sat(_Tp __x, _Tp __y) noexcept { +_LIBCPP_HIDE_FROM_ABI constexpr _Tp __sub_sat(_Tp __x, _Tp __y) noexcept { if (_Tp __sub; !__builtin_sub_overflow(__x, __y, &__sub)) return __sub; // Handle overflow @@ -65,7 +65,7 @@ _LIBCPP_HIDE_FROM_ABI constexpr _Tp sub_sat(_Tp __x, _Tp __y) noexcept { } template <__libcpp_integer _Tp> -_LIBCPP_HIDE_FROM_ABI constexpr _Tp mul_sat(_Tp __x, _Tp __y) noexcept { +_LIBCPP_HIDE_FROM_ABI constexpr _Tp __mul_sat(_Tp __x, _Tp __y) noexcept { if (_Tp __mul; !__builtin_mul_overflow(__x, __y, &__mul)) return __mul; // Handle overflow @@ -81,7 +81,7 @@ _LIBCPP_HIDE_FROM_ABI constexpr _Tp mul_sat(_Tp __x, _Tp __y) noexcept { } template <__libcpp_integer _Tp> -_LIBCPP_HIDE_FROM_ABI constexpr _Tp div_sat(_Tp __x, _Tp __y) noexcept { +_LIBCPP_HIDE_FROM_ABI constexpr _Tp __div_sat(_Tp __x, _Tp __y) noexcept { _LIBCPP_ASSERT_UNCATEGORIZED(__y != 0, "Division by 0 is undefined"); if constexpr (__libcpp_unsigned_integer<_Tp>) { return __x / __y; @@ -94,7 +94,7 @@ _LIBCPP_HIDE_FROM_ABI constexpr _Tp div_sat(_Tp __x, _Tp __y) noexcept { } template <__libcpp_integer _Rp, __libcpp_integer _Tp> -_LIBCPP_HIDE_FROM_ABI constexpr _Rp saturate_cast(_Tp __x) noexcept { +_LIBCPP_HIDE_FROM_ABI constexpr _Rp __saturate_cast(_Tp __x) noexcept { // Saturation is impossible edge case when ((min _Rp) < (min _Tp) && (max _Rp) > (max _Tp)) and it is expected to be // optimized out by the compiler. @@ -107,6 +107,35 @@ _LIBCPP_HIDE_FROM_ABI constexpr _Rp saturate_cast(_Tp __x) noexcept { return static_cast<_Rp>(__x); } +#endif // _LIBCPP_STD_VER >= 20 + +#if _LIBCPP_STD_VER >= 26 + +template <__libcpp_integer _Tp> +_LIBCPP_HIDE_FROM_ABI constexpr _Tp add_sat(_Tp __x, _Tp __y) noexcept { + return std::__add_sat(__x, __y); +} + +template <__libcpp_integer _Tp> +_LIBCPP_HIDE_FROM_ABI constexpr _Tp sub_sat(_Tp __x, _Tp __y) noexcept { + return std::__sub_sat(__x, __y); +} + +template <__libcpp_integer _Tp> +_LIBCPP_HIDE_FROM_ABI constexpr _Tp mul_sat(_Tp __x, _Tp __y) noexcept { + return std::__mul_sat(__x, __y); +} + +template <__libcpp_integer _Tp> +_LIBCPP_HIDE_FROM_ABI constexpr _Tp div_sat(_Tp __x, _Tp __y) noexcept { + return std::__div_sat(__x, __y); +} + +template <__libcpp_integer _Rp, __libcpp_integer _Tp> +_LIBCPP_HIDE_FROM_ABI constexpr _Rp saturate_cast(_Tp __x) noexcept { + return std::__saturate_cast<_Rp>(__x); +} + #endif // _LIBCPP_STD_VER >= 26 _LIBCPP_END_NAMESPACE_STD diff --git a/libcxx/include/__ranges/range_adaptor.h b/libcxx/include/__ranges/range_adaptor.h index 726b7eda019ee3abc8098bf7e682f74978bb3c1a..2da246f24e1d2f2a782e95bfdf5f521ef234cd94 100644 --- a/libcxx/include/__ranges/range_adaptor.h +++ b/libcxx/include/__ranges/range_adaptor.h @@ -19,6 +19,7 @@ #include <__functional/invoke.h> #include <__ranges/concepts.h> #include <__type_traits/decay.h> +#include <__type_traits/is_class.h> #include <__type_traits/is_nothrow_constructible.h> #include <__type_traits/remove_cvref.h> #include <__utility/forward.h> @@ -35,12 +36,15 @@ _LIBCPP_BEGIN_NAMESPACE_STD #if _LIBCPP_STD_VER >= 20 +namespace ranges { + // CRTP base that one can derive from in order to be considered a range adaptor closure // by the library. When deriving from this class, a pipe operator will be provided to // make the following hold: // - `x | f` is equivalent to `f(x)` // - `f1 | f2` is an adaptor closure `g` such that `g(x)` is equivalent to `f2(f1(x))` template + requires is_class_v<_Tp> && same_as<_Tp, remove_cv_t<_Tp>> struct __range_adaptor_closure; // Type that wraps an arbitrary function object and makes it into a range adaptor closure, @@ -52,27 +56,42 @@ struct __range_adaptor_closure_t : _Fn, __range_adaptor_closure<__range_adaptor_ _LIBCPP_CTAD_SUPPORTED_FOR_TYPE(__range_adaptor_closure_t); template -concept _RangeAdaptorClosure = derived_from, __range_adaptor_closure>>; +_Tp __derived_from_range_adaptor_closure(__range_adaptor_closure<_Tp>*); template -struct __range_adaptor_closure { - template - requires same_as<_Tp, remove_cvref_t<_Closure>> && invocable<_Closure, _View> - [[nodiscard]] _LIBCPP_HIDE_FROM_ABI friend constexpr decltype(auto) - operator|(_View&& __view, _Closure&& __closure) noexcept(is_nothrow_invocable_v<_Closure, _View>) { - return std::invoke(std::forward<_Closure>(__closure), std::forward<_View>(__view)); - } - - template <_RangeAdaptorClosure _Closure, _RangeAdaptorClosure _OtherClosure> - requires same_as<_Tp, remove_cvref_t<_Closure>> && constructible_from, _Closure> && - constructible_from, _OtherClosure> - [[nodiscard]] _LIBCPP_HIDE_FROM_ABI friend constexpr auto operator|(_Closure&& __c1, _OtherClosure&& __c2) noexcept( - is_nothrow_constructible_v, _Closure> && - is_nothrow_constructible_v, _OtherClosure>) { - return __range_adaptor_closure_t(std::__compose(std::forward<_OtherClosure>(__c2), std::forward<_Closure>(__c1))); - } +concept _RangeAdaptorClosure = !ranges::range> && requires { + // Ensure that `remove_cvref_t<_Tp>` is derived from `__range_adaptor_closure>` and isn't derived + // from `__range_adaptor_closure` for any other type `U`. + { ranges::__derived_from_range_adaptor_closure((remove_cvref_t<_Tp>*)nullptr) } -> same_as>; }; +template + requires invocable<_Closure, _Range> +[[nodiscard]] _LIBCPP_HIDE_FROM_ABI constexpr decltype(auto) +operator|(_Range&& __range, _Closure&& __closure) noexcept(is_nothrow_invocable_v<_Closure, _Range>) { + return std::invoke(std::forward<_Closure>(__closure), std::forward<_Range>(__range)); +} + +template <_RangeAdaptorClosure _Closure, _RangeAdaptorClosure _OtherClosure> + requires constructible_from, _Closure> && constructible_from, _OtherClosure> +[[nodiscard]] _LIBCPP_HIDE_FROM_ABI constexpr auto operator|(_Closure&& __c1, _OtherClosure&& __c2) noexcept( + is_nothrow_constructible_v, _Closure> && + is_nothrow_constructible_v, _OtherClosure>) { + return __range_adaptor_closure_t(std::__compose(std::forward<_OtherClosure>(__c2), std::forward<_Closure>(__c1))); +} + +template + requires is_class_v<_Tp> && same_as<_Tp, remove_cv_t<_Tp>> +struct __range_adaptor_closure {}; + +# if _LIBCPP_STD_VER >= 23 +template + requires is_class_v<_Tp> && same_as<_Tp, remove_cv_t<_Tp>> +class range_adaptor_closure : public __range_adaptor_closure<_Tp> {}; +# endif // _LIBCPP_STD_VER >= 23 + +} // namespace ranges + #endif // _LIBCPP_STD_VER >= 20 _LIBCPP_END_NAMESPACE_STD diff --git a/libcxx/include/ranges b/libcxx/include/ranges index 167d2137eaf45407b57754fa8360318255a83b49..07a525ed8641fdb1939e6b2998393a83cbda4837 100644 --- a/libcxx/include/ranges +++ b/libcxx/include/ranges @@ -93,6 +93,11 @@ namespace std::ranges { template concept viewable_range = see below; + // [range.adaptor.object], range adaptor objects + template + requires is_class_v && same_as> + class range_adaptor_closure { }; // Since c++23 + // [view.interface], class template view_interface template requires is_class_v && same_as> diff --git a/libcxx/include/streambuf b/libcxx/include/streambuf index 7964758c908f4ca2e0a674201baa99b5f6746b16..a5b4ab9520aedbe56f78277726cbeb87e26daf9c 100644 --- a/libcxx/include/streambuf +++ b/libcxx/include/streambuf @@ -107,10 +107,12 @@ protected: */ +#include <__assert> #include <__config> #include <__fwd/streambuf.h> #include <__locale> #include <__type_traits/is_same.h> +#include <__utility/is_valid_range.h> #include #include #include @@ -234,6 +236,9 @@ protected: inline _LIBCPP_HIDE_FROM_ABI_AFTER_V1 void gbump(int __n) { __ninp_ += __n; } inline _LIBCPP_HIDE_FROM_ABI_AFTER_V1 void setg(char_type* __gbeg, char_type* __gnext, char_type* __gend) { + _LIBCPP_ASSERT_VALID_INPUT_RANGE(std::__is_valid_range(__gbeg, __gnext), "[gbeg, gnext) must be a valid range"); + _LIBCPP_ASSERT_VALID_INPUT_RANGE(std::__is_valid_range(__gbeg, __gend), "[gbeg, gend) must be a valid range"); + _LIBCPP_ASSERT_VALID_INPUT_RANGE(std::__is_valid_range(__gnext, __gend), "[gnext, gend) must be a valid range"); __binp_ = __gbeg; __ninp_ = __gnext; __einp_ = __gend; @@ -249,6 +254,7 @@ protected: _LIBCPP_HIDE_FROM_ABI void __pbump(streamsize __n) { __nout_ += __n; } inline _LIBCPP_HIDE_FROM_ABI_AFTER_V1 void setp(char_type* __pbeg, char_type* __pend) { + _LIBCPP_ASSERT_VALID_INPUT_RANGE(std::__is_valid_range(__pbeg, __pend), "[pbeg, pend) must be a valid range"); __bout_ = __nout_ = __pbeg; __eout_ = __pend; } diff --git a/libcxx/include/variant b/libcxx/include/variant index 858a49b980bd9a66ce1acc8d5ba459ea0214a900..34150bd452842e4bf604eba6071d1cd19fd5eecd 100644 --- a/libcxx/include/variant +++ b/libcxx/include/variant @@ -657,6 +657,10 @@ private: } // namespace __visitation +// Adding semi-colons in macro expansions helps clang-format to do a better job. +// This macro is used to avoid compilation errors due to "stray" semi-colons. +# define _LIBCPP_EAT_SEMICOLON static_assert(true, "") + template struct _LIBCPP_TEMPLATE_VIS __alt { using __value_type = _Tp; @@ -691,11 +695,10 @@ union _LIBCPP_TEMPLATE_VIS __union<_DestructibleTrait, _Index> {}; __union(const __union&) = default; \ __union(__union&&) = default; \ \ - destructor \ + destructor; \ \ - __union& \ - operator=(const __union&) = default; \ - __union& operator=(__union&&) = default; \ + __union& operator=(const __union&) = default; \ + __union& operator=(__union&&) = default; \ \ private: \ char __dummy; \ @@ -705,9 +708,10 @@ union _LIBCPP_TEMPLATE_VIS __union<_DestructibleTrait, _Index> {}; friend struct __access::__union; \ } -_LIBCPP_VARIANT_UNION(_Trait::_TriviallyAvailable, ~__union() = default;); -_LIBCPP_VARIANT_UNION(_Trait::_Available, ~__union(){}); -_LIBCPP_VARIANT_UNION(_Trait::_Unavailable, ~__union() = delete;); +_LIBCPP_VARIANT_UNION(_Trait::_TriviallyAvailable, ~__union() = default); +_LIBCPP_VARIANT_UNION( + _Trait::_Available, _LIBCPP_HIDE_FROM_ABI ~__union() {} _LIBCPP_EAT_SEMICOLON); +_LIBCPP_VARIANT_UNION(_Trait::_Unavailable, ~__union() = delete); # undef _LIBCPP_VARIANT_UNION @@ -761,23 +765,27 @@ class _LIBCPP_TEMPLATE_VIS __dtor; using __base_type::__base_type; \ using __base_type::operator=; \ \ - __dtor(const __dtor&) = default; \ - __dtor(__dtor&&) = default; \ - destructor __dtor& operator=(const __dtor&) = default; \ - __dtor& operator=(__dtor&&) = default; \ + __dtor(const __dtor&) = default; \ + __dtor(__dtor&&) = default; \ + __dtor& operator=(const __dtor&) = default; \ + __dtor& operator=(__dtor&&) = default; \ + destructor; \ \ protected: \ - inline _LIBCPP_HIDE_FROM_ABI destroy \ + inline _LIBCPP_HIDE_FROM_ABI destroy; \ } _LIBCPP_VARIANT_DESTRUCTOR( - _Trait::_TriviallyAvailable, ~__dtor() = default; - , void __destroy() noexcept { this->__index = __variant_npos<__index_t>; }); + _Trait::_TriviallyAvailable, + ~__dtor() = default, // + _LIBCPP_HIDE_FROM_ABI void __destroy() noexcept { + this->__index = __variant_npos<__index_t>; + } _LIBCPP_EAT_SEMICOLON); _LIBCPP_VARIANT_DESTRUCTOR( _Trait::_Available, - ~__dtor() { __destroy(); }, - void __destroy() noexcept { + _LIBCPP_HIDE_FROM_ABI ~__dtor() { __destroy(); } _LIBCPP_EAT_SEMICOLON, + _LIBCPP_HIDE_FROM_ABI void __destroy() noexcept { if (!this->valueless_by_exception()) { __visitation::__base::__visit_alt( [](auto& __alt) noexcept { @@ -787,9 +795,9 @@ _LIBCPP_VARIANT_DESTRUCTOR( *this); } this->__index = __variant_npos<__index_t>; - }); + } _LIBCPP_EAT_SEMICOLON); -_LIBCPP_VARIANT_DESTRUCTOR(_Trait::_Unavailable, ~__dtor() = delete;, void __destroy() noexcept = delete;); +_LIBCPP_VARIANT_DESTRUCTOR(_Trait::_Unavailable, ~__dtor() = delete, void __destroy() noexcept = delete); # undef _LIBCPP_VARIANT_DESTRUCTOR @@ -839,20 +847,24 @@ class _LIBCPP_TEMPLATE_VIS __move_constructor; using __base_type::operator=; \ \ __move_constructor(const __move_constructor&) = default; \ - move_constructor ~__move_constructor() = default; \ + ~__move_constructor() = default; \ __move_constructor& operator=(const __move_constructor&) = default; \ __move_constructor& operator=(__move_constructor&&) = default; \ + move_constructor; \ } _LIBCPP_VARIANT_MOVE_CONSTRUCTOR(_Trait::_TriviallyAvailable, - __move_constructor(__move_constructor&& __that) = default;); + __move_constructor(__move_constructor&& __that) = default); _LIBCPP_VARIANT_MOVE_CONSTRUCTOR( _Trait::_Available, - __move_constructor(__move_constructor&& __that) noexcept(__all...>::value) - : __move_constructor(__valueless_t{}) { this->__generic_construct(*this, std::move(__that)); }); + _LIBCPP_HIDE_FROM_ABI __move_constructor(__move_constructor&& __that) noexcept( + __all...>::value) + : __move_constructor(__valueless_t{}) { + this->__generic_construct(*this, std::move(__that)); + } _LIBCPP_EAT_SEMICOLON); -_LIBCPP_VARIANT_MOVE_CONSTRUCTOR(_Trait::_Unavailable, __move_constructor(__move_constructor&&) = delete;); +_LIBCPP_VARIANT_MOVE_CONSTRUCTOR(_Trait::_Unavailable, __move_constructor(__move_constructor&&) = delete); # undef _LIBCPP_VARIANT_MOVE_CONSTRUCTOR @@ -869,20 +881,21 @@ class _LIBCPP_TEMPLATE_VIS __copy_constructor; using __base_type::__base_type; \ using __base_type::operator=; \ \ - copy_constructor __copy_constructor(__copy_constructor&&) = default; \ - ~__copy_constructor() = default; \ - __copy_constructor& operator=(const __copy_constructor&) = default; \ - __copy_constructor& operator=(__copy_constructor&&) = default; \ - } + __copy_constructor(__copy_constructor&&) = default; \ + ~__copy_constructor() = default; \ + __copy_constructor& operator=(const __copy_constructor&) = default; \ + __copy_constructor& operator=(__copy_constructor&&) = default; \ + copy_constructor; \ + } // namespace __variant_detail _LIBCPP_VARIANT_COPY_CONSTRUCTOR(_Trait::_TriviallyAvailable, - __copy_constructor(const __copy_constructor& __that) = default;); + __copy_constructor(const __copy_constructor& __that) = default); _LIBCPP_VARIANT_COPY_CONSTRUCTOR( - _Trait::_Available, __copy_constructor(const __copy_constructor& __that) - : __copy_constructor(__valueless_t{}) { this->__generic_construct(*this, __that); }); + _Trait::_Available, _LIBCPP_HIDE_FROM_ABI __copy_constructor(const __copy_constructor& __that) + : __copy_constructor(__valueless_t{}) { this->__generic_construct(*this, __that); } _LIBCPP_EAT_SEMICOLON); -_LIBCPP_VARIANT_COPY_CONSTRUCTOR(_Trait::_Unavailable, __copy_constructor(const __copy_constructor&) = delete;); +_LIBCPP_VARIANT_COPY_CONSTRUCTOR(_Trait::_Unavailable, __copy_constructor(const __copy_constructor&) = delete); # undef _LIBCPP_VARIANT_COPY_CONSTRUCTOR @@ -955,22 +968,22 @@ class _LIBCPP_TEMPLATE_VIS __move_assignment; __move_assignment(__move_assignment&&) = default; \ ~__move_assignment() = default; \ __move_assignment& operator=(const __move_assignment&) = default; \ - move_assignment \ + move_assignment; \ } _LIBCPP_VARIANT_MOVE_ASSIGNMENT(_Trait::_TriviallyAvailable, - __move_assignment& operator=(__move_assignment&& __that) = default;); + __move_assignment& operator=(__move_assignment&& __that) = default); _LIBCPP_VARIANT_MOVE_ASSIGNMENT( _Trait::_Available, - __move_assignment& + _LIBCPP_HIDE_FROM_ABI __move_assignment& operator=(__move_assignment&& __that) noexcept( __all<(is_nothrow_move_constructible_v<_Types> && is_nothrow_move_assignable_v<_Types>)...>::value) { this->__generic_assign(std::move(__that)); return *this; - }); + } _LIBCPP_EAT_SEMICOLON); -_LIBCPP_VARIANT_MOVE_ASSIGNMENT(_Trait::_Unavailable, __move_assignment& operator=(__move_assignment&&) = delete;); +_LIBCPP_VARIANT_MOVE_ASSIGNMENT(_Trait::_Unavailable, __move_assignment& operator=(__move_assignment&&) = delete); # undef _LIBCPP_VARIANT_MOVE_ASSIGNMENT @@ -987,22 +1000,23 @@ class _LIBCPP_TEMPLATE_VIS __copy_assignment; using __base_type::__base_type; \ using __base_type::operator=; \ \ - __copy_assignment(const __copy_assignment&) = default; \ - __copy_assignment(__copy_assignment&&) = default; \ - ~__copy_assignment() = default; \ - copy_assignment __copy_assignment& operator=(__copy_assignment&&) = default; \ + __copy_assignment(const __copy_assignment&) = default; \ + __copy_assignment(__copy_assignment&&) = default; \ + ~__copy_assignment() = default; \ + __copy_assignment& operator=(__copy_assignment&&) = default; \ + copy_assignment; \ } _LIBCPP_VARIANT_COPY_ASSIGNMENT(_Trait::_TriviallyAvailable, - __copy_assignment& operator=(const __copy_assignment& __that) = default;); + __copy_assignment& operator=(const __copy_assignment& __that) = default); _LIBCPP_VARIANT_COPY_ASSIGNMENT( - _Trait::_Available, __copy_assignment& operator=(const __copy_assignment& __that) { + _Trait::_Available, _LIBCPP_HIDE_FROM_ABI __copy_assignment& operator=(const __copy_assignment& __that) { this->__generic_assign(__that); return *this; - }); + } _LIBCPP_EAT_SEMICOLON); -_LIBCPP_VARIANT_COPY_ASSIGNMENT(_Trait::_Unavailable, __copy_assignment& operator=(const __copy_assignment&) = delete;); +_LIBCPP_VARIANT_COPY_ASSIGNMENT(_Trait::_Unavailable, __copy_assignment& operator=(const __copy_assignment&) = delete); # undef _LIBCPP_VARIANT_COPY_ASSIGNMENT diff --git a/libcxx/modules/std.compat/cstdlib.inc b/libcxx/modules/std.compat/cstdlib.inc index a45a0a1caf8ba9aac9105f8c638cd4c72f809454..4783cbf51623902891c9202493e616e57e5f83ed 100644 --- a/libcxx/modules/std.compat/cstdlib.inc +++ b/libcxx/modules/std.compat/cstdlib.inc @@ -25,7 +25,7 @@ export { using ::system; // [c.malloc], C library memory allocation - using ::aligned_alloc; + using ::aligned_alloc _LIBCPP_USING_IF_EXISTS; using ::calloc; using ::free; using ::malloc; diff --git a/libcxx/modules/std/ranges.inc b/libcxx/modules/std/ranges.inc index 82c7d99f8979a821707f7cf3c37324e644f78626..7d215867a4317f13ee927524bd22c4044687afe3 100644 --- a/libcxx/modules/std/ranges.inc +++ b/libcxx/modules/std/ranges.inc @@ -138,8 +138,10 @@ export namespace std { } #endif // _LIBCPP_HAS_NO_LOCALIZATION +#if _LIBCPP_STD_VER >= 23 // [range.adaptor.object], range adaptor objects - // using std::ranges::range_adaptor_closure; + using std::ranges::range_adaptor_closure; +#endif // [range.all], all view namespace views { diff --git a/libcxx/src/time_zone.cpp b/libcxx/src/time_zone.cpp index aef6ac674a11e667f2e26247fa21c821592ac03d..928f3d2855e456f809e2e787d612f2c23d39fd49 100644 --- a/libcxx/src/time_zone.cpp +++ b/libcxx/src/time_zone.cpp @@ -567,11 +567,22 @@ __first_rule(seconds __stdoff, const vector<__tz::__rule>& __rules) { false}; } - __named_rule_until __continuation_end{__continuation}; - if (__time >= __continuation_end.__until() && !__continuation_end.__needs_adjustment()) - // note std::unexpected(__end); is ambiguous with std::unexpected() in , - return __sys_info_result{std::unexpect, __continuation_end.__until()}; + if (__rule->__save.__time != 0s) { + // another fix for America/Punta_Arenas when not at the start of the + // sys_info object. + seconds __save = __rule->__save.__time; + if (__continuation_begin >= __rule_begin - __save && __time < __next.first) { + return __sys_info{ + sys_info{__continuation_begin, + __next.first, + __continuation.__stdoff + __save, + chrono::duration_cast(__save), + chrono::__format(__continuation, __rule->__letters, __save)}, + false}; + } + } + __named_rule_until __continuation_end{__continuation}; while (__next.second != __rules.end()) { #ifdef PRINT std::print( diff --git a/libcxx/test/libcxx/language.support/support.dynamic/libcpp_deallocate.sh.cpp b/libcxx/test/libcxx/language.support/support.dynamic/libcpp_deallocate.sh.cpp index f94ceaf57dbae8e045b88f17becae797db27c914..aa3ce210e3638d740ce70f092bb827886a680e7a 100644 --- a/libcxx/test/libcxx/language.support/support.dynamic/libcpp_deallocate.sh.cpp +++ b/libcxx/test/libcxx/language.support/support.dynamic/libcpp_deallocate.sh.cpp @@ -21,6 +21,9 @@ // GCC doesn't support the aligned-allocation flags. // XFAIL: gcc +// TODO(mordante) fix this test after updating clang in Docker +// UNSUPPORTED: clang-15, clang-16, clang-17, clang-18, clang-19 + // RUN: %{build} -faligned-allocation -fsized-deallocation // RUN: %{run} // RUN: %{build} -faligned-allocation -fno-sized-deallocation -DNO_SIZE diff --git a/libcxx/test/std/atomics/atomics.types.generic/atomics.types.float/fetch_add.pass.cpp b/libcxx/test/std/atomics/atomics.types.generic/atomics.types.float/fetch_add.pass.cpp index 7350c1ddf0e90120466abbed53377bee6a3db1f9..4119c39772e564592105af9886e775ceb7211921 100644 --- a/libcxx/test/std/atomics/atomics.types.generic/atomics.types.float/fetch_add.pass.cpp +++ b/libcxx/test/std/atomics/atomics.types.generic/atomics.types.float/fetch_add.pass.cpp @@ -6,7 +6,6 @@ // //===----------------------------------------------------------------------===// // UNSUPPORTED: c++03, c++11, c++14, c++17 -// UNSUPPORTED: LIBCXX-AIX-FIXME // XFAIL: !has-64-bit-atomics // https://github.com/llvm/llvm-project/issues/72893 diff --git a/libcxx/test/std/atomics/atomics.types.generic/atomics.types.float/fetch_sub.pass.cpp b/libcxx/test/std/atomics/atomics.types.generic/atomics.types.float/fetch_sub.pass.cpp index 84dcde5f2784f2eefc43fe334ce7f43adac5cf36..2460765a3c860ca930ca334b6798d1f58c1f7426 100644 --- a/libcxx/test/std/atomics/atomics.types.generic/atomics.types.float/fetch_sub.pass.cpp +++ b/libcxx/test/std/atomics/atomics.types.generic/atomics.types.float/fetch_sub.pass.cpp @@ -6,7 +6,6 @@ // //===----------------------------------------------------------------------===// // UNSUPPORTED: c++03, c++11, c++14, c++17 -// UNSUPPORTED: LIBCXX-AIX-FIXME // XFAIL: !has-64-bit-atomics // https://github.com/llvm/llvm-project/issues/72893 diff --git a/libcxx/test/std/atomics/atomics.types.generic/atomics.types.float/operator.minus_equals.pass.cpp b/libcxx/test/std/atomics/atomics.types.generic/atomics.types.float/operator.minus_equals.pass.cpp index 386a393e3550397e1b60ef2dcb29a505bf315c65..4bd303022c0dad9fa84d74595e47ca95803daf49 100644 --- a/libcxx/test/std/atomics/atomics.types.generic/atomics.types.float/operator.minus_equals.pass.cpp +++ b/libcxx/test/std/atomics/atomics.types.generic/atomics.types.float/operator.minus_equals.pass.cpp @@ -6,7 +6,6 @@ // //===----------------------------------------------------------------------===// // UNSUPPORTED: c++03, c++11, c++14, c++17 -// UNSUPPORTED: LIBCXX-AIX-FIXME // XFAIL: !has-64-bit-atomics // floating-point-type operator-=(floating-point-type) volatile noexcept; diff --git a/libcxx/test/std/atomics/atomics.types.generic/atomics.types.float/operator.plus_equals.pass.cpp b/libcxx/test/std/atomics/atomics.types.generic/atomics.types.float/operator.plus_equals.pass.cpp index afd06d537c7adbe8c4160afc3ce4875aab6cd117..69abb9ae63c38b6aca42072bb13cb3673cd7d2b7 100644 --- a/libcxx/test/std/atomics/atomics.types.generic/atomics.types.float/operator.plus_equals.pass.cpp +++ b/libcxx/test/std/atomics/atomics.types.generic/atomics.types.float/operator.plus_equals.pass.cpp @@ -6,7 +6,6 @@ // //===----------------------------------------------------------------------===// // UNSUPPORTED: c++03, c++11, c++14, c++17 -// UNSUPPORTED: LIBCXX-AIX-FIXME // XFAIL: !has-64-bit-atomics // floating-point-type operator+=(floating-point-type) volatile noexcept; diff --git a/libcxx/test/std/input.output/stream.buffers/streambuf/streambuf.cons/copy.pass.cpp b/libcxx/test/std/input.output/stream.buffers/streambuf/streambuf.cons/copy.pass.cpp index 58067511950703ae84482cb53c9849b5e4fd15f5..b458f93601a1ba4537d6a048d7040f95861b1db2 100644 --- a/libcxx/test/std/input.output/stream.buffers/streambuf/streambuf.cons/copy.pass.cpp +++ b/libcxx/test/std/input.output/stream.buffers/streambuf/streambuf.cons/copy.pass.cpp @@ -57,18 +57,20 @@ int main(int, char**) test t2 = t; } { - char g1, g2, g3, p1, p3; + char g[3]; + char p[3]; test t; - t.setg(&g1, &g2, &g3); - t.setp(&p1, &p3); + t.setg(&g[0], &g[1], &g[2]); + t.setp(&p[0], &p[2]); test t2 = t; } #ifndef TEST_HAS_NO_WIDE_CHARACTERS { - wchar_t g1, g2, g3, p1, p3; + wchar_t g[3]; + wchar_t p[3]; test t; - t.setg(&g1, &g2, &g3); - t.setp(&p1, &p3); + t.setg(&g[0], &g[1], &g[2]); + t.setp(&p[0], &p[2]); test t2 = t; } { diff --git a/libcxx/test/std/input.output/stream.buffers/streambuf/streambuf.protected/streambuf.assign/assign.pass.cpp b/libcxx/test/std/input.output/stream.buffers/streambuf/streambuf.protected/streambuf.assign/assign.pass.cpp index 8a976e77f0f13f8113408dd31ecfd9ebd31fae4a..45a8cdf3a23fead943779d8e7ffe2dd78f2cba77 100644 --- a/libcxx/test/std/input.output/stream.buffers/streambuf/streambuf.protected/streambuf.assign/assign.pass.cpp +++ b/libcxx/test/std/input.output/stream.buffers/streambuf/streambuf.protected/streambuf.assign/assign.pass.cpp @@ -59,10 +59,11 @@ int main(int, char**) t2 = t; } { - char g1, g2, g3, p1, p3; + char g[3]; + char p[3]; test t; - t.setg(&g1, &g2, &g3); - t.setp(&p1, &p3); + t.setg(&g[0], &g[1], &g[2]); + t.setp(&p[0], &p[2]); test t2; t2 = t; } @@ -73,10 +74,11 @@ int main(int, char**) t2 = t; } { - wchar_t g1, g2, g3, p1, p3; + wchar_t g[3]; + wchar_t p[3]; test t; - t.setg(&g1, &g2, &g3); - t.setp(&p1, &p3); + t.setg(&g[0], &g[1], &g[2]); + t.setp(&p[0], &p[2]); test t2; t2 = t; } diff --git a/libcxx/test/std/input.output/stream.buffers/streambuf/streambuf.protected/streambuf.assign/swap.pass.cpp b/libcxx/test/std/input.output/stream.buffers/streambuf/streambuf.protected/streambuf.assign/swap.pass.cpp index c575c2cb12711aec76e60f2c51d9a45959e09e7f..b90c4c053c9155309a953c1ce94c362f0497fcac 100644 --- a/libcxx/test/std/input.output/stream.buffers/streambuf/streambuf.protected/streambuf.assign/swap.pass.cpp +++ b/libcxx/test/std/input.output/stream.buffers/streambuf/streambuf.protected/streambuf.assign/swap.pass.cpp @@ -68,10 +68,11 @@ int main(int, char**) t2.swap(t); } { - char g1, g2, g3, p1, p3; + char g[3]; + char p[3]; test t; - t.setg(&g1, &g2, &g3); - t.setp(&p1, &p3); + t.setg(&g[0], &g[1], &g[2]); + t.setp(&p[0], &p[2]); test t2; t2.swap(t); } @@ -82,10 +83,11 @@ int main(int, char**) t2.swap(t); } { - wchar_t g1, g2, g3, p1, p3; + wchar_t g[3]; + wchar_t p[3]; test t; - t.setg(&g1, &g2, &g3); - t.setp(&p1, &p3); + t.setg(&g[0], &g[1], &g[2]); + t.setp(&p[0], &p[2]); test t2; t2.swap(t); } diff --git a/libcxx/test/std/input.output/stream.buffers/streambuf/streambuf.protected/streambuf.get.area/setg.assert.pass.cpp b/libcxx/test/std/input.output/stream.buffers/streambuf/streambuf.protected/streambuf.get.area/setg.assert.pass.cpp new file mode 100644 index 0000000000000000000000000000000000000000..becf89b12fdd186cb407a497c34844a5f73944b6 --- /dev/null +++ b/libcxx/test/std/input.output/stream.buffers/streambuf/streambuf.protected/streambuf.get.area/setg.assert.pass.cpp @@ -0,0 +1,68 @@ +//===----------------------------------------------------------------------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +// REQUIRES: has-unix-headers +// UNSUPPORTED: libcpp-hardening-mode=none +// XFAIL: libcpp-hardening-mode=debug && availability-verbose_abort-missing + +// + +// template > +// class basic_streambuf; + +// void setg(char_type* gbeg, char_type* gnext, char_type* gend); + +#include +#include +#include +#include + +#include "check_assertion.h" +#include "make_string.h" +#include "test_macros.h" + +template +struct streambuf : public std::basic_streambuf { + typedef std::basic_streambuf base; + + streambuf() {} + + void setg(CharT* gbeg, CharT* gnext, CharT* gend) { base::setg(gbeg, gnext, gend); } +}; + +template +void test() { + std::basic_string str = MAKE_STRING(CharT, "ABCDEF"); + CharT arr[6]; + std::copy(str.begin(), str.end(), arr); + + { + streambuf buff; + TEST_LIBCPP_ASSERT_FAILURE( + buff.setg(std::begin(arr) + 1, std::begin(arr), std::end(arr)), "[gbeg, gnext) must be a valid range"); + } + { + streambuf buff; + TEST_LIBCPP_ASSERT_FAILURE( + buff.setg(std::begin(arr) + 1, std::begin(arr) + 1, std::begin(arr)), "[gbeg, gend) must be a valid range"); + } + { + streambuf buff; + TEST_LIBCPP_ASSERT_FAILURE( + buff.setg(std::begin(arr), std::begin(arr) + 3, std::begin(arr) + 2), "[gnext, gend) must be a valid range"); + } +} + +int main(int, char**) { + test(); +#ifndef TEST_HAS_NO_WIDE_CHARACTERS + test(); +#endif + + return 0; +} diff --git a/libcxx/test/std/input.output/stream.buffers/streambuf/streambuf.protected/streambuf.put.area/setp.assert.pass.cpp b/libcxx/test/std/input.output/stream.buffers/streambuf/streambuf.protected/streambuf.put.area/setp.assert.pass.cpp new file mode 100644 index 0000000000000000000000000000000000000000..abd42272de508c7bb309b1caa5e603cd04ac92ee --- /dev/null +++ b/libcxx/test/std/input.output/stream.buffers/streambuf/streambuf.protected/streambuf.put.area/setp.assert.pass.cpp @@ -0,0 +1,57 @@ +//===----------------------------------------------------------------------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +// REQUIRES: has-unix-headers +// UNSUPPORTED: libcpp-hardening-mode=none +// XFAIL: libcpp-hardening-mode=debug && availability-verbose_abort-missing + +// + +// template > +// class basic_streambuf; + +// void setp(char_type* pbeg, char_type* pend); + +#include +#include +#include +#include + +#include "check_assertion.h" +#include "make_string.h" +#include "test_macros.h" + +template +struct streambuf : public std::basic_streambuf { + typedef std::basic_streambuf base; + + streambuf() {} + + void setp(CharT* pbeg, CharT* pend) { base::setp(pbeg, pend); } +}; + +template +void test() { + std::basic_string str = MAKE_STRING(CharT, "ABCDEF"); + CharT arr[6]; + std::copy(str.begin(), str.end(), arr); + + { + streambuf buff; + TEST_LIBCPP_ASSERT_FAILURE(buff.setp(std::begin(arr) + 3, std::begin(arr)), "[pbeg, pend) must be a valid range"); + } +} + +int main(int, char**) { + test(); +#ifndef TEST_HAS_NO_WIDE_CHARACTERS + test(); +#endif + + return 0; +} diff --git a/libcxx/test/std/language.support/support.dynamic/new.delete/new.delete.array/sized_delete_array14.pass.cpp b/libcxx/test/std/language.support/support.dynamic/new.delete/new.delete.array/sized_delete_array14.pass.cpp index 21663cdf956d425c175dfd3a778deb66f13349b8..0241e7cefcac3d33dc07372a7ab2695605815f80 100644 --- a/libcxx/test/std/language.support/support.dynamic/new.delete/new.delete.array/sized_delete_array14.pass.cpp +++ b/libcxx/test/std/language.support/support.dynamic/new.delete/new.delete.array/sized_delete_array14.pass.cpp @@ -8,11 +8,11 @@ // test sized operator delete[] replacement. +// TODO(mordante) fix this test after updating clang in Docker +// UNSUPPORTED: clang-15, clang-16, clang-17, clang-18, clang-19 // UNSUPPORTED: sanitizer-new-delete, c++03, c++11 - -// NOTE: Clang does not enable sized-deallocation in C++14 and beyond by -// default. It is only enabled when -fsized-deallocation is given. -// XFAIL: clang, apple-clang +// XFAIL: apple-clang +// XFAIL: using-built-library-before-llvm-11 #include #include diff --git a/libcxx/test/std/language.support/support.dynamic/new.delete/new.delete.single/sized_delete14.pass.cpp b/libcxx/test/std/language.support/support.dynamic/new.delete/new.delete.single/sized_delete14.pass.cpp index a8701ce7a86cff5df30a66c2dc1a429a7167da1a..2ab691618ea46d8172b896ad289fc5feabbf20c5 100644 --- a/libcxx/test/std/language.support/support.dynamic/new.delete/new.delete.single/sized_delete14.pass.cpp +++ b/libcxx/test/std/language.support/support.dynamic/new.delete/new.delete.single/sized_delete14.pass.cpp @@ -8,11 +8,11 @@ // test sized operator delete replacement. +// TODO(mordante) fix this test after updating clang in Docker +// UNSUPPORTED: clang-15, clang-16, clang-17, clang-18, clang-19 // UNSUPPORTED: sanitizer-new-delete, c++03, c++11 - -// NOTE: Clang does not enable sized-deallocation in C++14 and beyond by -// default. It is only enabled when -fsized-deallocation is given. -// XFAIL: clang, apple-clang +// XFAIL: apple-clang +// XFAIL: using-built-library-before-llvm-11 #include #include diff --git a/libcxx/test/std/ranges/range.adaptors/range.adaptor.object/range_adaptor_closure.pass.cpp b/libcxx/test/std/ranges/range.adaptors/range.adaptor.object/range_adaptor_closure.pass.cpp new file mode 100644 index 0000000000000000000000000000000000000000..9d1eb1243458133b6b08b632d73d359b690c3781 --- /dev/null +++ b/libcxx/test/std/ranges/range.adaptors/range.adaptor.object/range_adaptor_closure.pass.cpp @@ -0,0 +1,142 @@ +//===----------------------------------------------------------------------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +// UNSUPPORTED: c++03, c++11, c++14, c++17, c++20 + +// std::ranges::range_adaptor_closure; + +#include + +#include +#include + +#include "test_range.h" + +template +concept CanDeriveFromRangeAdaptorClosure = requires { typename std::ranges::range_adaptor_closure; }; +static_assert(!CanDeriveFromRangeAdaptorClosure); + +struct Foo {}; +static_assert(CanDeriveFromRangeAdaptorClosure); +static_assert(!CanDeriveFromRangeAdaptorClosure); +static_assert(!CanDeriveFromRangeAdaptorClosure); +static_assert(!CanDeriveFromRangeAdaptorClosure); +static_assert(!CanDeriveFromRangeAdaptorClosure); + +struct incomplete_t; +static_assert(CanDeriveFromRangeAdaptorClosure); + +using range_t = std::vector; + +template +concept RangeAdaptorClosure = + CanBePiped && CanBePiped && CanBePiped && + CanBePiped; + +struct callable : std::ranges::range_adaptor_closure { + static void operator()(const range_t&) {} +}; +static_assert(RangeAdaptorClosure); + +// `not_callable_1` doesn't have an `operator()` +struct not_callable_1 : std::ranges::range_adaptor_closure {}; +static_assert(!RangeAdaptorClosure); + +// `not_callable_2` doesn't have an `operator()` that accepts a `range` argument +struct not_callable_2 : std::ranges::range_adaptor_closure { + static void operator()() {} +}; +static_assert(!RangeAdaptorClosure); + +// `not_derived_from_1` doesn't derive from `std::ranges::range_adaptor_closure` +struct not_derived_from_1 { + static void operator()(const range_t&) {} +}; +static_assert(!RangeAdaptorClosure); + +// `not_derived_from_2` doesn't publicly derive from `std::ranges::range_adaptor_closure` +struct not_derived_from_2 : private std::ranges::range_adaptor_closure { + static void operator()(const range_t&) {} +}; +static_assert(!RangeAdaptorClosure); + +// `not_derived_from_3` doesn't derive from the correct specialization of `std::ranges::range_adaptor_closure` +struct not_derived_from_3 : std::ranges::range_adaptor_closure { + static void operator()(const range_t&) {} +}; +static_assert(!RangeAdaptorClosure); + +// `not_derived_from_4` doesn't derive from exactly one specialization of `std::ranges::range_adaptor_closure` +struct not_derived_from_4 + : std::ranges::range_adaptor_closure, + std::ranges::range_adaptor_closure { + static void operator()(const range_t&) {} +}; +static_assert(!RangeAdaptorClosure); + +// `is_range` models `range` +struct is_range : std::ranges::range_adaptor_closure { + static void operator()(const range_t&) {} + int* begin() const { return nullptr; } + int* end() const { return nullptr; } +}; +static_assert(std::ranges::range && std::ranges::range); +static_assert(!RangeAdaptorClosure); + +// user-defined range adaptor closure object +struct negate_fn : std::ranges::range_adaptor_closure { + template + static constexpr decltype(auto) operator()(Range&& range) { + return std::forward(range) | std::views::transform([](auto element) { return -element; }); + } +}; +static_assert(RangeAdaptorClosure); +constexpr auto negate = negate_fn{}; + +// user-defined range adaptor closure object +struct plus_1_fn : std::ranges::range_adaptor_closure { + template + static constexpr decltype(auto) operator()(Range&& range) { + return std::forward(range) | std::views::transform([](auto element) { return element + 1; }); + } +}; +static_assert(RangeAdaptorClosure); +constexpr auto plus_1 = plus_1_fn{}; + +constexpr bool test() { + const std::vector n{1, 2, 3, 4, 5}; + const std::vector n_negate{-1, -2, -3, -4, -5}; + + assert(std::ranges::equal(n | negate, n_negate)); + assert(std::ranges::equal(negate(n), n_negate)); + + assert(std::ranges::equal(n | negate | negate, n)); + assert(std::ranges::equal(n | (negate | negate), n)); + assert(std::ranges::equal((n | negate) | negate, n)); + assert(std::ranges::equal(negate(n) | negate, n)); + assert(std::ranges::equal(negate(n | negate), n)); + assert(std::ranges::equal((negate | negate)(n), n)); + assert(std::ranges::equal(negate(negate(n)), n)); + + const std::vector n_plus_1_negate{-2, -3, -4, -5, -6}; + assert(std::ranges::equal(n | plus_1 | negate, n_plus_1_negate)); + assert(std::ranges::equal( + n | plus_1 | std::views::transform([](auto element) { return element; }) | negate, n_plus_1_negate)); + + const std::vector n_negate_plus_1{0, -1, -2, -3, -4}; + assert(std::ranges::equal(n | negate | plus_1, n_negate_plus_1)); + assert(std::ranges::equal(n | std::views::reverse | negate | plus_1 | std::views::reverse, n_negate_plus_1)); + return true; +} + +int main(int, char**) { + test(); + static_assert(test()); + + return 0; +} diff --git a/libcxx/test/std/time/time.clock/time.clock.file/ostream.pass.cpp b/libcxx/test/std/time/time.clock/time.clock.file/ostream.pass.cpp index 18a4506b91566b6bf9a946251984df2b5d9ca689..11eab1dddfe385b0389d93579c77a9485b3b717c 100644 --- a/libcxx/test/std/time/time.clock/time.clock.file/ostream.pass.cpp +++ b/libcxx/test/std/time/time.clock/time.clock.file/ostream.pass.cpp @@ -71,8 +71,45 @@ template static void test_c() { using namespace std::literals::chrono_literals; + assert(stream_c_locale(std::chrono::file_time{-946'688'523'123'456'789ns}) == + SV("1940-01-01 22:57:56.876543211")); + + assert(stream_c_locale(std::chrono::file_time{-946'688'523'123'456us}) == + SV("1940-01-01 22:57:56.876544")); + + assert(stream_c_locale(std::chrono::file_time{-946'688'523'123ms}) == + SV("1940-01-01 22:57:56.877")); + + assert(stream_c_locale(std::chrono::file_time{-1000000000ns}) == + SV("1969-12-31 23:59:59.000000000")); + + assert(stream_c_locale(std::chrono::file_time{-1000000us}) == + SV("1969-12-31 23:59:59.000000")); + + assert(stream_c_locale(std::chrono::file_time{-1000ms}) == + SV("1969-12-31 23:59:59.000")); + + assert(stream_c_locale(std::chrono::file_time{-1ns}) == + SV("1969-12-31 23:59:59.999999999")); + + assert(stream_c_locale(std::chrono::file_time{0ns}) == + SV("1970-01-01 00:00:00.000000000")); + + assert(stream_c_locale(std::chrono::file_time{1ns}) == + SV("1970-01-01 00:00:00.000000001")); + + assert(stream_c_locale(std::chrono::file_time{1000000000ns}) == + SV("1970-01-01 00:00:01.000000000")); + + assert(stream_c_locale(std::chrono::file_time{1000000us}) == + SV("1970-01-01 00:00:01.000000")); + + assert(stream_c_locale(std::chrono::file_time{1000ms}) == + SV("1970-01-01 00:00:01.000")); + assert(stream_c_locale(file_time{946'688'523'123'456'789ns}) == SV("2000-01-01 01:02:03.123456789")); + assert(stream_c_locale(file_time{946'688'523'123'456us}) == SV("2000-01-01 01:02:03.123456")); @@ -107,6 +144,42 @@ template static void test_fr_FR() { using namespace std::literals::chrono_literals; + assert(stream_fr_FR_locale(std::chrono::file_time{-946'688'523'123'456'789ns}) == + SV("1940-01-01 22:57:56,876543211")); + + assert(stream_fr_FR_locale(std::chrono::file_time{-946'688'523'123'456us}) == + SV("1940-01-01 22:57:56,876544")); + + assert(stream_fr_FR_locale(std::chrono::file_time{-946'688'523'123ms}) == + SV("1940-01-01 22:57:56,877")); + + assert(stream_fr_FR_locale(std::chrono::file_time{-1000000000ns}) == + SV("1969-12-31 23:59:59,000000000")); + + assert(stream_fr_FR_locale(std::chrono::file_time{-1000000us}) == + SV("1969-12-31 23:59:59,000000")); + + assert(stream_fr_FR_locale(std::chrono::file_time{-1000ms}) == + SV("1969-12-31 23:59:59,000")); + + assert(stream_fr_FR_locale(std::chrono::file_time{-1ns}) == + SV("1969-12-31 23:59:59,999999999")); + + assert(stream_fr_FR_locale(std::chrono::file_time{0ns}) == + SV("1970-01-01 00:00:00,000000000")); + + assert(stream_fr_FR_locale(std::chrono::file_time{1ns}) == + SV("1970-01-01 00:00:00,000000001")); + + assert(stream_fr_FR_locale(std::chrono::file_time{1000000000ns}) == + SV("1970-01-01 00:00:01,000000000")); + + assert(stream_fr_FR_locale(std::chrono::file_time{1000000us}) == + SV("1970-01-01 00:00:01,000000")); + + assert(stream_fr_FR_locale(std::chrono::file_time{1000ms}) == + SV("1970-01-01 00:00:01,000")); + assert(stream_fr_FR_locale(file_time{946'688'523'123'456'789ns}) == SV("2000-01-01 01:02:03,123456789")); assert(stream_fr_FR_locale(file_time{946'688'523'123'456us}) == @@ -144,6 +217,42 @@ template static void test_ja_JP() { using namespace std::literals::chrono_literals; + assert(stream_ja_JP_locale(std::chrono::file_time{-946'688'523'123'456'789ns}) == + SV("1940-01-01 22:57:56.876543211")); + + assert(stream_ja_JP_locale(std::chrono::file_time{-946'688'523'123'456us}) == + SV("1940-01-01 22:57:56.876544")); + + assert(stream_ja_JP_locale(std::chrono::file_time{-946'688'523'123ms}) == + SV("1940-01-01 22:57:56.877")); + + assert(stream_ja_JP_locale(std::chrono::file_time{-1000000000ns}) == + SV("1969-12-31 23:59:59.000000000")); + + assert(stream_ja_JP_locale(std::chrono::file_time{-1000000us}) == + SV("1969-12-31 23:59:59.000000")); + + assert(stream_ja_JP_locale(std::chrono::file_time{-1000ms}) == + SV("1969-12-31 23:59:59.000")); + + assert(stream_ja_JP_locale(std::chrono::file_time{-1ns}) == + SV("1969-12-31 23:59:59.999999999")); + + assert(stream_ja_JP_locale(std::chrono::file_time{0ns}) == + SV("1970-01-01 00:00:00.000000000")); + + assert(stream_ja_JP_locale(std::chrono::file_time{1ns}) == + SV("1970-01-01 00:00:00.000000001")); + + assert(stream_ja_JP_locale(std::chrono::file_time{1000000000ns}) == + SV("1970-01-01 00:00:01.000000000")); + + assert(stream_ja_JP_locale(std::chrono::file_time{1000000us}) == + SV("1970-01-01 00:00:01.000000")); + + assert(stream_ja_JP_locale(std::chrono::file_time{1000ms}) == + SV("1970-01-01 00:00:01.000")); + assert(stream_ja_JP_locale(file_time{946'688'523'123'456'789ns}) == SV("2000-01-01 01:02:03.123456789")); assert(stream_ja_JP_locale(file_time{946'688'523'123'456us}) == diff --git a/libcxx/test/std/time/time.clock/time.clock.local/ostream.pass.cpp b/libcxx/test/std/time/time.clock/time.clock.local/ostream.pass.cpp index 9fdef8d5adc7825e2291a48c4e803bf8bd47557a..6ec63a14fbbd3307d491407853c061dd2f86959a 100644 --- a/libcxx/test/std/time/time.clock/time.clock.local/ostream.pass.cpp +++ b/libcxx/test/std/time/time.clock/time.clock.local/ostream.pass.cpp @@ -64,6 +64,24 @@ template static void test_c() { using namespace std::literals::chrono_literals; + assert(stream_c_locale(std::chrono::local_time{-946'688'523'123'456'789ns}) == + SV("1940-01-01 22:57:56.876543211")); + + assert(stream_c_locale(std::chrono::local_time{-946'688'523'123'456us}) == + SV("1940-01-01 22:57:56.876544")); + + assert(stream_c_locale(std::chrono::local_time{-946'688'523'123ms}) == + SV("1940-01-01 22:57:56.877")); + + assert(stream_c_locale(std::chrono::local_time{-1ns}) == + SV("1969-12-31 23:59:59.999999999")); + + assert(stream_c_locale(std::chrono::local_time{0ns}) == + SV("1970-01-01 00:00:00.000000000")); + + assert(stream_c_locale(std::chrono::local_time{1ns}) == + SV("1970-01-01 00:00:00.000000001")); + assert(stream_c_locale(std::chrono::local_time{946'688'523'123'456'789ns}) == SV("2000-01-01 01:02:03.123456789")); assert(stream_c_locale(std::chrono::local_time{946'688'523'123'456us}) == @@ -97,6 +115,24 @@ template static void test_fr_FR() { using namespace std::literals::chrono_literals; + assert(stream_fr_FR_locale(std::chrono::local_time{-946'688'523'123'456'789ns}) == + SV("1940-01-01 22:57:56,876543211")); + + assert(stream_fr_FR_locale(std::chrono::local_time{-946'688'523'123'456us}) == + SV("1940-01-01 22:57:56,876544")); + + assert(stream_fr_FR_locale(std::chrono::local_time{-946'688'523'123ms}) == + SV("1940-01-01 22:57:56,877")); + + assert(stream_fr_FR_locale(std::chrono::local_time{-1ns}) == + SV("1969-12-31 23:59:59,999999999")); + + assert(stream_fr_FR_locale(std::chrono::local_time{0ns}) == + SV("1970-01-01 00:00:00,000000000")); + + assert(stream_fr_FR_locale(std::chrono::local_time{1ns}) == + SV("1970-01-01 00:00:00,000000001")); + assert(stream_fr_FR_locale(std::chrono::local_time{946'688'523'123'456'789ns}) == SV("2000-01-01 01:02:03,123456789")); assert(stream_fr_FR_locale(std::chrono::local_time{946'688'523'123'456us}) == @@ -131,6 +167,24 @@ template static void test_ja_JP() { using namespace std::literals::chrono_literals; + assert(stream_ja_JP_locale(std::chrono::local_time{-946'688'523'123'456'789ns}) == + SV("1940-01-01 22:57:56.876543211")); + + assert(stream_ja_JP_locale(std::chrono::local_time{-946'688'523'123'456us}) == + SV("1940-01-01 22:57:56.876544")); + + assert(stream_ja_JP_locale(std::chrono::local_time{-946'688'523'123ms}) == + SV("1940-01-01 22:57:56.877")); + + assert(stream_ja_JP_locale(std::chrono::local_time{-1ns}) == + SV("1969-12-31 23:59:59.999999999")); + + assert(stream_ja_JP_locale(std::chrono::local_time{0ns}) == + SV("1970-01-01 00:00:00.000000000")); + + assert(stream_ja_JP_locale(std::chrono::local_time{1ns}) == + SV("1970-01-01 00:00:00.000000001")); + assert(stream_ja_JP_locale(std::chrono::local_time{946'688'523'123'456'789ns}) == SV("2000-01-01 01:02:03.123456789")); assert(stream_ja_JP_locale(std::chrono::local_time{946'688'523'123'456us}) == diff --git a/libcxx/test/std/time/time.clock/time.clock.system/sys_time.ostream.pass.cpp b/libcxx/test/std/time/time.clock/time.clock.system/sys_time.ostream.pass.cpp index 78d8da57c150a6b4e381027cb3970af29dee8dd5..e596ddefde51d99aeabf40a340c2320ba32bec7c 100644 --- a/libcxx/test/std/time/time.clock/time.clock.system/sys_time.ostream.pass.cpp +++ b/libcxx/test/std/time/time.clock/time.clock.system/sys_time.ostream.pass.cpp @@ -64,6 +64,24 @@ template static void test_c() { using namespace std::literals::chrono_literals; + assert(stream_c_locale(std::chrono::sys_time{-946'688'523'123'456'789ns}) == + SV("1940-01-01 22:57:56.876543211")); + + assert(stream_c_locale(std::chrono::sys_time{-946'688'523'123'456us}) == + SV("1940-01-01 22:57:56.876544")); + + assert(stream_c_locale(std::chrono::sys_time{-946'688'523'123ms}) == + SV("1940-01-01 22:57:56.877")); + + assert(stream_c_locale(std::chrono::sys_time{-1ns}) == + SV("1969-12-31 23:59:59.999999999")); + + assert(stream_c_locale(std::chrono::sys_time{0ns}) == + SV("1970-01-01 00:00:00.000000000")); + + assert(stream_c_locale(std::chrono::sys_time{1ns}) == + SV("1970-01-01 00:00:00.000000001")); + assert(stream_c_locale(std::chrono::sys_time{946'688'523'123'456'789ns}) == SV("2000-01-01 01:02:03.123456789")); assert(stream_c_locale(std::chrono::sys_time{946'688'523'123'456us}) == @@ -92,6 +110,24 @@ template static void test_fr_FR() { using namespace std::literals::chrono_literals; + assert(stream_fr_FR_locale(std::chrono::sys_time{-946'688'523'123'456'789ns}) == + SV("1940-01-01 22:57:56,876543211")); + + assert(stream_fr_FR_locale(std::chrono::sys_time{-946'688'523'123'456us}) == + SV("1940-01-01 22:57:56,876544")); + + assert(stream_fr_FR_locale(std::chrono::sys_time{-946'688'523'123ms}) == + SV("1940-01-01 22:57:56,877")); + + assert(stream_fr_FR_locale(std::chrono::sys_time{-1ns}) == + SV("1969-12-31 23:59:59,999999999")); + + assert(stream_fr_FR_locale(std::chrono::sys_time{0ns}) == + SV("1970-01-01 00:00:00,000000000")); + + assert(stream_fr_FR_locale(std::chrono::sys_time{1ns}) == + SV("1970-01-01 00:00:00,000000001")); + assert(stream_fr_FR_locale(std::chrono::sys_time{946'688'523'123'456'789ns}) == SV("2000-01-01 01:02:03,123456789")); assert(stream_fr_FR_locale(std::chrono::sys_time{946'688'523'123'456us}) == @@ -120,6 +156,24 @@ template static void test_ja_JP() { using namespace std::literals::chrono_literals; + assert(stream_ja_JP_locale(std::chrono::sys_time{-946'688'523'123'456'789ns}) == + SV("1940-01-01 22:57:56.876543211")); + + assert(stream_ja_JP_locale(std::chrono::sys_time{-946'688'523'123'456us}) == + SV("1940-01-01 22:57:56.876544")); + + assert(stream_ja_JP_locale(std::chrono::sys_time{-946'688'523'123ms}) == + SV("1940-01-01 22:57:56.877")); + + assert(stream_ja_JP_locale(std::chrono::sys_time{-1ns}) == + SV("1969-12-31 23:59:59.999999999")); + + assert(stream_ja_JP_locale(std::chrono::sys_time{0ns}) == + SV("1970-01-01 00:00:00.000000000")); + + assert(stream_ja_JP_locale(std::chrono::sys_time{1ns}) == + SV("1970-01-01 00:00:00.000000001")); + assert(stream_ja_JP_locale(std::chrono::sys_time{946'688'523'123'456'789ns}) == SV("2000-01-01 01:02:03.123456789")); assert(stream_ja_JP_locale(std::chrono::sys_time{946'688'523'123'456us}) == diff --git a/libcxx/test/std/time/time.zone/time.zone.timezone/time.zone.members/get_info.sys_time.pass.cpp b/libcxx/test/std/time/time.zone/time.zone.timezone/time.zone.members/get_info.sys_time.pass.cpp index 25d2ff11d09341c611f0fd6179f20688ccd27d6a..1a1705d5ae59a562927ea7b12b9af064a977beca 100644 --- a/libcxx/test/std/time/time.zone/time.zone.timezone/time.zone.members/get_info.sys_time.pass.cpp +++ b/libcxx/test/std/time/time.zone/time.zone.timezone/time.zone.members/get_info.sys_time.pass.cpp @@ -1299,6 +1299,78 @@ static void test_america_indiana_knox() { tz->get_info(to_sys_seconds(2006y, std::chrono::October, 29d, 6h, 59min, 59s))); } +static void test_america_punta_arenas() { + // Z America/Punta_Arenas -4:43:40 - LMT 1890 + // ... + // -4 - -04 1919 Jul + // -4:42:45 - SMT 1927 S + // -5 x -05/-04 1932 S + // ... + // + // R x 1927 1931 - S 1 0 1 - + // R x 1928 1932 - Ap 1 0 0 - + // ... + + using namespace std::literals::chrono_literals; + const std::chrono::time_zone* tz = std::chrono::locate_zone("America/Punta_Arenas"); + + assert_equal( + std::chrono::sys_info( + to_sys_seconds(1927y, std::chrono::September, 1d, 4h, 42min, 45s), + to_sys_seconds(1928y, std::chrono::April, 1d, 4h), + -4h, + 60min, + "-04"), + tz->get_info(to_sys_seconds(1927y, std::chrono::September, 1d, 4h, 42min, 45s))); + + assert_equal( + std::chrono::sys_info( + to_sys_seconds(1927y, std::chrono::September, 1d, 4h, 42min, 45s), + to_sys_seconds(1928y, std::chrono::April, 1d, 4h), + -4h, + 60min, + "-04"), + tz->get_info(to_sys_seconds(1928y, std::chrono::April, 1d, 3h, 59min, 59s))); +} + +static void test_europ_ljubljana() { + // Z Europe/Ljubljana 0:58:4 - LMT 1884 + // 1 - CET 1941 Ap 18 23 + // 1 c CE%sT 1945 May 8 2s + // 1 1 CEST 1945 S 16 2s + // 1 - CET 1982 N 27 + // 1 E CE%sT + // + // ... + // R c 1943 o - O 4 2s 0 - + // R c 1944 1945 - Ap M>=1 2s 1 S + // R c 1944 o - O 2 2s 0 - + // R c 1945 o - S 16 2s 0 - + // R c 1977 1980 - Ap Su>=1 2s 1 S + // ... + + using namespace std::literals::chrono_literals; + const std::chrono::time_zone* tz = std::chrono::locate_zone("Europe/Ljubljana"); + + assert_equal( + std::chrono::sys_info( + to_sys_seconds(1945y, std::chrono::April, 2d, 1h), + to_sys_seconds(1945y, std::chrono::September, 16d, 1h), + 2h, + 60min, + "CEST"), + tz->get_info(to_sys_seconds(1945y, std::chrono::April, 2d, 1h))); + + assert_equal( + std::chrono::sys_info( + to_sys_seconds(1945y, std::chrono::April, 2d, 1h), + to_sys_seconds(1945y, std::chrono::September, 16d, 1h), + 2h, + 60min, + "CEST"), + tz->get_info(to_sys_seconds(1945y, std::chrono::September, 16d, 0h, 59min, 59s))); +} + int main(int, const char**) { // Basic tests test_gmt(); @@ -1333,5 +1405,9 @@ int main(int, const char**) { test_america_ciudad_juarez(); test_america_indiana_knox(); + // Reverse search bugs + test_america_punta_arenas(); + test_europ_ljubljana(); + return 0; } diff --git a/libcxx/test/std/utilities/format/format.functions/escaped_output.unicode.pass.cpp b/libcxx/test/std/utilities/format/format.functions/escaped_output.unicode.pass.cpp index bf5c0a51f944aedd65734e7dd3d70e4cff77fe43..96c1e2664f7a6487ca733fd4f0e69b85b5564ac9 100644 --- a/libcxx/test/std/utilities/format/format.functions/escaped_output.unicode.pass.cpp +++ b/libcxx/test/std/utilities/format/format.functions/escaped_output.unicode.pass.cpp @@ -223,7 +223,7 @@ void test_char() { static_assert(sizeof(CharT) == 4, "add support for unexpected size"); // Unicode fitting in a 32-bit wchar_t - constexpr wchar_t x = 0x1ffff; + constexpr wchar_t x = 0x1ffff; constexpr std::uint32_t y = 0x1ffff; static_assert(x == y); @@ -290,7 +290,7 @@ void test_string() { test_format(SV("[\"\ud7ff\"]"), SV("[{:?}]"), "\xed\x9f\xbf"); // U+D7FF last valid #else /* U+D800..D+DFFFF surrogate range */ - test_format(SV(R"(["\u{d7ff}"])"), SV("[{:?}]"), "\xed\x9f\xbf"); // U+D7FF last valid + test_format(SV(R"(["\u{d7ff}"])"), SV("[{:?}]"), "\xed\x9f\xbf"); // U+D7FF last valid #endif test_format(SV(R"(["\x{ed}\x{a0}\x{80}"])"), SV("[{:?}]"), "\xed\xa0\x80"); // U+D800 test_format(SV(R"(["\x{ed}\x{af}\x{bf}"])"), SV("[{:?}]"), "\xed\xaf\xbf"); // U+DBFF @@ -319,7 +319,8 @@ void test_string() { test_format(SV("[\"\u00c3(\"]"), SV("[{:?}]"), L"\xc3\x28"); } - test_format(SV(R"(["🤷🏻\u{200d}♂\u{fe0f}"])"), SV("[{:?}]"), SV("🤷🏻‍♂️")); + // LWG-3965 + test_format(SV(R"(["🤷🏻\u{200d}♂️"])"), SV("[{:?}]"), SV("🤷🏻‍♂️")); // *** Special cases *** test_format(SV(R"("\t\n\r\\'\" ")"), SV("{:?}"), SV("\t\n\r\\'\" ")); @@ -336,6 +337,11 @@ void test_string() { if constexpr (sizeof(CharT) == 1) test_format(SV(R"("\x{80}")"), SV("{:?}"), SV("\x80")); + // *** P2713R1 examples *** + test_format(SV(R"(["\u{301}"])"), SV("[{:?}]"), SV("\u0301")); + test_format(SV(R"(["\\\u{301}"])"), SV("[{:?}]"), SV("\\\u0301")); + test_format(SV(R"(["ẹ́"])"), SV("[{:?}]"), SV("e\u0301\u0323")); + #ifndef TEST_HAS_NO_WIDE_CHARACTERS if constexpr (sizeof(CharT) > 1) { using V = std::basic_string_view; @@ -373,7 +379,7 @@ void test_string() { static_assert(sizeof(CharT) == 4, "add support for unexpected size"); // Unicode fitting in a 32-bit wchar_t - constexpr wchar_t x = 0x1ffff; + constexpr wchar_t x = 0x1ffff; constexpr std::uint32_t y = 0x1ffff; static_assert(x == y); @@ -406,20 +412,18 @@ void test_format_functions(TestFunction check) { check(SV(R"(*"hellö"**)"), SV("{:*^10?}"), SV("hellö")); check(SV(R"("hellö"***)"), SV("{:*<10?}"), SV("hellö")); - check(SV(R"("hello\u{308}")"), SV("{:*>10?}"), SV("hello\u0308")); - check(SV(R"(***"hello\u{308}")"), SV("{:*>17?}"), SV("hello\u0308")); - check(SV(R"(*"hello\u{308}"**)"), SV("{:*^17?}"), SV("hello\u0308")); - check(SV(R"("hello\u{308}"***)"), SV("{:*<17?}"), SV("hello\u0308")); + check(SV(R"(***"hellö")"), SV("{:*>10?}"), SV("hello\u0308")); + check(SV(R"(*"hellö"**)"), SV("{:*^10?}"), SV("hello\u0308")); + check(SV(R"("hellö"***)"), SV("{:*<10?}"), SV("hello\u0308")); - check(SV(R"("hello 🤷🏻\u{200d}♂\u{fe0f}")"), SV("{:*>10?}"), SV("hello 🤷🏻‍♂️")); - check(SV(R"(***"hello 🤷🏻\u{200d}♂\u{fe0f}")"), SV("{:*>30?}"), SV("hello 🤷🏻‍♂️")); - check(SV(R"(*"hello 🤷🏻\u{200d}♂\u{fe0f}"**)"), SV("{:*^30?}"), SV("hello 🤷🏻‍♂️")); - check(SV(R"("hello 🤷🏻\u{200d}♂\u{fe0f}"***)"), SV("{:*<30?}"), SV("hello 🤷🏻‍♂️")); + check(SV(R"(***"hello 🤷🏻\u{200d}♂️")"), SV("{:*>22?}"), SV("hello 🤷🏻‍♂️")); + check(SV(R"(*"hello 🤷🏻\u{200d}♂️"**)"), SV("{:*^22?}"), SV("hello 🤷🏻‍♂️")); + check(SV(R"("hello 🤷🏻\u{200d}♂️"***)"), SV("{:*<22?}"), SV("hello 🤷🏻‍♂️")); // *** width *** check(SV(R"("hellö" )"), SV("{:10?}"), SV("hellö")); - check(SV(R"("hello\u{308}" )"), SV("{:17?}"), SV("hello\u0308")); - check(SV(R"("hello 🤷🏻\u{200d}♂\u{fe0f}" )"), SV("{:30?}"), SV("hello 🤷🏻‍♂️")); + check(SV(R"("hellö" )"), SV("{:10?}"), SV("hello\u0308")); + check(SV(R"("hello 🤷🏻\u{200d}♂️" )"), SV("{:22?}"), SV("hello 🤷🏻‍♂️")); // *** precision *** check(SV(R"("hell)"), SV("{:.5?}"), SV("hellö")); @@ -431,9 +435,8 @@ void test_format_functions(TestFunction check) { check(SV(R"("hello 🤷🏻)"), SV("{:.9?}"), SV("hello 🤷🏻‍♂️")); check(SV(R"("hello 🤷🏻\)"), SV("{:.10?}"), SV("hello 🤷🏻‍♂️")); check(SV(R"("hello 🤷🏻\u{200d})"), SV("{:.17?}"), SV("hello 🤷🏻‍♂️")); - check(SV(R"("hello 🤷🏻\u{200d}♂)"), SV("{:.18?}"), SV("hello 🤷🏻‍♂️")); - check(SV(R"("hello 🤷🏻\u{200d}♂\)"), SV("{:.19?}"), SV("hello 🤷🏻‍♂️")); - check(SV(R"("hello 🤷🏻\u{200d}♂\u{fe0f}")"), SV("{:.28?}"), SV("hello 🤷🏻‍♂️")); + check(SV(R"("hello 🤷🏻\u{200d}♂️)"), SV("{:.18?}"), SV("hello 🤷🏻‍♂️")); + check(SV(R"("hello 🤷🏻\u{200d}♂️")"), SV("{:.19?}"), SV("hello 🤷🏻‍♂️")); // *** width & precision *** check(SV(R"("hell#########################)"), SV("{:#<30.5?}"), SV("hellö")); @@ -445,9 +448,8 @@ void test_format_functions(TestFunction check) { check(SV(R"("hello 🤷🏻#####################)"), SV("{:#<30.9?}"), SV("hello 🤷🏻‍♂️")); check(SV(R"("hello 🤷🏻\####################)"), SV("{:#<30.10?}"), SV("hello 🤷🏻‍♂️")); check(SV(R"("hello 🤷🏻\u{200d}#############)"), SV("{:#<30.17?}"), SV("hello 🤷🏻‍♂️")); - check(SV(R"("hello 🤷🏻\u{200d}♂############)"), SV("{:#<30.18?}"), SV("hello 🤷🏻‍♂️")); - check(SV(R"("hello 🤷🏻\u{200d}♂\###########)"), SV("{:#<30.19?}"), SV("hello 🤷🏻‍♂️")); - check(SV(R"("hello 🤷🏻\u{200d}♂\u{fe0f}"###)"), SV("{:#<30.28?}"), SV("hello 🤷🏻‍♂️")); + check(SV(R"("hello 🤷🏻\u{200d}♂️############)"), SV("{:#<30.18?}"), SV("hello 🤷🏻‍♂️")); + check(SV(R"("hello 🤷🏻\u{200d}♂️"###########)"), SV("{:#<30.19?}"), SV("hello 🤷🏻‍♂️")); } template diff --git a/libcxx/utils/generate_escaped_output_table.py b/libcxx/utils/generate_escaped_output_table.py index c6bde8f2411cf6ccc882b522ccc0183fcb4fd997..a11ce259096d5a49bbb80dda8b34ee5f86c96df0 100755 --- a/libcxx/utils/generate_escaped_output_table.py +++ b/libcxx/utils/generate_escaped_output_table.py @@ -39,12 +39,6 @@ LINE_REGEX = re.compile( ) -def filterCoreProperty(element: PropertyRange) -> Optional[PropertyRange]: - if element.prop == "Grapheme_Extend": - return element - return None - - # https://www.unicode.org/reports/tr44/#GC_Values_Table def filterGeneralProperty(element: PropertyRange) -> Optional[PropertyRange]: if element.prop in ["Zs", "Zl", "Zp", "Cc", "Cf", "Cs", "Co", "Cn"]: @@ -94,10 +88,9 @@ DATA_ARRAY_TEMPLATE = """ /// The entries of the characters to escape in format's debug string. /// /// Contains the entries for [format.string.escaped]/2.2.1.2.1 -/// CE is a Unicode encoding and C corresponds to either a UCS scalar value -/// whose Unicode property General_Category has a value in the groups -/// Separator (Z) or Other (C) or to a UCS scalar value which has the Unicode -/// property Grapheme_Extend=Yes, as described by table 12 of UAX #44 +/// CE is a Unicode encoding and C corresponds to a UCS scalar value whose +/// Unicode property General_Category has a value in the groups Separator (Z) +/// or Other (C), as described by table 12 of UAX #44 /// /// Separator (Z) consists of General_Category /// - Space_Separator, @@ -112,7 +105,6 @@ DATA_ARRAY_TEMPLATE = """ /// - Unassigned. /// /// The data is generated from -/// - https://www.unicode.org/Public/UCD/latest/ucd/DerivedCoreProperties.txt /// - https://www.unicode.org/Public/UCD/latest/ucd/extracted/DerivedGeneralCategory.txt /// /// The table is similar to the table @@ -132,7 +124,7 @@ _LIBCPP_HIDE_FROM_ABI inline constexpr uint32_t __entries[{size}] = {{ /// lookup table would add 446 entries to the table (in Unicode 14). /// Instead the only the start of the region is stored, every code point in /// this region needs to be escaped. -inline constexpr uint32_t __unallocated_region_lower_bound = 0x{unallocated:08x}; +_LIBCPP_HIDE_FROM_ABI inline constexpr uint32_t __unallocated_region_lower_bound = 0x{unallocated:08x}; /// Returns whether the code unit needs to be escaped. /// @@ -262,7 +254,7 @@ def property_ranges_to_table(ranges: list[PropertyRange]) -> list[Entry]: return result -cpp_entrytemplate = " 0x{:08x}" +cpp_entrytemplate = " 0x{:08x} /* {:08x} - {:08x} [{:>5}] */" def generate_cpp_data(ranges: list[PropertyRange], unallocated: int) -> str: @@ -272,7 +264,15 @@ def generate_cpp_data(ranges: list[PropertyRange], unallocated: int) -> str: DATA_ARRAY_TEMPLATE.format( size=len(table), entries=",\n".join( - [cpp_entrytemplate.format(x.lower << 11 | x.offset) for x in table] + [ + cpp_entrytemplate.format( + x.lower << 11 | x.offset, + x.lower, + x.lower + x.offset, + x.offset + 1, + ) + for x in table + ] ), unallocated=unallocated, ) @@ -291,12 +291,6 @@ def generate_data_tables() -> str: / "unicode" / "DerivedGeneralCategory.txt" ) - derived_core_catagory_path = ( - Path(__file__).absolute().parent - / "data" - / "unicode" - / "DerivedCoreProperties.txt" - ) properties = list() with derived_general_catagory_path.open(encoding="utf-8") as f: @@ -308,15 +302,6 @@ def generate_data_tables() -> str: ) ) ) - with derived_core_catagory_path.open(encoding="utf-8") as f: - properties.extend( - list( - filter( - filterCoreProperty, - [x for line in f if (x := parsePropertyLine(line))], - ) - ) - ) data = compactPropertyRanges(sorted(properties, key=lambda x: x.lower)) @@ -328,8 +313,12 @@ def generate_data_tables() -> str: # # When this region becomes substantially smaller we need to investigate # this design. + # + # Due to P2713R1 Escaping improvements in std::format the range + # E0100..E01EF ; Grapheme_Extend # Mn [240] VARIATION SELECTOR-17..VARIATION SELECTOR-256 + # is no longer part of these entries. This causes an increase in the size + # of the table. assert data[-1].upper == 0x10FFFF - assert data[-1].upper - data[-1].lower > 900000 return "\n".join([generate_cpp_data(data[:-1], data[-1].lower)]) diff --git a/lld/ELF/Arch/RISCV.cpp b/lld/ELF/Arch/RISCV.cpp index 20de1b9b7bde965fefadd5a967c9022dbfbec6cf..20088d92bafa2f007a669834a4f5c26ffb75f0c6 100644 --- a/lld/ELF/Arch/RISCV.cpp +++ b/lld/ELF/Arch/RISCV.cpp @@ -15,8 +15,8 @@ #include "llvm/Support/LEB128.h" #include "llvm/Support/RISCVAttributeParser.h" #include "llvm/Support/RISCVAttributes.h" -#include "llvm/Support/RISCVISAInfo.h" #include "llvm/Support/TimeProfiler.h" +#include "llvm/TargetParser/RISCVISAInfo.h" using namespace llvm; using namespace llvm::object; diff --git a/lld/test/ELF/lto/i386-global-offset-table.ll b/lld/test/ELF/lto/i386-global-offset-table.ll new file mode 100644 index 0000000000000000000000000000000000000000..3fa11f6e6d40d72a10b5434bb0b8dd1c60e7448e --- /dev/null +++ b/lld/test/ELF/lto/i386-global-offset-table.ll @@ -0,0 +1,29 @@ +; REQUIRES: x86 +;; LTO-generated relocatable files may reference _GLOBAL_OFFSET_TABLE_ while +;; the IR does not mention _GLOBAL_OFFSET_TABLE_. +;; Test that there is no spurious "undefined symbol" error. + +; RUN: rm -rf %t && mkdir %t && cd %t +; RUN: llvm-as %s -o a.bc +; RUN: ld.lld -pie a.bc -o a +; RUN: llvm-nm a | FileCheck %s + +; CHECK: d _GLOBAL_OFFSET_TABLE_ + +target datalayout = "e-m:e-p:32:32-p270:32:32-p271:32:32-p272:64:64-i128:128-f64:32:64-f80:32-n8:16:32-S128" +target triple = "i386-pc-linux-gnu" + +@i = global i32 0 + +define dso_local void @_start() { +entry: + %0 = load i32, ptr @i + %inc = add nsw i32 %0, 1 + store i32 %inc, ptr @i + ret void +} + +!llvm.module.flags = !{!0, !1} + +!0 = !{i32 8, !"PIC Level", i32 2} +!1 = !{i32 7, !"PIE Level", i32 2} diff --git a/lld/test/ELF/lto/x86-64-global-offset-table.ll b/lld/test/ELF/lto/x86-64-global-offset-table.ll new file mode 100644 index 0000000000000000000000000000000000000000..4b0f638b409e1b22761d64aa74924caa286a77c4 --- /dev/null +++ b/lld/test/ELF/lto/x86-64-global-offset-table.ll @@ -0,0 +1,71 @@ +; REQUIRES: x86 +;; LTO-generated relocatable files may reference _GLOBAL_OFFSET_TABLE_ while +;; the IR does not mention _GLOBAL_OFFSET_TABLE_. +;; Test that there is no spurious "undefined symbol" error. + +; RUN: rm -rf %t && split-file %s %t && cd %t +; RUN: opt -module-summary b.ll -o b.bc + +;; Test Thin LTO. +; RUN: cat a.ll medium.ll | opt -module-summary - -o medium.bc +; RUN: ld.lld -pie --no-relax medium.bc b.bc -o medium +; RUN: llvm-objdump -dt medium | FileCheck %s + +;; Test regular LTO. +; RUN: cat a.ll large.ll | llvm-as - -o large.bc +; RUN: ld.lld -pie large.bc b.bc -o large +; RUN: llvm-objdump -dt large | FileCheck %s + +;; Explicit reference of _GLOBAL_OFFSET_TABLE_ is fine. +; RUN: cat a.ll medium.ll ref.ll | opt -module-summary - -o ref.bc +; RUN: ld.lld -pie -u ref ref.bc b.bc -y _GLOBAL_OFFSET_TABLE_ -o ref 2>&1 | FileCheck %s --check-prefix=TRACE +; RUN: llvm-objdump -dt ref | FileCheck %s + +; TRACE: ref.bc: reference to _GLOBAL_OFFSET_TABLE_ +; TRACE-NEXT: ref.bc: reference to _GLOBAL_OFFSET_TABLE_ +; TRACE-NEXT: : definition of _GLOBAL_OFFSET_TABLE_ +; TRACE-NEXT: ref.lto.ref.o: reference to _GLOBAL_OFFSET_TABLE_ + +;; The IR symbol table references _GLOBAL_OFFSET_TABLE_, which causes lld to define the symbol. +; CHECK: .got.plt 0000000000000000 .hidden _GLOBAL_OFFSET_TABLE_ +; CHECK: movabsq + +;--- a.ll +target datalayout = "e-m:e-p270:32:32-p271:32:32-p272:64:64-i64:64-i128:128-f80:128-n8:16:32:64-S128" +target triple = "x86_64-unknown-linux-gnu" + +@i = external global i32 + +define dso_local void @_start() { +entry: + %0 = load i32, ptr @i + %inc = add nsw i32 %0, 1 + store i32 %inc, ptr @i + ret void +} + +!llvm.module.flags = !{!0, !1, !2, !3} + +!0 = !{i32 8, !"PIC Level", i32 2} +!1 = !{i32 7, !"PIE Level", i32 2} +!2 = !{i32 1, !"Large Data Threshold", i64 0} + +;--- medium.ll +!3 = !{i32 1, !"Code Model", i32 3} + +;--- large.ll +!3 = !{i32 1, !"Code Model", i32 4} + +;--- ref.ll +@_GLOBAL_OFFSET_TABLE_ = external global [0 x i8] + +define dso_local ptr @ref() { +entry: + ret ptr @_GLOBAL_OFFSET_TABLE_ +} + +;--- b.ll +target datalayout = "e-m:e-p270:32:32-p271:32:32-p272:64:64-i64:64-i128:128-f80:128-n8:16:32:64-S128" +target triple = "x86_64-unknown-linux-gnu" + +@i = global i32 0 diff --git a/lldb/CMakeLists.txt b/lldb/CMakeLists.txt index 7844d93d78d29af8c9d60daa0b0f0dac33a18385..b0764f1053277f6539e500f2abae00ca44d106ba 100644 --- a/lldb/CMakeLists.txt +++ b/lldb/CMakeLists.txt @@ -75,6 +75,14 @@ if (LLDB_ENABLE_PYTHON) endif() endif() endforeach() + # Make sure lldb extension has "_d" suffix on Windows in Debug mode. + if(WIN32 AND CMAKE_BUILD_TYPE STREQUAL Debug) + string(SUBSTRING ${LLDB_PYTHON_EXT_SUFFIX} 0 2 FIRST_2_CHARS) + # Add "_d" manually if LLDB_PYTHON_EXT_SUFFIX lacks it due to release Python configuration. + if(NOT FIRST_2_CHARS STREQUAL "_d") + set(LLDB_PYTHON_EXT_SUFFIX "_d${LLDB_PYTHON_EXT_SUFFIX}") + endif() + endif() endif () if (LLDB_ENABLE_LUA) diff --git a/lldb/bindings/interface/SBValueDocstrings.i b/lldb/bindings/interface/SBValueDocstrings.i index 6bab923e8b35a61afdcd11ceed5cfd1a13a230ae..59fa807f5ec95c281458e456067790aecebe0ce7 100644 --- a/lldb/bindings/interface/SBValueDocstrings.i +++ b/lldb/bindings/interface/SBValueDocstrings.i @@ -135,6 +135,26 @@ linked list." %feature("docstring", "Expands nested expressions like .a->b[0].c[1]->d." ) lldb::SBValue::GetValueForExpressionPath; +%feature("docstring", " + Return the value as an address. On failure, LLDB_INVALID_ADDRESS + will be returned. On architectures like AArch64, where the + top (unaddressable) bits can be used for authentication, + memory tagging, or top byte ignore, this method will return + the value with those top bits cleared. + + GetValueAsUnsigned returns the actual value, with the + authentication/Top Byte Ignore/Memory Tagging Extension bits. + + Calling this on a random value which is not a pointer is + incorrect. Call GetType().IsPointerType() if in doubt. + + An SB API program may want to show both the literal byte value + and the address it refers to in memory. These two SBValue + methods allow SB API writers to behave appropriately for their + interface." +) lldb::SBValue::GetValueAsAddress; + + %feature("doctstring", " Returns the number for children. diff --git a/lldb/docs/conf.py b/lldb/docs/conf.py index ec7f93710ab6f2015fc30c0c196a28944d6eea4e..27a1cd7c3c31ac3d7b8f43f5137ea03e91608237 100644 --- a/lldb/docs/conf.py +++ b/lldb/docs/conf.py @@ -13,6 +13,9 @@ import sys, os, re, shutil from datetime import date +# Add path for llvm_slug module. +sys.path.insert(0, os.path.abspath(os.path.join("..", "..", "llvm", "docs"))) + building_man_page = tags.has("builder-man") # For the website we need to setup the path to the generated LLDB module that @@ -42,6 +45,23 @@ automodapi_toctreedirnm = "python_api" # coming with Sphinx (named 'sphinx.ext.*') or your custom ones. extensions = ["sphinx.ext.todo", "sphinx.ext.mathjax", "sphinx.ext.intersphinx"] +# When building man pages, we do not use the markdown pages, +# So, we can continue without the myst_parser dependencies. +# Doing so reduces dependencies of some packaged llvm distributions. +try: + import myst_parser + + extensions.append("myst_parser") +except ImportError: + if not tags.has("builder-man"): + raise + +# Automatic anchors for markdown titles +from llvm_slug import make_slug + +myst_heading_anchors = 6 +myst_heading_slug_func = make_slug + autodoc_default_options = {"special-members": True} # Unless we only generate the basic manpage we need the plugin for generating @@ -69,6 +89,7 @@ templates_path = ["_templates"] # The suffix of source filenames. source_suffix = { ".rst": "restructuredtext", + ".md": "markdown", } # The encoding of source files. diff --git a/lldb/docs/index.rst b/lldb/docs/index.rst index c378ab97d97bbb406ac7a563d5030fe2054c5449..7a27f6914fa89ddf7003b9d5b7cff21d5e8a907d 100644 --- a/lldb/docs/index.rst +++ b/lldb/docs/index.rst @@ -157,6 +157,8 @@ interesting areas to contribute to lldb. resources/sbapi resources/dataformatters resources/extensions + resources/lldbgdbremote + resources/lldbplatformpackets resources/caveats resources/projects Public C++ API diff --git a/lldb/docs/lldb-gdb-remote.txt b/lldb/docs/lldb-gdb-remote.txt deleted file mode 100644 index 6c29de61daba7edd46ae0e5d28b9074d46872492..0000000000000000000000000000000000000000 --- a/lldb/docs/lldb-gdb-remote.txt +++ /dev/null @@ -1,2286 +0,0 @@ -LLDB has added new GDB server packets to better support multi-threaded and -remote debugging. Why? Normally you need to start the correct GDB and the -correct GDB server when debugging. If you have mismatch, then things go wrong -very quickly. LLDB makes extensive use of the GDB remote protocol and we -wanted to make sure that the experience was a bit more dynamic where we can -discover information about a remote target without having to know anything up -front. We also ran into performance issues with the existing GDB remote -protocol that can be overcome when using a reliable communications layer. -Some packets improve performance, others allow for remote process launching -(if you have an OS), and others allow us to dynamically figure out what -registers a thread might have. Again with GDB, both sides pre-agree on how the -registers will look (how many, their register number,name and offsets). We -prefer to be able to dynamically determine what kind of architecture, OS and -vendor we are debugging, as well as how things are laid out when it comes to -the thread register contexts. Below are the details on the new packets we have -added above and beyond the standard GDB remote protocol packets. - -//---------------------------------------------------------------------- -// "QStartNoAckMode" -// -// BRIEF -// Try to enable no ACK mode to skip sending ACKs and NACKs. -// -// PRIORITY TO IMPLEMENT -// High. Any GDB remote server that can implement this should if the -// connection is reliable. This improves packet throughput and increases -// the performance of the connection. -//---------------------------------------------------------------------- -Having to send an ACK/NACK after every packet slows things down a bit, so we -have a way to disable ACK packets to minimize the traffic for reliable -communication interfaces (like sockets). Below GDB or LLDB will send this -packet to try and disable ACKs. All lines that start with "send packet: " are -from GDB/LLDB, and all lines that start with "read packet: " are from the GDB -remote server: - -send packet: $QStartNoAckMode#b0 -read packet: + -read packet: $OK#9a -send packet: + - -//---------------------------------------------------------------------- -// "QSupported" -// -// BRIEF -// Query the GDB remote server for features it supports -// -// PRIORITY TO IMPLEMENT -// Optional. -//---------------------------------------------------------------------- - -QSupported is a standard GDB Remote Serial Protocol packet, but -there are several additions to the response that lldb can parse. -They are not all listed here. - -An example exchange: - -send packet: qSupported:xmlRegisters=i386,arm,mips,arc;multiprocess+;fork-events+;vfork-events+ - -read packet: qXfer:features:read+;PacketSize=20000;qEcho+;native-signals+;SupportedCompressions=lzfse,zlib-deflate,lz4,lzma;SupportedWatchpointTypes=aarch64-mask,aarch64-bas; - -In the example above, three lldb extensions are shown: - - PacketSize=20000 - The base 16 maximum packet size that the stub can handle. - SupportedCompressions= - A list of compression types that the stub can use to compress packets - when the QEnableCompression packet is used to request one of them. - SupportedWatchpointTypes= - A list of watchpoint types that this stub can manage. - Currently defined names are: - x86_64 64-bit x86-64 watchpoints - (1, 2, 4, 8 byte watchpoints aligned to those amounts) - aarch64-bas AArch64 Byte Address Select watchpoints - (any number of contiguous bytes within a doubleword) - aarch64-mask AArch64 MASK watchpoints - (any power-of-2 region of memory from 8 to 2GB, aligned) - If nothing is specified, lldb will default to sending power-of-2 - watchpoints, up to a pointer size, `sizeof(void*)`, a reasonable - baseline assumption. - -//---------------------------------------------------------------------- -// "A" - launch args packet -// -// BRIEF -// Launch a program using the supplied arguments -// -// PRIORITY TO IMPLEMENT -// Low. Only needed if the remote target wants to launch a target after -// making a connection to a GDB server that isn't already connected to -// an inferior process. -//---------------------------------------------------------------------- - -We have added support for the "set program arguments" packet where we can -start a connection to a remote server and then later supply the path to the -executable and the arguments to use when executing: - -GDB remote docs for this: - -set program arguments(reserved) Aarglen,argnum,arg,... - -Where A is followed by the length in bytes of the hex encoded argument, -followed by an argument integer, and followed by the ASCII characters -converted into hex bytes foreach arg - -send packet: $A98,0,2f566f6c756d65732f776f726b2f67636c6179746f6e2f446f63756d656e74732f7372632f6174746163682f612e6f7574#00 -read packet: $OK#00 - -The above packet helps when you have remote debugging abilities where you -could launch a process on a remote host, this isn't needed for bare board -debugging. - -//---------------------------------------------------------------------- -// "QEnvironment:NAME=VALUE" -// -// BRIEF -// Setup the environment up for a new child process that will soon be -// launched using the "A" packet. -// -// NB: key/value pairs are sent as-is so gdb-remote protocol meta characters -// (e.g. '#' or '$') are not acceptable. If any non-printable or -// metacharacters are present in the strings, QEnvironmentHexEncoded -// should be used instead if it is available. If you don't want to -// scan the environment strings before sending, prefer -// the QEnvironmentHexEncoded packet over QEnvironment, if it is -// available. -// -// PRIORITY TO IMPLEMENT -// Low. Only needed if the remote target wants to launch a target after -// making a connection to a GDB server that isn't already connected to -// an inferior process. -//---------------------------------------------------------------------- - -Both GDB and LLDB support passing down environment variables. Is it ok to -respond with a "$#00" (unimplemented): - -send packet: $QEnvironment:ACK_COLOR_FILENAME=bold yellow#00 -read packet: $OK#00 - -This packet can be sent one or more times _prior_ to sending a "A" packet. - -//---------------------------------------------------------------------- -// "QEnvironmentHexEncoded:HEX-ENCODING(NAME=VALUE)" -// -// BRIEF -// Setup the environment up for a new child process that will soon be -// launched using the "A" packet. -// -// The only difference between this packet and QEnvironment is that the -// environment key-value pair is ascii hex encoded for transmission. -// This allows values with gdb-remote metacharacters like '#' to be sent. -// -// PRIORITY TO IMPLEMENT -// Low. Only needed if the remote target wants to launch a target after -// making a connection to a GDB server that isn't already connected to -// an inferior process. -//---------------------------------------------------------------------- - -Both GDB and LLDB support passing down environment variables. Is it ok to -respond with a "$#00" (unimplemented): - -send packet: $QEnvironment:41434b5f434f4c4f525f46494c454e414d453d626f6c642379656c6c6f77#00 -read packet: $OK#00 - -This packet can be sent one or more times _prior_ to sending a "A" packet. - -//---------------------------------------------------------------------- -// "QEnableErrorStrings" -// -// BRIEF -// This packet enables reporting of Error strings in remote packet -// replies from the server to client. If the server supports this -// feature, it should send an OK response. The client can expect the -// following error replies if this feature is enabled in the server -> -// -// EXX;AAAAAAAAA -// -// where AAAAAAAAA will be a hex encoded ASCII string. -// XX is hex encoded byte number. -// -// It must be noted that even if the client has enabled reporting -// strings in error replies, it must not expect error strings to all -// error replies. -// -// PRIORITY TO IMPLEMENT -// Low. Only needed if the remote target wants to provide strings that -// are human readable along with an error code. -//---------------------------------------------------------------------- - -send packet: $QEnableErrorStrings -read packet: $OK#00 - -//---------------------------------------------------------------------- -// "QSetSTDIN:" -// "QSetSTDOUT:" -// "QSetSTDERR:" -// -// BRIEF -// Setup where STDIN, STDOUT, and STDERR go prior to sending an "A" -// packet. -// -// PRIORITY TO IMPLEMENT -// Low. Only needed if the remote target wants to launch a target after -// making a connection to a GDB server that isn't already connected to -// an inferior process. -//---------------------------------------------------------------------- - -When launching a program through the GDB remote protocol with the "A" packet, -you might also want to specify where stdin/out/err go: - -QSetSTDIN: -QSetSTDOUT: -QSetSTDERR: - -These packets must be sent _prior_ to sending a "A" packet. - -//---------------------------------------------------------------------- -// "QSetWorkingDir:" -// -// BRIEF -// Set the working directory prior to sending an "A" packet. -// -// PRIORITY TO IMPLEMENT -// Low. Only needed if the remote target wants to launch a target after -// making a connection to a GDB server that isn't already connected to -// an inferior process. -//---------------------------------------------------------------------- - -Or specify the working directory: - -QSetWorkingDir: - -This packet must be sent _prior_ to sending a "A" packet. - -//---------------------------------------------------------------------- -// "QSetDisableASLR:" -// -// BRIEF -// Enable or disable ASLR on the next "A" packet. -// -// PRIORITY TO IMPLEMENT -// Low. Only needed if the remote target wants to launch a target after -// making a connection to a GDB server that isn't already connected to -// an inferior process and if the target supports disabling ASLR -// (Address space layout randomization). -//---------------------------------------------------------------------- - -Or control if ASLR is enabled/disabled: - -send packet: QSetDisableASLR:1 -read packet: OK - -send packet: QSetDisableASLR:0 -read packet: OK - -This packet must be sent _prior_ to sending a "A" packet. - -//---------------------------------------------------------------------- -// QListThreadsInStopReply -// -// BRIEF -// Enable the threads: and thread-pcs: data in the question-mark packet -// ("T packet") responses when the stub reports that a program has -// stopped executing. -// -// PRIORITY TO IMPLEMENT -// Performance. This is a performance benefit to lldb if the thread id's -// and thread pc values are provided to lldb in the T stop packet -- if -// they are not provided to lldb, lldb will likely need to send one to -// two packets per thread to fetch the data at every private stop. -//---------------------------------------------------------------------- - -send packet: QListThreadsInStopReply -read packet: OK - -//---------------------------------------------------------------------- -// jLLDBTraceSupported -// -// BRIEF -// Get the processor tracing type supported by the gdb-server for the current -// inferior. Responses might be different depending on the architecture and -// capabilities of the underlying OS. -// -// OUTPUT SCHEMA -// { -// "name": , -// Tracing technology name, e.g. intel-pt, arm-etm. -// "description": , -// Description for this technology. -// } -// -// If no tracing technology is supported for the inferior, or no process is -// running, then an error message is returned. -// -// NOTE -// This packet is used by Trace plug-ins (see lldb_private::Trace.h) to -// do live tracing. Specifically, the name of the plug-in should match the name -// of the tracing technology returned by this packet. -//---------------------------------------------------------------------- - -send packet: jLLDBTraceSupported -read packet: {"name":, "description":}/E;AAAAAAAAA - -//---------------------------------------------------------------------- -// jLLDBTraceStart -// -// BRIEF -// Start tracing a process or its threads using a provided tracing technology. -// The input and output are specified as JSON objects. In case of success, an OK -// response is returned, or an error otherwise. -// -// PROCESS TRACING -// This traces existing and future threads of the current process. An error is -// returned if the process is already being traced. -// -// THREAD TRACING -// This traces specific threads. -// -// INPUT SCHEMA -// { -// "type": , -// Tracing technology name, e.g. intel-pt, arm-etm. -// -// /* thread tracing only */ -// "tids"?: [], -// Individual threads to trace. -// -// ... other parameters specific to the provided tracing type -// } -// -// NOTES -// - If "tids" is not provided, then the operation is "process tracing", -// otherwise it's "thread tracing". -// - Each tracing technology can have different levels of support for "thread -// tracing" and "process tracing". -// -// INTEL-PT -// intel-pt supports both "thread tracing" and "process tracing". -// -// "Process tracing" is implemented in two different ways. If the -// "perCpuTracing" option is false, then each thread is traced individually -// but managed by the same "process trace" instance. This means that the -// amount of trace buffers used is proportional to the number of running -// threads. This is the recommended option unless the number of threads is -// huge. If "perCpuTracing" is true, then each cpu core is traced invidually -// instead of each thread, which uses a fixed number of trace buffers, but -// might result in less data available for less frequent threads. See -// "perCpuTracing" below for more information. -// -// Each actual intel pt trace buffer, either from "process tracing" or "thread -// tracing", is stored in an in-memory circular buffer, which keeps the most -// recent data. -// -// Additional params in the input schema: -// { -// "iptTraceSize": , -// Size in bytes used by each individual per-thread or per-cpu trace -// buffer. It must be a power of 2 greater than or equal to 4096 (2^12) -// bytes. -// -// "enableTsc": , -// Whether to enable TSC timestamps or not. This is supported on -// all devices that support intel-pt. A TSC timestamp is generated along -// with PSB (synchronization) packets, whose frequency can be configured -// with the "psbPeriod" parameter. -// -// "psbPeriod"?: , -// This value defines the period in which PSB packets will be generated. -// A PSB packet is a synchronization packet that contains a TSC -// timestamp and the current absolute instruction pointer. -// -// This parameter can only be used if -// -// /sys/bus/event_source/devices/intel_pt/caps/psb_cyc -// -// is 1. Otherwise, the PSB period will be defined by the processor. -// -// If supported, valid values for this period can be found in -/ -// /sys/bus/event_source/devices/intel_pt/caps/psb_periods -// -// which contains a hexadecimal number, whose bits represent valid -// values e.g. if bit 2 is set, then value 2 is valid. -// -// The psb_period value is converted to the approximate number of -// raw trace bytes between PSB packets as: -// -// 2 ^ (value + 11) -// -// e.g. value 3 means 16KiB between PSB packets. Defaults to -// 0 if supported. -// -// /* process tracing only */ -// "perCpuTracing": -// Instead of having an individual trace buffer per thread, this option -// triggers the collection on a per cpu core basis. This effectively -// traces the entire activity on all cores. At decoding time, in order -// to correctly associate a decoded instruction with a thread, the -// context switch trace of each core is needed, as well as a record per -// cpu indicating which thread was running on each core when tracing -// started. These secondary traces are correlated with the intel-pt -// trace by comparing TSC timestamps. -// -// This option forces the capture of TSC timestamps (see "enableTsc"). -// -// Note: This option can't be used simulatenously with any other trace -// sessions because of its system-wide nature. -// -// /* process tracing only */ -// "processBufferSizeLimit": , -// Maximum total buffer size per process in bytes. -// This limit applies to the sum of the sizes of all thread or cpu core -// buffers for the current process, excluding the ones started with -// "thread tracing". -// -// If "perCpuTracing" is false, whenever a thread is attempted to be -// traced due to "process tracing" and the limit would be reached, the -// process is stopped with a "tracing" reason along with a meaningful -// description, so that the user can retrace the process if needed. -// -// If "perCpuTracing" is true, then starting the system-wide trace -// session fails if all the individual per-cpu trace buffers require -// in total more memory that the limit impossed by this parameter. -// } -// -// Notes: -// - Modifying the parameters of an existing trace is not supported. The user -// needs to stop the trace and start a new one. -// - If "process tracing" is attempted and there are individual threads -// already being traced with "thread tracing", these traces are left -// unaffected and the threads not traced twice. -// - If "thread tracing" is attempted on a thread already being traced with -// either "thread tracing" or "process tracing", it fails. -//---------------------------------------------------------------------- - -Process tracing: -send packet: jLLDBTraceStart:{"type":,...other params}] -read packet: OK/E;AAAAAAAAA - -Thread tracing: -send packet: jLLDBTraceStart:{"type":,"tids":,...other params}] -read packet: OK/E;AAAAAAAAA - -//---------------------------------------------------------------------- -// jLLDBTraceStop -// -// BRIEF -// Stop tracing a process or its threads using a provided tracing technology. -// The input and output are specified as JSON objects. In case of success, an OK -// response is returned, or an error otherwise. -// -// PROCESS TRACE STOPPING -// Stopping a process trace stops the active traces initiated with -// "thread tracing". -// -// THREAD TRACE STOPPING -// This is a best effort request, which tries to stop as many traces as -// possible. -// -// INPUT SCHEMA -// The schema for the input is -// -// { -// "type": -// Tracing technology name, e.g. intel-pt, arm-etm. -// -// /* thread trace stopping only */ -// "tids": [] -// Individual thread traces to stop. -// } -// -// NOTES -// - If "tids" is not provided, then the operation is "process trace stopping". -// -// INTEL PT -// Stopping a specific thread trace started with "process tracing" is allowed. -//---------------------------------------------------------------------- - -Process trace stopping: -send packet: jLLDBTraceStop:{"type":}] -read packet: OK/E;AAAAAAAAA - -Thread trace stopping: -send packet: jLLDBTraceStop:{"type":,"tids":}] -read packet: OK/E;AAAAAAAAA - -//---------------------------------------------------------------------- -// jLLDBTraceGetState -// -// BRIEF -// Get the current state of the process and its threads being traced by -// a given trace technology. The response is a JSON object with custom -// information depending on the trace technology. In case of errors, an -// error message is returned. -// -// INPUT SCHEMA -// { -// "type": -// Tracing technology name, e.g. intel-pt, arm-etm. -// } -// -// OUTPUT SCHEMA -// { -// "tracedThreads": [{ -// "tid": , -// "binaryData": [ -// { -// "kind": , -// Identifier for some binary data related to this thread to -// fetch with the jLLDBTraceGetBinaryData packet. -// "size": , -// Size in bytes of this thread data. -// }, -// ] -// }], -// "processBinaryData": [ -// { -// "kind": , -// Identifier for some binary data related to this process to -// fetch with the jLLDBTraceGetBinaryData packet. -// "size": , -// Size in bytes of this thread data. -// }, -// ], -// "cpus"?: [ -// "id": , -// Identifier for this CPU logical core. -// "binaryData": [ -// { -// "kind": , -// Identifier for some binary data related to this thread to -// fetch with the jLLDBTraceGetBinaryData packet. -// "size": , -// Size in bytes of this cpu core data. -// }, -// ] -// ], -// "warnings"?: [], -// Non-fatal messages useful for troubleshooting. -// -// ... other attributes specific to the given tracing technology -// } -// -// NOTES -// - "traceThreads" includes all thread traced by both "process tracing" and -// "thread tracing". -// -// INTEL PT -// -// If per-cpu process tracing is enabled, "tracedThreads" will contain all -// the threads of the process without any trace buffers. Besides that, the -// "cpus" field will also be returned with per cpu core trace buffers. -// A side effect of per-cpu tracing is that all the threads of unrelated -// processes will also be traced, thus polluting the tracing data. -// -// Binary data kinds: -// - iptTrace: trace buffer for a thread or a cpu. -// - perfContextSwitchTrace: context switch trace for a cpu generated by -// perf_event_open. -// - procfsCpuInfo: contents of the /proc/cpuinfo file. -// -// Additional attributes: -// tscPerfZeroConversion: -// -// This field allows converting Intel processor's TSC values to nanoseconds. -// It is available through the Linux perf_event API when cap_user_time and cap_user_time_zero -// are set. -// See the documentation of time_zero in -// https://man7.org/linux/man-pages/man2/perf_event_open.2.html for more information about -// the calculation and the meaning of the values in the schema below. -/// -// Schema for this field: -// -// "tscPerfZeroConversion": { -// "timeMult": , -// "timeShift": , -// "timeZero": , -// } -//---------------------------------------------------------------------- - -send packet: jLLDBTraceGetState:{"type":}] -read packet: {...object}/E;AAAAAAAAA - -//---------------------------------------------------------------------- -// jLLDBTraceGetBinaryData -// -// BRIEF -// Get binary data given a trace technology and a data identifier. -// The input is specified as a JSON object and the response has the same format -// as the "binary memory read" (aka "x") packet. In case of failures, an error -// message is returned. -// -// SCHEMA -// The schema for the input is -// -// { -// "type": , -// Tracing technology name, e.g. intel-pt, arm-etm. -// "kind": , -// Identifier for the data. -// "cpuId": , -// Core id in decimal if the data belongs to a CPU core. -// "tid"?: , -// Tid in decimal if the data belongs to a thread. -// } -//---------------------------------------------------------------------- - -send packet: jLLDBTraceGetBinaryData:{"type":,"kind":,"tid":,"offset":,"size":}] -read packet: /E;AAAAAAAAA - -//---------------------------------------------------------------------- -// "qRegisterInfo" -// -// BRIEF -// Discover register information from the remote GDB server. -// -// PRIORITY TO IMPLEMENT -// High. Any target that can self describe its registers, should do so. -// This means if new registers are ever added to a remote target, they -// will get picked up automatically, and allows registers to change -// depending on the actual CPU type that is used. -// -// NB: qRegisterInfo is deprecated in favor of the standard gdb remote -// serial protocol register description method, -// "qXfer:features:read:target.xml". -// If qXfer:features:read:target.xml is supported, qRegisterInfo does -// not need to be implemented. The target.xml format is used by most -// gdb RSP stubs whereas qRegisterInfo was an lldb-only design. -// qRegisterInfo requires one packet per register and can have undesirable -// performance costs at the start of a debug session, whereas target.xml -// may be able to describe all registers in a single packet. -//---------------------------------------------------------------------- - -With LLDB, for register information, remote GDB servers can add -support for the "qRegisterInfoN" packet where "N" is a zero based -base 16 register number that must start at zero and increase by one -for each register that is supported. The response is done in typical -GDB remote fashion where a series of "KEY:VALUE;" pairs are returned. -An example for the x86_64 registers is included below: - -send packet: $qRegisterInfo0#00 -read packet: $name:rax;bitsize:64;offset:0;encoding:uint;format:hex;set:General Purpose Registers;gcc:0;dwarf:0;#00 -send packet: $qRegisterInfo1#00 -read packet: $name:rbx;bitsize:64;offset:8;encoding:uint;format:hex;set:General Purpose Registers;gcc:3;dwarf:3;#00 -send packet: $qRegisterInfo2#00 -read packet: $name:rcx;bitsize:64;offset:16;encoding:uint;format:hex;set:General Purpose Registers;gcc:2;dwarf:2;#00 -send packet: $qRegisterInfo3#00 -read packet: $name:rdx;bitsize:64;offset:24;encoding:uint;format:hex;set:General Purpose Registers;gcc:1;dwarf:1;#00 -send packet: $qRegisterInfo4#00 -read packet: $name:rdi;bitsize:64;offset:32;encoding:uint;format:hex;set:General Purpose Registers;gcc:5;dwarf:5;#00 -send packet: $qRegisterInfo5#00 -read packet: $name:rsi;bitsize:64;offset:40;encoding:uint;format:hex;set:General Purpose Registers;gcc:4;dwarf:4;#00 -send packet: $qRegisterInfo6#00 -read packet: $name:rbp;alt-name:fp;bitsize:64;offset:48;encoding:uint;format:hex;set:General Purpose Registers;gcc:6;dwarf:6;generic:fp;#00 -send packet: $qRegisterInfo7#00 -read packet: $name:rsp;alt-name:sp;bitsize:64;offset:56;encoding:uint;format:hex;set:General Purpose Registers;gcc:7;dwarf:7;generic:sp;#00 -send packet: $qRegisterInfo8#00 -read packet: $name:r8;bitsize:64;offset:64;encoding:uint;format:hex;set:General Purpose Registers;gcc:8;dwarf:8;#00 -send packet: $qRegisterInfo9#00 -read packet: $name:r9;bitsize:64;offset:72;encoding:uint;format:hex;set:General Purpose Registers;gcc:9;dwarf:9;#00 -send packet: $qRegisterInfoa#00 -read packet: $name:r10;bitsize:64;offset:80;encoding:uint;format:hex;set:General Purpose Registers;gcc:10;dwarf:10;#00 -send packet: $qRegisterInfob#00 -read packet: $name:r11;bitsize:64;offset:88;encoding:uint;format:hex;set:General Purpose Registers;gcc:11;dwarf:11;#00 -send packet: $qRegisterInfoc#00 -read packet: $name:r12;bitsize:64;offset:96;encoding:uint;format:hex;set:General Purpose Registers;gcc:12;dwarf:12;#00 -send packet: $qRegisterInfod#00 -read packet: $name:r13;bitsize:64;offset:104;encoding:uint;format:hex;set:General Purpose Registers;gcc:13;dwarf:13;#00 -send packet: $qRegisterInfoe#00 -read packet: $name:r14;bitsize:64;offset:112;encoding:uint;format:hex;set:General Purpose Registers;gcc:14;dwarf:14;#00 -send packet: $qRegisterInfof#00 -read packet: $name:r15;bitsize:64;offset:120;encoding:uint;format:hex;set:General Purpose Registers;gcc:15;dwarf:15;#00 -send packet: $qRegisterInfo10#00 -read packet: $name:rip;alt-name:pc;bitsize:64;offset:128;encoding:uint;format:hex;set:General Purpose Registers;gcc:16;dwarf:16;generic:pc;#00 -send packet: $qRegisterInfo11#00 -read packet: $name:rflags;alt-name:flags;bitsize:64;offset:136;encoding:uint;format:hex;set:General Purpose Registers;#00 -send packet: $qRegisterInfo12#00 -read packet: $name:cs;bitsize:64;offset:144;encoding:uint;format:hex;set:General Purpose Registers;#00 -send packet: $qRegisterInfo13#00 -read packet: $name:fs;bitsize:64;offset:152;encoding:uint;format:hex;set:General Purpose Registers;#00 -send packet: $qRegisterInfo14#00 -read packet: $name:gs;bitsize:64;offset:160;encoding:uint;format:hex;set:General Purpose Registers;#00 -send packet: $qRegisterInfo15#00 -read packet: $name:fctrl;bitsize:16;offset:176;encoding:uint;format:hex;set:Floating Point Registers;#00 -send packet: $qRegisterInfo16#00 -read packet: $name:fstat;bitsize:16;offset:178;encoding:uint;format:hex;set:Floating Point Registers;#00 -send packet: $qRegisterInfo17#00 -read packet: $name:ftag;bitsize:8;offset:180;encoding:uint;format:hex;set:Floating Point Registers;#00 -send packet: $qRegisterInfo18#00 -read packet: $name:fop;bitsize:16;offset:182;encoding:uint;format:hex;set:Floating Point Registers;#00 -send packet: $qRegisterInfo19#00 -read packet: $name:fioff;bitsize:32;offset:184;encoding:uint;format:hex;set:Floating Point Registers;#00 -send packet: $qRegisterInfo1a#00 -read packet: $name:fiseg;bitsize:16;offset:188;encoding:uint;format:hex;set:Floating Point Registers;#00 -send packet: $qRegisterInfo1b#00 -read packet: $name:fooff;bitsize:32;offset:192;encoding:uint;format:hex;set:Floating Point Registers;#00 -send packet: $qRegisterInfo1c#00 -read packet: $name:foseg;bitsize:16;offset:196;encoding:uint;format:hex;set:Floating Point Registers;#00 -send packet: $qRegisterInfo1d#00 -read packet: $name:mxcsr;bitsize:32;offset:200;encoding:uint;format:hex;set:Floating Point Registers;#00 -send packet: $qRegisterInfo1e#00 -read packet: $name:mxcsrmask;bitsize:32;offset:204;encoding:uint;format:hex;set:Floating Point Registers;#00 -send packet: $qRegisterInfo1f#00 -read packet: $name:stmm0;bitsize:80;offset:208;encoding:vector;format:vector-uint8;set:Floating Point Registers;gcc:33;dwarf:33;#00 -send packet: $qRegisterInfo20#00 -read packet: $name:stmm1;bitsize:80;offset:224;encoding:vector;format:vector-uint8;set:Floating Point Registers;gcc:34;dwarf:34;#00 -send packet: $qRegisterInfo21#00 -read packet: $name:stmm2;bitsize:80;offset:240;encoding:vector;format:vector-uint8;set:Floating Point Registers;gcc:35;dwarf:35;#00 -send packet: $qRegisterInfo22#00 -read packet: $name:stmm3;bitsize:80;offset:256;encoding:vector;format:vector-uint8;set:Floating Point Registers;gcc:36;dwarf:36;#00 -send packet: $qRegisterInfo23#00 -read packet: $name:stmm4;bitsize:80;offset:272;encoding:vector;format:vector-uint8;set:Floating Point Registers;gcc:37;dwarf:37;#00 -send packet: $qRegisterInfo24#00 -read packet: $name:stmm5;bitsize:80;offset:288;encoding:vector;format:vector-uint8;set:Floating Point Registers;gcc:38;dwarf:38;#00 -send packet: $qRegisterInfo25#00 -read packet: $name:stmm6;bitsize:80;offset:304;encoding:vector;format:vector-uint8;set:Floating Point Registers;gcc:39;dwarf:39;#00 -send packet: $qRegisterInfo26#00 -read packet: $name:stmm7;bitsize:80;offset:320;encoding:vector;format:vector-uint8;set:Floating Point Registers;gcc:40;dwarf:40;#00 -send packet: $qRegisterInfo27#00 -read packet: $name:xmm0;bitsize:128;offset:336;encoding:vector;format:vector-uint8;set:Floating Point Registers;gcc:17;dwarf:17;#00 -send packet: $qRegisterInfo28#00 -read packet: $name:xmm1;bitsize:128;offset:352;encoding:vector;format:vector-uint8;set:Floating Point Registers;gcc:18;dwarf:18;#00 -send packet: $qRegisterInfo29#00 -read packet: $name:xmm2;bitsize:128;offset:368;encoding:vector;format:vector-uint8;set:Floating Point Registers;gcc:19;dwarf:19;#00 -send packet: $qRegisterInfo2a#00 -read packet: $name:xmm3;bitsize:128;offset:384;encoding:vector;format:vector-uint8;set:Floating Point Registers;gcc:20;dwarf:20;#00 -send packet: $qRegisterInfo2b#00 -read packet: $name:xmm4;bitsize:128;offset:400;encoding:vector;format:vector-uint8;set:Floating Point Registers;gcc:21;dwarf:21;#00 -send packet: $qRegisterInfo2c#00 -read packet: $name:xmm5;bitsize:128;offset:416;encoding:vector;format:vector-uint8;set:Floating Point Registers;gcc:22;dwarf:22;#00 -send packet: $qRegisterInfo2d#00 -read packet: $name:xmm6;bitsize:128;offset:432;encoding:vector;format:vector-uint8;set:Floating Point Registers;gcc:23;dwarf:23;#00 -send packet: $qRegisterInfo2e#00 -read packet: $name:xmm7;bitsize:128;offset:448;encoding:vector;format:vector-uint8;set:Floating Point Registers;gcc:24;dwarf:24;#00 -send packet: $qRegisterInfo2f#00 -read packet: $name:xmm8;bitsize:128;offset:464;encoding:vector;format:vector-uint8;set:Floating Point Registers;gcc:25;dwarf:25;#00 -send packet: $qRegisterInfo30#00 -read packet: $name:xmm9;bitsize:128;offset:480;encoding:vector;format:vector-uint8;set:Floating Point Registers;gcc:26;dwarf:26;#00 -send packet: $qRegisterInfo31#00 -read packet: $name:xmm10;bitsize:128;offset:496;encoding:vector;format:vector-uint8;set:Floating Point Registers;gcc:27;dwarf:27;#00 -send packet: $qRegisterInfo32#00 -read packet: $name:xmm11;bitsize:128;offset:512;encoding:vector;format:vector-uint8;set:Floating Point Registers;gcc:28;dwarf:28;#00 -send packet: $qRegisterInfo33#00 -read packet: $name:xmm12;bitsize:128;offset:528;encoding:vector;format:vector-uint8;set:Floating Point Registers;gcc:29;dwarf:29;#00 -send packet: $qRegisterInfo34#00 -read packet: $name:xmm13;bitsize:128;offset:544;encoding:vector;format:vector-uint8;set:Floating Point Registers;gcc:30;dwarf:30;#00 -send packet: $qRegisterInfo35#00 -read packet: $name:xmm14;bitsize:128;offset:560;encoding:vector;format:vector-uint8;set:Floating Point Registers;gcc:31;dwarf:31;#00 -send packet: $qRegisterInfo36#00 -read packet: $name:xmm15;bitsize:128;offset:576;encoding:vector;format:vector-uint8;set:Floating Point Registers;gcc:32;dwarf:32;#00 -send packet: $qRegisterInfo37#00 -read packet: $name:trapno;bitsize:32;offset:696;encoding:uint;format:hex;set:Exception State Registers;#00 -send packet: $qRegisterInfo38#00 -read packet: $name:err;bitsize:32;offset:700;encoding:uint;format:hex;set:Exception State Registers;#00 -send packet: $qRegisterInfo39#00 -read packet: $name:faultvaddr;bitsize:64;offset:704;encoding:uint;format:hex;set:Exception State Registers;#00 -send packet: $qRegisterInfo3a#00 -read packet: $E45#00 - -As we see above we keep making subsequent calls to the remote server to -discover all registers by increasing the number appended to qRegisterInfo and -we get a response back that is a series of "key=value;" strings. - -The offset: fields should not leave a gap anywhere in the g/G packet -- the -register values should be appended one after another. For instance, if the -register context for a thread looks like - -struct rctx { - uint32_t gpr1; // offset 0 - uint32_t gpr2; // offset 4 - uint32_t gpr3; // offset 8 - uint64_t fp1; // offset 16 -}; - -You may end up with a 4-byte gap between gpr3 and fp1 on architectures -that align values like this. The correct offset: value for fp1 is 12 - -in the g/G packet fp1 will immediately follow gpr3, even though the -in-memory thread structure has an empty 4 bytes for alignment between -these two registers. - -The keys and values are detailed below: - -Key Value -========== ================================================================ -name The primary register name as a string ("rbp" for example) - -alt-name An alternate name for a register as a string ("fp" for example for - the above "rbp") - -bitsize Size in bits of a register (32, 64, etc). Base 10. - -offset The offset within the "g" and "G" packet of the register data for - this register. This is the byte offset once the data has been - transformed into binary, not the character offset into the g/G - packet. Base 10. - -encoding The encoding type of the register which must be one of: - - uint (unsigned integer) - sint (signed integer) - ieee754 (IEEE 754 float) - vector (vector register) - -format The preferred format for display of this register. The value must - be one of: - - binary - decimal - hex - float - vector-sint8 - vector-uint8 - vector-sint16 - vector-uint16 - vector-sint32 - vector-uint32 - vector-float32 - vector-uint128 - -set The register set name as a string that this register belongs to. - -gcc The GCC compiler registers number for this register (used for - EH frame and other compiler information that is encoded in the - executable files). The supplied number will be decoded like a - string passed to strtoul() with a base of zero, so the number - can be decimal, or hex if it is prefixed with "0x". - - NOTE: If the compiler doesn't have a register number for this - register, this key/value pair should be omitted. - -dwarf The DWARF register number for this register that is used for this - register in the debug information. The supplied number will be decoded - like a string passed to strtoul() with a base of zero, so the number - can be decimal, or hex if it is prefixed with "0x". - - NOTE: If the compiler doesn't have a register number for this - register, this key/value pair should be omitted. - -generic If the register is a generic register that most CPUs have, classify - it correctly so the debugger knows. Valid values are one of: - pc (a program counter register. for example "name=eip;" (i386), - "name=rip;" (x86_64), "name=r15;" (32 bit arm) would - include a "generic=pc;" key value pair) - sp (a stack pointer register. for example "name=esp;" (i386), - "name=rsp;" (x86_64), "name=r13;" (32 bit arm) would - include a "generic=sp;" key value pair) - fp (a frame pointer register. for example "name=ebp;" (i386), - "name=rbp;" (x86_64), "name=r7;" (32 bit arm with macosx - ABI) would include a "generic=fp;" key value pair) - ra (a return address register. for example "name=lr;" (32 bit ARM) - would include a "generic=ra;" key value pair) - flags (a CPU flags register. for example "name=eflags;" (i386), - "name=rflags;" (x86_64), "name=cpsr;" (32 bit ARM) - would include a "generic=flags;" key value pair) - arg1 - arg8 (specified for registers that contain function - arguments when the argument fits into a register) - -container-regs - The value for this key is a comma separated list of raw hex (optional - leading "0x") register numbers. - - This specifies that this register is contained in other concrete - register values. For example "eax" is in the lower 32 bits of the - "rax" register value for x86_64, so "eax" could specify that it is - contained in "rax" by specifying the register number for "rax" (whose - register number is 0x00) - - "container-regs:00;" - - If a register is comprised of one or more registers, like "d0" is ARM - which is a 64 bit register, it might be made up of "s0" and "s1". If - the register number for "s0" is 0x20, and the register number of "s1" - is "0x21", the "container-regs" key/value pair would be: - - "container-regs:20,21;" - - This is handy for defining what GDB used to call "pseudo" registers. - These registers are never requested by LLDB via the register read - or write packets, the container registers will be requested on behalf - of this register. - -invalidate-regs - The value for this key is a comma separated list of raw hex (optional - leading "0x") register numbers. - - This specifies which register values should be invalidated when this - register is modified. For example if modifying "eax" would cause "rax", - "eax", "ax", "ah", and "al" to be modified where rax is 0x0, eax is 0x15, - ax is 0x25, ah is 0x35, and al is 0x39, the "invalidate-regs" key/value - pair would be: - - "invalidate-regs:0,15,25,35,39;" - - If there is a single register that gets invalidated, then omit the comma - and just list a single register: - - "invalidate-regs:0;" - - This is handy when modifying a specific register can cause other - register values to change. For example, when debugging an ARM target, - modifying the CPSR register can cause the r8 - r14 and cpsr value to - change depending on if the mode has changed. - -//---------------------------------------------------------------------- -// "qPlatform_shell" -// -// BRIEF -// Run a command in a shell on the connected remote machine. -// -// PRIORITY TO IMPLEMENT -// High. This command allows LLDB clients to run arbitrary shell -// commands on a remote host. -// -/---------------------------------------------------------------------- - -The request consists of the command to be executed encoded in ASCII characters -converted into hex bytes. - -The response to this packet consists of the letter F followed by the return code, -followed by the signal number (or 0 if no signal was delivered), and escaped bytes -of captured program output. - -Below is an example communication from a client sending an "ls -la" command: - -send packet: $qPlatform_shell:6c73202d6c61,00000002#ec -read packet: $F,00000000,00000000,total 4736 -drwxrwxr-x 16 username groupname 4096 Aug 15 21:36 . -drwxr-xr-x 17 username groupname 4096 Aug 10 16:39 .. --rw-rw-r-- 1 username groupname 73875 Aug 12 16:46 notes.txt -drwxrwxr-x 5 username groupname 4096 Aug 15 21:36 source.cpp --rw-r--r-- 1 username groupname 2792 Aug 12 16:46 a.out --rw-r--r-- 1 username groupname 3190 Aug 12 16:46 Makefile - -//---------------------------------------------------------------------- -// "qPlatform_mkdir" -// -// BRIEF -// Creates a new directory on the connected remote machine. -// -// PRIORITY TO IMPLEMENT -// Low. This command allows LLDB clients to create new directories on -// a remote host. -// -/---------------------------------------------------------------------- - -Request: - qPlatform_mkdir:, - -Reply: - F - mkdir called successfully and returned with the given return code - Exx - An error occurred - -//---------------------------------------------------------------------- -// "qPlatform_chmod" -// -// BRIEF -// Change the permissions of a file on the connected remote machine. -// -// PRIORITY TO IMPLEMENT -// Low. This command allows LLDB clients to change the permissions of -// a file on the remote host. -// -/---------------------------------------------------------------------- - -Request: - qPlatform_chmod:, - -Reply: - F - chmod called successfully and returned with the given return code - Exx - An error occurred - -//---------------------------------------------------------------------- -// "qHostInfo" -// -// BRIEF -// Get information about the host we are remotely connected to. -// -// PRIORITY TO IMPLEMENT -// High. This packet is usually very easy to implement and can help -// LLDB select the correct plug-ins for the job based on the target -// triple information that is supplied. -//---------------------------------------------------------------------- - -LLDB supports a host info call that gets all sorts of details of the system -that is being debugged: - -send packet: $qHostInfo#00 -read packet: $cputype:16777223;cpusubtype:3;ostype:darwin;vendor:apple;endian:little;ptrsize:8;#00 - -Key value pairs are one of: - -cputype: is a number that is the mach-o CPU type that is being debugged (base 10) -cpusubtype: is a number that is the mach-o CPU subtype type that is being debugged (base 10) -triple: a string for the target triple (x86_64-apple-macosx) that can be used to specify arch + vendor + os in one entry -vendor: a string for the vendor (apple), not needed if "triple" is specified -ostype: a string for the OS being debugged (macosx, linux, freebsd, ios, watchos), not needed if "triple" is specified -endian: is one of "little", "big", or "pdp" -ptrsize: an unsigned number that represents how big pointers are in bytes on the debug target -hostname: the hostname of the host that is running the GDB server if available -os_build: a string for the OS build for the remote host as a string value -os_kernel: a string describing the kernel version -os_version: a version string that represents the current OS version (10.8.2) -watchpoint_exceptions_received: one of "before" or "after" to specify if a watchpoint is triggered before or after the pc when it stops -default_packet_timeout: an unsigned number that specifies the default timeout in seconds -distribution_id: optional. For linux, specifies distribution id (e.g. ubuntu, fedora, etc.) -osmajor: optional, specifies the major version number of the OS (e.g. for macOS 10.12.2, it would be 10) -osminor: optional, specifies the minor version number of the OS (e.g. for macOS 10.12.2, it would be 12) -ospatch: optional, specifies the patch level number of the OS (e.g. for macOS 10.12.2, it would be 2) -vm-page-size: optional, specifies the target system VM page size, base 10. - Needed for the "dirty-pages:" list in the qMemoryRegionInfo - packet, where a list of dirty pages is sent from the remote - stub. This page size tells lldb how large each dirty page is. -addressing_bits: optional, specifies how many bits in addresses are - significant for addressing, base 10. If bits 38..0 - in a 64-bit pointer are significant for addressing, - then the value is 39. This is needed on e.g. AArch64 - v8.3 ABIs that use pointer authentication, so lldb - knows which bits to clear/set to get the actual - addresses. -low_mem_addressing_bits: optional, specifies how many bits in - addresses in low memory are significant for addressing, base 10. - AArch64 can have different page table setups for low and high - memory, and therefore a different number of bits used for addressing. -high_mem_addressing_bits: optional, specifies how many bits in - addresses in high memory are significant for addressing, base 10. - AArch64 can have different page table setups for low and high - memory, and therefore a different number of bits used for addressing. - -//---------------------------------------------------------------------- -// "qGDBServerVersion" -// -// BRIEF -// Get version information about this implementation of the gdb-remote -// protocol. -// -// PRIORITY TO IMPLEMENT -// High. This packet is usually very easy to implement and can help -// LLDB to work around bugs in a server's implementation when they -// are found. -//---------------------------------------------------------------------- - -The goal of this packet is to provide enough information about an -implementation of the gdb-remote-protocol server that lldb can -work around implementation problems that are discovered after the -version has been released/deployed. The name and version number -should be sufficiently unique that lldb can unambiguously identify -the origin of the program (for instance, debugserver from lldb) and -the version/submission number/patch level of the program - whatever -is appropriate for your server implementation. - -The packet follows the key-value pair model, semicolon separated. - -send packet: $qGDBServerVersion#00 -read packet: $name:debugserver;version:310.2;#00 - -Other clients may find other key-value pairs to be useful for identifying -a gdb stub. Patch level, release name, build number may all be keys that -better describe your implementation's version. -Suggested key names: - - name : the name of your remote server - "debugserver" is the lldb standard - implementation - - version : identifies the version number of this server - - patch_level : the patch level of this server - - release_name : the name of this release, if your project uses names - - build_number : if you use a build system with increasing build numbers, - this may be the right key name for your server - - major_version : major version number - minor_version : minor version number - -//---------------------------------------------------------------------- -// "qProcessInfo" -// -// BRIEF -// Get information about the process we are currently debugging. -// -// PRIORITY TO IMPLEMENT -// Medium. On systems which can launch multiple different architecture processes, -// the qHostInfo may not disambiguate sufficiently to know what kind of -// process is being debugged. -// e.g. on a 64-bit x86 Mac system both 32-bit and 64-bit user processes are possible, -// and with Mach-O universal files, the executable file may contain both 32- and -// 64-bit slices so it may be impossible to know until you're attached to a real -// process to know what you're working with. -// -// All numeric fields return base 16 numbers without any "0x" prefix. -//---------------------------------------------------------------------- - -An i386 process: - -send packet: $qProcessInfo#00 -read packet: $pid:42a8;parent-pid:42bf;real-uid:ecf;real-gid:b;effective-uid:ecf;effective-gid:b;cputype:7;cpusubtype:3;ostype:macosx;vendor:apple;endian:little;ptrsize:4;#00 - -An x86_64 process: - -send packet: $qProcessInfo#00 -read packet: $pid:d22c;parent-pid:d34d;real-uid:ecf;real-gid:b;effective-uid:ecf;effective-gid:b;cputype:1000007;cpusubtype:3;ostype:macosx;vendor:apple;endian:little;ptrsize:8;#00 - -Key value pairs include: - -pid: the process id -parent-pid: the process of the parent process (often debugserver will become the parent when attaching) -real-uid: the real user id of the process -real-gid: the real group id of the process -effective-uid: the effective user id of the process -effective-gid: the effective group id of the process -cputype: the Mach-O CPU type of the process (base 16) -cpusubtype: the Mach-O CPU subtype of the process (base 16) -ostype: is a string the represents the OS being debugged (darwin, linux, freebsd) -vendor: is a string that represents the vendor (apple) -endian: is one of "little", "big", or "pdp" -ptrsize: is a number that represents how big pointers are in bytes - -main-binary-uuid: is the UUID of a firmware type binary that the gdb stub knows about -main-binary-address: is the load address of the firmware type binary -main-binary-slide: is the slide of the firmware type binary, if address isn't known - -binary-addresses: A comma-separated list of binary load addresses base 16. - lldb will parse the binaries in memory to get UUIDs, then - try to find the binaries & debug info by UUID. Intended for - use with a small number of firmware type binaries where the - search for binary/debug info may be expensive. - -//---------------------------------------------------------------------- -// "qShlibInfoAddr" -// -// BRIEF -// Get an address where the dynamic linker stores information about -// where shared libraries are loaded. -// -// PRIORITY TO IMPLEMENT -// High if you have a dynamic loader plug-in in LLDB for your target -// triple (see the "qHostInfo" packet) that can use this information. -// Many times address load randomization can make it hard to detect -// where the dynamic loader binary and data structures are located and -// some platforms know, or can find out where this information is. -// -// Low if you have a debug target where all object and symbol files -// contain static load addresses. -//---------------------------------------------------------------------- - -LLDB and GDB both support the "qShlibInfoAddr" packet which is a hint to each -debugger as to where to find the dynamic loader information. For darwin -binaries that run in user land this is the address of the "all_image_infos" -structure in the "/usr/lib/dyld" executable, or the result of a TASK_DYLD_INFO -call. The result is returned as big endian hex bytes that are the address -value: - -send packet: $qShlibInfoAddr#00 -read packet: $7fff5fc40040#00 - - - -//---------------------------------------------------------------------- -// "qThreadStopInfo" -// -// BRIEF -// Get information about why a thread, whose ID is "", is stopped. -// -// PRIORITY TO IMPLEMENT -// High if you need to support multi-threaded or multi-core debugging. -// Many times one thread will hit a breakpoint and while the debugger -// is in the process of suspending the other threads, other threads -// will also hit a breakpoint. This packet allows LLDB to know why all -// threads (live system debug) / cores (JTAG) in your program have -// stopped and allows LLDB to display and control your program -// correctly. -//---------------------------------------------------------------------- - -LLDB tries to use the "qThreadStopInfo" packet which is formatted as -"qThreadStopInfo%x" where %x is the hex thread ID. This requests information -about why a thread is stopped. The response is the same as the stop reply -packets and tells us what happened to the other threads. The standard GDB -remote packets love to think that there is only _one_ reason that _one_ thread -stops at a time. This allows us to see why all threads stopped and allows us -to implement better multi-threaded debugging support. - -//---------------------------------------------------------------------- -// "QThreadSuffixSupported" -// -// BRIEF -// Try to enable thread suffix support for the 'g', 'G', 'p', and 'P' -// packets. -// -// PRIORITY TO IMPLEMENT -// High. Adding a thread suffix allows us to read and write registers -// more efficiently and stops us from having to select a thread with -// one packet and then read registers with a second packet. It also -// makes sure that no errors can occur where the debugger thinks it -// already has a thread selected (see the "Hg" packet from the standard -// GDB remote protocol documentation) yet the remote GDB server actually -// has another thread selected. -//---------------------------------------------------------------------- - -When reading thread registers, you currently need to set the current -thread, then read the registers. This is kind of cumbersome, so we added the -ability to query if the remote GDB server supports adding a "thread:;" -suffix to all packets that request information for a thread. To test if the -remote GDB server supports this feature: - -send packet: $QThreadSuffixSupported#00 -read packet: OK - -If "OK" is returned, then the 'g', 'G', 'p' and 'P' packets can accept a -thread suffix. So to send a 'g' packet (read all register values): - -send packet: $g;thread:;#00 -read packet: .... - -send packet: $G;thread:;#00 -read packet: .... - -send packet: $p1a;thread:;#00 -read packet: .... - -send packet: $P1a=1234abcd;thread:;#00 -read packet: .... - - -otherwise, without this you would need to always send two packets: - -send packet: $Hg#00 -read packet: .... -send packet: $g#00 -read packet: .... - -We also added support for allocating and deallocating memory. We use this to -allocate memory so we can run JITed code. - -//---------------------------------------------------------------------- -// "_M," -// -// BRIEF -// Allocate memory on the remote target with the specified size and -// permissions. -// -// PRIORITY TO IMPLEMENT -// High if you want LLDB to be able to JIT code and run that code. JIT -// code also needs data which is also allocated and tracked. -// -// Low if you don't support running JIT'ed code. -//---------------------------------------------------------------------- - -The allocate memory packet starts with "_M,". It returns a -raw big endian address value, or "" for unimplemented, or "EXX" for an error -code. The packet is formatted as: - -char packet[256]; -int packet_len; -packet_len = ::snprintf ( - packet, - sizeof(packet), - "_M%zx,%s%s%s", - (size_t)size, - permissions & lldb::ePermissionsReadable ? "r" : "", - permissions & lldb::ePermissionsWritable ? "w" : "", - permissions & lldb::ePermissionsExecutable ? "x" : ""); - -You request a size and give the permissions. This packet does NOT need to be -implemented if you don't want to support running JITed code. The return value -is just the address of the newly allocated memory as raw big endian hex bytes. - -//---------------------------------------------------------------------- -// "_m" -// -// BRIEF -// Deallocate memory that was previously allocated using an allocate -// memory pack. -// -// PRIORITY TO IMPLEMENT -// High if you want LLDB to be able to JIT code and run that code. JIT -// code also needs data which is also allocated and tracked. -// -// Low if you don't support running JIT'ed code. -//---------------------------------------------------------------------- - -The deallocate memory packet is "_m" where you pass in the address you -got back from a previous call to the allocate memory packet. It returns "OK" -if the memory was successfully deallocated, or "EXX" for an error, or "" if -not supported. - -//---------------------------------------------------------------------- -// "qMemoryRegionInfo:" -// -// BRIEF -// Get information about the address range that contains "" -// -// PRIORITY TO IMPLEMENT -// Medium. This is nice to have, but it isn't necessary. It helps LLDB -// do stack unwinding when we branch into memory that isn't executable. -// If we can detect that the code we are stopped in isn't executable, -// then we can recover registers for stack frames above the current -// frame. Otherwise we must assume we are in some JIT'ed code (not JIT -// code that LLDB has made) and assume that no registers are available -// in higher stack frames. -//---------------------------------------------------------------------- - -We added a way to get information for a memory region. The packet is: - - qMemoryRegionInfo: - -Where is a big endian hex address. The response is returned in a series -of tuples like the data returned in a stop reply packet. The currently valid -tuples to return are: - - start:; // is a big endian hex address that is - // the start address of the range that contains - - size:; // is a big endian hex byte size of the address - // of the range that contains - - permissions:; // is a string that contains one - // or more of the characters from "rwx" - - name:; // is a hex encoded string that contains the name of - // the memory region mapped at the given address. In case of - // regions backed by a file it have to be the absolute path of - // the file while for anonymous regions it have to be the name - // associated to the region if that is available. - - flags:; // where is a space separated string - // of flag names. Currently the only supported flag - // is "mt" for AArch64 memory tagging. lldb will - // ignore any other flags in this field. - - type:[][,]; // memory types that apply to this region, e.g. - // "stack" for stack memory. - - error:; // where is - // a hex encoded string value that - // contains an error string - - dirty-pages:[][, -// QRestoreRegisterState:;thread:XXXX; -// -// BRIEF -// The QRestoreRegisterState packet tells the remote debugserver to -// restore all registers using the "save_id" which is an unsigned -// integer that was returned from a previous call to -// QSaveRegisterState. The restoration process can only be done once -// as the data backing the register state will be freed upon the -// completion of the QRestoreRegisterState command. -// -// If thread suffixes are enabled the second form of this packet is -// used, otherwise the first form is used. -// -// RESPONSE -// "OK" - if all registers were successfully restored -// "EXX" - for any errors -// -// PRIORITY TO IMPLEMENT -// Low, this is mostly a convenience packet to avoid having to send all -// registers via a g packet. It should only be implemented if support -// for the QSaveRegisterState is added. -//---------------------------------------------------------------------- - -//---------------------------------------------------------------------- -// qFileLoadAddress: -// -// BRIEF -// Get the load address of a memory mapped file. -// The load address is defined as the address of the first memory -// region what contains data mapped from the specified file. -// -// RESPONSE -// - Load address of the file in big endian encoding -// "E01" - the requested file isn't loaded -// "EXX" - for any other errors -// -// PRIORITY TO IMPLEMENT -// Low, required if dynamic linker don't fill in the load address of -// some object file in the rendezvous data structure. -//---------------------------------------------------------------------- - -//---------------------------------------------------------------------- -// qModuleInfo:; -// -// BRIEF -// Get information for a module by given module path and architecture. -// -// RESPONSE -// "(uuid|md5):...;triple:...;file_offset:...;file_size...;" -// "EXX" - for any errors -// -// PRIORITY TO IMPLEMENT -// Optional, required if dynamic loader cannot fetch module's information like -// UUID directly from inferior's memory. -//---------------------------------------------------------------------- - -//---------------------------------------------------------------------- -// jModulesInfo:[{"file":"...",triple:"..."}, ...] -// -// BRIEF -// Get information for a list of modules by given module path and -// architecture. -// -// RESPONSE -// A JSON array of dictionaries containing the following keys: uuid, -// triple, file_path, file_offset, file_size. The meaning of the fields -// is the same as in the qModuleInfo packet. The server signals the -// failure to retrieve the module info for a file by ommiting the -// corresponding array entry from the response. The server may also -// include entries the client did not ask for, if it has reason to -// the modules will be interesting to the client. -// -// PRIORITY TO IMPLEMENT -// Optional. If not implemented, qModuleInfo packet will be used, which -// may be slower if the target contains a large number of modules and -// the communication link has a non-negligible latency. -//---------------------------------------------------------------------- - -//---------------------------------------------------------------------- -// Stop reply packet extensions -// -// BRIEF -// This section describes some of the additional information you can -// specify in stop reply packets that help LLDB to know more detailed -// information about your threads. -// -// DESCRIPTION -// Standard GDB remote stop reply packets are reply packets sent in -// response to a packet that made the program run. They come in the -// following forms: -// -// "SAA" -// "S" means signal and "AA" is a hex signal number that describes why -// the thread or stopped. It doesn't specify which thread, so the "T" -// packet is recommended to use instead of the "S" packet. -// -// "TAAkey1:value1;key2:value2;..." -// "T" means a thread stopped due to a unix signal where "AA" is a hex -// signal number that describes why the program stopped. This is -// followed by a series of key/value pairs: -// - If key is a hex number, it is a register number and value is -// the hex value of the register in debuggee endian byte order. -// - If key == "thread", then the value is the big endian hex -// thread-id of the stopped thread. -// - If key == "core", then value is a hex number of the core on -// which the stop was detected. -// - If key == "watch" or key == "rwatch" or key == "awatch", then -// value is the data address in big endian hex -// - If key == "library", then value is ignore and "qXfer:libraries:read" -// packets should be used to detect any newly loaded shared libraries -// -// "WAA" -// "W" means the process exited and "AA" is the exit status. -// -// "XAA" -// "X" means the process exited and "AA" is signal that caused the program -// to exit. -// -// "O" -// "O" means STDOUT has data that was written to its console and is -// being delivered to the debugger. This packet happens asynchronously -// and the debugger is expected to continue to wait for another stop reply -// packet. -// -// LLDB EXTENSIONS -// -// We have extended the "T" packet to be able to also understand the -// following keys and values: -// -// KEY VALUE DESCRIPTION -// =========== ======== ================================================ -// "metype" unsigned mach exception type (the value of the EXC_XXX enumerations) -// as an unsigned integer. For targets with mach -// kernels only. -// -// "mecount" unsigned mach exception data count as an unsigned integer -// For targets with mach kernels only. -// -// "medata" unsigned There should be "mecount" of these and it is the data -// that goes along with a mach exception (as an unsigned -// integer). For targets with mach kernels only. -// -// "name" string The name of the thread as a plain string. The string -// must not contain an special packet characters or -// contain a ':' or a ';'. Use "hexname" if the thread -// name has special characters. -// -// "hexname" ascii-hex An ASCII hex string that contains the name of the thread -// -// "qaddr" hex Big endian hex value that contains the libdispatch -// queue address for the queue of the thread. -// -// "reason" enum The enumeration must be one of: -// "trace" the program stopped after a single instruction -// was executed on a core. Usually done when single -// stepping past a breakpoint -// "breakpoint" a breakpoint set using a 'z' packet was hit. -// "trap" stopped due to user interruption -// "signal" stopped due to an actual unix signal, not -// just the debugger using a unix signal to keep -// the GDB remote client happy. -// "watchpoint". Can be used with of the -// "watch"/"rwatch"/"awatch" key value pairs. -// Or can be used *instead* of those keys, -// with the specially formatted "description" field. -// "exception" an exception stop reason. Use with -// the "description" key/value pair to describe the -// exceptional event the user should see as the stop -// reason. -// "description" ascii-hex An ASCII hex string that contains a more descriptive -// reason that the thread stopped. This is only needed -// if none of the key/value pairs are enough to -// describe why something stopped. -// -// For "reason:watchpoint", "description" is an ascii-hex -// encoded string with between one and three base 10 numbers, -// space separated. The three numbers are -// 1. watchpoint address. This address should always be within -// a memory region lldb has a watchpoint on. -// On architectures where the actual reported hit address may -// be outside the watchpoint that was triggered, the remote -// stub should determine which watchpoint was triggered and -// report an address from within its range. -// 2. watchpoint hardware register index number. -// 3. actual watchpoint trap address, which may be outside -// the range of any watched region of memory. On MIPS, an addr -// outside a watched range means lldb should disable the wp, -// step, re-enable the wp and continue silently. -// -// On MIPS, the low 3 bits are masked so if a watchpoint is on -// 0x1004, a 2-byte write to 0x1000 will trigger the watchpoint -// (a false positive hit), and lldb needs to disable the -// watchpoint at 0x1004, inst-step, then re-enable the watchpoint -// and not make this a user visible event. The description here -// would be "0x1004 0 0x1000". lldb needs a known watchpoint address -// in the first field, so it can disable it & step. -// -// On AArch64 we have a related issue, where you watch 4 bytes at -// 0x1004, an instruction does an 8-byte write starting at -// 0x1000 (a true watchpoint hit) and the hardware may report the -// trap address as 0x1000 - before the watched memory region - -// with the write extending into the watched region. This can -// be reported as "0x1004 0 0x1000". lldb will use 0x1004 to -// identify which Watchpoint was triggered, and can report 0x1000 -// to the user. The behavior of silently stepping over the -// watchpoint, with an 3rd field addr outside the range, is -// restricted to MIPS. -// There may be false-positive watchpoint hits on AArch64 as well, -// in the SVE Streaming Mode, but that is less common (see ESR -// register flag "WPF", "Watchpoint might be False-Positive") and -// not currently handled by lldb. -// -// "threads" comma-sep-base16 A list of thread ids for all threads (including -// the thread that we're reporting as stopped) that -// are live in the process right now. lldb may -// request that this be included in the T packet via -// the QListThreadsInStopReply packet earlier in -// the debug session. -// -// Example: -// threads:63387,633b2,63424,63462,63486; -// -// "thread-pcs" comma-sep-base16 A list of pc values for all threads that currently -// exist in the process, including the thread that -// this T packet is reporting as stopped. -// This key-value pair will only be emitted when the -// "threads" key is already included in the T packet. -// The pc values correspond to the threads reported -// in the "threads" list. The number of pcs in the -// "thread-pcs" list will be the same as the number of -// threads in the "threads" list. -// lldb may request that this be included in the T -// packet via the QListThreadsInStopReply packet -// earlier in the debug session. -// -// Example: -// thread-pcs:dec14,2cf872b0,2cf8681c,2d02d68c,2cf716a8; -// -// "addressing_bits" unsigned optional Specifies how many bits in addresses -// are significant for addressing, base -// 10. If bits 38..0 in a 64-bit -// pointer are significant for -// addressing, then the value is 39. -// This is needed on e.g. AArch64 -// v8.3 ABIs that use pointer -// authentication in the high bits. -// This value is normally sent in the -// qHostInfo packet response, and if the -// value cannot change during the process -// lifetime, it does not need to be -// duplicated here in the stop packet. -// For a firmware environment with early -// start code that may be changing the -// page table setup, a dynamically set -// value may be needed. -// "low_mem_addressing_bits" unsigned optional, specifies how many bits in -// addresses in low memory are significant -// for addressing, base 10. AArch64 can -// have different page table setups for low -// and high memory, and therefore a different -// number of bits used for addressing. -// "high_mem_addressing_bits" unsigned optional, specifies how many bits in -// addresses in high memory are significant -// for addressing, base 10. AArch64 can have -// different page table setups for low and -// high memory, and therefore a different -// number of bits used for addressing. -// -// BEST PRACTICES: -// Since register values can be supplied with this packet, it is often useful -// to return the PC, SP, FP, LR (if any), and FLAGS registers so that separate -// packets don't need to be sent to read each of these registers from each -// thread. -// -// If a thread is stopped for no reason (like just because another thread -// stopped, or because when one core stops all cores should stop), use a -// "T" packet with "00" as the signal number and fill in as many key values -// and registers as possible. -// -// LLDB likes to know why a thread stopped since many thread control -// operations like stepping over a source line, actually are implemented -// by running the process multiple times. If a breakpoint is hit while -// trying to step over a source line and LLDB finds out that a breakpoint -// is hit in the "reason", we will know to stop trying to do the step -// over because something happened that should stop us from trying to -// do the step. If we are at a breakpoint and we disable the breakpoint -// at the current PC and do an instruction single step, knowing that -// we stopped due to a "trace" helps us know that we can continue -// running versus stopping due to a "breakpoint" (if we have two -// breakpoint instruction on consecutive instructions). So the more info -// we can get about the reason a thread stops, the better job LLDB can -// do when controlling your process. A typical GDB server behavior is -// to send a SIGTRAP for breakpoints _and_ also when instruction single -// stepping, in this case the debugger doesn't really know why we -// stopped and it can make it hard for the debugger to control your -// program correctly. What if a real SIGTRAP was delivered to a thread -// while we were trying to single step? We wouldn't know the difference -// with a standard GDB remote server and we could do the wrong thing. -// -// PRIORITY TO IMPLEMENT -// High. Having the extra information in your stop reply packets makes -// your debug session more reliable and informative. -//---------------------------------------------------------------------- - - -//---------------------------------------------------------------------- -// PLATFORM EXTENSION - for use as a GDB remote platform -//---------------------------------------------------------------------- -// "qfProcessInfo" -// "qsProcessInfo" -// -// BRIEF -// Get the first process info (qfProcessInfo) or subsequent process -// info (qsProcessInfo) for one or more processes on the remote -// platform. The first call gets the first match and subsequent calls -// to qsProcessInfo gets the subsequent matches. Return an error EXX, -// where XX are two hex digits, when no more matches are available. -// -// PRIORITY TO IMPLEMENT -// Required. The qfProcessInfo packet can be followed by a ':' and -// some key value pairs. The key value pairs in the command are: -// -// KEY VALUE DESCRIPTION -// =========== ======== ================================================ -// "name" ascii-hex An ASCII hex string that contains the name of -// the process that will be matched. -// "name_match" enum One of: "equals", "starts_with", "ends_with", -// "contains" or "regex" -// "pid" integer A string value containing the decimal process ID -// "parent_pid" integer A string value containing the decimal parent -// process ID -// "uid" integer A string value containing the decimal user ID -// "gid" integer A string value containing the decimal group ID -// "euid" integer A string value containing the decimal effective user ID -// "egid" integer A string value containing the decimal effective group ID -// "all_users" bool A boolean value that specifies if processes should -// be listed for all users, not just the user that the -// platform is running as -// "triple" string An ASCII triple string ("x86_64", -// "x86_64-apple-macosx", "armv7-apple-ios") -// "args" string A string value containing the process arguments -// separated by the character '-', where each argument is -// hex-encoded. It includes argv[0]. -// -// The response consists of key/value pairs where the key is separated from the -// values with colons and each pair is terminated with a semi colon. For a list -// of the key/value pairs in the response see the "qProcessInfoPID" packet -// documentation. -// -// Sample packet/response: -// send packet: $qfProcessInfo#00 -// read packet: $pid:60001;ppid:59948;uid:7746;gid:11;euid:7746;egid:11;name:6c6c6462;triple:x86_64-apple-macosx;#00 -// send packet: $qsProcessInfo#00 -// read packet: $pid:59992;ppid:192;uid:7746;gid:11;euid:7746;egid:11;name:6d64776f726b6572;triple:x86_64-apple-macosx;#00 -// send packet: $qsProcessInfo#00 -// read packet: $E04#00 -//---------------------------------------------------------------------- - - -//---------------------------------------------------------------------- -// PLATFORM EXTENSION - for use as a GDB remote platform -//---------------------------------------------------------------------- -// "qLaunchGDBServer" -// -// BRIEF -// Have the remote platform launch a GDB server. -// -// PRIORITY TO IMPLEMENT -// Required. The qLaunchGDBServer packet must be followed by a ':' and -// some key value pairs. The key value pairs in the command are: -// -// KEY VALUE DESCRIPTION -// =========== ======== ================================================ -// "port" integer A string value containing the decimal port ID or -// zero if the port should be bound and returned -// -// "host" integer The host that connections should be limited to -// when the GDB server is connected to. -// -// The response consists of key/value pairs where the key is separated from the -// values with colons and each pair is terminated with a semi colon. -// -// Sample packet/response: -// send packet: $qLaunchGDBServer:port:0;host:lldb.apple.com;#00 -// read packet: $pid:60025;port:50776;#00 -// -// The "pid" key/value pair is only specified if the remote platform launched -// a separate process for the GDB remote server and can be omitted if no -// process was separately launched. -// -// The "port" key/value pair in the response lets clients know what port number -// to attach to in case zero was specified as the "port" in the sent command. -//---------------------------------------------------------------------- - - -//---------------------------------------------------------------------- -// PLATFORM EXTENSION - for use as a GDB remote platform -//---------------------------------------------------------------------- -// "qProcessInfoPID:PID" -// -// BRIEF -// Have the remote platform get detailed information on a process by -// ID. PID is specified as a decimal integer. -// -// PRIORITY TO IMPLEMENT -// Optional. -// -// The response consists of key/value pairs where the key is separated from the -// values with colons and each pair is terminated with a semi colon. -// -// The key value pairs in the response are: -// -// KEY VALUE DESCRIPTION -// =========== ======== ================================================ -// "pid" integer Process ID as a decimal integer string -// "ppid" integer Parent process ID as a decimal integer string -// "uid" integer A string value containing the decimal user ID -// "gid" integer A string value containing the decimal group ID -// "euid" integer A string value containing the decimal effective user ID -// "egid" integer A string value containing the decimal effective group ID -// "name" ascii-hex An ASCII hex string that contains the name of the process -// "triple" string A target triple ("x86_64-apple-macosx", "armv7-apple-ios") -// -// Sample packet/response: -// send packet: $qProcessInfoPID:60050#00 -// read packet: $pid:60050;ppid:59948;uid:7746;gid:11;euid:7746;egid:11;name:6c6c6462;triple:x86_64-apple-macosx;#00 -//---------------------------------------------------------------------- - -//---------------------------------------------------------------------- -// "vAttachName" -// -// BRIEF -// Same as vAttach, except instead of a "pid" you send a process name. -// -// PRIORITY TO IMPLEMENT -// Low. Only needed for "process attach -n". If the packet isn't supported -// then "process attach -n" will fail gracefully. So you need only to support -// it if attaching to a process by name makes sense for your environment. -//---------------------------------------------------------------------- - -//---------------------------------------------------------------------- -// "vAttachWait" -// -// BRIEF -// Same as vAttachName, except that the stub should wait for the next instance -// of a process by that name to be launched and attach to that. -// -// PRIORITY TO IMPLEMENT -// Low. Only needed to support "process attach -w -n" which will fail -// gracefully if the packet is not supported. -//---------------------------------------------------------------------- - -//---------------------------------------------------------------------- -// "qAttachOrWaitSupported" -// -// BRIEF -// This is a binary "is it supported" query. Return OK if you support -// vAttachOrWait -// -// PRIORITY TO IMPLEMENT -// Low. This is required if you support vAttachOrWait, otherwise no support -// is needed since the standard "I don't recognize this packet" response -// will do the right thing. -//---------------------------------------------------------------------- - -//---------------------------------------------------------------------- -// "vAttachOrWait" -// -// BRIEF -// Same as vAttachWait, except that the stub will attach to a process -// by name if it exists, and if it does not, it will wait for a process -// of that name to appear and attach to it. -// -// PRIORITY TO IMPLEMENT -// Low. Only needed to implement "process attach -w -i false -n". If -// you don't implement it but do implement -n AND lldb can somehow get -// a process list from your device, it will fall back on scanning the -// process list, and sending vAttach or vAttachWait depending on -// whether the requested process exists already. This is racy, -// however, so if you want to support this behavior it is better to -// support this packet. -//---------------------------------------------------------------------- - -//---------------------------------------------------------------------- -// "jThreadExtendedInfo" -// -// BRIEF -// This packet, which takes its arguments as JSON and sends its reply as -// JSON, allows the gdb remote stub to provide additional information -// about a given thread. -// -// PRIORITY TO IMPLEMENT -// Low. This packet is only needed if the gdb remote stub wants to -// provide interesting additional information about a thread for the -// user. -// -// This packet takes its arguments in JSON form ( http://www.json.org ). -// At a minimum, a thread must be specified, for example: -// -// jThreadExtendedInfo:{"thread":612910} -// -// Because this is a JSON string, the thread number is provided in base 10. -// Additional key-value pairs may be provided by lldb to the gdb remote -// stub. For instance, on some versions of macOS, lldb can read offset -// information out of the system libraries. Using those offsets, debugserver -// is able to find the Thread Specific Address (TSD) for a thread and include -// that in the return information. So lldb will send these additional fields -// like so: -// -// jThreadExtendedInfo:{"plo_pthread_tsd_base_address_offset":0,"plo_pthread_tsd_base_offset":224,"plo_pthread_tsd_entry_size":8,"thread":612910} -// -// There are no requirements for what is included in the response. A simple -// reply on a OS X Yosemite / iOS 8 may include the pthread_t value, the -// Thread Specific Data (TSD) address, the dispatch_queue_t value if the thread -// is associated with a GCD queue, and the requested Quality of Service (QoS) -// information about that thread. For instance, a reply may look like: -// -// {"tsd_address":4371349728,"requested_qos":{"enum_value":33,"constant_name":"QOS_CLASS_USER_INTERACTIVE","printable_name":"User Interactive"},"pthread_t":4371349504,"dispatch_queue_t":140735087127872} -// -// tsd_address, pthread_t, and dispatch_queue_t are all simple key-value pairs. -// The JSON standard requires that numbers be expressed in base 10 - so all of -// these are. requested_qos is a dictionary with three key-value pairs in it - -// so the UI layer may choose the form most appropriate for displaying to the user. -// -// Sending JSON over gdb-remote protocol introduces some problems. We may be -// sending strings with arbitrary contents in them, including the '#', '$', and '*' -// characters that have special meaning in gdb-remote protocol and cannot occur -// in the middle of the string. The standard solution for this would be to require -// ascii-hex encoding of all strings, or ascii-hex encode the entire JSON payload. -// -// Instead, the binary escaping convention is used for JSON data. This convention -// (e.g. used for the X packet) says that if '#', '$', '*', or '}' are to occur in -// the payload, the character '}' (0x7d) is emitted, then the metacharacter is emitted -// xor'ed by 0x20. The '}' character occurs in every JSON payload at least once, and -// '}' ^ 0x20 happens to be ']' so the raw packet characters for a request will look -// like -// -// jThreadExtendedInfo:{"thread":612910}] -// -// on the wire. -//---------------------------------------------------------------------- - -//---------------------------------------------------------------------- -// "QEnableCompression" -// -// BRIEF -// This packet enables compression of the packets that the debug stub sends to lldb. -// If the debug stub can support compression, it indictes this in the reply of the -// "qSupported" packet. e.g. -// LLDB SENDS: qSupported:xmlRegisters=i386,arm,mips -// STUB REPLIES: qXfer:features:read+;SupportedCompressions=lzfse,zlib-deflate,lz4,lzma; -// -// If lldb knows how to use any of these compression algorithms, it can ask that this -// compression mode be enabled. -// -// QEnableCompression:type:zlib-deflate; -// -// The debug stub should reply with an uncompressed "OK" packet to indicate that the -// request was accepted. All further packets the stub sends will use this compression. -// -// Packets are compressed as the last step before they are sent from the stub, and -// decompressed as the first step after they are received. The packet format in compressed -// mode becomes one of two: -// -// $N#00 -// -// $C:#00 -// -// Where "#00" is the actual checksum value if noack mode is not enabled. The checksum -// value is for the "N" or -// "C:" bytes in the packet. -// -// The size of the uncompressed payload in base 10 is provided because it will simplify -// decompression if the final buffer size needed is known ahead of time. -// -// Compression on low-latency connections is unlikely to be an improvement. Particularly -// when the debug stub and lldb are running on the same host. It should only be used -// for slow connections, and likely only for larger packets. -// -// Example compression algorithsm that may be used include -// -// zlib-deflate -// The raw DEFLATE format as described in IETF RFC 1951. With the ZLIB library, you -// can compress to this format with an initialization like -// deflateInit2 (&stream, 5, Z_DEFLATED, -15, 8, Z_DEFAULT_STRATEGY) -// and you can decompress with an initialization like -// inflateInit2 (&stream, -15) -// -// lz4 -// https://en.wikipedia.org/wiki/LZ4_(compression_algorithm) -// https://github.com/Cyan4973/lz4 -// The libcompression APIs on darwin systems call this COMPRESSION_LZ4_RAW. -// -// lzfse -// Compression algorithm added in macOS 10.11, with open source C reference -// implementation on github. -// https://en.wikipedia.org/wiki/LZFSE -// https://github.com/lzfse/lzfse -// -// lzma -// libcompression implements "LZMA level 6", the default compression for the -// open source LZMA implementation. -//---------------------------------------------------------------------- - -//---------------------------------------------------------------------- -// "jGetLoadedDynamicLibrariesInfos" -// -// BRIEF -// This packet asks the remote debug stub to send the details about libraries -// being added/removed from the process as a performance optimization. -// -// There are two ways this packet can be used. Both return a dictionary of -// binary images formatted the same way. -// -// One requests information on all shared libraries: -// jGetLoadedDynamicLibrariesInfos:{"fetch_all_solibs":true} -// with an optional `"report_load_commands":false` which can be added, asking -// that only the dyld SPI information (load addresses, filenames) be returned. -// The default behavior is that debugserver scans the mach-o header and load -// commands of each binary, and returns it in the JSON reply. -// -// And the second requests information about a list of shared libraries, given their load addresses: -// jGetLoadedDynamicLibrariesInfos:{"solib_addresses":[8382824135,3258302053,830202858503]} -// -// The second call is both a performance optimization (instead of having lldb read the mach-o header/load commands -// out of memory with generic read packets) but also adds additional information in the form of the -// filename of the shared libraries (which is not available in the mach-o header/load commands.) -// -// An example using the OS X 10.11 style call: -// -// LLDB SENDS: jGetLoadedDynamicLibrariesInfos:{"image_count":1,"image_list_address":140734800075128} -// STUB REPLIES: ${"images":[{"load_address":4294967296,"mod_date":0,"pathname":"/tmp/a.out","uuid":"02CF262C-ED6F-3965-9E14-63538B465CFF","mach_header":{"magic":4277009103,"cputype":16777223,"cpusubtype":18446744071562067971,"filetype":2},"segments":{"name":"__PAGEZERO","vmaddr":0,"vmsize":4294967296,"fileoff":0,"filesize":0,"maxprot":0},{"name":"__TEXT","vmaddr":4294967296,"vmsize":4096,"fileoff":0,"filesize":4096,"maxprot":7},{"name":"__LINKEDIT","vmaddr":4294971392,"vmsize":4096,"fileoff":4096,"filesize":152,"maxprot":7}}]}#00 -// -// Or pretty-printed, -// -// STUB REPLIES: ${"images": -// [ -// {"load_address":4294967296, -// "mod_date":0, -// "pathname":"/tmp/a.out", -// "uuid":"02CF262C-ED6F-3965-9E14-63538B465CFF", -// "mach_header": -// {"magic":4277009103, -// "cputype":16777223, -// "cpusubtype":18446744071562067971, -// "filetype":2 -// }, -// "segments": -// [ -// {"name":"__PAGEZERO", -// "vmaddr":0, -// "vmsize":4294967296, -// "fileoff":0, -// "filesize":0, -// "maxprot":0 -// }, -// {"name":"__TEXT", -// "vmaddr":4294967296, -// "vmsize":4096, -// "fileoff":0, -// "filesize":4096, -// "maxprot":7 -// }, -// {"name":"__LINKEDIT", -// "vmaddr":4294971392, -// "vmsize":4096, -// "fileoff":4096, -// "filesize":152, -// "maxprot":7 -// } -// ] -// } -// ] -// } -// -// -// This is similar to the qXfer:libraries:read packet, and it could -// be argued that it should be merged into that packet. A separate -// packet was created primarily because lldb needs to specify the -// number of images to be read and the address from which the initial -// information is read. Also the XML DTD would need to be extended -// quite a bit to provide all the information that the DynamicLoaderMacOSX -// would need to work correctly on this platform. -// -// PRIORITY TO IMPLEMENT -// On OS X 10.11, iOS 9, tvOS 9, watchOS 2 and older: Low. If this packet is absent, -// lldb will read the Mach-O headers/load commands out of memory. -// On macOS 10.12, iOS 10, tvOS 10, watchOS 3 and newer: High. If this packet is absent, -// lldb will not know anything about shared libraries in the inferior, or where the main -// executable loaded. -//---------------------------------------------------------------------- - -//---------------------------------------------------------------------- -// "jThreadsInfo" -// -// BRIEF -// Ask for the server for thread stop information of all threads. -// -// PRIORITY TO IMPLEMENT -// Low. This is a performance optimization, which speeds up debugging by avoiding -// multiple round-trips for retrieving thread information. The information from this -// packet can be retrieved using a combination of qThreadStopInfo and m packets. -//---------------------------------------------------------------------- - -The data in this packet is very similar to the stop reply packets, but is packaged in -JSON and uses JSON arrays where applicable. The JSON output looks like: - [ - { "tid":1580681, - "metype":6, - "medata":[2,0], - "reason":"exception", - "qaddr":140735118423168, - "registers": { - "0":"8000000000000000", - "1":"0000000000000000", - "2":"20fabf5fff7f0000", - "3":"e8f8bf5fff7f0000", - "4":"0100000000000000", - "5":"d8f8bf5fff7f0000", - "6":"b0f8bf5fff7f0000", - "7":"20f4bf5fff7f0000", - "8":"8000000000000000", - "9":"61a8db78a61500db", - "10":"3200000000000000", - "11":"4602000000000000", - "12":"0000000000000000", - "13":"0000000000000000", - "14":"0000000000000000", - "15":"0000000000000000", - "16":"960b000001000000", - "17":"0202000000000000", - "18":"2b00000000000000", - "19":"0000000000000000", - "20":"0000000000000000" - }, - "memory":[ - {"address":140734799804592,"bytes":"c8f8bf5fff7f0000c9a59e8cff7f0000"}, - {"address":140734799804616,"bytes":"00000000000000000100000000000000"} - ] - } - ] - -It contains an array of dictionaries with all of the key value pairs that are -normally in the stop reply packet, including the expedited registers. The registers are -passed as hex-encoded JSON string in debuggee-endian byte order. Note that the register -numbers are decimal numbers, unlike the stop-reply packet, where they are written in -hex. The packet also contains expedited memory in the "memory" key. This allows the -server to expedite memory that the client is likely to use (e.g., areas around the -stack pointer, which are needed for computing backtraces) and it reduces the packet -count. - -On macOS with debugserver, we expedite the frame pointer backchain for a thread -(up to 256 entries) by reading 2 pointers worth of bytes at the frame pointer (for -the previous FP and PC), and follow the backchain. Most backtraces on macOS and -iOS now don't require us to read any memory! - -//---------------------------------------------------------------------- -// "jGetSharedCacheInfo" -// -// BRIEF -// This packet asks the remote debug stub to send the details about the inferior's -// shared cache. The shared cache is a collection of common libraries/frameworks that -// are mapped into every process at the same address on Darwin systems, and can be -// identified by a load address and UUID. -// -// -// LLDB SENDS: jGetSharedCacheInfo:{} -// STUB REPLIES: ${"shared_cache_base_address":140735683125248,"shared_cache_uuid":"DDB8D70C-C9A2-3561-B2C8-BE48A4F33F96","no_shared_cache":false,"shared_cache_private_cache":false]}#00 -// -// PRIORITY TO IMPLEMENT -// Low. When both lldb and the inferior process are running on the same computer, and lldb -// and the inferior process have the same shared cache, lldb may (as an optimization) read -// the shared cache out of its own memory instead of using gdb-remote read packets to read -// them from the inferior process. -//---------------------------------------------------------------------- - -//---------------------------------------------------------------------- -// "qQueryGDBServer" -// -// BRIEF -// Ask the platform for the list of gdbservers we have to connect -// -// PRIORITY TO IMPLEMENT -// Low. The packet is required to support connecting to gdbserver started -// by the platform instance automatically. -//---------------------------------------------------------------------- - -If the remote platform automatically started one or more gdbserver instance (without -lldb asking it) then it have to return the list of port number or socket name for -each of them what can be used by lldb to connect to those instances. - -The data in this packet is a JSON array of JSON objects with the following keys: -"port": (optional) -"socket_name": (optional) - -Example packet: -[ - { "port": 1234 }, - { "port": 5432 }, - { "socket_name": "foo" } -] - -//---------------------------------------------------------------------- -// "QSetDetachOnError" -// -// BRIEF -// Sets what the server should do when the communication channel with LLDB -// goes down. Either kill the inferior process (0) or remove breakpoints and -// detach (1). -// -// PRIORITY TO IMPLEMENT -// Low. Only required if the target wants to keep the inferior process alive -// when the communication channel goes down. -//---------------------------------------------------------------------- - -The data in this packet is a single a character, which should be '0' if the -inferior process should be killed, or '1' if the server should remove all -breakpoints and detach from the inferior. - -//---------------------------------------------------------------------- -// "jGetDyldProcessState" -// -// BRIEF -// This packet fetches the process launch state, as reported by libdyld on -// Darwin systems, most importantly to indicate when the system libraries -// have initialized sufficiently to safely call utility functions. -// -// -// LLDB SENDS: jGetDyldProcessState -// STUB REPLIES: {"process_state_value":48,"process_state string":"dyld_process_state_libSystem_initialized"} -// -// PRIORITY TO IMPLEMENT -// Low. This packet is needed to prevent lldb's utility functions for -// scanning the Objective-C class list from running very early in -// process startup. -//---------------------------------------------------------------------- diff --git a/lldb/docs/lldb-platform-packets.txt b/lldb/docs/lldb-platform-packets.txt deleted file mode 100644 index 4cf575e5ee8adbf365508704651075b8ada04c38..0000000000000000000000000000000000000000 --- a/lldb/docs/lldb-platform-packets.txt +++ /dev/null @@ -1,451 +0,0 @@ -Here is a brief overview of the packets that an lldb platform server -needs to implement for the lldb testsuite to be run on a remote -target device/system. - -These are almost all lldb extensions to the gdb-remote serial -protocol. Many of the vFile: packets are described to the "Host -I/O Packets" detailed in the gdb-remote protocol documentation, -although the lldb platform extensions include packets that are not -defined there (vFile:size:, vFile:mode:, vFile:symlink, vFile:chmod:). -Most importantly, the flags that lldb passes to vFile:open: are -incompatible with the flags that gdb specifies. - - -//---------------------------------------------------------------------- -// QStartNoAckMode -// -// BRIEF -// A request to stop sending ACK packets for each properly formatted packet. -// -// EXAMPLE -// A platform session will typically start like this: -// -// receive: +$QStartNoAckMode#b0 -// send: + <-- ACKing the properly formatted QStartNoAckMode packet -// send: $OK#9a -// receive: + <-- Our OK packet getting ACKed -// -// ACK mode is now disabled. - -//---------------------------------------------------------------------- -// qHostInfo -// -// BRIEF -// Describe the hardware and OS of the target system -// -// EXAMPLE -// -// receive: qHostInfo -// send: cputype:16777228;cpusubtype:1;ostype:ios;watchpoint_exceptions_received:before;os_version:12.1;vendor:apple;default_packet_timeout:5; -// -// All numbers are base 10, os_version is a string that will be parsed as major.minor.patch. - -//---------------------------------------------------------------------- -// qModuleInfo -// -// BRIEF -// Report information about a binary on the target system -// -// EXAMPLE -// receive: qModuleInfo:2f62696e2f6c73; -// -// FIXME finish this packet description, v. GDBRemoteCommunicationServerCommon::Handle_qModuleInfo - - -//---------------------------------------------------------------------- -// qGetWorkingDir -// -// BRIEF -// Get the current working directory of the platform stub in -// ASCII hex encoding. -// -// EXAMPLE -// -// receive: qGetWorkingDir -// send: 2f4170706c65496e7465726e616c2f6c6c64622f73657474696e67732f342f5465737453657474696e67732e746573745f646973617373656d626c65725f73657474696e6773 - - - -//---------------------------------------------------------------------- -// QSetWorkingDir: -// -// BRIEF -// Set the current working directory of the platform stub in -// ASCII hex encoding. -// -// EXAMPLE -// -// receive: QSetWorkingDir:2f4170706c65496e7465726e616c2f6c6c64622f73657474696e67732f342f5465737453657474696e67732e746573745f646973617373656d626c65725f73657474696e6773 -// send: OK - -//---------------------------------------------------------------------- -// qPlatform_mkdir: -// -// BRIEF -// Create a directory on the target system. -// -// EXAMPLE -// -// receive: qPlatform_mkdir:000001fd,2f746d702f6131 -// send: F0 -// -// request packet has the fields: -// 1. mode bits in base 16 -// 2. file path in ascii-hex encoding -// -// response is F followed by the return value of the mkdir() call, -// base 16 encoded. - -//---------------------------------------------------------------------- -// qPlatform_shell: -// -// BRIEF -// Run a shell command on the target system, return the output. -// -// EXAMPLE -// -// receive: qPlatform_shell:6c73202f746d702f,0000000a -// send: F,0,0, -// -// request packet has the fields: -// 1. shell command ascii-hex encoded -// 2. timeout -// 3. {optional} working directory ascii-hex encoded -// -// Response is F followed by the return value of the command (base 16), -// followed by another number, followed by the output of the command -/ in binary-escaped-data encoding. - -//---------------------------------------------------------------------- -// qLaunchGDBServer -// -// BRIEF -// Start a gdbserver process (gdbserver, debugserver, lldb-server) -// on the target system. -// -// EXAMPLE -// -// receive: qLaunchGDBServer;host:; -// send: pid:1337;port:43001; -// -// request packet hostname field is not ascii-hex encoded. Hostnames -// don't have $ or # characters in them. -// -// response to the packet is the pid of the newly launched gdbserver, -// and the port it is listening for a connection on. -// -// When the testsuite is running, lldb may use the pid to kill off a -// debugserver that doesn't seem to be responding, etc. - -//---------------------------------------------------------------------- -// qKillSpawnedProcess: -// -// BRIEF -// Kill a process running on the target system. -// -// EXAMPLE -// -// receive: qKillSpawnedProcess:1337 -// send: OK -// -// The request packet has the process ID in base 10. - -//---------------------------------------------------------------------- -// qProcessInfoPID: -// -// BRIEF -// Gather information about a process running on the target -// -// EXAMPLE -// -// receive: qProcessInfoPID:71964 -// send: pid:71964;name:612e6f7574; -// -// The request packet has the pid encoded in base 10. -// -// The reply has semicolon-separated name:value fields, two are -// shown here. pid is base 10 encoded. name is ascii hex encoded. -// lldb-server can reply with many additional fields, but I think -// this is enough for the testsuite. - -//---------------------------------------------------------------------- -// qfProcessInfo: -// -// BRIEF -// Search the process table for processes matching criteria, -// respond with them in multiple packets. -// -// EXAMPLE -// -// receive: qfProcessInfo:name_match:equals;name:6e6f70726f6365737365786973747377697468746869736e616d65; -// send: pid:3500;name:612e6f7574; -// -// The request packet has a criteria to search for, followed by -// a specific name. -// -// KEY VALUE DESCRIPTION -// =========== ======== ================================================ -// "name" ascii-hex An ASCII hex string that contains the name of -// the process that will be matched. -// "name_match" enum One of: "equals", "starts_with", "ends_with", -// "contains" or "regex" -// "pid" integer A string value containing the decimal process ID -// "parent_pid" integer A string value containing the decimal parent -// process ID -// "uid" integer A string value containing the decimal user ID -// "gid" integer A string value containing the decimal group ID -// "euid" integer A string value containing the decimal effective user ID -// "egid" integer A string value containing the decimal effective group ID -// "all_users" bool A boolean value that specifies if processes should -// be listed for all users, not just the user that the -// platform is running as -// "triple" ascii-hex An ASCII hex target triple string ("x86_64", -// "x86_64-apple-macosx", "armv7-apple-ios") -// -// If no criteria is given, qfProcessInfo will request a list of every process. -// -// The lldb testsuite currently only uses name_match:equals and the -// no-criteria mode to list every process. -// -// The response should include any information about the process that -// can be retrieved in semicolon-separated name:value fields. -// In this example, pid is base 10, name is ascii-hex encoded. -// The testsuite seems to only require these two. -// -// This packet only responds with one process. To get further matches to -// the search, qsProcessInfo should be sent. -// -// If no process match is found, Exx should be returned. -// -// Sample packet/response: -// send packet: $qfProcessInfo#00 -// read packet: $pid:60001;ppid:59948;uid:7746;gid:11;euid:7746;egid:11;name:6c6c6462;triple:7838365f36342d6170706c652d6d61636f7378;#00 -// send packet: $qsProcessInfo#00 -// read packet: $pid:59992;ppid:192;uid:7746;gid:11;euid:7746;egid:11;name:6d64776f726b6572;triple:7838365f36342d6170706c652d6d61636f7378;#00 -// send packet: $qsProcessInfo#00 -// read packet: $E04#00 - -//---------------------------------------------------------------------- -// qsProcessInfo -// -// BRIEF -// Return the next process info found by the most recent qfProcessInfo: -// packet. -// -// EXAMPLE -// -// Continues to return the results of the qfProcessInfo. Once all matches -// have been sent, Exx is returned to indicate end of matches. - -//---------------------------------------------------------------------- -// qPathComplete -// -// BRIEF -// Get a list of matched disk files/directories by passing a boolean flag -// and a partial path. -// -// EXAMPLE -// -// receive: qPathComplete:0,6d61696e -// send: M6d61696e2e637070 -// receive: qPathComplete:1,746573 -// send: M746573742f,74657374732f -// -// If the first argument is zero, the result should contain all -// files (including directories) starting with the given path. If the -// argument is one, the result should contain only directories. -// -// The result should be a comma-separated list of hex-encoded paths. -// Paths denoting a directory should end with a directory separator ('/' or '\'). - -//---------------------------------------------------------------------- -// vFile:size: -// -// BRIEF -// Get the size of a file on the target system, filename in ASCII hex. -// -// EXAMPLE -// -// receive: vFile:size:2f746d702f61 -// send: Fc008 -// -// response is "F" followed by the file size in base 16. -// "F-1,errno" with the errno if an error occurs, base 16. - - -//---------------------------------------------------------------------- -// vFile:mode: -// -// BRIEF -// Get the mode bits of a file on the target system, filename in ASCII hex. -// -// EXAMPLE -// -// receive: vFile:mode:2f746d702f61 -// send: F1ed -// -// response is "F" followed by the mode bits in base 16, this 0x1ed would -// correspond to 0755 in octal. -// "F-1,errno" with the errno if an error occurs, base 16. - -//---------------------------------------------------------------------- -// vFile:unlink: -// -// BRIEF -// Remove a file on the target system. -// -// EXAMPLE -// -// receive: vFile:unlink:2f746d702f61 -// send: F0 -// -// Argument is a file path in ascii-hex encoding. -// Response is "F" plus the return value of unlink(), base 16 encoding. -// Return value may optionally be followed by a comma and the base16 -// value of errno if unlink failed. - -//---------------------------------------------------------------------- -// vFile:symlink: -// -// BRIEF -// Create a symbolic link (symlink, soft-link) on the target system. -// -// EXAMPLE -// -// receive: vFile:symlink:, -// send: F0,0 -// -// Argument file paths are in ascii-hex encoding. -// Response is "F" plus the return value of symlink(), base 16 encoding, -// optionally followed by the value of errno if it failed, also base 16. - -//---------------------------------------------------------------------- -// vFile:chmod: -// qPlatform_chmod: -// -// BRIEF -// Change the permission mode bits on a file on the target -// -// EXAMPLE -// -// receive: vFile:chmod:180,2f746d702f61 -// send: F0 -// -// Arguments are the mode bits to set, base 16, and a file path in -// ascii-hex encoding. -// Response is "F" plus the return value of chmod(), base 16 encoding. -// -// I don't know why there are two packets for the same thing, v. -// vFile:chmod:. - -//---------------------------------------------------------------------- -// vFile:chmod: -// -// BRIEF -// Change the permission mode bits on a file on the target -// -// EXAMPLE -// -// receive: vFile:chmod:180,2f746d702f61 -// send: F0 -// -// Arguments are the mode bits to set, base 16, and a file path in -// ascii-hex encoding. -// Response is "F" plus the return value of chmod(), base 10 encoding. - - -//---------------------------------------------------------------------- -// vFile:open: -// -// BRIEF -// Open a file on the remote system and return the file descriptor of it. -// -// EXAMPLE -// -// receive: vFile:open:2f746d702f61,00000001,00000180 -// send: F8 -// -// request packet has the fields: -// 1. ASCII hex encoded filename -// 2. flags passed to the open call, base 16. -// Note that these are not the oflags that open(2) takes, but -// are the constant values in enum OpenOptions from lldb's File.h -// 3. mode bits, base 16 -// -// response is F followed by the opened file descriptor in base 16. -// "F-1,errno" with the errno if an error occurs, base 16. -// -//---------------------------------------------------------------------- -// vFile:close: -// -// BRIEF -// Close a previously opened file descriptor. -// -// EXAMPLE -// -// receive: vFile:close:7 -// send: F0 -// -// File descriptor is in base 16. -// "F-1,errno" with the errno if an error occurs, -// errno is base 16. - - -//---------------------------------------------------------------------- -// vFile:pread: -// -// BRIEF -// Read data from an opened file descriptor. -// -// EXAMPLE -// -// receive: vFile:pread:7,1024,0 -// send: F4;a'b\00 -// -// request packet has the fields: -// 1. file descriptor, base 16 -// 2. number of bytes to be read, base 16 -// 3. offset into file to start from, base 16 -// -// Response is F, followed by the number of bytes read (base 16), a -// semicolon, followed by the data in the binary-escaped-data encoding. - - -//---------------------------------------------------------------------- -// vFile:pwrite: -// -// BRIEF -// Write data to a previously opened file descriptor. -// -// EXAMPLE -// -// receive: vFile:pwrite:8,0,\cf\fa\ed\fe\0c\00\00 -// send: F1024 -// -// request packet has the fields: -// 1. file descriptor, base 16 -// 2. offset into file to start from, base 16 -// 3. binary-escaped-data to be written -// -// Response is F, followed by the number of bytes written (base 16) - - - - - -Finally, the platform must be able to launch processes so that debugserver -can attach to them. To do this, the following packets should be handled: - -QSetDisableASLR -QSetDetachOnError -QSetSTDOUT -QSetSTDERR -QSetSTDIN -QEnvironment -QEnvironmentHexEncoded -A -qLaunchSuccess -qProcessInfo - -Most of these are documented in the standard gdb-remote protocol -and/or the lldb-gdb-remote.txt documentation. diff --git a/lldb/docs/resources/lldbgdbremote.md b/lldb/docs/resources/lldbgdbremote.md new file mode 100644 index 0000000000000000000000000000000000000000..05e4f714f7f704f732f3be0cf1d8e5eca1c92808 --- /dev/null +++ b/lldb/docs/resources/lldbgdbremote.md @@ -0,0 +1,2666 @@ +# GDB Remote Protocol Extensions + +LLDB has added new GDB server packets to better support multi-threaded and +remote debugging. + +Why? Normally you need to start the correct GDB and the +correct GDB server when debugging. If you have mismatch, then things go wrong +very quickly. LLDB makes extensive use of the GDB remote protocol and we +wanted to make sure that the experience was a bit more dynamic where we can +discover information about a remote target without having to know anything up +front. + +We also ran into performance issues with the existing GDB remote +protocol that can be overcome when using a reliable communications layer. + +Some packets improve performance, others allow for remote process launching +(if you have an OS), and others allow us to dynamically figure out what +registers a thread might have. Again with GDB, both sides pre-agree on how the +registers will look (how many, their register number,name and offsets). + +We prefer to be able to dynamically determine what kind of architecture, OS and +vendor we are debugging, as well as how things are laid out when it comes to +the thread register contexts. + +Below are the details on the new packets we have added above and beyond the +standard GDB remote protocol packets. + +## QStartNoAckMode + +### Brief + +Try to enable no ACK mode to skip sending ACKs and NACKs. + +### Priority To Implement + +High. Any GDB remote server that can implement this should if the +connection is reliable. This improves packet throughput and increases +the performance of the connection. + +### Description + +Having to send an ACK/NACK after every packet slows things down a bit, so we +have a way to disable ACK packets to minimize the traffic for reliable +communication interfaces (like sockets). Below GDB or LLDB will send this +packet to try and disable ACKs. All lines that start with "send packet: " are +from GDB/LLDB, and all lines that start with "read packet: " are from the GDB +remote server: +``` +send packet: $QStartNoAckMode#b0 +read packet: + +read packet: $OK#9a +send packet: + +``` + +## QSupported + +### Brief + +Query the GDB remote server for features it supports + +### Priority To Implement + +Optional. + +### Description + +QSupported is a standard GDB Remote Serial Protocol packet, but +there are several additions to the response that lldb can parse. +They are not all listed here. + +An example exchange: +``` +send packet: qSupported:xmlRegisters=i386,arm,mips,arc;multiprocess+;fork-events+;vfork-events+ + +read packet: qXfer:features:read+;PacketSize=20000;qEcho+;native-signals+;SupportedCompressions=lzfse,zlib-deflate,lz4,lzma;SupportedWatchpointTypes=aarch64-mask,aarch64-bas; +``` + +In the example above, three lldb extensions are shown: + + * `PacketSize=20000` + * The base 16 maximum packet size that the stub can handle. + * `SupportedCompressions=` + * A list of compression types that the stub can use to compress packets + when the QEnableCompression packet is used to request one of them. + * `SupportedWatchpointTypes=` + * A list of watchpoint types that this stub can manage. Currently defined + names are: + * `x86_64` - 64-bit x86-64 watchpoints (1, 2, 4, 8 byte watchpoints + aligned to those amounts) + * `aarch64-bas` AArch64 Byte Address Select watchpoints + (any number of contiguous bytes within a doubleword) + * `aarch64-mask` AArch64 MASK watchpoints + (any power-of-2 region of memory from 8 to 2GB, aligned) + + If nothing is specified, lldb will default to sending power-of-2 + watchpoints, up to a pointer size, `sizeof(void*)`, a reasonable + baseline assumption. + + +## "A" - launch args packet + +### Brief + +Launch a program using the supplied arguments + +### Priority To Implement + +Low. Only needed if the remote target wants to launch a target after +making a connection to a GDB server that isn't already connected to +an inferior process. + +### Description + +We have added support for the "set program arguments" packet where we can +start a connection to a remote server and then later supply the path to the +executable and the arguments to use when executing: + +GDB remote docs for this: +``` +set program arguments(reserved) Aarglen,argnum,arg,... +``` +Where A is followed by the length in bytes of the hex encoded argument, +followed by an argument integer, and followed by the ASCII characters +converted into hex bytes for each arg: +``` +send packet: $A98,0,2f566f6c756d65732f776f726b2f67636c6179746f6e2f446f63756d656e74732f7372632f6174746163682f612e6f7574#00 +read packet: $OK#00 +``` +The above packet helps when you have remote debugging abilities where you +could launch a process on a remote host, this isn't needed for bare board +debugging. + +## qLaunchSuccess + +### Brief + +Check whether launching a process with the `A` packet succeeded. + +### Description + +Returns the status of the last attempt to launch a process. +Either `OK` if no error ocurred, or `E` followed by a string +describing the error. + +### Priority To Implement + +High, launching processes is a key part of LLDB's platform mode. + +## QEnvironment:NAME=VALUE + +### Brief + +Setup the environment up for a new child process that will soon be +launched using the "A" packet. + +NB: key/value pairs are sent as-is so gdb-remote protocol meta characters +(e.g. `#` or `$`) are not acceptable. If any non-printable or +metacharacters are present in the strings, `QEnvironmentHexEncoded` +should be used instead if it is available. If you don't want to +scan the environment strings before sending, prefer +the `QEnvironmentHexEncoded` packet over `QEnvironment`, if it is +available. + +### Priority To Implement + +Low. Only needed if the remote target wants to launch a target after +making a connection to a GDB server that isn't already connected to +an inferior process. + +### Description + +Both GDB and LLDB support passing down environment variables. Is it ok to +respond with a `$#00` (unimplemented): +``` +send packet: $QEnvironment:ACK_COLOR_FILENAME=bold yellow#00 +read packet: $OK#00 +``` +This packet can be sent one or more times _prior_ to sending a "A" packet. + +## QEnvironmentHexEncoded:HEX-ENCODING(NAME=VALUE) + +### Brief + +Setup the environment up for a new child process that will soon be +launched using the "A" packet. + +The only difference between this packet and `QEnvironment` is that the +environment key-value pair is ascii hex encoded for transmission. +This allows values with gdb-remote metacharacters like `#` to be sent. + +### Priority To Implement + +Low. Only needed if the remote target wants to launch a target after +making a connection to a GDB server that isn't already connected to +an inferior process. + +### Description + +Both GDB and LLDB support passing down environment variables. Is it ok to +respond with a `$#00` (unimplemented): +``` +send packet: $QEnvironment:41434b5f434f4c4f525f46494c454e414d453d626f6c642379656c6c6f77#00 +read packet: $OK#00 +``` +This packet can be sent one or more times _prior_ to sending a "A" packet. + +## QEnableErrorStrings + +### Brief + +This packet enables reporting of Error strings in remote packet +replies from the server to client. If the server supports this +feature, it should send an OK response. The client can expect the +following error replies if this feature is enabled in the server: +``` +EXX;AAAAAAAAA +``` +where `AAAAAAAAA` will be a hex encoded ASCII string. +`XX`` is hex encoded byte number. + +It must be noted that even if the client has enabled reporting +strings in error replies, it must not expect error strings to all +error replies. + +### Priority To Implement + +Low. Only needed if the remote target wants to provide strings that +are human readable along with an error code. + +### Example + +``` +send packet: $QEnableErrorStrings +read packet: $OK#00 +``` + +## QSetSTDIN:\ / QSetSTDOUT:\ / QSetSTDERR:\ + +### Brief + +Setup where STDIN, STDOUT, and STDERR go prior to sending an "A" +packet. + +### Priority To Implement + +Low. Only needed if the remote target wants to launch a target after +making a connection to a GDB server that isn't already connected to +an inferior process. + +### Description + +When launching a program through the GDB remote protocol with the "A" packet, +you might also want to specify where stdin/out/err go: +``` +QSetSTDIN: +QSetSTDOUT: +QSetSTDERR: +``` +These packets must be sent _prior_ to sending a "A" packet. + +## QSetWorkingDir:\ + +### Brief + +Set the working directory prior to sending an "A" packet. + +### Priority To Implement + +Low. Only needed if the remote target wants to launch a target after +making a connection to a GDB server that isn't already connected to +an inferior process. + +### Description + +Or specify the working directory: +``` +QSetWorkingDir: +``` +This packet must be sent _prior_ to sending a "A" packet. + +## qGetWorkingDir + +### Brief + +Get the current working directory of the platform stub in +ASCII hex encoding. + +### Example + +``` +receive: qGetWorkingDir +send: 2f4170706c65496e7465726e616c2f6c6c64622f73657474696e67732f342f5465737453657474696e67732e746573745f646973617373656d626c65725f73657474696e6773 +``` + +## QSetDisableASLR:\ + +### Brief + +Enable or disable ASLR on the next "A" packet. + +### Priority To Implement + +Low. Only needed if the remote target wants to launch a target after +making a connection to a GDB server that isn't already connected to +an inferior process and if the target supports disabling ASLR +(Address space layout randomization). + +### Description + +Or control if ASLR is enabled/disabled: +``` +send packet: QSetDisableASLR:1 +read packet: OK + +send packet: QSetDisableASLR:0 +read packet: OK +``` +This packet must be sent _prior_ to sending a "A" packet. + +## QListThreadsInStopReply + +### Brief + +Enable the `threads:` and `thread-pcs:` data in the question-mark packet +("T packet") responses when the stub reports that a program has +stopped executing. + +### Priority To Implement + +Performance. This is a performance benefit to lldb if the thread id's +and thread pc values are provided to lldb in the T stop packet -- if +they are not provided to lldb, lldb will likely need to send one to +two packets per thread to fetch the data at every private stop. + +### Example + +``` +send packet: QListThreadsInStopReply +read packet: OK +``` + +## jLLDBTraceSupported + +### Brief + +Get the processor tracing type supported by the gdb-server for the current +inferior. Responses might be different depending on the architecture and +capabilities of the underlying OS. + +### Output Schema + +``` + { + "name": , + Tracing technology name, e.g. intel-pt, arm-etm. + "description": , + Description for this technology. + } +``` + +If no tracing technology is supported for the inferior, or no process is +running, then an error message is returned. + +### Note + +This packet is used by Trace plug-ins (see `lldb_private::Trace.h`) to +do live tracing. Specifically, the name of the plug-in should match the name +of the tracing technology returned by this packet. + +### Example + +``` +send packet: jLLDBTraceSupported +read packet: {"name":, "description":}/E;AAAAAAAAA +``` + +## jLLDBTraceStart + +### Brief + +Start tracing a process or its threads using a provided tracing technology. +The input and output are specified as JSON objects. In case of success, an OK +response is returned, or an error otherwise. + +### Process Tracing + +This traces existing and future threads of the current process. An error is +returned if the process is already being traced. + +### Thread Tracing + +This traces specific threads. + +### Input Schema + +``` +{ + "type": , + Tracing technology name, e.g. intel-pt, arm-etm. + + /* thread tracing only */ + "tids"?: [], + Individual threads to trace. + + ... other parameters specific to the provided tracing type +} +``` + +### Notes + +- If "tids" is not provided, then the operation is "process tracing", + otherwise it's "thread tracing". +- Each tracing technology can have different levels of support for "thread + tracing" and "process tracing". + +### Intel-Pt + +intel-pt supports both "thread tracing" and "process tracing". + +"Process tracing" is implemented in two different ways. If the +"perCpuTracing" option is false, then each thread is traced individually +but managed by the same "process trace" instance. This means that the +amount of trace buffers used is proportional to the number of running +threads. This is the recommended option unless the number of threads is +huge. If "perCpuTracing" is true, then each cpu core is traced invidually +instead of each thread, which uses a fixed number of trace buffers, but +might result in less data available for less frequent threads. See +"perCpuTracing" below for more information. + +Each actual intel pt trace buffer, either from "process tracing" or "thread +tracing", is stored in an in-memory circular buffer, which keeps the most +recent data. + +Additional params in the input schema: +``` + { + "iptTraceSize": , + Size in bytes used by each individual per-thread or per-cpu trace + buffer. It must be a power of 2 greater than or equal to 4096 (2^12) + bytes. + + "enableTsc": , + Whether to enable TSC timestamps or not. This is supported on + all devices that support intel-pt. A TSC timestamp is generated along + with PSB (synchronization) packets, whose frequency can be configured + with the "psbPeriod" parameter. + + "psbPeriod"?: , + This value defines the period in which PSB packets will be generated. + A PSB packet is a synchronization packet that contains a TSC + timestamp and the current absolute instruction pointer. + + This parameter can only be used if + + /sys/bus/event_source/devices/intel_pt/caps/psb_cyc + + is 1. Otherwise, the PSB period will be defined by the processor. + + If supported, valid values for this period can be found in + + /sys/bus/event_source/devices/intel_pt/caps/psb_periods + + which contains a hexadecimal number, whose bits represent valid + values e.g. if bit 2 is set, then value 2 is valid. + + The psb_period value is converted to the approximate number of + raw trace bytes between PSB packets as: + + 2 ^ (value + 11) + + e.g. value 3 means 16KiB between PSB packets. Defaults to + 0 if supported. + + /* process tracing only */ + "perCpuTracing": + Instead of having an individual trace buffer per thread, this option + triggers the collection on a per cpu core basis. This effectively + traces the entire activity on all cores. At decoding time, in order + to correctly associate a decoded instruction with a thread, the + context switch trace of each core is needed, as well as a record per + cpu indicating which thread was running on each core when tracing + started. These secondary traces are correlated with the intel-pt + trace by comparing TSC timestamps. + + This option forces the capture of TSC timestamps (see "enableTsc"). + + Note: This option can't be used simulatenously with any other trace + sessions because of its system-wide nature. + + /* process tracing only */ + "processBufferSizeLimit": , + Maximum total buffer size per process in bytes. + This limit applies to the sum of the sizes of all thread or cpu core + buffers for the current process, excluding the ones started with + "thread tracing". + + If "perCpuTracing" is false, whenever a thread is attempted to be + traced due to "process tracing" and the limit would be reached, the + process is stopped with a "tracing" reason along with a meaningful + description, so that the user can retrace the process if needed. + + If "perCpuTracing" is true, then starting the system-wide trace + session fails if all the individual per-cpu trace buffers require + in total more memory that the limit impossed by this parameter. + } +``` + +Notes: + - Modifying the parameters of an existing trace is not supported. The user + needs to stop the trace and start a new one. + - If "process tracing" is attempted and there are individual threads + already being traced with "thread tracing", these traces are left + unaffected and the threads not traced twice. + - If "thread tracing" is attempted on a thread already being traced with + either "thread tracing" or "process tracing", it fails. + +### Examples + +Process tracing: +``` +send packet: jLLDBTraceStart:{"type":,...other params}] +read packet: OK/E;AAAAAAAAA +``` + +Thread tracing: +``` +send packet: jLLDBTraceStart:{"type":,"tids":,...other params}] +read packet: OK/E;AAAAAAAAA +``` + +## jLLDBTraceStop + +### Brief + +Stop tracing a process or its threads using a provided tracing technology. +The input and output are specified as JSON objects. In case of success, an OK +response is returned, or an error otherwise. + +### Process Trace Stopping + +Stopping a process trace stops the active traces initiated with +"thread tracing". + +### Thread Trace Stopping + +This is a best effort request, which tries to stop as many traces as +possible. + +### Input Schema + +The schema for the input is +``` +{ + "type": + Tracing technology name, e.g. intel-pt, arm-etm. + + /* thread trace stopping only */ + "tids": [] + Individual thread traces to stop. +} +``` + +### Notes + +- If "tids" is not provided, then the operation is "process trace stopping". + +### Intel Pt + +Stopping a specific thread trace started with "process tracing" is allowed. + +### Examples + +Process trace stopping: +``` +send packet: jLLDBTraceStop:{"type":}] +read packet: OK/E;AAAAAAAAA +``` +Thread trace stopping: +``` +send packet: jLLDBTraceStop:{"type":,"tids":}] +read packet: OK/E;AAAAAAAAA +``` + +## jLLDBTraceGetState + +### Brief + +Get the current state of the process and its threads being traced by +a given trace technology. The response is a JSON object with custom +information depending on the trace technology. In case of errors, an +error message is returned. + +### Input Schema + +``` +{ + "type": + Tracing technology name, e.g. intel-pt, arm-etm. +} +``` + +### Output Schema + +``` +{ + "tracedThreads": [{ + "tid": , + "binaryData": [ + { + "kind": , + Identifier for some binary data related to this thread to + fetch with the jLLDBTraceGetBinaryData packet. + "size": , + Size in bytes of this thread data. + }, + ] + }], + "processBinaryData": [ + { + "kind": , + Identifier for some binary data related to this process to + fetch with the jLLDBTraceGetBinaryData packet. + "size": , + Size in bytes of this thread data. + }, + ], + "cpus"?: [ + "id": , + Identifier for this CPU logical core. + "binaryData": [ + { + "kind": , + Identifier for some binary data related to this thread to + fetch with the jLLDBTraceGetBinaryData packet. + "size": , + Size in bytes of this cpu core data. + }, + ] + ], + "warnings"?: [], + Non-fatal messages useful for troubleshooting. + + ... other attributes specific to the given tracing technology +} +``` + +### Notes + + - "traceThreads" includes all thread traced by both "process tracing" and + "thread tracing". + +### Intel Pt + +If per-cpu process tracing is enabled, "tracedThreads" will contain all +the threads of the process without any trace buffers. Besides that, the +"cpus" field will also be returned with per cpu core trace buffers. +A side effect of per-cpu tracing is that all the threads of unrelated +processes will also be traced, thus polluting the tracing data. + +Binary data kinds: + - iptTrace: trace buffer for a thread or a cpu. + - perfContextSwitchTrace: context switch trace for a cpu generated by + perf_event_open. + - procfsCpuInfo: contents of the /proc/cpuinfo file. + +Additional attributes: + * tscPerfZeroConversion + * This field allows converting Intel processor's TSC values to nanoseconds. + It is available through the Linux perf_event API when cap_user_time and cap_user_time_zero + are set. + See the documentation of time_zero in + https://man7.org/linux/man-pages/man2/perf_event_open.2.html for more information about + the calculation and the meaning of the values in the schema below. + + Schema for this field: + ``` + "tscPerfZeroConversion": { + "timeMult": , + "timeShift": , + "timeZero": , + } + ``` + +### Example + +``` +send packet: jLLDBTraceGetState:{"type":}] +read packet: {...object}/E;AAAAAAAAA +``` + +## jLLDBTraceGetBinaryData + +### Brief + +Get binary data given a trace technology and a data identifier. +The input is specified as a JSON object and the response has the same format +as the "binary memory read" (aka "x") packet. In case of failures, an error +message is returned. + +### Schema + +The schema for the input is: +``` +{ + "type": , + Tracing technology name, e.g. intel-pt, arm-etm. + "kind": , + Identifier for the data. + "cpuId": , + Core id in decimal if the data belongs to a CPU core. + "tid"?: , + Tid in decimal if the data belongs to a thread. +} +``` + +### Example + +``` +send packet: jLLDBTraceGetBinaryData:{"type":,"kind":,"tid":,"offset":,"size":}] +read packet: /E;AAAAAAAAA +``` + +## qRegisterInfo\ + +### Brief + +Discover register information from the remote GDB server. + +### Priority To Implement + +High. Any target that can self describe its registers, should do so. +This means if new registers are ever added to a remote target, they +will get picked up automatically, and allows registers to change +depending on the actual CPU type that is used. + +NB: `qRegisterInfo` is deprecated in favor of the standard gdb remote +serial protocol register description method, +`qXfer:features:read:target.xml`. +If `qXfer:features:read:target.xml` is supported, `qRegisterInfo` does +not need to be implemented. The target.xml format is used by most +gdb RSP stubs whereas `qRegisterInfo` was an lldb-only design. +`qRegisterInfo` requires one packet per register and can have undesirable +performance costs at the start of a debug session, whereas target.xml +may be able to describe all registers in a single packet. + +### Description + +With LLDB, for register information, remote GDB servers can add +support for the "qRegisterInfoN" packet where "N" is a zero based +base 16 register number that must start at zero and increase by one +for each register that is supported. The response is done in typical +GDB remote fashion where a series of "KEY:VALUE;" pairs are returned. +An example for the x86_64 registers is included below: +``` +send packet: $qRegisterInfo0#00 +read packet: $name:rax;bitsize:64;offset:0;encoding:uint;format:hex;set:General Purpose Registers;gcc:0;dwarf:0;#00 +send packet: $qRegisterInfo1#00 +read packet: $name:rbx;bitsize:64;offset:8;encoding:uint;format:hex;set:General Purpose Registers;gcc:3;dwarf:3;#00 +send packet: $qRegisterInfo2#00 +read packet: $name:rcx;bitsize:64;offset:16;encoding:uint;format:hex;set:General Purpose Registers;gcc:2;dwarf:2;#00 +send packet: $qRegisterInfo3#00 +read packet: $name:rdx;bitsize:64;offset:24;encoding:uint;format:hex;set:General Purpose Registers;gcc:1;dwarf:1;#00 +send packet: $qRegisterInfo4#00 +read packet: $name:rdi;bitsize:64;offset:32;encoding:uint;format:hex;set:General Purpose Registers;gcc:5;dwarf:5;#00 +send packet: $qRegisterInfo5#00 +read packet: $name:rsi;bitsize:64;offset:40;encoding:uint;format:hex;set:General Purpose Registers;gcc:4;dwarf:4;#00 +send packet: $qRegisterInfo6#00 +read packet: $name:rbp;alt-name:fp;bitsize:64;offset:48;encoding:uint;format:hex;set:General Purpose Registers;gcc:6;dwarf:6;generic:fp;#00 +send packet: $qRegisterInfo7#00 +read packet: $name:rsp;alt-name:sp;bitsize:64;offset:56;encoding:uint;format:hex;set:General Purpose Registers;gcc:7;dwarf:7;generic:sp;#00 +send packet: $qRegisterInfo8#00 +read packet: $name:r8;bitsize:64;offset:64;encoding:uint;format:hex;set:General Purpose Registers;gcc:8;dwarf:8;#00 +send packet: $qRegisterInfo9#00 +read packet: $name:r9;bitsize:64;offset:72;encoding:uint;format:hex;set:General Purpose Registers;gcc:9;dwarf:9;#00 +send packet: $qRegisterInfoa#00 +read packet: $name:r10;bitsize:64;offset:80;encoding:uint;format:hex;set:General Purpose Registers;gcc:10;dwarf:10;#00 +send packet: $qRegisterInfob#00 +read packet: $name:r11;bitsize:64;offset:88;encoding:uint;format:hex;set:General Purpose Registers;gcc:11;dwarf:11;#00 +send packet: $qRegisterInfoc#00 +read packet: $name:r12;bitsize:64;offset:96;encoding:uint;format:hex;set:General Purpose Registers;gcc:12;dwarf:12;#00 +send packet: $qRegisterInfod#00 +read packet: $name:r13;bitsize:64;offset:104;encoding:uint;format:hex;set:General Purpose Registers;gcc:13;dwarf:13;#00 +send packet: $qRegisterInfoe#00 +read packet: $name:r14;bitsize:64;offset:112;encoding:uint;format:hex;set:General Purpose Registers;gcc:14;dwarf:14;#00 +send packet: $qRegisterInfof#00 +read packet: $name:r15;bitsize:64;offset:120;encoding:uint;format:hex;set:General Purpose Registers;gcc:15;dwarf:15;#00 +send packet: $qRegisterInfo10#00 +read packet: $name:rip;alt-name:pc;bitsize:64;offset:128;encoding:uint;format:hex;set:General Purpose Registers;gcc:16;dwarf:16;generic:pc;#00 +send packet: $qRegisterInfo11#00 +read packet: $name:rflags;alt-name:flags;bitsize:64;offset:136;encoding:uint;format:hex;set:General Purpose Registers;#00 +send packet: $qRegisterInfo12#00 +read packet: $name:cs;bitsize:64;offset:144;encoding:uint;format:hex;set:General Purpose Registers;#00 +send packet: $qRegisterInfo13#00 +read packet: $name:fs;bitsize:64;offset:152;encoding:uint;format:hex;set:General Purpose Registers;#00 +send packet: $qRegisterInfo14#00 +read packet: $name:gs;bitsize:64;offset:160;encoding:uint;format:hex;set:General Purpose Registers;#00 +send packet: $qRegisterInfo15#00 +read packet: $name:fctrl;bitsize:16;offset:176;encoding:uint;format:hex;set:Floating Point Registers;#00 +send packet: $qRegisterInfo16#00 +read packet: $name:fstat;bitsize:16;offset:178;encoding:uint;format:hex;set:Floating Point Registers;#00 +send packet: $qRegisterInfo17#00 +read packet: $name:ftag;bitsize:8;offset:180;encoding:uint;format:hex;set:Floating Point Registers;#00 +send packet: $qRegisterInfo18#00 +read packet: $name:fop;bitsize:16;offset:182;encoding:uint;format:hex;set:Floating Point Registers;#00 +send packet: $qRegisterInfo19#00 +read packet: $name:fioff;bitsize:32;offset:184;encoding:uint;format:hex;set:Floating Point Registers;#00 +send packet: $qRegisterInfo1a#00 +read packet: $name:fiseg;bitsize:16;offset:188;encoding:uint;format:hex;set:Floating Point Registers;#00 +send packet: $qRegisterInfo1b#00 +read packet: $name:fooff;bitsize:32;offset:192;encoding:uint;format:hex;set:Floating Point Registers;#00 +send packet: $qRegisterInfo1c#00 +read packet: $name:foseg;bitsize:16;offset:196;encoding:uint;format:hex;set:Floating Point Registers;#00 +send packet: $qRegisterInfo1d#00 +read packet: $name:mxcsr;bitsize:32;offset:200;encoding:uint;format:hex;set:Floating Point Registers;#00 +send packet: $qRegisterInfo1e#00 +read packet: $name:mxcsrmask;bitsize:32;offset:204;encoding:uint;format:hex;set:Floating Point Registers;#00 +send packet: $qRegisterInfo1f#00 +read packet: $name:stmm0;bitsize:80;offset:208;encoding:vector;format:vector-uint8;set:Floating Point Registers;gcc:33;dwarf:33;#00 +send packet: $qRegisterInfo20#00 +read packet: $name:stmm1;bitsize:80;offset:224;encoding:vector;format:vector-uint8;set:Floating Point Registers;gcc:34;dwarf:34;#00 +send packet: $qRegisterInfo21#00 +read packet: $name:stmm2;bitsize:80;offset:240;encoding:vector;format:vector-uint8;set:Floating Point Registers;gcc:35;dwarf:35;#00 +send packet: $qRegisterInfo22#00 +read packet: $name:stmm3;bitsize:80;offset:256;encoding:vector;format:vector-uint8;set:Floating Point Registers;gcc:36;dwarf:36;#00 +send packet: $qRegisterInfo23#00 +read packet: $name:stmm4;bitsize:80;offset:272;encoding:vector;format:vector-uint8;set:Floating Point Registers;gcc:37;dwarf:37;#00 +send packet: $qRegisterInfo24#00 +read packet: $name:stmm5;bitsize:80;offset:288;encoding:vector;format:vector-uint8;set:Floating Point Registers;gcc:38;dwarf:38;#00 +send packet: $qRegisterInfo25#00 +read packet: $name:stmm6;bitsize:80;offset:304;encoding:vector;format:vector-uint8;set:Floating Point Registers;gcc:39;dwarf:39;#00 +send packet: $qRegisterInfo26#00 +read packet: $name:stmm7;bitsize:80;offset:320;encoding:vector;format:vector-uint8;set:Floating Point Registers;gcc:40;dwarf:40;#00 +send packet: $qRegisterInfo27#00 +read packet: $name:xmm0;bitsize:128;offset:336;encoding:vector;format:vector-uint8;set:Floating Point Registers;gcc:17;dwarf:17;#00 +send packet: $qRegisterInfo28#00 +read packet: $name:xmm1;bitsize:128;offset:352;encoding:vector;format:vector-uint8;set:Floating Point Registers;gcc:18;dwarf:18;#00 +send packet: $qRegisterInfo29#00 +read packet: $name:xmm2;bitsize:128;offset:368;encoding:vector;format:vector-uint8;set:Floating Point Registers;gcc:19;dwarf:19;#00 +send packet: $qRegisterInfo2a#00 +read packet: $name:xmm3;bitsize:128;offset:384;encoding:vector;format:vector-uint8;set:Floating Point Registers;gcc:20;dwarf:20;#00 +send packet: $qRegisterInfo2b#00 +read packet: $name:xmm4;bitsize:128;offset:400;encoding:vector;format:vector-uint8;set:Floating Point Registers;gcc:21;dwarf:21;#00 +send packet: $qRegisterInfo2c#00 +read packet: $name:xmm5;bitsize:128;offset:416;encoding:vector;format:vector-uint8;set:Floating Point Registers;gcc:22;dwarf:22;#00 +send packet: $qRegisterInfo2d#00 +read packet: $name:xmm6;bitsize:128;offset:432;encoding:vector;format:vector-uint8;set:Floating Point Registers;gcc:23;dwarf:23;#00 +send packet: $qRegisterInfo2e#00 +read packet: $name:xmm7;bitsize:128;offset:448;encoding:vector;format:vector-uint8;set:Floating Point Registers;gcc:24;dwarf:24;#00 +send packet: $qRegisterInfo2f#00 +read packet: $name:xmm8;bitsize:128;offset:464;encoding:vector;format:vector-uint8;set:Floating Point Registers;gcc:25;dwarf:25;#00 +send packet: $qRegisterInfo30#00 +read packet: $name:xmm9;bitsize:128;offset:480;encoding:vector;format:vector-uint8;set:Floating Point Registers;gcc:26;dwarf:26;#00 +send packet: $qRegisterInfo31#00 +read packet: $name:xmm10;bitsize:128;offset:496;encoding:vector;format:vector-uint8;set:Floating Point Registers;gcc:27;dwarf:27;#00 +send packet: $qRegisterInfo32#00 +read packet: $name:xmm11;bitsize:128;offset:512;encoding:vector;format:vector-uint8;set:Floating Point Registers;gcc:28;dwarf:28;#00 +send packet: $qRegisterInfo33#00 +read packet: $name:xmm12;bitsize:128;offset:528;encoding:vector;format:vector-uint8;set:Floating Point Registers;gcc:29;dwarf:29;#00 +send packet: $qRegisterInfo34#00 +read packet: $name:xmm13;bitsize:128;offset:544;encoding:vector;format:vector-uint8;set:Floating Point Registers;gcc:30;dwarf:30;#00 +send packet: $qRegisterInfo35#00 +read packet: $name:xmm14;bitsize:128;offset:560;encoding:vector;format:vector-uint8;set:Floating Point Registers;gcc:31;dwarf:31;#00 +send packet: $qRegisterInfo36#00 +read packet: $name:xmm15;bitsize:128;offset:576;encoding:vector;format:vector-uint8;set:Floating Point Registers;gcc:32;dwarf:32;#00 +send packet: $qRegisterInfo37#00 +read packet: $name:trapno;bitsize:32;offset:696;encoding:uint;format:hex;set:Exception State Registers;#00 +send packet: $qRegisterInfo38#00 +read packet: $name:err;bitsize:32;offset:700;encoding:uint;format:hex;set:Exception State Registers;#00 +send packet: $qRegisterInfo39#00 +read packet: $name:faultvaddr;bitsize:64;offset:704;encoding:uint;format:hex;set:Exception State Registers;#00 +send packet: $qRegisterInfo3a#00 +read packet: $E45#00 +``` + +As we see above we keep making subsequent calls to the remote server to +discover all registers by increasing the number appended to `qRegisterInfo` and +we get a response back that is a series of `key=value;` strings. + +The `offset:` fields should not leave a gap anywhere in the g/G packet -- the +register values should be appended one after another. For instance, if the +register context for a thread looks like: +``` +struct rctx { + uint32_t gpr1; // offset 0 + uint32_t gpr2; // offset 4 + uint32_t gpr3; // offset 8 + uint64_t fp1; // offset 16 +}; +``` + +You may end up with a 4-byte gap between gpr3 and fp1 on architectures +that align values like this. The correct offset: value for fp1 is 12 - +in the g/G packet fp1 will immediately follow gpr3, even though the +in-memory thread structure has an empty 4 bytes for alignment between +these two registers. + +The keys and values are detailed below: + +* `name` - + The primary register name as a string ("rbp" for example) +* `alt-name` - + An alternate name for a register as a string ("fp" for example + for the above "rbp") +* `bitsize` - Size in bits of a register (32, 64, etc). Base 10. +* `offset` - + The offset within the "g" and "G" packet of the register data for + this register. This is the byte offset once the data has been + transformed into binary, not the character offset into the g/G + packet. Base 10. +* `encoding` - + The encoding type of the register which must be one of: + * `uint` (unsigned integer) + * `sint` (signed integer) + * `ieee754` (IEEE 754 float) + * `vector` (vector register) +* format - + The preferred format for display of this register. The value must be one of: + * `binary` + * `decimal` + * `hex` + * `float` + * `vector-sint8` + * `vector-uint8` + * `vector-sint16` + * `vector-uint16` + * `vector-sint32` + * `vector-uint32` + * `vector-float32` + * `vector-uint128` +* `set`- + The register set name as a string that this register belongs to. +* `gcc` - + The GCC compiler registers number for this register (used for + EH frame and other compiler information that is encoded in the + executable files). The supplied number will be decoded like a + string passed to strtoul() with a base of zero, so the number + can be decimal, or hex if it is prefixed with "0x". + + **Note:** If the compiler doesn't have a register number for this + register, this key/value pair should be omitted. +* `dwarf` - + The DWARF register number for this register that is used for this + register in the debug information. The supplied number will be decoded + like a string passed to strtoul() with a base of zero, so the number + can be decimal, or hex if it is prefixed with "0x". + + **Note:** If the compiler doesn't have a register number for this + register, this key/value pair should be omitted. +* `generic` - + If the register is a generic register that most CPUs have, classify + it correctly so the debugger knows. Valid values are one of: + * `pc` (a program counter register. for example `name=eip;` (i386), + `name=rip;` (x86_64), `name=r15;` (32 bit arm) would + include a `generic=pc;` key value pair) + * `sp` (a stack pointer register. for example `name=esp;` (i386), + `name=rsp;` (x86_64), `name=r13;` (32 bit arm) would + include a `generic=sp;` key value pair) + * `fp` (a frame pointer register. for example `name=ebp;` (i386), + `name=rbp;` (x86_64), `name=r7;` (32 bit arm with macosx + ABI) would include a `generic=fp;` key value pair) + * `ra` (a return address register. for example `name=lr;` (32 bit ARM) + would include a `generic=ra;` key value pair) + * `flags` (a CPU flags register. for example `name=eflags;` (i386), + `name=rflags;` (x86_64), `name=cpsr;` (32 bit ARM) + would include a `generic=flags;` key value pair) + * `arg1` - `arg8` (specified for registers that contain function + arguments when the argument fits into a register) +* `container-regs` - + The value for this key is a comma separated list of raw hex (optional + leading "0x") register numbers. + + This specifies that this register is contained in other concrete + register values. For example "eax" is in the lower 32 bits of the + "rax" register value for x86_64, so "eax" could specify that it is + contained in "rax" by specifying the register number for "rax" (whose + register number is 0x00): + ``` + container-regs:00; + ``` + If a register is comprised of one or more registers, like "d0" is ARM + which is a 64 bit register, it might be made up of "s0" and "s1". If + the register number for "s0" is 0x20, and the register number of "s1" + is "0x21", the "container-regs" key/value pair would be: + ``` + container-regs:20,21; + ``` + This is handy for defining what GDB used to call "pseudo" registers. + These registers are never requested by LLDB via the register read + or write packets, the container registers will be requested on behalf + of this register. +* `invalidate-regs` - + The value for this key is a comma separated list of raw hex (optional + leading "0x") register numbers. + + This specifies which register values should be invalidated when this + register is modified. For example if modifying "eax" would cause "rax", + "eax", "ax", "ah", and "al" to be modified where rax is 0x0, eax is 0x15, + ax is 0x25, ah is 0x35, and al is 0x39, the "invalidate-regs" key/value + pair would be: + ``` + invalidate-regs:0,15,25,35,39; + ``` + If there is a single register that gets invalidated, then omit the comma + and just list a single register: + ``` + invalidate-regs:0; + ``` + This is handy when modifying a specific register can cause other + register values to change. For example, when debugging an ARM target, + modifying the CPSR register can cause the r8 - r14 and cpsr value to + change depending on if the mode has changed. + + +## qPlatform_shell + +### Brief + +Run a command in a shell on the connected remote machine. + +### Priority To Implement + +High. This command allows LLDB clients to run arbitrary shell +commands on a remote host. + +### Description + +The request consists of the command to be executed encoded in ASCII characters +converted into hex bytes. + +The response to this packet consists of the letter F followed by the return code, +followed by the signal number (or 0 if no signal was delivered), and escaped bytes +of captured program output. + +Below is an example communication from a client sending an "ls -la" command: +``` +send packet: $qPlatform_shell:6c73202d6c61,00000002#ec +read packet: $F,00000000,00000000,total 4736 +drwxrwxr-x 16 username groupname 4096 Aug 15 21:36 . +drwxr-xr-x 17 username groupname 4096 Aug 10 16:39 .. +-rw-rw-r-- 1 username groupname 73875 Aug 12 16:46 notes.txt +drwxrwxr-x 5 username groupname 4096 Aug 15 21:36 source.cpp +-rw-r--r-- 1 username groupname 2792 Aug 12 16:46 a.out +-rw-r--r-- 1 username groupname 3190 Aug 12 16:46 Makefile +``` + +## qPlatform_mkdir + +### Brief + +Creates a new directory on the connected remote machine. + +### Priority To Implement + +Low. This command allows LLDB clients to create new directories on +a remote host. + +### Description + +Request: `qPlatform_mkdir:,` + +The request packet has the fields: + 1. mode bits in base 16 + 2. file path in ascii-hex encoding + +Reply: + * `F` + (mkdir called successfully and returned with the given return code) + * `Exx` (An error occurred) + + +## vFile:chmod / qPlatform_chmod + +### Brief + +Change the permissions of a file on the connected remote machine. + +### Priority To Implement + +Low. This command allows LLDB clients to change the permissions of +a file on the remote host. + +### Description + +Request: `qPlatform_chmod:,` + +Reply: +* `F` + (chmod called successfully and returned with the given return code) +* `Exx` (An error occurred) + +## qHostInfo + +### Brief + +Get information about the host we are remotely connected to. + +### Priority To Implement + +High. This packet is usually very easy to implement and can help +LLDB select the correct plug-ins for the job based on the target +triple information that is supplied. + +### Description + +LLDB supports a host info call that gets all sorts of details of the system +that is being debugged: +``` +send packet: $qHostInfo#00 +read packet: $cputype:16777223;cpusubtype:3;ostype:darwin;vendor:apple;endian:little;ptrsize:8;#00 +``` + +Key value pairs are one of: +* `cputype`: is a number that is the mach-o CPU type that is being debugged (base 10) +* `cpusubtype`: is a number that is the mach-o CPU subtype type that is being debugged (base 10) +* `triple`: a string for the target triple (x86_64-apple-macosx) that can be used to specify arch + vendor + os in one entry +* `vendor`: a string for the vendor (apple), not needed if "triple" is specified +* `ostype`: a string for the OS being debugged (macosx, linux, freebsd, ios, watchos), not needed if "triple" is specified +* `endian`: is one of "little", "big", or "pdp" +* `ptrsize`: an unsigned number that represents how big pointers are in bytes on the debug target +* `hostname`: the hostname of the host that is running the GDB server if available +* `os_build`: a string for the OS build for the remote host as a string value +* `os_kernel`: a string describing the kernel version +* `os_version`: a version string that represents the current OS version (10.8.2) +* `watchpoint_exceptions_received`: one of "before" or "after" to specify if a watchpoint is triggered before or after the pc when it stops +* `default_packet_timeout`: an unsigned number that specifies the default timeout in seconds +* `distribution_id`: optional. For linux, specifies distribution id (e.g. ubuntu, fedora, etc.) +* `osmajor`: optional, specifies the major version number of the OS (e.g. for macOS 10.12.2, it would be 10) +* `osminor`: optional, specifies the minor version number of the OS (e.g. for macOS 10.12.2, it would be 12) +* `ospatch`: optional, specifies the patch level number of the OS (e.g. for macOS 10.12.2, it would be 2) +* `vm-page-size`: optional, specifies the target system VM page size, base 10. + Needed for the "dirty-pages:" list in the qMemoryRegionInfo + packet, where a list of dirty pages is sent from the remote + stub. This page size tells lldb how large each dirty page is. +* `addressing_bits`: optional, specifies how many bits in addresses are + significant for addressing, base 10. If bits 38..0 + in a 64-bit pointer are significant for addressing, + then the value is 39. This is needed on e.g. AArch64 + v8.3 ABIs that use pointer authentication, so lldb + knows which bits to clear/set to get the actual + addresses. +* `low_mem_addressing_bits`: optional, specifies how many bits in + addresses in low memory are significant for addressing, base 10. + AArch64 can have different page table setups for low and high + memory, and therefore a different number of bits used for addressing. +* `high_mem_addressing_bits`: optional, specifies how many bits in + addresses in high memory are significant for addressing, base 10. + AArch64 can have different page table setups for low and high + memory, and therefore a different number of bits used for addressing. + +## qGDBServerVersion + +### Brief + +Get version information about this implementation of the gdb-remote +protocol. + +### Priority To Implement + +High. This packet is usually very easy to implement and can help +LLDB to work around bugs in a server's implementation when they +are found. + +### Description + +The goal of this packet is to provide enough information about an +implementation of the gdb-remote-protocol server that lldb can +work around implementation problems that are discovered after the +version has been released/deployed. The name and version number +should be sufficiently unique that lldb can unambiguously identify +the origin of the program (for instance, debugserver from lldb) and +the version/submission number/patch level of the program - whatever +is appropriate for your server implementation. + +The packet follows the key-value pair model, semicolon separated. +``` +send packet: $qGDBServerVersion#00 +read packet: $name:debugserver;version:310.2;#00 +``` + +Other clients may find other key-value pairs to be useful for identifying +a gdb stub. Patch level, release name, build number may all be keys that +better describe your implementation's version. + +Suggested key names: +* `name`: the name of your remote server - "debugserver" is the lldb standard + implementation +* `version`: identifies the version number of this server +* `patch_level`: the patch level of this server +* `release_name`: the name of this release, if your project uses names +* `build_number`: if you use a build system with increasing build numbers, + this may be the right key name for your server +* `major_version`: major version number +* `minor_version`: minor version number + +## qProcessInfo + +### Brief + +Get information about the process we are currently debugging. + +### Priority To Implement + +Medium. On systems which can launch multiple different architecture processes, +the qHostInfo may not disambiguate sufficiently to know what kind of +process is being debugged. + +For example on a 64-bit x86 Mac system both 32-bit and 64-bit user processes are possible, +and with Mach-O universal files, the executable file may contain both 32- and +64-bit slices so it may be impossible to know until you're attached to a real +process to know what you're working with. + +All numeric fields return base 16 numbers without any "0x" prefix. + +### Description + +An i386 process: +``` +send packet: $qProcessInfo#00 +read packet: $pid:42a8;parent-pid:42bf;real-uid:ecf;real-gid:b;effective-uid:ecf;effective-gid:b;cputype:7;cpusubtype:3;ostype:macosx;vendor:apple;endian:little;ptrsize:4;#00 +``` + +An x86_64 process: +``` +send packet: $qProcessInfo#00 +read packet: $pid:d22c;parent-pid:d34d;real-uid:ecf;real-gid:b;effective-uid:ecf;effective-gid:b;cputype:1000007;cpusubtype:3;ostype:macosx;vendor:apple;endian:little;ptrsize:8;#00 +``` + +Key value pairs include: +* `pid`: the process id +* `parent-pid`: the process of the parent process (often debugserver will become the parent when attaching) +* `real-uid`: the real user id of the process +* `real-gid`: the real group id of the process +* `effective-uid`: the effective user id of the process +* `effective-gid`: the effective group id of the process +* `cputype`: the Mach-O CPU type of the process (base 16) +* `cpusubtype`: the Mach-O CPU subtype of the process (base 16) +* `ostype`: is a string the represents the OS being debugged (darwin, linux, freebsd) +* `vendor`: is a string that represents the vendor (apple) +* `endian`: is one of "little", "big", or "pdp" +* `ptrsize`: is a number that represents how big pointers are in bytes +* `main-binary-uuid`: is the UUID of a firmware type binary that the gdb stub knows about +* `main-binary-address`: is the load address of the firmware type binary +* `main-binary-slide`: is the slide of the firmware type binary, if address isn't known +* `binary-addresses`: A comma-separated list of binary load addresses base 16. + lldb will parse the binaries in memory to get UUIDs, then + try to find the binaries & debug info by UUID. Intended for + use with a small number of firmware type binaries where the + search for binary/debug info may be expensive. + +## qShlibInfoAddr + +### Brief + +Get an address where the dynamic linker stores information about +where shared libraries are loaded. + +### Priority To Implement + +High if you have a dynamic loader plug-in in LLDB for your target +triple (see the "qHostInfo" packet) that can use this information. +Many times address load randomization can make it hard to detect +where the dynamic loader binary and data structures are located and +some platforms know, or can find out where this information is. + +Low if you have a debug target where all object and symbol files +contain static load addresses. + +### Description + +LLDB and GDB both support the `qShlibInfoAddr` packet which is a hint to each +debugger as to where to find the dynamic loader information. For darwin +binaries that run in user land this is the address of the `all_image_infos` +structure in the `/usr/lib/dyld` executable, or the result of a `TASK_DYLD_INFO` +call. The result is returned as big endian hex bytes that are the address +value: +``` +send packet: $qShlibInfoAddr#00 +read packet: $7fff5fc40040#00 +``` + +## qThreadStopInfo\ + +### Brief + +Get information about why a thread, whose ID is ``, is stopped. + +### Priority To Implement + +High if you need to support multi-threaded or multi-core debugging. +Many times one thread will hit a breakpoint and while the debugger +is in the process of suspending the other threads, other threads +will also hit a breakpoint. This packet allows LLDB to know why all +threads (live system debug) / cores (JTAG) in your program have +stopped and allows LLDB to display and control your program +correctly. + +### Description + +LLDB tries to use the `qThreadStopInfo` packet which is formatted as +`qThreadStopInfo%x` where `%x` is the hex thread ID. This requests information +about why a thread is stopped. The response is the same as the stop reply +packets and tells us what happened to the other threads. The standard GDB +remote packets love to think that there is only _one_ reason that _one_ thread +stops at a time. This allows us to see why all threads stopped and allows us +to implement better multi-threaded debugging support. + +## QThreadSuffixSupported + +### Brief + +Try to enable thread suffix support for the `g`, `G`, `p`, and `P` packets. + +### Priority To Implement + +High. Adding a thread suffix allows us to read and write registers +more efficiently and stops us from having to select a thread with +one packet and then read registers with a second packet. It also +makes sure that no errors can occur where the debugger thinks it +already has a thread selected (see the `Hg` packet from the standard +GDB remote protocol documentation) yet the remote GDB server actually +has another thread selected. + +### Description + +When reading thread registers, you currently need to set the current +thread, then read the registers. This is kind of cumbersome, so we added the +ability to query if the remote GDB server supports adding a `thread:;` +suffix to all packets that request information for a thread. To test if the +remote GDB server supports this feature: +``` +send packet: $QThreadSuffixSupported#00 +read packet: OK +``` + +If `OK` is returned, then the `g`, `G`, `p` and `P` packets can accept a +thread suffix. So to send a `g` packet (read all register values): +``` +send packet: $g;thread:;#00 +read packet: .... + +send packet: $G;thread:;#00 +read packet: .... + +send packet: $p1a;thread:;#00 +read packet: .... + +send packet: $P1a=1234abcd;thread:;#00 +read packet: .... +``` + +otherwise, without this you would need to always send two packets: +``` +send packet: $Hg#00 +read packet: .... +send packet: $g#00 +read packet: .... +``` + +We also added support for allocating and deallocating memory. We use this to +allocate memory so we can run JITed code. + +## _M\,\ + +### Brief + +Allocate memory on the remote target with the specified size and +permissions. + +### Priority To Implement + +High if you want LLDB to be able to JIT code and run that code. JIT +code also needs data which is also allocated and tracked. + +Low if you don't support running JIT'ed code. + +### Description + +The allocate memory packet starts with `_M,`. It returns a +raw big endian address value, or an empty response for unimplemented, or `EXX` for an error +code. The packet is formatted as: +``` +char packet[256]; +int packet_len; +packet_len = ::snprintf ( + packet, + sizeof(packet), + "_M%zx,%s%s%s", + (size_t)size, + permissions & lldb::ePermissionsReadable ? "r" : "", + permissions & lldb::ePermissionsWritable ? "w" : "", + permissions & lldb::ePermissionsExecutable ? "x" : ""); +``` + +You request a size and give the permissions. This packet does NOT need to be +implemented if you don't want to support running JITed code. The return value +is just the address of the newly allocated memory as raw big endian hex bytes. + +## _m\ + +### Brief + +Deallocate memory that was previously allocated using an allocate +memory pack. + +### Priority To Implement + +High if you want LLDB to be able to JIT code and run that code. JIT +code also needs data which is also allocated and tracked. + +Low if you don't support running JIT'ed code. + +### Description + +The deallocate memory packet is `_m` where you pass in the address you +got back from a previous call to the allocate memory packet. It returns `OK` +if the memory was successfully deallocated, or `EXX`" for an error, or an +empty response if not supported. + +## qMemoryRegionInfo:\ + +### Brief + +Get information about the address range that contains ``. + +### Priority To Implement + +Medium. This is nice to have, but it isn't necessary. It helps LLDB +do stack unwinding when we branch into memory that isn't executable. +If we can detect that the code we are stopped in isn't executable, +then we can recover registers for stack frames above the current +frame. Otherwise we must assume we are in some JIT'ed code (not JIT +code that LLDB has made) and assume that no registers are available +in higher stack frames. + +### Description + +We added a way to get information for a memory region. The packet is: +``` +qMemoryRegionInfo: +``` + +Where `` is a big endian hex address. The response is returned in a series +of tuples like the data returned in a stop reply packet. The currently valid +tuples to return are: +* `start:;` - `` is a big endian hex address that is + the start address of the range that contains `` +* `size:;` - `` is a big endian hex byte size of the address + of the range that contains `` +* `permissions:;` - `` is a string that contains one + or more of the characters from `rwx` +* `name:;` - `` is a hex encoded string that contains the name of + the memory region mapped at the given address. In case of + regions backed by a file it have to be the absolute path of + the file while for anonymous regions it have to be the name + associated to the region if that is available. +* `flags:;` - where `` is a space separated string + of flag names. Currently the only supported flag + is `mt` for AArch64 memory tagging. lldb will + ignore any other flags in this field. +* `type:[][,];` - memory types that apply to this region, e.g. + `stack` for stack memory. +* `error:;` - where `` is + a hex encoded string value that + contains an error string +* `dirty-pages:[][,` - The save_id result is a non-zero unsigned integer value + that can be passed back to the GDB server using a + `QRestoreRegisterState` packet to restore the registers + one time. +* `EXX` - or an error code in the form of `EXX` where `XX` is a + hex error code. + +### Priority To Implement + +Low, this is mostly a convenience packet to avoid having to send all +registers with a `g` packet. It should only be implemented if support +for the `QRestoreRegisterState` is added. + +## QRestoreRegisterState:\ / QRestoreRegisterState:\;thread:XXXX; + +### Brief + +The `QRestoreRegisterState` packet tells the remote debugserver to +restore all registers using the `save_id` which is an unsigned +integer that was returned from a previous call to +`QSaveRegisterState`. The restoration process can only be done once +as the data backing the register state will be freed upon the +completion of the `QRestoreRegisterState` command. + +If thread suffixes are enabled the second form of this packet is +used, otherwise the first form is used. + +### Response + +* `OK` - if all registers were successfully restored +* `EXX` - for any errors + +### Priority To Implement + +Low, this is mostly a convenience packet to avoid having to send all +registers with a `g` packet. It should only be implemented if support +for the `QSaveRegisterState` is added. + +## qFileLoadAddress:\ + +### Brief + +Get the load address of a memory mapped file. +The load address is defined as the address of the first memory +region what contains data mapped from the specified file. + +### Response + +* `` - Load address of the file in big endian encoding +* `E01` - the requested file isn't loaded +* `EXX` - for any other errors + +### Priority To Implement + +Low, required if dynamic linker don't fill in the load address of +some object file in the rendezvous data structure. + +## qModuleInfo:\;\ + +### Brief + +Get information for a module by given module path and architecture. + +### Response + +* `(uuid|md5):...;triple:...;file_offset:...;file_size...;` +* `EXX` - for any errors + +### Priority To Implement + +Optional, required if dynamic loader cannot fetch module's information like +UUID directly from inferior's memory. + +## jModulesInfo:[{"file":"...",triple:"..."}, ...] + +### Brief + +Get information for a list of modules by given module path and +architecture. + +### Response + +A JSON array of dictionaries containing the following keys: +* `uuid` +* `triple` +* `file_path` +* `file_offset` +* `file_size` + +The meaning of the fields is the same as in the `qModuleInfo` packet. The server +signals the failure to retrieve the module info for a file by ommiting the +corresponding array entry from the response. The server may also +include entries the client did not ask for, if it has reason to +the modules will be interesting to the client. + +### Priority To Implement + +Optional. If not implemented, `qModuleInfo` packet will be used, which +may be slower if the target contains a large number of modules and +the communication link has a non-negligible latency. + +## Stop reply packet extensions + +### Brief + +This section describes some of the additional information you can +specify in stop reply packets that help LLDB to know more detailed +information about your threads. + +### Description + +Standard GDB remote stop reply packets are reply packets sent in +response to a packet that made the program run. They come in the +following forms: + +* `SAA` - + `S` means signal and `AA` is a hex signal number that describes why + the thread or stopped. It doesn't specify which thread, so the `T` + packet is recommended to use instead of the `S` packet. + +* `TAAkey1:value1;key2:value2;...` - + `T` means a thread stopped due to a unix signal where `AA` is a hex + signal number that describes why the program stopped. This is + followed by a series of key/value pairs: + * If key is a hex number, it is a register number and value is + the hex value of the register in debuggee endian byte order. + * If key == "thread", then the value is the big endian hex + thread-id of the stopped thread. + * If key == "core", then value is a hex number of the core on + which the stop was detected. + * If key == "watch" or key == "rwatch" or key == "awatch", then + value is the data address in big endian hex + * If key == "library", then value is ignore and "qXfer:libraries:read" + packets should be used to detect any newly loaded shared libraries + +* `WAA` - `W` means the process exited and `AA` is the exit status. + +* `XAA` - `X` means the process exited and `AA` is signal that caused the program + to exit. + +* `O` - `O` means `STDOUT` has data that was written to its + console and is being delivered to the debugger. This packet happens asynchronously + and the debugger is expected to continue to wait for another stop reply + packet. + +### Lldb Extensions + +We have extended the `T` packet to be able to also understand the +following keys and values: + +* `metype` - `unsigned` - + mach exception type (the value of the `EXC_XXX` enumerations) + as an unsigned integer. For targets with mach + kernels only. +* `mecount` - `unsigned` - + mach exception data count as an unsigned integer + For targets with mach kernels only. +* `medata` - `unsigned` - + There should be `mecount` of these and it is the data + that goes along with a mach exception (as an unsigned + integer). For targets with mach kernels only. +* `name` - `string` - + The name of the thread as a plain string. The string + must not contain an special packet characters or + contain a `:` or a `;`. Use `hexname` if the thread + name has special characters. +* `hexname` - `ascii-hex` - An ASCII hex string that contains the name of the thread +* `qaddr` - `hex` - + Big endian hex value that contains the `libdispatch` + queue address for the queue of the thread. +* `reason` - `enum` - The enumeration must be one of: + * `trace` - + the program stopped after a single instruction + was executed on a core. Usually done when single + stepping past a breakpoint + * `breakpoint` - a breakpoint set using a `z` packet was hit. + * `trap` - stopped due to user interruption + * `signal` - + stopped due to an actual unix signal, not + just the debugger using a unix signal to keep + the GDB remote client happy. + * `watchpoint` - Can be used with of the `watch`/`rwatch`/`awatch` key value + pairs. Or can be used *instead* of those keys, with the specially formatted + `description` field. + * `exception` - an exception stop reason. Use with + the `description` key/value pair to describe the + exceptional event the user should see as the stop + reason. + * `description` - + An ASCII hex string that contains a more descriptive + reason that the thread stopped. This is only needed + if none of the key/value pairs are enough to + describe why something stopped. + + For `reason:watchpoint`, `description` is an ascii-hex + encoded string with between one and three base 10 numbers, + space separated. The three numbers are: + 1. Watchpoint address. This address should always be within + a memory region lldb has a watchpoint on. + On architectures where the actual reported hit address may + be outside the watchpoint that was triggered, the remote + stub should determine which watchpoint was triggered and + report an address from within its range. + 2. Wwatchpoint hardware register index number. + 3. Actual watchpoint trap address, which may be outside + the range of any watched region of memory. On MIPS, an addr + outside a watched range means lldb should disable the wp, + step, re-enable the wp and continue silently. + + On MIPS, the low 3 bits are masked so if a watchpoint is on + 0x1004, a 2-byte write to 0x1000 will trigger the watchpoint + (a false positive hit), and lldb needs to disable the + watchpoint at 0x1004, inst-step, then re-enable the watchpoint + and not make this a user visible event. The description here + would be "0x1004 0 0x1000". lldb needs a known watchpoint address + in the first field, so it can disable it and step. + + On AArch64 we have a related issue, where you watch 4 bytes at + 0x1004, an instruction does an 8-byte write starting at + 0x1000 (a true watchpoint hit) and the hardware may report the + trap address as 0x1000 - before the watched memory region - + with the write extending into the watched region. This can + be reported as "0x1004 0 0x1000". lldb will use 0x1004 to + identify which Watchpoint was triggered, and can report 0x1000 + to the user. The behavior of silently stepping over the + watchpoint, with an 3rd field addr outside the range, is + restricted to MIPS. + + There may be false-positive watchpoint hits on AArch64 as well, + in the SVE Streaming Mode, but that is less common (see ESR + register flag "WPF", "Watchpoint might be False-Positive") and + not currently handled by lldb. +* `threads` - `comma-sep-base16` - + A list of thread ids for all threads (including + the thread that we're reporting as stopped) that + are live in the process right now. lldb may + request that this be included in the T packet via + the QListThreadsInStopReply packet earlier in + the debug session. + + Example: + ``` + threads:63387,633b2,63424,63462,63486; + ``` +* `thread-pcs` - `comma-sep-base16` - + A list of pc values for all threads that currently + exist in the process, including the thread that + this `T` packet is reporting as stopped. + This key-value pair will only be emitted when the + `threads` key is already included in the `T` packet. + The pc values correspond to the threads reported + in the `threads` list. The number of pcs in the + `thread-pcs` list will be the same as the number of + threads in the `threads` list. + lldb may request that this be included in the `T` + packet via the `QListThreadsInStopReply` packet + earlier in the debug session. + + Example: + ``` + thread-pcs:dec14,2cf872b0,2cf8681c,2d02d68c,2cf716a8; + ``` +* `addressing_bits` - `unsigned` (optional) - + Specifies how many bits in addresses are significant for addressing, base + 10. If bits 38..0 in a 64-bit pointer are significant for addressing, then the + value is 39. This is needed on e.g. AArch64 v8.3 ABIs that use pointer + authentication in the high bits. This value is normally sent in the `qHostInfo` + packet response, and if the value cannot change during the process lifetime, + it does not need to be duplicated here in the stop packet. For a firmware + environment with early start code that may be changing the page table setup, + a dynamically set value may be needed. +* `low_mem_addressing_bits` - `unsigned` (optional) - + Specifies how many bits in addresses in low memory are significant for + addressing, base 10. AArch64 can have different page table setups for low + and high memory, and therefore a different number of bits used for addressing. +* `high_mem_addressing_bits` - `unsigned` (optional) - + Specifies how many bits in addresses in high memory are significant for + addressing, base 10. AArch64 can have different page table setups for low and + high memory, and therefore a different number of bits used for addressing. + +### Best Practices + +Since register values can be supplied with this packet, it is often useful +to return the PC, SP, FP, LR (if any), and FLAGS registers so that separate +packets don't need to be sent to read each of these registers from each +thread. + +If a thread is stopped for no reason (like just because another thread +stopped, or because when one core stops all cores should stop), use a +`T` packet with `00` as the signal number and fill in as many key values +and registers as possible. + +LLDB likes to know why a thread stopped since many thread control +operations like stepping over a source line, actually are implemented +by running the process multiple times. If a breakpoint is hit while +trying to step over a source line and LLDB finds out that a breakpoint +is hit in the "reason", we will know to stop trying to do the step +over because something happened that should stop us from trying to +do the step. If we are at a breakpoint and we disable the breakpoint +at the current PC and do an instruction single step, knowing that +we stopped due to a "trace" helps us know that we can continue +running versus stopping due to a "breakpoint" (if we have two +breakpoint instruction on consecutive instructions). So the more info +we can get about the reason a thread stops, the better job LLDB can +do when controlling your process. A typical GDB server behavior is +to send a SIGTRAP for breakpoints _and_ also when instruction single +stepping, in this case the debugger doesn't really know why we +stopped and it can make it hard for the debugger to control your +program correctly. What if a real SIGTRAP was delivered to a thread +while we were trying to single step? We wouldn't know the difference +with a standard GDB remote server and we could do the wrong thing. + +### Priority To Implement + +High. Having the extra information in your stop reply packets makes +your debug session more reliable and informative. + +## qfProcessInfo / qsProcessInfo (Platform Extension) + +### Brief + +Get the first process info (`qfProcessInfo`) or subsequent process +info (`qsProcessInfo`) for one or more processes on the remote +platform. The first call gets the first match and subsequent calls +to `qsProcessInfo` gets the subsequent matches. Return an error `EXX`, +where `XX` are two hex digits, when no more matches are available. + +### Priority To Implement + +Required. The `qfProcessInfo` packet can be followed by a `:` and +some key value pairs. The key value pairs in the command are: + +* `name` - `ascii-hex` - + An ASCII hex string that contains the name of the process that will be matched. +* `name_match` - `enum` - + One of: + * `equals` + * `starts_with` + * `ends_with` + * `contains` + * `regex` +* `pid` - `integer`- A string value containing the decimal process ID +* `parent_pid` - `integer` - A string value containing the decimal parent process ID +* `uid` - `integer` - A string value containing the decimal user ID +* `gid` - `integer` - A string value containing the decimal group ID +* `euid` - `integer` - A string value containing the decimal effective user ID +* `egid` - `integer` - A string value containing the decimal effective group ID +* `all_users` - `bool` - + A boolean value that specifies if processes should + be listed for all users, not just the user that the + platform is running as +* `triple` - `string` - + An ASCII triple string (`x86_64`, `x86_64-apple-macosx`, `armv7-apple-ios`) +* `args` - `string` - + A string value containing the process arguments separated by the character `-`, + where each argument is hex-encoded. It includes `argv[0]`. + +The response consists of key/value pairs where the key is separated from the +values with colons and each pair is terminated with a semi colon. For a list +of the key/value pairs in the response see the `qProcessInfoPID` packet +documentation. + +Sample packet/response: +``` +send packet: $qfProcessInfo#00 +read packet: $pid:60001;ppid:59948;uid:7746;gid:11;euid:7746;egid:11;name:6c6c6462;triple:x86_64-apple-macosx;#00 +send packet: $qsProcessInfo#00 +read packet: $pid:59992;ppid:192;uid:7746;gid:11;euid:7746;egid:11;name:6d64776f726b6572;triple:x86_64-apple-macosx;#00 +send packet: $qsProcessInfo#00 +read packet: $E04#00 +``` + +## qPathComplete (Platform Extension) + +### Brief + +Get a list of matched disk files/directories by passing a boolean flag +and a partial path. + +### Example + +``` +receive: qPathComplete:0,6d61696e +send: M6d61696e2e637070 +receive: qPathComplete:1,746573 +send: M746573742f,74657374732f +``` + +If the first argument is zero, the result should contain all +files (including directories) starting with the given path. If the +argument is one, the result should contain only directories. + +The result should be a comma-separated list of hex-encoded paths. +Paths denoting a directory should end with a directory separator (`/` or `\`. + +## qKillSpawnedProcess (Platform Extension) + +### Brief + +Kill a process running on the target system. + +### Example + +``` +receive: qKillSpawnedProcess:1337 +send: OK +``` +The request packet has the process ID in base 10. + +## qLaunchGDBServer (Platform Extension) + +### Brief + +Have the remote platform launch a GDB server. + +### Priority To Implement + +Required. The `qLaunchGDBServer` packet must be followed by a `:` and +some key value pairs. The key value pairs in the command are: +* `port` - `integer` - + A string value containing the decimal port ID or zero if the port should be + bound and returned +* `host` - `integer` - + The host that connections should be limited to when the GDB server is connected to. + +### Description + +The response consists of key/value pairs where the key is separated from the +values with colons and each pair is terminated with a semi colon. + +Sample packet/response: +``` +send packet: $qLaunchGDBServer:port:0;host:lldb.apple.com;#00 +read packet: $pid:60025;port:50776;#00 +``` + +The `pid` key/value pair is only specified if the remote platform launched +a separate process for the GDB remote server and can be omitted if no +process was separately launched. + +The `port` key/value pair in the response lets clients know what port number +to attach to in case zero was specified as the "port" in the sent command. + + +## qProcessInfoPID:PID (Platform Extension) + +### Brief + +Have the remote platform get detailed information on a process by +ID. PID is specified as a decimal integer. + +### Priority To Implement + +Optional. + +### Description + +The response consists of key/value pairs where the key is separated from the +values with colons and each pair is terminated with a semi colon. + +The key value pairs in the response are: +* `pid` - `integer` - Process ID as a decimal integer string +* `ppid` - `integer` - Parent process ID as a decimal integer string +* `uid` - `integer` - A string value containing the decimal user ID +* `gid` - `integer` - A string value containing the decimal group ID +* `euid` - `integer` - A string value containing the decimal effective user ID +* `egid` - `integer` - A string value containing the decimal effective group ID +* `name` - `ascii-hex` - An ASCII hex string that contains the name of the process +* `triple` - `string` - A target triple (`x86_64-apple-macosx`, `armv7-apple-ios`) + +Sample packet/response: +``` +send packet: $qProcessInfoPID:60050#00 +read packet: $pid:60050;ppid:59948;uid:7746;gid:11;euid:7746;egid:11;name:6c6c6462;triple:x86_64-apple-macosx;#00 +``` + +## vAttachName + +### Brief + +Same as `vAttach`, except instead of a `pid` you send a process name. + +### Priority To Implement + +Low. Only needed for `process attach -n`. If the packet isn't supported +then `process attach -n` will fail gracefully. So you need only to support +it if attaching to a process by name makes sense for your environment. + +## vAttachWait + +### Brief + +Same as `vAttachName`, except that the stub should wait for the next instance +of a process by that name to be launched and attach to that. + +### Priority To Implement + +Low. Only needed to support `process attach -w -n` which will fail +gracefully if the packet is not supported. + +## qAttachOrWaitSupported + +### Brief + +This is a binary "is it supported" query. Return OK if you support +`vAttachOrWait`. + +### Priority To Implement + +Low. This is required if you support `vAttachOrWait`, otherwise no support +is needed since the standard "I don't recognize this packet" response +will do the right thing. + +## vAttachOrWait + +### Brief + +Same as `vAttachWait`, except that the stub will attach to a process +by name if it exists, and if it does not, it will wait for a process +of that name to appear and attach to it. + +### Priority To Implement + +Low. Only needed to implement `process attach -w -i false -n`. If +you don't implement it but do implement `-n` AND lldb can somehow get +a process list from your device, it will fall back on scanning the +process list, and sending `vAttach` or `vAttachWait` depending on +whether the requested process exists already. This is racy, +however, so if you want to support this behavior it is better to +support this packet. + +## jThreadExtendedInfo + +### Brief + +This packet, which takes its arguments as JSON and sends its reply as +JSON, allows the gdb remote stub to provide additional information +about a given thread. + +### Priority To Implement + +Low. This packet is only needed if the gdb remote stub wants to +provide interesting additional information about a thread for the +user. + +### Description + +This packet takes its arguments in [JSON](http://www.json.org). +At a minimum, a thread must be specified, for example: +``` +jThreadExtendedInfo:{"thread":612910} +``` + +Because this is a JSON string, the thread number is provided in base 10. +Additional key-value pairs may be provided by lldb to the gdb remote +stub. For instance, on some versions of macOS, lldb can read offset +information out of the system libraries. Using those offsets, debugserver +is able to find the Thread Specific Address (TSD) for a thread and include +that in the return information. So lldb will send these additional fields +like so: +``` +jThreadExtendedInfo:{"plo_pthread_tsd_base_address_offset":0,"plo_pthread_tsd_base_offset":224,"plo_pthread_tsd_entry_size":8,"thread":612910} +``` + +There are no requirements for what is included in the response. A simple +reply on a OS X Yosemite / iOS 8 may include the pthread_t value, the +Thread Specific Data (TSD) address, the dispatch_queue_t value if the thread +is associated with a GCD queue, and the requested Quality of Service (QoS) +information about that thread. For instance, a reply may look like: +``` +{"tsd_address":4371349728,"requested_qos":{"enum_value":33,"constant_name":"QOS_CLASS_USER_INTERACTIVE","printable_name":"User Interactive"},"pthread_t":4371349504,"dispatch_queue_t":140735087127872} +``` + +`tsd_address`, `pthread_t`, and `dispatch_queue_t` are all simple key-value pairs. +The JSON standard requires that numbers be expressed in base 10 - so all of +these are. `requested_qos` is a dictionary with three key-value pairs in it - +so the UI layer may choose the form most appropriate for displaying to the user. + +Sending JSON over gdb-remote protocol introduces some problems. We may be +sending strings with arbitrary contents in them, including the `#`, `$`, and `*` +characters that have special meaning in gdb-remote protocol and cannot occur +in the middle of the string. The standard solution for this would be to require +ascii-hex encoding of all strings, or ascii-hex encode the entire JSON payload. + +Instead, the binary escaping convention is used for JSON data. This convention +(e.g. used for the `X` packet) says that if `#`, `$`, `*`, or `}` are to occur in +the payload, the character `}` (`0x7d`) is emitted, then the metacharacter is emitted +xor'ed by `0x20`. The `}` character occurs in every JSON payload at least once, and +`} ^ 0x20` happens to be `]` so the raw packet characters for a request will look +like: +``` +jThreadExtendedInfo:{"thread":612910}] +``` + +## QEnableCompression + +### Brief + +This packet enables compression of the packets that the debug stub sends to lldb. +If the debug stub can support compression, it indictes this in the reply of the +"qSupported" packet. For example: +``` +LLDB SENDS: qSupported:xmlRegisters=i386,arm,mips +STUB REPLIES: qXfer:features:read+;SupportedCompressions=lzfse,zlib-deflate,lz4,lzma; +``` + +If lldb knows how to use any of these compression algorithms, it can ask that this +compression mode be enabled. +``` +QEnableCompression:type:zlib-deflate; +``` + +The debug stub should reply with an uncompressed `OK` packet to indicate that the +request was accepted. All further packets the stub sends will use this compression. + +Packets are compressed as the last step before they are sent from the stub, and +decompressed as the first step after they are received. The packet format in compressed +mode becomes one of two: +``` +$N#00 + +$C:#00 +``` + +Where `#00` is the actual checksum value if noack mode is not enabled. The checksum +value is for the `N` or +`C:` bytes in the packet. + +The size of the uncompressed payload in base 10 is provided because it will simplify +decompression if the final buffer size needed is known ahead of time. + +Compression on low-latency connections is unlikely to be an improvement. Particularly +when the debug stub and lldb are running on the same host. It should only be used +for slow connections, and likely only for larger packets. + +Example compression algorithms that may be used include: +* `zlib-deflate` - + The raw DEFLATE format as described in IETF RFC 1951. With the ZLIB library, you + can compress to this format with an initialization like + deflateInit2 (&stream, 5, Z_DEFLATED, -15, 8, Z_DEFAULT_STRATEGY) + and you can decompress with an initialization like + inflateInit2 (&stream, -15). +* `lz4` - + https://en.wikipedia.org/wiki/LZ4_(compression_algorithm) + https://github.com/Cyan4973/lz4 + The libcompression APIs on darwin systems call this `COMPRESSION_LZ4_RAW`. +* `lzfse` - + Compression algorithm added in macOS 10.11, with open source C reference + implementation on github. + https://en.wikipedia.org/wiki/LZFSE + https://github.com/lzfse/lzfse +* `lzma` - + libcompression implements "LZMA level 6", the default compression for the + open source LZMA implementation. + +## jGetLoadedDynamicLibrariesInfos + +### Brief + +This packet asks the remote debug stub to send the details about libraries +being added/removed from the process as a performance optimization. + +There are two ways this packet can be used. Both return a dictionary of +binary images formatted the same way. + +One requests information on all shared libraries: +``` +jGetLoadedDynamicLibrariesInfos:{"fetch_all_solibs":true} +``` +with an optional `"report_load_commands":false` which can be added, asking +that only the dyld SPI information (load addresses, filenames) be returned. +The default behavior is that debugserver scans the mach-o header and load +commands of each binary, and returns it in the JSON reply. + +And the second requests information about a list of shared libraries, given their load addresses: +``` +jGetLoadedDynamicLibrariesInfos:{"solib_addresses":[8382824135,3258302053,830202858503]} +``` + +The second call is both a performance optimization (instead of having lldb read the mach-o header/load commands +out of memory with generic read packets) but also adds additional information in the form of the +filename of the shared libraries (which is not available in the mach-o header/load commands.) + +An example using the OS X 10.11 style call: +``` +LLDB SENDS: jGetLoadedDynamicLibrariesInfos:{"image_count":1,"image_list_address":140734800075128} +STUB REPLIES: ${"images":[{"load_address":4294967296,"mod_date":0,"pathname":"/tmp/a.out","uuid":"02CF262C-ED6F-3965-9E14-63538B465CFF","mach_header":{"magic":4277009103,"cputype":16777223,"cpusubtype":18446744071562067971,"filetype":2},"segments":{"name":"__PAGEZERO","vmaddr":0,"vmsize":4294967296,"fileoff":0,"filesize":0,"maxprot":0},{"name":"__TEXT","vmaddr":4294967296,"vmsize":4096,"fileoff":0,"filesize":4096,"maxprot":7},{"name":"__LINKEDIT","vmaddr":4294971392,"vmsize":4096,"fileoff":4096,"filesize":152,"maxprot":7}}]}#00 +``` + +Or pretty-printed: +``` +STUB REPLIES: ${"images": + [ + {"load_address":4294967296, + "mod_date":0, + "pathname":"/tmp/a.out", + "uuid":"02CF262C-ED6F-3965-9E14-63538B465CFF", + "mach_header": + {"magic":4277009103, + "cputype":16777223, + "cpusubtype":18446744071562067971, + "filetype":2 + }, + "segments": + [ + {"name":"__PAGEZERO", + "vmaddr":0, + "vmsize":4294967296, + "fileoff":0, + "filesize":0, + "maxprot":0 + }, + {"name":"__TEXT", + "vmaddr":4294967296, + "vmsize":4096, + "fileoff":0, + "filesize":4096, + "maxprot":7 + }, + {"name":"__LINKEDIT", + "vmaddr":4294971392, + "vmsize":4096, + "fileoff":4096, + "filesize":152, + "maxprot":7 + } + ] + } + ] + } +``` + +### Description + +This is similar to the `qXfer:libraries:read` packet, and it could +be argued that it should be merged into that packet. A separate +packet was created primarily because lldb needs to specify the +number of images to be read and the address from which the initial +information is read. Also the XML DTD would need to be extended +quite a bit to provide all the information that the `DynamicLoaderMacOSX` +would need to work correctly on this platform. + +### Priority To Implement + +On OS X 10.11, iOS 9, tvOS 9, watchOS 2 and older: Low. If this packet is absent, +lldb will read the Mach-O headers/load commands out of memory. +On macOS 10.12, iOS 10, tvOS 10, watchOS 3 and newer: High. If this packet is absent, +lldb will not know anything about shared libraries in the inferior, or where the main +executable loaded. + +## jThreadsInfo + +### Brief + +Ask for the server for thread stop information of all threads. + +### Priority To Implement + +Low. This is a performance optimization, which speeds up debugging by avoiding +multiple round-trips for retrieving thread information. The information from this +packet can be retrieved using a combination of `qThreadStopInfo` and `m` packets. + +### Description + +The data in this packet is very similar to the stop reply packets, but is packaged in +JSON and uses JSON arrays where applicable. The JSON output looks like: +``` + [ + { "tid":1580681, + "metype":6, + "medata":[2,0], + "reason":"exception", + "qaddr":140735118423168, + "registers": { + "0":"8000000000000000", + "1":"0000000000000000", + "2":"20fabf5fff7f0000", + "3":"e8f8bf5fff7f0000", + "4":"0100000000000000", + "5":"d8f8bf5fff7f0000", + "6":"b0f8bf5fff7f0000", + "7":"20f4bf5fff7f0000", + "8":"8000000000000000", + "9":"61a8db78a61500db", + "10":"3200000000000000", + "11":"4602000000000000", + "12":"0000000000000000", + "13":"0000000000000000", + "14":"0000000000000000", + "15":"0000000000000000", + "16":"960b000001000000", + "17":"0202000000000000", + "18":"2b00000000000000", + "19":"0000000000000000", + "20":"0000000000000000" + }, + "memory":[ + {"address":140734799804592,"bytes":"c8f8bf5fff7f0000c9a59e8cff7f0000"}, + {"address":140734799804616,"bytes":"00000000000000000100000000000000"} + ] + } + ] +``` + +It contains an array of dictionaries with all of the key value pairs that are +normally in the stop reply packet, including the expedited registers. The registers are +passed as hex-encoded JSON string in debuggee-endian byte order. Note that the register +numbers are decimal numbers, unlike the stop-reply packet, where they are written in +hex. The packet also contains expedited memory in the `memory` key. This allows the +server to expedite memory that the client is likely to use (e.g., areas around the +stack pointer, which are needed for computing backtraces) and it reduces the packet +count. + +On macOS with debugserver, we expedite the frame pointer backchain for a thread +(up to 256 entries) by reading 2 pointers worth of bytes at the frame pointer (for +the previous FP and PC), and follow the backchain. Most backtraces on macOS and +iOS now don't require us to read any memory! + +## jGetSharedCacheInfo + +### Brief + +This packet asks the remote debug stub to send the details about the inferior's +shared cache. The shared cache is a collection of common libraries/frameworks that +are mapped into every process at the same address on Darwin systems, and can be +identified by a load address and UUID. + +``` +LLDB SENDS: jGetSharedCacheInfo:{} +STUB REPLIES: ${"shared_cache_base_address":140735683125248,"shared_cache_uuid":"DDB8D70C-C9A2-3561-B2C8-BE48A4F33F96","no_shared_cache":false,"shared_cache_private_cache":false]}#00 +``` + +### Priority To Implement + +Low. When both lldb and the inferior process are running on the same computer, and lldb +and the inferior process have the same shared cache, lldb may (as an optimization) read +the shared cache out of its own memory instead of using gdb-remote read packets to read +them from the inferior process. + +## qQueryGDBServer + +### Brief + +Ask the platform for the list of gdbservers we have to connect + +### Priority To Implement + +Low. The packet is required to support connecting to gdbserver started +by the platform instance automatically. + +### Description + +If the remote platform automatically started one or more gdbserver instance (without +lldb asking it) then it have to return the list of port number or socket name for +each of them what can be used by lldb to connect to those instances. + +The data in this packet is a JSON array of JSON objects with the following keys: +* `port`: `` (optional) +* `socket_name`: `` (optional) + +Example packet: +``` +[ + { "port": 1234 }, + { "port": 5432 }, + { "socket_name": "foo" } +] +``` + +## QSetDetachOnError + +### Brief + +Sets what the server should do when the communication channel with LLDB +goes down. Either kill the inferior process (`0`) or remove breakpoints and +detach (`1`). + +### Priority To Implement + +Low. Only required if the target wants to keep the inferior process alive +when the communication channel goes down. + +### Description + +The data in this packet is a single a character, which should be `0` if the +inferior process should be killed, or `1` if the server should remove all +breakpoints and detach from the inferior. + +## jGetDyldProcessState + +### Brief + +This packet fetches the process launch state, as reported by libdyld on +Darwin systems, most importantly to indicate when the system libraries +have initialized sufficiently to safely call utility functions. + +``` +LLDB SENDS: jGetDyldProcessState +STUB REPLIES: {"process_state_value":48,"process_state string":"dyld_process_state_libSystem_initialized"} +``` + +### Priority To Implement + +Low. This packet is needed to prevent lldb's utility functions for +scanning the Objective-C class list from running very early in +process startup. + +## vFile Packets + +Though some of these may match the ones described in GDB's protocol +documentation, we include our own expectations here in case of +mismatches or extensions. + +### vFile:size + +#### Brief + +Get the size of a file on the target system, filename in ASCII hex. + +#### Example + +``` +receive: vFile:size:2f746d702f61 +send: Fc008 +``` + +response is `F` followed by the file size in base 16. +`F-1,errno` with the errno if an error occurs, base 16. + +### vFile:mode + +#### Brief + +Get the mode bits of a file on the target system, filename in ASCII hex. + +#### Example + +``` +receive: vFile:mode:2f746d702f61 +send: F1ed +``` + +response is `F` followed by the mode bits in base 16, this `0x1ed` would +correspond to `0755` in octal. +`F-1,errno` with the errno if an error occurs, base 16. + +### vFile:unlink + +#### Brief + +Remove a file on the target system. + +#### Example + +``` +receive: vFile:unlink:2f746d702f61 +send: F0 +``` + +Argument is a file path in ascii-hex encoding. +Response is `F` plus the return value of `unlink()`, base 16 encoding. +Return value may optionally be followed by a comma and the base16 +value of errno if unlink failed. + +### vFile:symlink + +#### Brief + +Create a symbolic link (symlink, soft-link) on the target system. + +#### Example + +``` +receive: vFile:symlink:, +send: F0,0 +``` + +Argument file paths are in ascii-hex encoding. +Response is `F` plus the return value of `symlink()`, base 16 encoding, +optionally followed by the value of errno if it failed, also base 16. + +### vFile:open + +#### Brief + +Open a file on the remote system and return the file descriptor of it. + +#### Example + +``` +receive: vFile:open:2f746d702f61,00000001,00000180 +send: F8 +``` + +request packet has the fields: + 1. ASCII hex encoded filename + 2. Flags passed to the open call, base 16. + Note that these are not the `oflags` that `open(2)` takes, but + are the constant values in `enum OpenOptions` from LLDB's + [`File.h`](https://github.com/llvm/llvm-project/blob/main/lldb/include/lldb/Host/File.h). + 3. Mode bits, base 16 + +response is `F` followed by the opened file descriptor in base 16. +`F-1,errno` with the errno if an error occurs, base 16. + +### vFile:close + +#### Brief + +Close a previously opened file descriptor. + +#### Example + +``` +receive: vFile:close:7 +send: F0 +``` + +File descriptor is in base 16. `F-1,errno` with the errno if an error occurs, +errno is base 16. + +### vFile:pread + +#### Brief + +Read data from an opened file descriptor. + +#### Example + +``` +receive: vFile:pread:7,1024,0 +send: F4;a'b\00 +``` + +Request packet has the fields: + 1. File descriptor, base 16 + 2. Number of bytes to be read, base 16 + 3. Offset into file to start from, base 16 + +Response is `F`, followed by the number of bytes read (base 16), a +semicolon, followed by the data in the binary-escaped-data encoding. + +### vFile:pwrite + +#### Brief + +Write data to a previously opened file descriptor. + +#### Example + +``` +receive: vFile:pwrite:8,0,\cf\fa\ed\fe\0c\00\00 +send: F1024 +``` + +Request packet has the fields: + 1. File descriptor, base 16 + 2. Offset into file to start from, base 16 + 3. binary-escaped-data to be written + +Response is `F`, followed by the number of bytes written (base 16). + +### vFile:MD5 + +#### Brief + +Generate an MD5 hash of the file at the given path. + +#### Example + +``` +receive: vFile:MD5:2f746d702f61 +send (success): F,00000000000000001111111111111111 +send (failure): F,x +``` + +Request packet contains the ASCII hex encoded filename. + +If the hash succeeded, the response is `F,` followed by the low 64 +bits of the result, and finally the high 64 bits of the result. Both are in +hex format without a prefix. + +The response is `F,`, followed by `x` if the file did not exist +or failed to hash. + +### vFile:exists + +#### Brief + +Check whether the file at the given path exists. + +#### Example + +``` +receive: vFile:exists:2f746d702f61 +send (exists): F,1 +send (does not exist): F,0 +``` + +Request packet contains the ASCII hex encoded filename. + +The response is a return code where 1 means the file exists +and 0 means it does not. \ No newline at end of file diff --git a/lldb/docs/resources/lldbplatformpackets.md b/lldb/docs/resources/lldbplatformpackets.md new file mode 100644 index 0000000000000000000000000000000000000000..f7262e193d940d99f94f3ed19777de6f8d370fd2 --- /dev/null +++ b/lldb/docs/resources/lldbplatformpackets.md @@ -0,0 +1,49 @@ +# LLDB Platform Packets + +This is a list of the packets that an lldb platform server +needs to implement for the lldb testsuite to be run on a remote +target device/system. + +These are almost all lldb extensions to the gdb-remote serial +protocol. Many of the `vFile:` packets are also described in the "Host +I/O Packets" detailed in the gdb-remote protocol documentation, +although the lldb platform extensions include packets that are not +defined there (`vFile:size:`, `vFile:mode:`, `vFile:symlink`, `vFile:chmod:`). + +Most importantly, the flags that LLDB passes to `vFile:open:` are +incompatible with the flags that GDB specifies. + +* [QStartNoAckMode](./lldbgdbremote.md#qstartnoackmode) +* [qHostInfo](./lldbgdbremote.md#qhostinfo) +* [qModuleInfo](./lldbgdbremote.md#qmoduleinfo-module-path-arch-triple) +* [qGetWorkingDir](./lldbgdbremote.md#qgetworkingdir) +* [QSetWorkingDir](./lldbgdbremote.md#qsetworkingdir-ascii-hex-path) +* [qPlatform_mkdir](./lldbgdbremote.md#qplatform-mkdir) +* [qPlatform_shell](./lldbgdbremote.md#qplatform-shell) +* [qLaunchGDBServer](./lldbgdbremote.md#qlaunchgdbserver-platform-extension) +* [qKillSpawnedProcess](./lldbgdbremote.md#qkillspawnedprocess-platform-extension) +* [qProcessInfoPID](./lldbgdbremote.md#qprocessinfopid-pid-platform-extension) + * It is likely that you only need to support the `pid` and `name` fields. +* [qProcessInfo](./lldbgdbremote.md#qprocessinfo) + * The lldb test suite currently only uses `name_match:equals` and the no-criteria mode to list every process. +* [qPathComplete](./lldbgdbremote.md#qpathcomplete-platform-extension) +* [vFile:chmod](./lldbgdbremote.md#vfile-chmod-qplatform-chmod) +* [vFile:size](./lldbgdbremote.md#vfile-size) +* [vFile:mode](./lldbgdbremote.md#vfile-mode) +* [vFile:unlink](./lldbgdbremote.md#vfile-unlink) +* [vFile:symlink](./lldbgdbremote.md#vfile-symlink) +* [vFile:open](./lldbgdbremote.md#vfile-open) +* [vFile:close](./lldbgdbremote.md#vfile-close) +* [vFile:pread](./lldbgdbremote.md#vfile-pread) +* [vFile:pwrite](./lldbgdbremote.md#vfile-pwrite) + +The remote platform must be able to launch processes so that debugserver +can attach to them. This requires the following packets in addition to the +previous list: +* [QSetDisableASLR](./lldbgdbremote.md#qsetdisableaslr-bool) +* [QSetDetatchOnError](./lldbgdbremote.md#qsetdetachonerror) +* [QSetSTDIN / QSetSTDOUT / QSetSTDERR](./lldbgdbremote.md#qsetstdin-ascii-hex-path-qsetstdout-ascii-hex-path-qsetstderr-ascii-hex-path) (all 3) +* [QEnvironment](./lldbgdbremote.md#qenvironment-name-value) +* [QEnvironmentHexEncoded](./lldbgdbremote.md#qenvironmenthexencoded-hex-encoding-name-value) +* [A](./lldbgdbremote.md#a-launch-args-packet) +* [qLaunchSuccess](./lldbgdbremote.md#qlaunchsuccess) diff --git a/lldb/docs/resources/test.rst b/lldb/docs/resources/test.rst index 094fde8b1b5a0a2a88475d318413166154ef9f42..382e42bf22b1029e26e67c1eb129acb4abf39457 100644 --- a/lldb/docs/resources/test.rst +++ b/lldb/docs/resources/test.rst @@ -618,9 +618,9 @@ On non-Windows platforms, you can use the ``-d`` option to ``dotest.py`` which will cause the script to print out the pid of the test and wait for a while until a debugger is attached. Then run ``lldb -p `` to attach. -To instead debug a test's python source, edit the test and insert -``import pdb; pdb.set_trace()`` at the point you want to start debugging. In -addition to pdb's debugging facilities, lldb commands can be executed with the +To instead debug a test's python source, edit the test and insert ``import pdb; pdb.set_trace()`` or ``breakpoint()`` (Python 3 only) at the point you want to start debugging. The ``breakpoint()`` command can be used for any LLDB Python script, not just for API tests. + +In addition to pdb's debugging facilities, lldb commands can be executed with the help of a pdb alias. For example ``lldb bt`` and ``lldb v some_var``. Add this line to your ``~/.pdbrc``: diff --git a/lldb/include/lldb/API/SBLineEntry.h b/lldb/include/lldb/API/SBLineEntry.h index 7c2431ba3c8a51df1d3b3ef3247d4eb9807afb72..d70c4fac6ec7174e2a50f9fe7b35cfb611632c62 100644 --- a/lldb/include/lldb/API/SBLineEntry.h +++ b/lldb/include/lldb/API/SBLineEntry.h @@ -29,6 +29,9 @@ public: lldb::SBAddress GetEndAddress() const; + lldb::SBAddress + GetSameLineContiguousAddressRangeEnd(bool include_inlined_functions) const; + explicit operator bool() const; bool IsValid() const; diff --git a/lldb/include/lldb/API/SBProcess.h b/lldb/include/lldb/API/SBProcess.h index 7da3335a7234b7688784e40376ac4581dd587a91..f1b5d1fb92ce2917532487965e0d1ea570f51cfa 100644 --- a/lldb/include/lldb/API/SBProcess.h +++ b/lldb/include/lldb/API/SBProcess.h @@ -562,6 +562,8 @@ public: lldb::SBScriptObject GetScriptedImplementation(); + void GetStatus(SBStream &status); + protected: friend class SBAddress; friend class SBBreakpoint; diff --git a/lldb/include/lldb/API/SBSymbolContextList.h b/lldb/include/lldb/API/SBSymbolContextList.h index 4026afc213571c5393fa9f07ba4a4ab4cf72a9fc..95100d219df20f3c076f71d2f2d21cbec052fd13 100644 --- a/lldb/include/lldb/API/SBSymbolContextList.h +++ b/lldb/include/lldb/API/SBSymbolContextList.h @@ -44,6 +44,7 @@ public: protected: friend class SBModule; friend class SBTarget; + friend class SBCompileUnit; lldb_private::SymbolContextList *operator->() const; diff --git a/lldb/include/lldb/API/SBTarget.h b/lldb/include/lldb/API/SBTarget.h index 3644ac056da3dca07fd563acfea64b7f45cb5d7b..feeaa1cb71132bcdee19b572d7b8c0e5237df0f6 100644 --- a/lldb/include/lldb/API/SBTarget.h +++ b/lldb/include/lldb/API/SBTarget.h @@ -879,6 +879,10 @@ public: uint32_t count, const char *flavor_string); + lldb::SBInstructionList ReadInstructions(lldb::SBAddress start_addr, + lldb::SBAddress end_addr, + const char *flavor_string); + lldb::SBInstructionList GetInstructions(lldb::SBAddress base_addr, const void *buf, size_t size); @@ -954,6 +958,7 @@ protected: friend class SBSection; friend class SBSourceManager; friend class SBSymbol; + friend class SBTypeStaticField; friend class SBValue; friend class SBVariablesOptions; diff --git a/lldb/include/lldb/API/SBType.h b/lldb/include/lldb/API/SBType.h index 9980fe1218305bb93361a508f8e28645bab16673..5b9ff2170b2b240e5cc5299ef9f183fd61cc1e62 100644 --- a/lldb/include/lldb/API/SBType.h +++ b/lldb/include/lldb/API/SBType.h @@ -107,6 +107,35 @@ protected: lldb::TypeMemberFunctionImplSP m_opaque_sp; }; +class LLDB_API SBTypeStaticField { +public: + SBTypeStaticField(); + + SBTypeStaticField(const lldb::SBTypeStaticField &rhs); + lldb::SBTypeStaticField &operator=(const lldb::SBTypeStaticField &rhs); + + ~SBTypeStaticField(); + + explicit operator bool() const; + + bool IsValid() const; + + const char *GetName(); + + const char *GetMangledName(); + + lldb::SBType GetType(); + + lldb::SBValue GetConstantValue(lldb::SBTarget target); + +protected: + friend class SBType; + + explicit SBTypeStaticField(lldb_private::CompilerDecl decl); + + std::unique_ptr m_opaque_up; +}; + class SBType { public: SBType(); @@ -182,6 +211,8 @@ public: lldb::SBTypeMember GetVirtualBaseClassAtIndex(uint32_t idx); + lldb::SBTypeStaticField GetStaticFieldWithName(const char *name); + lldb::SBTypeEnumMemberList GetEnumMembers(); uint32_t GetNumberOfTemplateArguments(); @@ -242,6 +273,7 @@ protected: friend class SBTypeNameSpecifier; friend class SBTypeMember; friend class SBTypeMemberFunction; + friend class SBTypeStaticField; friend class SBTypeList; friend class SBValue; friend class SBWatchpoint; diff --git a/lldb/include/lldb/API/SBValue.h b/lldb/include/lldb/API/SBValue.h index bbcccaab51aaee196e61ffb17ccb0d5ae9e69a36..8f4c4fd56dfb18193d0d34f704292713a71c3c23 100644 --- a/lldb/include/lldb/API/SBValue.h +++ b/lldb/include/lldb/API/SBValue.h @@ -68,6 +68,8 @@ public: uint64_t GetValueAsUnsigned(uint64_t fail_value = 0); + lldb::addr_t GetValueAsAddress(); + ValueType GetValueType(); // If you call this on a newly created ValueObject, it will always return @@ -426,6 +428,7 @@ protected: friend class SBModule; friend class SBTarget; friend class SBThread; + friend class SBTypeStaticField; friend class SBTypeSummary; friend class SBValueList; diff --git a/lldb/include/lldb/Core/Debugger.h b/lldb/include/lldb/Core/Debugger.h index 418c2403d020f48429c76de2ed10795b7492d369..49ff0737acef82d2174f3b52de11d9db1e113f9c 100644 --- a/lldb/include/lldb/Core/Debugger.h +++ b/lldb/include/lldb/Core/Debugger.h @@ -89,7 +89,7 @@ public: using DebuggerList = std::vector; - static ConstString GetStaticBroadcasterClass(); + static llvm::StringRef GetStaticBroadcasterClass(); /// Get the public broadcaster for this debugger. Broadcaster &GetBroadcaster() { return m_broadcaster; } diff --git a/lldb/include/lldb/Core/ThreadedCommunication.h b/lldb/include/lldb/Core/ThreadedCommunication.h index 7ebb77beb77f3d97ebb00de28548ec6594f629a1..24412b2027932db7197a24e09d8dbb854dc8d797 100644 --- a/lldb/include/lldb/Core/ThreadedCommunication.h +++ b/lldb/include/lldb/Core/ThreadedCommunication.h @@ -216,9 +216,9 @@ public: /// void SynchronizeWithReadThread(); - static ConstString &GetStaticBroadcasterClass(); + static llvm::StringRef GetStaticBroadcasterClass(); - ConstString &GetBroadcasterClass() const override { + llvm::StringRef GetBroadcasterClass() const override { return GetStaticBroadcasterClass(); } diff --git a/lldb/include/lldb/Interpreter/CommandInterpreter.h b/lldb/include/lldb/Interpreter/CommandInterpreter.h index d190bcdcab4497d4327b7d481ce11b135c2895f1..70a55a77465bfe1e37ae4bb3c8d86316c0f2c03e 100644 --- a/lldb/include/lldb/Interpreter/CommandInterpreter.h +++ b/lldb/include/lldb/Interpreter/CommandInterpreter.h @@ -255,9 +255,9 @@ public: // These two functions fill out the Broadcaster interface: - static ConstString &GetStaticBroadcasterClass(); + static llvm::StringRef GetStaticBroadcasterClass(); - ConstString &GetBroadcasterClass() const override { + llvm::StringRef GetBroadcasterClass() const override { return GetStaticBroadcasterClass(); } diff --git a/lldb/include/lldb/Symbol/CompilerDecl.h b/lldb/include/lldb/Symbol/CompilerDecl.h index 825a4f15836fce8aa7bca038cc54a67ffe1fd02d..5c99cae3781c58b7d592a6dd6899f580d2b6f604 100644 --- a/lldb/include/lldb/Symbol/CompilerDecl.h +++ b/lldb/include/lldb/Symbol/CompilerDecl.h @@ -73,6 +73,9 @@ public: CompilerDeclContext GetDeclContext() const; + // If this decl has a type, return it. + CompilerType GetType() const; + // If this decl represents a function, return the return type CompilerType GetFunctionReturnType() const; @@ -91,6 +94,10 @@ public: /// the subsequent entry, so the topmost entry is the global namespace. std::vector GetCompilerContext() const; + // If decl represents a constant value, return it. Otherwise, return an + // invalid/empty Scalar. + Scalar GetConstantValue() const; + private: TypeSystem *m_type_system = nullptr; void *m_opaque_decl = nullptr; diff --git a/lldb/include/lldb/Symbol/CompilerType.h b/lldb/include/lldb/Symbol/CompilerType.h index b71c531f21633adef119a96c4cac45680d18f7ad..9e889a53086b2ac60b005b460eec6dd307bc4edb 100644 --- a/lldb/include/lldb/Symbol/CompilerType.h +++ b/lldb/include/lldb/Symbol/CompilerType.h @@ -416,6 +416,8 @@ public: CompilerType GetVirtualBaseClassAtIndex(size_t idx, uint32_t *bit_offset_ptr) const; + CompilerDecl GetStaticFieldWithName(llvm::StringRef name) const; + uint32_t GetIndexOfFieldWithName(const char *name, CompilerType *field_compiler_type = nullptr, uint64_t *bit_offset_ptr = nullptr, diff --git a/lldb/include/lldb/Symbol/TypeSystem.h b/lldb/include/lldb/Symbol/TypeSystem.h index 3a927d313b823da5e38ad2b69beba4902c686552..ad3b853227a9f6c8730ba6a966a2ec62276a42b9 100644 --- a/lldb/include/lldb/Symbol/TypeSystem.h +++ b/lldb/include/lldb/Symbol/TypeSystem.h @@ -27,6 +27,8 @@ #include "lldb/Symbol/CompilerDecl.h" #include "lldb/Symbol/CompilerDeclContext.h" #include "lldb/Symbol/Type.h" +#include "lldb/Utility/Scalar.h" +#include "lldb/lldb-forward.h" #include "lldb/lldb-private.h" #include "lldb/lldb-types.h" @@ -110,6 +112,8 @@ public: virtual std::vector DeclGetCompilerContext(void *opaque_decl); + virtual Scalar DeclGetConstantValue(void *opaque_decl) { return Scalar(); } + virtual CompilerType GetTypeForDecl(void *opaque_decl) = 0; // CompilerDeclContext functions @@ -339,6 +343,11 @@ public: GetVirtualBaseClassAtIndex(lldb::opaque_compiler_type_t type, size_t idx, uint32_t *bit_offset_ptr) = 0; + virtual CompilerDecl GetStaticFieldWithName(lldb::opaque_compiler_type_t type, + llvm::StringRef name) { + return CompilerDecl(); + } + virtual CompilerType GetChildCompilerTypeAtIndex( lldb::opaque_compiler_type_t type, ExecutionContext *exe_ctx, size_t idx, bool transparent_pointers, bool omit_empty_base_classes, diff --git a/lldb/include/lldb/Target/Process.h b/lldb/include/lldb/Target/Process.h index 2f3a3c22422efeca205c9a9ea33c7af5fb0fb15b..aac0cf51680a9e230adad75c73a5e58728e25661 100644 --- a/lldb/include/lldb/Target/Process.h +++ b/lldb/include/lldb/Target/Process.h @@ -381,7 +381,7 @@ public: // These two functions fill out the Broadcaster interface: - static ConstString &GetStaticBroadcasterClass(); + static llvm::StringRef GetStaticBroadcasterClass(); static constexpr llvm::StringRef AttachSynchronousHijackListenerName = "lldb.internal.Process.AttachSynchronous.hijack"; @@ -390,7 +390,7 @@ public: static constexpr llvm::StringRef ResumeSynchronousHijackListenerName = "lldb.internal.Process.ResumeSynchronous.hijack"; - ConstString &GetBroadcasterClass() const override { + llvm::StringRef GetBroadcasterClass() const override { return GetStaticBroadcasterClass(); } diff --git a/lldb/include/lldb/Target/Target.h b/lldb/include/lldb/Target/Target.h index 2c2e6b2831ccee7cc50840f9b5975bb1baeca246..cade60f3cc8cd9bd1f2b718c5e1f545a68f41830 100644 --- a/lldb/include/lldb/Target/Target.h +++ b/lldb/include/lldb/Target/Target.h @@ -499,9 +499,9 @@ public: // These two functions fill out the Broadcaster interface: - static ConstString &GetStaticBroadcasterClass(); + static llvm::StringRef GetStaticBroadcasterClass(); - ConstString &GetBroadcasterClass() const override { + llvm::StringRef GetBroadcasterClass() const override { return GetStaticBroadcasterClass(); } diff --git a/lldb/include/lldb/Target/TargetList.h b/lldb/include/lldb/Target/TargetList.h index a0bc6f1f820b848104b179560375a3f75cbe2be5..a0cddc6b2966f5737354af1df2168fbd6301ee49 100644 --- a/lldb/include/lldb/Target/TargetList.h +++ b/lldb/include/lldb/Target/TargetList.h @@ -37,9 +37,9 @@ public: // These two functions fill out the Broadcaster interface: - static ConstString &GetStaticBroadcasterClass(); + static llvm::StringRef GetStaticBroadcasterClass(); - ConstString &GetBroadcasterClass() const override { + llvm::StringRef GetBroadcasterClass() const override { return GetStaticBroadcasterClass(); } diff --git a/lldb/include/lldb/Target/Thread.h b/lldb/include/lldb/Target/Thread.h index 1efef93b17ded8cff671aef3786735056fa2d493..c17bddf4d98b85886cd53662f5c8304d58f9dafd 100644 --- a/lldb/include/lldb/Target/Thread.h +++ b/lldb/include/lldb/Target/Thread.h @@ -74,9 +74,9 @@ public: eBroadcastBitThreadSelected = (1 << 4) }; - static ConstString &GetStaticBroadcasterClass(); + static llvm::StringRef GetStaticBroadcasterClass(); - ConstString &GetBroadcasterClass() const override { + llvm::StringRef GetBroadcasterClass() const override { return GetStaticBroadcasterClass(); } diff --git a/lldb/include/lldb/Utility/Broadcaster.h b/lldb/include/lldb/Utility/Broadcaster.h index f39e677fe9ee0410653ddd28657a9ba358b5d91e..58436ddb9f26d88738d130fe653e573028890a99 100644 --- a/lldb/include/lldb/Utility/Broadcaster.h +++ b/lldb/include/lldb/Utility/Broadcaster.h @@ -39,12 +39,12 @@ namespace lldb_private { /// Debugger maintains a list of BroadcastEventSpec's and when it is made class BroadcastEventSpec { public: - BroadcastEventSpec(const ConstString &broadcaster_class, uint32_t event_bits) + BroadcastEventSpec(llvm::StringRef broadcaster_class, uint32_t event_bits) : m_broadcaster_class(broadcaster_class), m_event_bits(event_bits) {} ~BroadcastEventSpec() = default; - ConstString GetBroadcasterClass() const { return m_broadcaster_class; } + const std::string &GetBroadcasterClass() const { return m_broadcaster_class; } uint32_t GetEventBits() const { return m_event_bits; } @@ -67,7 +67,7 @@ public: bool operator<(const BroadcastEventSpec &rhs) const; private: - ConstString m_broadcaster_class; + std::string m_broadcaster_class; uint32_t m_event_bits; }; @@ -307,7 +307,7 @@ public: /// FIXME: Probably should make a ManagedBroadcaster subclass with all the /// bits needed to work with the BroadcasterManager, so that it is clearer /// how to add one. - virtual ConstString &GetBroadcasterClass() const; + virtual llvm::StringRef GetBroadcasterClass() const; lldb::BroadcasterManagerSP GetManager(); diff --git a/lldb/packages/Python/lldbsuite/test/tools/lldb-dap/dap_server.py b/lldb/packages/Python/lldbsuite/test/tools/lldb-dap/dap_server.py index 27a76a652f4063c1a78975a39a840f49bb3623cf..5838281bcb1a10fb73f0efedffc9f5bbd1f67d6c 100644 --- a/lldb/packages/Python/lldbsuite/test/tools/lldb-dap/dap_server.py +++ b/lldb/packages/Python/lldbsuite/test/tools/lldb-dap/dap_server.py @@ -811,23 +811,34 @@ class DebugCommunication(object): command_dict = {"command": "next", "type": "request", "arguments": args_dict} return self.send_recv(command_dict) - def request_stepIn(self, threadId): + def request_stepIn(self, threadId, targetId): if self.exit_status is not None: - raise ValueError("request_continue called after process exited") - args_dict = {"threadId": threadId} + raise ValueError("request_stepIn called after process exited") + args_dict = {"threadId": threadId, "targetId": targetId} command_dict = {"command": "stepIn", "type": "request", "arguments": args_dict} return self.send_recv(command_dict) + def request_stepInTargets(self, frameId): + if self.exit_status is not None: + raise ValueError("request_stepInTargets called after process exited") + args_dict = {"frameId": frameId} + command_dict = { + "command": "stepInTargets", + "type": "request", + "arguments": args_dict, + } + return self.send_recv(command_dict) + def request_stepOut(self, threadId): if self.exit_status is not None: - raise ValueError("request_continue called after process exited") + raise ValueError("request_stepOut called after process exited") args_dict = {"threadId": threadId} command_dict = {"command": "stepOut", "type": "request", "arguments": args_dict} return self.send_recv(command_dict) def request_pause(self, threadId=None): if self.exit_status is not None: - raise ValueError("request_continue called after process exited") + raise ValueError("request_pause called after process exited") if threadId is None: threadId = self.get_thread_id() args_dict = {"threadId": threadId} diff --git a/lldb/packages/Python/lldbsuite/test/tools/lldb-dap/lldbdap_testcase.py b/lldb/packages/Python/lldbsuite/test/tools/lldb-dap/lldbdap_testcase.py index 23f650d2d36fddfa3210a82d21ae01bbe25f8b82..d56ea5dca14beb8dcc692edcc880bf14270f4d88 100644 --- a/lldb/packages/Python/lldbsuite/test/tools/lldb-dap/lldbdap_testcase.py +++ b/lldb/packages/Python/lldbsuite/test/tools/lldb-dap/lldbdap_testcase.py @@ -218,8 +218,8 @@ class DAPTestCaseBase(TestBase): """Set a top level global variable only.""" return self.dap_server.request_setVariable(2, name, str(value), id=id) - def stepIn(self, threadId=None, waitForStop=True): - self.dap_server.request_stepIn(threadId=threadId) + def stepIn(self, threadId=None, targetId=None, waitForStop=True): + self.dap_server.request_stepIn(threadId=threadId, targetId=targetId) if waitForStop: return self.dap_server.wait_for_stopped() return None diff --git a/lldb/source/API/SBCommandInterpreter.cpp b/lldb/source/API/SBCommandInterpreter.cpp index 7b87dc507e4beacc4eccca1b60d638eab17e27cc..83c0951c56db607b6bc34e54ca042fed18375d63 100644 --- a/lldb/source/API/SBCommandInterpreter.cpp +++ b/lldb/source/API/SBCommandInterpreter.cpp @@ -512,7 +512,8 @@ SBBroadcaster SBCommandInterpreter::GetBroadcaster() { const char *SBCommandInterpreter::GetBroadcasterClass() { LLDB_INSTRUMENT(); - return CommandInterpreter::GetStaticBroadcasterClass().AsCString(); + return ConstString(CommandInterpreter::GetStaticBroadcasterClass()) + .AsCString(); } const char *SBCommandInterpreter::GetArgumentTypeAsCString( diff --git a/lldb/source/API/SBCommunication.cpp b/lldb/source/API/SBCommunication.cpp index f93898718be6c09fb1836a4e624555242d1f9f50..ee33e2abd854e869552aac85cd1195c3d884975b 100644 --- a/lldb/source/API/SBCommunication.cpp +++ b/lldb/source/API/SBCommunication.cpp @@ -170,5 +170,6 @@ SBBroadcaster SBCommunication::GetBroadcaster() { const char *SBCommunication::GetBroadcasterClass() { LLDB_INSTRUMENT(); - return ThreadedCommunication::GetStaticBroadcasterClass().AsCString(); + return ConstString(ThreadedCommunication::GetStaticBroadcasterClass()) + .AsCString(); } diff --git a/lldb/source/API/SBDebugger.cpp b/lldb/source/API/SBDebugger.cpp index fbcf30e67fc1cd52d29bffc577733f5c35f40bf2..9c662dfbf4417eef86098370ebf3ad2323eee3d1 100644 --- a/lldb/source/API/SBDebugger.cpp +++ b/lldb/source/API/SBDebugger.cpp @@ -112,7 +112,7 @@ SBDebugger &SBDebugger::operator=(const SBDebugger &rhs) { const char *SBDebugger::GetBroadcasterClass() { LLDB_INSTRUMENT(); - return Debugger::GetStaticBroadcasterClass().AsCString(); + return ConstString(Debugger::GetStaticBroadcasterClass()).AsCString(); } const char *SBDebugger::GetProgressFromEvent(const lldb::SBEvent &event, diff --git a/lldb/source/API/SBEvent.cpp b/lldb/source/API/SBEvent.cpp index cc611449e25099a21aa29c6c565389128bab553c..aa9c0ff097d45666d76085c3778e9587c21a1d4f 100644 --- a/lldb/source/API/SBEvent.cpp +++ b/lldb/source/API/SBEvent.cpp @@ -95,7 +95,8 @@ const char *SBEvent::GetBroadcasterClass() const { const Event *lldb_event = get(); if (lldb_event) - return lldb_event->GetBroadcaster()->GetBroadcasterClass().AsCString(); + return ConstString(lldb_event->GetBroadcaster()->GetBroadcasterClass()) + .AsCString(); else return "unknown class"; } diff --git a/lldb/source/API/SBLineEntry.cpp b/lldb/source/API/SBLineEntry.cpp index 99a7b8fe644cb52e372a8f02915a112824eed1ee..216ea6d18eab89c42c590dce13d35dbbdf1f10cf 100644 --- a/lldb/source/API/SBLineEntry.cpp +++ b/lldb/source/API/SBLineEntry.cpp @@ -67,6 +67,21 @@ SBAddress SBLineEntry::GetEndAddress() const { return sb_address; } +SBAddress SBLineEntry::GetSameLineContiguousAddressRangeEnd( + bool include_inlined_functions) const { + LLDB_INSTRUMENT_VA(this); + + SBAddress sb_address; + if (m_opaque_up) { + AddressRange line_range = m_opaque_up->GetSameLineContiguousAddressRange( + include_inlined_functions); + + sb_address.SetAddress(line_range.GetBaseAddress()); + sb_address.OffsetAddress(line_range.GetByteSize()); + } + return sb_address; +} + bool SBLineEntry::IsValid() const { LLDB_INSTRUMENT_VA(this); return this->operator bool(); diff --git a/lldb/source/API/SBProcess.cpp b/lldb/source/API/SBProcess.cpp index b80664882ebcac8eecb8229678d816af9e5be476..c37c111c5a58e0314d854eaa5243dac2e0407dcf 100644 --- a/lldb/source/API/SBProcess.cpp +++ b/lldb/source/API/SBProcess.cpp @@ -77,7 +77,7 @@ SBProcess::~SBProcess() = default; const char *SBProcess::GetBroadcasterClassName() { LLDB_INSTRUMENT(); - return Process::GetStaticBroadcasterClass().AsCString(); + return ConstString(Process::GetStaticBroadcasterClass()).AsCString(); } const char *SBProcess::GetPluginName() { @@ -807,7 +807,7 @@ SBBroadcaster SBProcess::GetBroadcaster() const { const char *SBProcess::GetBroadcasterClass() { LLDB_INSTRUMENT(); - return Process::GetStaticBroadcasterClass().AsCString(); + return ConstString(Process::GetStaticBroadcasterClass()).AsCString(); } size_t SBProcess::ReadMemory(addr_t addr, void *dst, size_t dst_len, @@ -928,6 +928,14 @@ size_t SBProcess::WriteMemory(addr_t addr, const void *src, size_t src_len, return bytes_written; } +void SBProcess::GetStatus(SBStream &status) { + LLDB_INSTRUMENT_VA(this, status); + + ProcessSP process_sp(GetSP()); + if (process_sp) + process_sp->GetStatus(status.ref()); +} + bool SBProcess::GetDescription(SBStream &description) { LLDB_INSTRUMENT_VA(this, description); diff --git a/lldb/source/API/SBTarget.cpp b/lldb/source/API/SBTarget.cpp index cc9f1fdd76afaa5ab96810fd72ead766b1a08f25..962ce9ba83cc7764c9ecf264aa4d919bf97e3aa1 100644 --- a/lldb/source/API/SBTarget.cpp +++ b/lldb/source/API/SBTarget.cpp @@ -147,7 +147,7 @@ SBModule SBTarget::GetModuleAtIndexFromEvent(const uint32_t idx, const char *SBTarget::GetBroadcasterClassName() { LLDB_INSTRUMENT(); - return Target::GetStaticBroadcasterClass().AsCString(); + return ConstString(Target::GetStaticBroadcasterClass()).AsCString(); } bool SBTarget::IsValid() const { @@ -2011,6 +2011,30 @@ lldb::SBInstructionList SBTarget::ReadInstructions(lldb::SBAddress base_addr, return sb_instructions; } +lldb::SBInstructionList SBTarget::ReadInstructions(lldb::SBAddress start_addr, + lldb::SBAddress end_addr, + const char *flavor_string) { + LLDB_INSTRUMENT_VA(this, start_addr, end_addr, flavor_string); + + SBInstructionList sb_instructions; + + TargetSP target_sp(GetSP()); + if (target_sp) { + lldb::addr_t start_load_addr = start_addr.GetLoadAddress(*this); + lldb::addr_t end_load_addr = end_addr.GetLoadAddress(*this); + if (end_load_addr > start_load_addr) { + lldb::addr_t size = end_load_addr - start_load_addr; + + AddressRange range(start_load_addr, size); + const bool force_live_memory = true; + sb_instructions.SetDisassembler(Disassembler::DisassembleRange( + target_sp->GetArchitecture(), nullptr, flavor_string, *target_sp, + range, force_live_memory)); + } + } + return sb_instructions; +} + lldb::SBInstructionList SBTarget::GetInstructions(lldb::SBAddress base_addr, const void *buf, size_t size) { diff --git a/lldb/source/API/SBThread.cpp b/lldb/source/API/SBThread.cpp index eb9cf063802cd47b7ec773faa5897ee06f76e195..ac3e2cd25daa946a7809e20c2da030f4dd49db2b 100644 --- a/lldb/source/API/SBThread.cpp +++ b/lldb/source/API/SBThread.cpp @@ -53,7 +53,7 @@ using namespace lldb_private; const char *SBThread::GetBroadcasterClassName() { LLDB_INSTRUMENT(); - return Thread::GetStaticBroadcasterClass().AsCString(); + return ConstString(Thread::GetStaticBroadcasterClass()).AsCString(); } // Constructors diff --git a/lldb/source/API/SBType.cpp b/lldb/source/API/SBType.cpp index ac0e56303fae3ef9bf69392c61685dd8f8a16907..6cecb5c9ea810bade03cf2633a498d630648f86f 100644 --- a/lldb/source/API/SBType.cpp +++ b/lldb/source/API/SBType.cpp @@ -7,16 +7,21 @@ //===----------------------------------------------------------------------===// #include "lldb/API/SBType.h" +#include "Utils.h" #include "lldb/API/SBDefines.h" #include "lldb/API/SBModule.h" #include "lldb/API/SBStream.h" #include "lldb/API/SBTypeEnumMember.h" #include "lldb/Core/Mangled.h" +#include "lldb/Core/ValueObjectConstResult.h" +#include "lldb/Symbol/CompilerDecl.h" #include "lldb/Symbol/CompilerType.h" #include "lldb/Symbol/Type.h" #include "lldb/Symbol/TypeSystem.h" #include "lldb/Utility/ConstString.h" +#include "lldb/Utility/DataExtractor.h" #include "lldb/Utility/Instrumentation.h" +#include "lldb/Utility/Scalar.h" #include "lldb/Utility/Stream.h" #include "llvm/ADT/APSInt.h" @@ -325,6 +330,79 @@ lldb::SBTypeMemberFunction SBType::GetMemberFunctionAtIndex(uint32_t idx) { return sb_func_type; } +SBTypeStaticField::SBTypeStaticField() { LLDB_INSTRUMENT_VA(this); } + +SBTypeStaticField::SBTypeStaticField(lldb_private::CompilerDecl decl) + : m_opaque_up(decl ? std::make_unique(decl) : nullptr) {} + +SBTypeStaticField::SBTypeStaticField(const SBTypeStaticField &rhs) { + LLDB_INSTRUMENT_VA(this, rhs); + + m_opaque_up = clone(rhs.m_opaque_up); +} + +SBTypeStaticField &SBTypeStaticField::operator=(const SBTypeStaticField &rhs) { + LLDB_INSTRUMENT_VA(this, rhs); + + m_opaque_up = clone(rhs.m_opaque_up); + return *this; +} + +SBTypeStaticField::~SBTypeStaticField() { LLDB_INSTRUMENT_VA(this); } + +SBTypeStaticField::operator bool() const { + LLDB_INSTRUMENT_VA(this); + + return IsValid(); +} + +bool SBTypeStaticField::IsValid() const { + LLDB_INSTRUMENT_VA(this); + + return m_opaque_up != nullptr; +} + +const char *SBTypeStaticField::GetName() { + LLDB_INSTRUMENT_VA(this); + + if (!IsValid()) + return ""; + return m_opaque_up->GetName().GetCString(); +} + +const char *SBTypeStaticField::GetMangledName() { + LLDB_INSTRUMENT_VA(this); + + if (!IsValid()) + return ""; + return m_opaque_up->GetMangledName().GetCString(); +} + +SBType SBTypeStaticField::GetType() { + LLDB_INSTRUMENT_VA(this); + + if (!IsValid()) + return SBType(); + return SBType(m_opaque_up->GetType()); +} + +SBValue SBTypeStaticField::GetConstantValue(lldb::SBTarget target) { + LLDB_INSTRUMENT_VA(this, target); + + if (!IsValid()) + return SBValue(); + + Scalar value = m_opaque_up->GetConstantValue(); + if (!value.IsValid()) + return SBValue(); + DataExtractor data; + value.GetData(data); + auto value_obj_sp = ValueObjectConstResult::Create( + target.GetSP().get(), m_opaque_up->GetType(), m_opaque_up->GetName(), + data); + return SBValue(std::move(value_obj_sp)); +} + lldb::SBType SBType::GetUnqualifiedType() { LLDB_INSTRUMENT_VA(this); @@ -438,6 +516,16 @@ SBTypeMember SBType::GetVirtualBaseClassAtIndex(uint32_t idx) { return sb_type_member; } +SBTypeStaticField SBType::GetStaticFieldWithName(const char *name) { + LLDB_INSTRUMENT_VA(this, name); + + if (!IsValid() || !name) + return SBTypeStaticField(); + + return SBTypeStaticField(m_opaque_sp->GetCompilerType(/*prefer_dynamic=*/true) + .GetStaticFieldWithName(name)); +} + SBTypeEnumMemberList SBType::GetEnumMembers() { LLDB_INSTRUMENT_VA(this); diff --git a/lldb/source/API/SBValue.cpp b/lldb/source/API/SBValue.cpp index 94a8f3ea319e8920c1ed94cb85df89ab6152f6b4..c53ec5a746482939e5530f5a995dc41b560e9bd5 100644 --- a/lldb/source/API/SBValue.cpp +++ b/lldb/source/API/SBValue.cpp @@ -909,6 +909,25 @@ uint64_t SBValue::GetValueAsUnsigned(uint64_t fail_value) { return fail_value; } +lldb::addr_t SBValue::GetValueAsAddress() { + addr_t fail_value = LLDB_INVALID_ADDRESS; + ValueLocker locker; + lldb::ValueObjectSP value_sp(GetSP(locker)); + if (value_sp) { + bool success = true; + uint64_t ret_val = fail_value; + ret_val = value_sp->GetValueAsUnsigned(fail_value, &success); + if (!success) + return fail_value; + ProcessSP process_sp = m_opaque_sp->GetProcessSP(); + if (!process_sp) + return ret_val; + return process_sp->FixDataAddress(ret_val); + } + + return fail_value; +} + bool SBValue::MightHaveChildren() { LLDB_INSTRUMENT_VA(this); diff --git a/lldb/source/Core/Debugger.cpp b/lldb/source/Core/Debugger.cpp index 19b3cf3bbf46b152861d4f8132f34c26560cd6ea..cac4642873b772ab9f566a0f3d40b04630fc209a 100644 --- a/lldb/source/Core/Debugger.cpp +++ b/lldb/source/Core/Debugger.cpp @@ -823,8 +823,8 @@ TargetSP Debugger::FindTargetWithProcess(Process *process) { return target_sp; } -ConstString Debugger::GetStaticBroadcasterClass() { - static ConstString class_name("lldb.debugger"); +llvm::StringRef Debugger::GetStaticBroadcasterClass() { + static constexpr llvm::StringLiteral class_name("lldb.debugger"); return class_name; } @@ -846,7 +846,7 @@ Debugger::Debugger(lldb::LogOutputCallback log_callback, void *baton) m_loaded_plugins(), m_event_handler_thread(), m_io_handler_thread(), m_sync_broadcaster(nullptr, "lldb.debugger.sync"), m_broadcaster(m_broadcaster_manager_sp, - GetStaticBroadcasterClass().AsCString()), + GetStaticBroadcasterClass().str()), m_forward_listener_sp(), m_clear_once() { // Initialize the debugger properties as early as possible as other parts of // LLDB will start querying them during construction. diff --git a/lldb/source/Core/ThreadedCommunication.cpp b/lldb/source/Core/ThreadedCommunication.cpp index 7d8aae5d8ff689b96a392418472da10e385a2d95..2f3dada3ac93b198d45fcb4ac729ca4ddeb4ee22 100644 --- a/lldb/source/Core/ThreadedCommunication.cpp +++ b/lldb/source/Core/ThreadedCommunication.cpp @@ -32,8 +32,8 @@ using namespace lldb; using namespace lldb_private; -ConstString &ThreadedCommunication::GetStaticBroadcasterClass() { - static ConstString class_name("lldb.communication"); +llvm::StringRef ThreadedCommunication::GetStaticBroadcasterClass() { + static constexpr llvm::StringLiteral class_name("lldb.communication"); return class_name; } diff --git a/lldb/source/Interpreter/CommandInterpreter.cpp b/lldb/source/Interpreter/CommandInterpreter.cpp index 8c3972a2ba4ce26286869677317f6429f22295d3..4c58ecc3c1848f3d3a74f12965196c57f61d1e8b 100644 --- a/lldb/source/Interpreter/CommandInterpreter.cpp +++ b/lldb/source/Interpreter/CommandInterpreter.cpp @@ -119,15 +119,15 @@ enum { #include "InterpreterPropertiesEnum.inc" }; -ConstString &CommandInterpreter::GetStaticBroadcasterClass() { - static ConstString class_name("lldb.commandInterpreter"); +llvm::StringRef CommandInterpreter::GetStaticBroadcasterClass() { + static constexpr llvm::StringLiteral class_name("lldb.commandInterpreter"); return class_name; } CommandInterpreter::CommandInterpreter(Debugger &debugger, bool synchronous_execution) : Broadcaster(debugger.GetBroadcasterManager(), - CommandInterpreter::GetStaticBroadcasterClass().AsCString()), + CommandInterpreter::GetStaticBroadcasterClass().str()), Properties( OptionValuePropertiesSP(new OptionValueProperties("interpreter"))), IOHandlerDelegate(IOHandlerDelegate::Completion::LLDBCommand), diff --git a/lldb/source/Plugins/ExpressionParser/Clang/ASTUtils.h b/lldb/source/Plugins/ExpressionParser/Clang/ASTUtils.h index cefec15a79809d88da4c2579cbafc1bb9c954d17..17f1506036c6995d03f7b27f3ce6dc4455b45a33 100644 --- a/lldb/source/Plugins/ExpressionParser/Clang/ASTUtils.h +++ b/lldb/source/Plugins/ExpressionParser/Clang/ASTUtils.h @@ -30,7 +30,7 @@ public: ~ExternalASTSourceWrapper() override; - clang::Decl *GetExternalDecl(uint32_t ID) override { + clang::Decl *GetExternalDecl(clang::GlobalDeclID ID) override { return m_Source->GetExternalDecl(ID); } @@ -266,7 +266,7 @@ public: // ExternalASTSource. //===--------------------------------------------------------------------===// - clang::Decl *GetExternalDecl(uint32_t ID) override { + clang::Decl *GetExternalDecl(clang::GlobalDeclID ID) override { for (size_t i = 0; i < Sources.size(); ++i) if (clang::Decl *Result = Sources[i]->GetExternalDecl(ID)) return Result; diff --git a/lldb/source/Plugins/ExpressionParser/Clang/ClangASTSource.h b/lldb/source/Plugins/ExpressionParser/Clang/ClangASTSource.h index f34e4661a81ca34b6f552b21373404c82e746fce..83c910477acc8d446ec9244ca523bc15f320afec 100644 --- a/lldb/source/Plugins/ExpressionParser/Clang/ClangASTSource.h +++ b/lldb/source/Plugins/ExpressionParser/Clang/ClangASTSource.h @@ -49,7 +49,7 @@ public: ~ClangASTSource() override; /// Interface stubs. - clang::Decl *GetExternalDecl(uint32_t) override { return nullptr; } + clang::Decl *GetExternalDecl(clang::GlobalDeclID) override { return nullptr; } clang::Stmt *GetExternalDeclStmt(uint64_t) override { return nullptr; } clang::Selector GetExternalSelector(uint32_t) override { return clang::Selector(); diff --git a/lldb/source/Plugins/LanguageRuntime/ObjC/AppleObjCRuntime/AppleObjCRuntimeV2.cpp b/lldb/source/Plugins/LanguageRuntime/ObjC/AppleObjCRuntime/AppleObjCRuntimeV2.cpp index d3fc487aed4333d2b2425b516d9fe69ce74c1854..9409497f1c81ba56b3dc87903f7cf345e5509ac9 100644 --- a/lldb/source/Plugins/LanguageRuntime/ObjC/AppleObjCRuntime/AppleObjCRuntimeV2.cpp +++ b/lldb/source/Plugins/LanguageRuntime/ObjC/AppleObjCRuntime/AppleObjCRuntimeV2.cpp @@ -1869,15 +1869,15 @@ AppleObjCRuntimeV2::DynamicClassInfoExtractor::ComputeHelper( if (loader->IsFullyInitialized()) { switch (exe_ctx.GetTargetRef().GetDynamicClassInfoHelper()) { case eDynamicClassInfoHelperAuto: - LLVM_FALLTHROUGH; + [[fallthrough]]; case eDynamicClassInfoHelperGetRealizedClassList: if (m_runtime.m_has_objc_getRealizedClassList_trylock) return DynamicClassInfoExtractor::objc_getRealizedClassList_trylock; - LLVM_FALLTHROUGH; + [[fallthrough]]; case eDynamicClassInfoHelperCopyRealizedClassList: if (m_runtime.m_has_objc_copyRealizedClassList) return DynamicClassInfoExtractor::objc_copyRealizedClassList; - LLVM_FALLTHROUGH; + [[fallthrough]]; case eDynamicClassInfoHelperRealizedClassesStruct: return DynamicClassInfoExtractor::gdb_objc_realized_classes; } diff --git a/lldb/source/Plugins/Process/gdb-remote/GDBRemoteCommunicationServerLLGS.cpp b/lldb/source/Plugins/Process/gdb-remote/GDBRemoteCommunicationServerLLGS.cpp index 3d37bb226a65fdab355e4c4366da74a3d42e4a8c..ae1a77e5be8321d76a80962bfe36c09a8acc4ab6 100644 --- a/lldb/source/Plugins/Process/gdb-remote/GDBRemoteCommunicationServerLLGS.cpp +++ b/lldb/source/Plugins/Process/gdb-remote/GDBRemoteCommunicationServerLLGS.cpp @@ -2087,7 +2087,7 @@ void GDBRemoteCommunicationServerLLGS::AddProcessThreads( GDBRemoteCommunication::PacketResult GDBRemoteCommunicationServerLLGS::Handle_qfThreadInfo( StringExtractorGDBRemote &packet) { - assert(m_debugged_processes.size() == 1 || + assert(m_debugged_processes.size() <= 1 || bool(m_extensions_supported & NativeProcessProtocol::Extension::multiprocess)); diff --git a/lldb/source/Plugins/SymbolFile/CTF/SymbolFileCTF.cpp b/lldb/source/Plugins/SymbolFile/CTF/SymbolFileCTF.cpp index 65f5b1a5f1b0a2ee555a5a8540b0aa5ea9b101ca..386ba44c5ea6538c790110f3ad64eb18b3a1ad38 100644 --- a/lldb/source/Plugins/SymbolFile/CTF/SymbolFileCTF.cpp +++ b/lldb/source/Plugins/SymbolFile/CTF/SymbolFileCTF.cpp @@ -342,7 +342,7 @@ SymbolFileCTF::CreateInteger(const CTFInteger &ctf_integer) { CompilerType compiler_type = m_ast->GetBasicType(basic_type); - if (basic_type != eBasicTypeVoid) { + if (basic_type != eBasicTypeVoid && basic_type != eBasicTypeBool) { // Make sure the type we got is an integer type. bool compiler_type_is_signed = false; if (!compiler_type.IsIntegerType(compiler_type_is_signed)) @@ -802,7 +802,8 @@ size_t SymbolFileCTF::ParseFunctions(CompileUnit &cu) { } Type *arg_type = ResolveTypeUID(arg_uid); - arg_types.push_back(arg_type->GetFullCompilerType()); + arg_types.push_back(arg_type ? arg_type->GetFullCompilerType() + : CompilerType()); } if (symbol) { @@ -813,8 +814,9 @@ size_t SymbolFileCTF::ParseFunctions(CompileUnit &cu) { // Create function type. CompilerType func_type = m_ast->CreateFunctionType( - ret_type->GetFullCompilerType(), arg_types.data(), arg_types.size(), - is_variadic, 0, clang::CallingConv::CC_C); + ret_type ? ret_type->GetFullCompilerType() : CompilerType(), + arg_types.data(), arg_types.size(), is_variadic, 0, + clang::CallingConv::CC_C); lldb::user_id_t function_type_uid = m_types.size() + 1; TypeSP type_sp = MakeType(function_type_uid, symbol->GetName(), 0, nullptr, diff --git a/lldb/source/Plugins/SymbolFile/DWARF/DWARFASTParserClang.cpp b/lldb/source/Plugins/SymbolFile/DWARF/DWARFASTParserClang.cpp index 41d81fbcf1b08744949a7d72f4bc07735ecd6ac7..12dafd3f5d5d5195700747cb85536d13b1414322 100644 --- a/lldb/source/Plugins/SymbolFile/DWARF/DWARFASTParserClang.cpp +++ b/lldb/source/Plugins/SymbolFile/DWARF/DWARFASTParserClang.cpp @@ -495,6 +495,7 @@ TypeSP DWARFASTParserClang::ParseTypeFromDWARF(const SymbolContext &sc, case DW_TAG_const_type: case DW_TAG_restrict_type: case DW_TAG_volatile_type: + case DW_TAG_LLVM_ptrauth_type: case DW_TAG_atomic_type: case DW_TAG_unspecified_type: { type_sp = ParseTypeModifier(sc, die, attrs); diff --git a/lldb/source/Plugins/TypeSystem/Clang/TypeSystemClang.cpp b/lldb/source/Plugins/TypeSystem/Clang/TypeSystemClang.cpp index 2621f682011b41e5cb715d0a75c2192b60e348dc..8fc0f9103f55416e46b8188006257afef7e0a2b5 100644 --- a/lldb/source/Plugins/TypeSystem/Clang/TypeSystemClang.cpp +++ b/lldb/source/Plugins/TypeSystem/Clang/TypeSystemClang.cpp @@ -9,6 +9,7 @@ #include "TypeSystemClang.h" #include "clang/AST/DeclBase.h" +#include "clang/AST/ExprCXX.h" #include "llvm/Support/Casting.h" #include "llvm/Support/FormatAdapters.h" #include "llvm/Support/FormatVariadic.h" @@ -838,8 +839,11 @@ lldb::BasicType TypeSystemClang::GetBasicTypeEnumeration(llvm::StringRef name) { {"__int128_t", eBasicTypeInt128}, {"__uint128_t", eBasicTypeUnsignedInt128}, - // Miscellaneous + // "bool" {"bool", eBasicTypeBool}, + {"_Bool", eBasicTypeBool}, + + // Miscellaneous {"float", eBasicTypeFloat}, {"double", eBasicTypeDouble}, {"long double", eBasicTypeLongDouble}, @@ -1145,6 +1149,8 @@ CompilerType TypeSystemClang::GetTypeForDecl(clang::NamedDecl *decl) { return GetTypeForDecl(interface_decl); if (clang::TagDecl *tag_decl = llvm::dyn_cast(decl)) return GetTypeForDecl(tag_decl); + if (clang::ValueDecl *value_decl = llvm::dyn_cast(decl)) + return GetTypeForDecl(value_decl); return CompilerType(); } @@ -1156,6 +1162,10 @@ CompilerType TypeSystemClang::GetTypeForDecl(ObjCInterfaceDecl *decl) { return GetType(getASTContext().getObjCInterfaceType(decl)); } +CompilerType TypeSystemClang::GetTypeForDecl(clang::ValueDecl *value_decl) { + return GetType(value_decl->getType()); +} + #pragma mark Structure, Unions, Classes void TypeSystemClang::SetOwningModule(clang::Decl *decl, @@ -1227,7 +1237,7 @@ CompilerType TypeSystemClang::CreateRecordType( // complete definition just in case. bool has_name = !name.empty(); - CXXRecordDecl *decl = CXXRecordDecl::CreateDeserialized(ast, 0); + CXXRecordDecl *decl = CXXRecordDecl::CreateDeserialized(ast, GlobalDeclID()); decl->setTagKind(static_cast(kind)); decl->setDeclContext(decl_ctx); if (has_name) @@ -1399,7 +1409,7 @@ clang::FunctionTemplateDecl *TypeSystemClang::CreateFunctionTemplateDecl( TemplateParameterList *template_param_list = CreateTemplateParameterList( ast, template_param_infos, template_param_decls); FunctionTemplateDecl *func_tmpl_decl = - FunctionTemplateDecl::CreateDeserialized(ast, 0); + FunctionTemplateDecl::CreateDeserialized(ast, GlobalDeclID()); func_tmpl_decl->setDeclContext(decl_ctx); func_tmpl_decl->setLocation(func_decl->getLocation()); func_tmpl_decl->setDeclName(func_decl->getDeclName()); @@ -1561,7 +1571,8 @@ ClassTemplateDecl *TypeSystemClang::CreateClassTemplateDecl( TemplateParameterList *template_param_list = CreateTemplateParameterList( ast, template_param_infos, template_param_decls); - CXXRecordDecl *template_cxx_decl = CXXRecordDecl::CreateDeserialized(ast, 0); + CXXRecordDecl *template_cxx_decl = + CXXRecordDecl::CreateDeserialized(ast, GlobalDeclID()); template_cxx_decl->setTagKind(static_cast(kind)); // What decl context do we use here? TU? The actual decl context? template_cxx_decl->setDeclContext(decl_ctx); @@ -1578,7 +1589,8 @@ ClassTemplateDecl *TypeSystemClang::CreateClassTemplateDecl( // template_cxx_decl->startDefinition(); // template_cxx_decl->completeDefinition(); - class_template_decl = ClassTemplateDecl::CreateDeserialized(ast, 0); + class_template_decl = + ClassTemplateDecl::CreateDeserialized(ast, GlobalDeclID()); // What decl context do we use here? TU? The actual decl context? class_template_decl->setDeclContext(decl_ctx); class_template_decl->setDeclName(decl_name); @@ -1639,7 +1651,7 @@ TypeSystemClang::CreateClassTemplateSpecializationDecl( ast, template_param_infos.GetParameterPackArgs()); } ClassTemplateSpecializationDecl *class_template_specialization_decl = - ClassTemplateSpecializationDecl::CreateDeserialized(ast, 0); + ClassTemplateSpecializationDecl::CreateDeserialized(ast, GlobalDeclID()); class_template_specialization_decl->setTagKind( static_cast(kind)); class_template_specialization_decl->setDeclContext(decl_ctx); @@ -1789,7 +1801,8 @@ CompilerType TypeSystemClang::CreateObjCClass( if (!decl_ctx) decl_ctx = ast.getTranslationUnitDecl(); - ObjCInterfaceDecl *decl = ObjCInterfaceDecl::CreateDeserialized(ast, 0); + ObjCInterfaceDecl *decl = + ObjCInterfaceDecl::CreateDeserialized(ast, GlobalDeclID()); decl->setDeclContext(decl_ctx); decl->setDeclName(&ast.Idents.get(name)); /*isForwardDecl,*/ @@ -1897,7 +1910,7 @@ TypeSystemClang::CreateBlockDeclaration(clang::DeclContext *ctx, OptionalClangModuleID owning_module) { if (ctx) { clang::BlockDecl *decl = - clang::BlockDecl::CreateDeserialized(getASTContext(), 0); + clang::BlockDecl::CreateDeserialized(getASTContext(), GlobalDeclID()); decl->setDeclContext(ctx); ctx->addDecl(decl); SetOwningModule(decl, owning_module); @@ -1966,7 +1979,7 @@ clang::VarDecl *TypeSystemClang::CreateVariableDeclaration( const char *name, clang::QualType type) { if (decl_context) { clang::VarDecl *var_decl = - clang::VarDecl::CreateDeserialized(getASTContext(), 0); + clang::VarDecl::CreateDeserialized(getASTContext(), GlobalDeclID()); var_decl->setDeclContext(decl_context); if (name && name[0]) var_decl->setDeclName(&getASTContext().Idents.getOwn(name)); @@ -2126,7 +2139,7 @@ FunctionDecl *TypeSystemClang::CreateFunctionDeclaration( clang::DeclarationName declarationName = GetDeclarationName(name, function_clang_type); - func_decl = FunctionDecl::CreateDeserialized(ast, 0); + func_decl = FunctionDecl::CreateDeserialized(ast, GlobalDeclID()); func_decl->setDeclContext(decl_ctx); func_decl->setDeclName(declarationName); func_decl->setType(ClangUtil::GetQualType(function_clang_type)); @@ -2187,7 +2200,7 @@ ParmVarDecl *TypeSystemClang::CreateParameterDeclaration( const char *name, const CompilerType ¶m_type, int storage, bool add_decl) { ASTContext &ast = getASTContext(); - auto *decl = ParmVarDecl::CreateDeserialized(ast, 0); + auto *decl = ParmVarDecl::CreateDeserialized(ast, GlobalDeclID()); decl->setDeclContext(decl_ctx); if (name && name[0]) decl->setDeclName(&ast.Idents.get(name)); @@ -2292,7 +2305,7 @@ CompilerType TypeSystemClang::CreateEnumerationType( // TODO: ask about these... // const bool IsFixed = false; - EnumDecl *enum_decl = EnumDecl::CreateDeserialized(ast, 0); + EnumDecl *enum_decl = EnumDecl::CreateDeserialized(ast, GlobalDeclID()); enum_decl->setDeclContext(decl_ctx); if (!name.empty()) enum_decl->setDeclName(&ast.Idents.get(name)); @@ -4531,7 +4544,7 @@ CompilerType TypeSystemClang::CreateTypedef( decl_ctx = getASTContext().getTranslationUnitDecl(); clang::TypedefDecl *decl = - clang::TypedefDecl::CreateDeserialized(clang_ast, 0); + clang::TypedefDecl::CreateDeserialized(clang_ast, GlobalDeclID()); decl->setDeclContext(decl_ctx); decl->setDeclName(&clang_ast.Idents.get(typedef_name)); decl->setTypeSourceInfo(clang_ast.getTrivialTypeSourceInfo(qual_type)); @@ -4848,7 +4861,7 @@ lldb::Encoding TypeSystemClang::GetEncoding(lldb::opaque_compiler_type_t type, case clang::BuiltinType::Kind::OCLQueue: case clang::BuiltinType::Kind::OCLReserveID: case clang::BuiltinType::Kind::OCLSampler: - case clang::BuiltinType::Kind::OMPArraySection: + case clang::BuiltinType::Kind::ArraySection: case clang::BuiltinType::Kind::OMPArrayShaping: case clang::BuiltinType::Kind::OMPIterator: case clang::BuiltinType::Kind::Overload: @@ -5900,6 +5913,36 @@ CompilerType TypeSystemClang::GetVirtualBaseClassAtIndex( return CompilerType(); } +CompilerDecl +TypeSystemClang::GetStaticFieldWithName(lldb::opaque_compiler_type_t type, + llvm::StringRef name) { + clang::QualType qual_type = RemoveWrappingTypes(GetCanonicalQualType(type)); + switch (qual_type->getTypeClass()) { + case clang::Type::Record: { + if (!GetCompleteType(type)) + return CompilerDecl(); + + const clang::RecordType *record_type = + llvm::cast(qual_type.getTypePtr()); + const clang::RecordDecl *record_decl = record_type->getDecl(); + + clang::DeclarationName decl_name(&getASTContext().Idents.get(name)); + for (NamedDecl *decl : record_decl->lookup(decl_name)) { + auto *var_decl = dyn_cast(decl); + if (!var_decl || var_decl->getStorageClass() != clang::SC_Static) + continue; + + return CompilerDecl(this, var_decl); + } + break; + } + + default: + break; + } + return CompilerDecl(); +} + // If a pointer to a pointee type (the clang_type arg) says that it has no // children, then we either need to trust it, or override it and return a // different result. For example, an "int *" has one child that is an integer, @@ -5970,7 +6013,7 @@ uint32_t TypeSystemClang::GetNumPointeeChildren(clang::QualType type) { case clang::BuiltinType::ARCUnbridgedCast: case clang::BuiltinType::PseudoObject: case clang::BuiltinType::BuiltinFn: - case clang::BuiltinType::OMPArraySection: + case clang::BuiltinType::ArraySection: return 1; default: return 0; @@ -7288,7 +7331,7 @@ clang::FieldDecl *TypeSystemClang::AddFieldToRecordType( clang::RecordDecl *record_decl = ast->GetAsRecordDecl(type); if (record_decl) { - field = clang::FieldDecl::CreateDeserialized(clang_ast, 0); + field = clang::FieldDecl::CreateDeserialized(clang_ast, GlobalDeclID()); field->setDeclContext(record_decl); field->setDeclName(ident); field->setType(ClangUtil::GetQualType(field_clang_type)); @@ -7335,7 +7378,8 @@ clang::FieldDecl *TypeSystemClang::AddFieldToRecordType( field_clang_type.GetCompleteType(); - auto *ivar = clang::ObjCIvarDecl::CreateDeserialized(clang_ast, 0); + auto *ivar = + clang::ObjCIvarDecl::CreateDeserialized(clang_ast, GlobalDeclID()); ivar->setDeclContext(class_interface_decl); ivar->setDeclName(ident); ivar->setType(ClangUtil::GetQualType(field_clang_type)); @@ -7501,7 +7545,8 @@ clang::VarDecl *TypeSystemClang::AddVariableToRecordType( if (!name.empty()) ident = &ast->getASTContext().Idents.get(name); - var_decl = clang::VarDecl::CreateDeserialized(ast->getASTContext(), 0); + var_decl = + clang::VarDecl::CreateDeserialized(ast->getASTContext(), GlobalDeclID()); var_decl->setDeclContext(record_decl); var_decl->setDeclName(ident); var_decl->setType(ClangUtil::GetQualType(var_type)); @@ -7602,8 +7647,8 @@ clang::CXXMethodDecl *TypeSystemClang::AddMethodToCXXRecordType( : clang::ExplicitSpecKind::ResolvedFalse); if (name.starts_with("~")) { - cxx_dtor_decl = - clang::CXXDestructorDecl::CreateDeserialized(getASTContext(), 0); + cxx_dtor_decl = clang::CXXDestructorDecl::CreateDeserialized( + getASTContext(), GlobalDeclID()); cxx_dtor_decl->setDeclContext(cxx_record_decl); cxx_dtor_decl->setDeclName( getASTContext().DeclarationNames.getCXXDestructorName( @@ -7615,7 +7660,7 @@ clang::CXXMethodDecl *TypeSystemClang::AddMethodToCXXRecordType( cxx_method_decl = cxx_dtor_decl; } else if (decl_name == cxx_record_decl->getDeclName()) { cxx_ctor_decl = clang::CXXConstructorDecl::CreateDeserialized( - getASTContext(), 0, 0); + getASTContext(), GlobalDeclID(), 0); cxx_ctor_decl->setDeclContext(cxx_record_decl); cxx_ctor_decl->setDeclName( getASTContext().DeclarationNames.getCXXConstructorName( @@ -7641,8 +7686,8 @@ clang::CXXMethodDecl *TypeSystemClang::AddMethodToCXXRecordType( if (!TypeSystemClang::CheckOverloadedOperatorKindParameterCount( is_method, op_kind, num_params)) return nullptr; - cxx_method_decl = - clang::CXXMethodDecl::CreateDeserialized(getASTContext(), 0); + cxx_method_decl = clang::CXXMethodDecl::CreateDeserialized( + getASTContext(), GlobalDeclID()); cxx_method_decl->setDeclContext(cxx_record_decl); cxx_method_decl->setDeclName( getASTContext().DeclarationNames.getCXXOperatorName(op_kind)); @@ -7653,7 +7698,8 @@ clang::CXXMethodDecl *TypeSystemClang::AddMethodToCXXRecordType( } else if (num_params == 0) { // Conversion operators don't take params... auto *cxx_conversion_decl = - clang::CXXConversionDecl::CreateDeserialized(getASTContext(), 0); + clang::CXXConversionDecl::CreateDeserialized(getASTContext(), + GlobalDeclID()); cxx_conversion_decl->setDeclContext(cxx_record_decl); cxx_conversion_decl->setDeclName( getASTContext().DeclarationNames.getCXXConversionFunctionName( @@ -7668,8 +7714,8 @@ clang::CXXMethodDecl *TypeSystemClang::AddMethodToCXXRecordType( } if (cxx_method_decl == nullptr) { - cxx_method_decl = - clang::CXXMethodDecl::CreateDeserialized(getASTContext(), 0); + cxx_method_decl = clang::CXXMethodDecl::CreateDeserialized( + getASTContext(), GlobalDeclID()); cxx_method_decl->setDeclContext(cxx_record_decl); cxx_method_decl->setDeclName(decl_name); cxx_method_decl->setType(method_qual_type); @@ -7852,7 +7898,7 @@ bool TypeSystemClang::AddObjCClassProperty( ClangUtil::GetQualType(property_clang_type)); clang::ObjCPropertyDecl *property_decl = - clang::ObjCPropertyDecl::CreateDeserialized(clang_ast, 0); + clang::ObjCPropertyDecl::CreateDeserialized(clang_ast, GlobalDeclID()); property_decl->setDeclContext(class_interface_decl); property_decl->setDeclName(&clang_ast.Idents.get(property_name)); property_decl->setType(ivar_decl @@ -7941,7 +7987,8 @@ bool TypeSystemClang::AddObjCClassProperty( clang::ObjCImplementationControl::None; const bool HasRelatedResultType = false; - getter = clang::ObjCMethodDecl::CreateDeserialized(clang_ast, 0); + getter = + clang::ObjCMethodDecl::CreateDeserialized(clang_ast, GlobalDeclID()); getter->setDeclName(getter_sel); getter->setReturnType(ClangUtil::GetQualType(property_clang_type_to_access)); getter->setDeclContext(class_interface_decl); @@ -7983,7 +8030,8 @@ bool TypeSystemClang::AddObjCClassProperty( clang::ObjCImplementationControl::None; const bool HasRelatedResultType = false; - setter = clang::ObjCMethodDecl::CreateDeserialized(clang_ast, 0); + setter = + clang::ObjCMethodDecl::CreateDeserialized(clang_ast, GlobalDeclID()); setter->setDeclName(setter_sel); setter->setReturnType(result_type); setter->setDeclContext(class_interface_decl); @@ -8111,7 +8159,8 @@ clang::ObjCMethodDecl *TypeSystemClang::AddMethodToObjCObjectType( return nullptr; // some debug information is corrupt. We are not going to // deal with it. - auto *objc_method_decl = clang::ObjCMethodDecl::CreateDeserialized(ast, 0); + auto *objc_method_decl = + clang::ObjCMethodDecl::CreateDeserialized(ast, GlobalDeclID()); objc_method_decl->setDeclName(method_selector); objc_method_decl->setReturnType(method_function_prototype->getReturnType()); objc_method_decl->setDeclContext( @@ -8357,7 +8406,8 @@ clang::EnumConstantDecl *TypeSystemClang::AddEnumerationValueToEnumerationType( return nullptr; clang::EnumConstantDecl *enumerator_decl = - clang::EnumConstantDecl::CreateDeserialized(getASTContext(), 0); + clang::EnumConstantDecl::CreateDeserialized(getASTContext(), + GlobalDeclID()); enumerator_decl->setDeclContext(enutype->getDecl()); if (name && name[0]) enumerator_decl->setDeclName(&getASTContext().Idents.get(name)); @@ -9074,6 +9124,21 @@ CompilerType TypeSystemClang::DeclGetFunctionArgumentType(void *opaque_decl, return CompilerType(); } +Scalar TypeSystemClang::DeclGetConstantValue(void *opaque_decl) { + clang::Decl *decl = static_cast(opaque_decl); + clang::VarDecl *var_decl = llvm::dyn_cast(decl); + if (!var_decl) + return Scalar(); + clang::Expr *init_expr = var_decl->getInit(); + if (!init_expr) + return Scalar(); + std::optional value = + init_expr->getIntegerConstantExpr(getASTContext()); + if (!value) + return Scalar(); + return Scalar(*value); +} + // CompilerDeclContext functions std::vector TypeSystemClang::DeclContextFindDeclByName( diff --git a/lldb/source/Plugins/TypeSystem/Clang/TypeSystemClang.h b/lldb/source/Plugins/TypeSystem/Clang/TypeSystemClang.h index 68b82e9688f12b5a6afe2184632e926149065e1b..62f14df7638dce2a650fa5efe451f516381c7812 100644 --- a/lldb/source/Plugins/TypeSystem/Clang/TypeSystemClang.h +++ b/lldb/source/Plugins/TypeSystem/Clang/TypeSystemClang.h @@ -22,6 +22,7 @@ #include "clang/AST/ASTContext.h" #include "clang/AST/ASTFwd.h" +#include "clang/AST/Decl.h" #include "clang/AST/TemplateBase.h" #include "clang/AST/Type.h" #include "clang/Basic/TargetInfo.h" @@ -251,6 +252,8 @@ public: CompilerType GetTypeForDecl(clang::ObjCInterfaceDecl *objc_decl); + CompilerType GetTypeForDecl(clang::ValueDecl *value_decl); + template CompilerType GetTypeForIdentifier(llvm::StringRef type_name, @@ -559,6 +562,8 @@ public: std::vector DeclGetCompilerContext(void *opaque_decl) override; + Scalar DeclGetConstantValue(void *opaque_decl) override; + CompilerType GetTypeForDecl(void *opaque_decl) override; // CompilerDeclContext override functions @@ -868,6 +873,9 @@ public: size_t idx, uint32_t *bit_offset_ptr) override; + CompilerDecl GetStaticFieldWithName(lldb::opaque_compiler_type_t type, + llvm::StringRef name) override; + static uint32_t GetNumPointeeChildren(clang::QualType type); CompilerType GetChildCompilerTypeAtIndex( diff --git a/lldb/source/Symbol/CompilerDecl.cpp b/lldb/source/Symbol/CompilerDecl.cpp index 0eb630e5b9e1137b189d25eff0e03770615224e2..5fa0a32f041ad7d496a9ad525945520bf24220d7 100644 --- a/lldb/source/Symbol/CompilerDecl.cpp +++ b/lldb/source/Symbol/CompilerDecl.cpp @@ -9,6 +9,7 @@ #include "lldb/Symbol/CompilerDecl.h" #include "lldb/Symbol/CompilerDeclContext.h" #include "lldb/Symbol/TypeSystem.h" +#include "lldb/Utility/Scalar.h" using namespace lldb_private; @@ -24,6 +25,10 @@ CompilerDeclContext CompilerDecl::GetDeclContext() const { return m_type_system->DeclGetDeclContext(m_opaque_decl); } +CompilerType CompilerDecl::GetType() const { + return m_type_system->GetTypeForDecl(m_opaque_decl); +} + CompilerType CompilerDecl::GetFunctionReturnType() const { return m_type_system->DeclGetFunctionReturnType(m_opaque_decl); } @@ -52,3 +57,7 @@ std::vector CompilerDecl::GetCompilerContext() const { return m_type_system->DeclGetCompilerContext(m_opaque_decl); } + +Scalar CompilerDecl::GetConstantValue() const { + return m_type_system->DeclGetConstantValue(m_opaque_decl); +} diff --git a/lldb/source/Symbol/CompilerType.cpp b/lldb/source/Symbol/CompilerType.cpp index 96e74b890d2d90ab80f9191022707a0cfb138b56..9523fb6ea77c20d2df5cf28142c321077b5857a0 100644 --- a/lldb/source/Symbol/CompilerType.cpp +++ b/lldb/source/Symbol/CompilerType.cpp @@ -849,6 +849,12 @@ CompilerType::GetVirtualBaseClassAtIndex(size_t idx, return CompilerType(); } +CompilerDecl CompilerType::GetStaticFieldWithName(llvm::StringRef name) const { + if (IsValid()) + return GetTypeSystem()->GetStaticFieldWithName(m_type, name); + return CompilerDecl(); +} + uint32_t CompilerType::GetIndexOfFieldWithName( const char *name, CompilerType *field_compiler_type_ptr, uint64_t *bit_offset_ptr, uint32_t *bitfield_bit_size_ptr, diff --git a/lldb/source/Target/Process.cpp b/lldb/source/Target/Process.cpp index 606518ca5412671643c99afcffda927e72d822a1..30c240b064b59ce10c8abd11ecf5d49007b51992 100644 --- a/lldb/source/Target/Process.cpp +++ b/lldb/source/Target/Process.cpp @@ -408,8 +408,8 @@ ProcessSP Process::FindPlugin(lldb::TargetSP target_sp, return process_sp; } -ConstString &Process::GetStaticBroadcasterClass() { - static ConstString class_name("lldb.process"); +llvm::StringRef Process::GetStaticBroadcasterClass() { + static constexpr llvm::StringLiteral class_name("lldb.process"); return class_name; } @@ -423,7 +423,7 @@ Process::Process(lldb::TargetSP target_sp, ListenerSP listener_sp, const UnixSignalsSP &unix_signals_sp) : ProcessProperties(this), Broadcaster((target_sp->GetDebugger().GetBroadcasterManager()), - Process::GetStaticBroadcasterClass().AsCString()), + Process::GetStaticBroadcasterClass().str()), m_target_wp(target_sp), m_public_state(eStateUnloaded), m_private_state(eStateUnloaded), m_private_state_broadcaster(nullptr, diff --git a/lldb/source/Target/Target.cpp b/lldb/source/Target/Target.cpp index 09b0ac42631d1a3529e5e02a6b5c72bf69898bd5..aa4895bb5a6d653cdadc4798f496c4c0ecf9bf5b 100644 --- a/lldb/source/Target/Target.cpp +++ b/lldb/source/Target/Target.cpp @@ -87,8 +87,8 @@ const Target::Arch &Target::Arch::operator=(const ArchSpec &spec) { return *this; } -ConstString &Target::GetStaticBroadcasterClass() { - static ConstString class_name("lldb.target"); +llvm::StringRef Target::GetStaticBroadcasterClass() { + static constexpr llvm::StringLiteral class_name("lldb.target"); return class_name; } @@ -96,7 +96,7 @@ Target::Target(Debugger &debugger, const ArchSpec &target_arch, const lldb::PlatformSP &platform_sp, bool is_dummy_target) : TargetProperties(this), Broadcaster(debugger.GetBroadcasterManager(), - Target::GetStaticBroadcasterClass().AsCString()), + Target::GetStaticBroadcasterClass().str()), ExecutionContextScope(), m_debugger(debugger), m_platform_sp(platform_sp), m_mutex(), m_arch(target_arch), m_images(this), m_section_load_history(), m_breakpoint_list(false), m_internal_breakpoint_list(true), diff --git a/lldb/source/Target/TargetList.cpp b/lldb/source/Target/TargetList.cpp index b5d308739d0facdbd78d8d3eb9eec5bdd17d0d44..10467753666f8814065d6af4f784def11db2deed 100644 --- a/lldb/source/Target/TargetList.cpp +++ b/lldb/source/Target/TargetList.cpp @@ -29,15 +29,15 @@ using namespace lldb; using namespace lldb_private; -ConstString &TargetList::GetStaticBroadcasterClass() { - static ConstString class_name("lldb.targetList"); +llvm::StringRef TargetList::GetStaticBroadcasterClass() { + static constexpr llvm::StringLiteral class_name("lldb.targetList"); return class_name; } // TargetList constructor TargetList::TargetList(Debugger &debugger) : Broadcaster(debugger.GetBroadcasterManager(), - TargetList::GetStaticBroadcasterClass().AsCString()), + TargetList::GetStaticBroadcasterClass().str()), m_target_list(), m_target_list_mutex(), m_selected_target_idx(0) { CheckInWithManager(); } diff --git a/lldb/source/Target/Thread.cpp b/lldb/source/Target/Thread.cpp index 412e44ede9c13b4eb2114ce9932291d0dad1f62b..e75f5a356cec2fe02133ddd7e3262ebd44d7f84e 100644 --- a/lldb/source/Target/Thread.cpp +++ b/lldb/source/Target/Thread.cpp @@ -205,15 +205,15 @@ Thread::ThreadEventData::GetStackFrameFromEvent(const Event *event_ptr) { // Thread class -ConstString &Thread::GetStaticBroadcasterClass() { - static ConstString class_name("lldb.thread"); +llvm::StringRef Thread::GetStaticBroadcasterClass() { + static constexpr llvm::StringLiteral class_name("lldb.thread"); return class_name; } Thread::Thread(Process &process, lldb::tid_t tid, bool use_invalid_index_id) : ThreadProperties(false), UserID(tid), Broadcaster(process.GetTarget().GetDebugger().GetBroadcasterManager(), - Thread::GetStaticBroadcasterClass().AsCString()), + Thread::GetStaticBroadcasterClass().str()), m_process_wp(process.shared_from_this()), m_stop_info_sp(), m_stop_info_stop_id(0), m_stop_info_override_stop_id(0), m_should_run_before_public_stop(false), diff --git a/lldb/source/Utility/Broadcaster.cpp b/lldb/source/Utility/Broadcaster.cpp index 12903edc36b1b98675ec5d3bde2c4a8a8b3c5a3a..bd65ffd86a1d0f0d69a7ab6d3b4011086904dfe8 100644 --- a/lldb/source/Utility/Broadcaster.cpp +++ b/lldb/source/Utility/Broadcaster.cpp @@ -373,8 +373,8 @@ void Broadcaster::BroadcasterImpl::RestoreBroadcaster() { m_hijacking_masks.pop_back(); } -ConstString &Broadcaster::GetBroadcasterClass() const { - static ConstString class_name("lldb.anonymous"); +llvm::StringRef Broadcaster::GetBroadcasterClass() const { + static constexpr llvm::StringLiteral class_name("lldb.anonymous"); return class_name; } diff --git a/lldb/test/API/clear-sbvalue-nonaddressable-bits/Makefile b/lldb/test/API/clear-sbvalue-nonaddressable-bits/Makefile new file mode 100644 index 0000000000000000000000000000000000000000..10495940055b63d2b69fd0ee465e69dad1889d2f --- /dev/null +++ b/lldb/test/API/clear-sbvalue-nonaddressable-bits/Makefile @@ -0,0 +1,3 @@ +C_SOURCES := main.c + +include Makefile.rules diff --git a/lldb/test/API/clear-sbvalue-nonaddressable-bits/TestClearSBValueNonAddressableBits.py b/lldb/test/API/clear-sbvalue-nonaddressable-bits/TestClearSBValueNonAddressableBits.py new file mode 100644 index 0000000000000000000000000000000000000000..382b0e7a81d231ed49eed5ee9e0fca8bd80065a5 --- /dev/null +++ b/lldb/test/API/clear-sbvalue-nonaddressable-bits/TestClearSBValueNonAddressableBits.py @@ -0,0 +1,59 @@ +"""Test that SBValue clears non-addressable bits""" + +import lldb +from lldbsuite.test.decorators import * +from lldbsuite.test.lldbtest import * +from lldbsuite.test import lldbutil + + +class TestClearSBValueNonAddressableBits(TestBase): + NO_DEBUG_INFO_TESTCASE = True + + # On AArch64 systems, the top bits that are not used for + # addressing may be used for TBI, MTE, and/or pointer + # authentication. + @skipIf(archs=no_match(["aarch64", "arm64", "arm64e"])) + + # Only run this test on systems where TBI is known to be + # enabled, so the address mask will clear the TBI bits. + @skipUnlessPlatform(["linux"] + lldbplatformutil.getDarwinOSTriples()) + def test(self): + self.source = "main.c" + self.build() + (target, process, thread, bkpt) = lldbutil.run_to_source_breakpoint( + self, "break here", lldb.SBFileSpec(self.source, False) + ) + + if self.TraceOn(): + self.runCmd("frame variable") + self.runCmd("frame variable &count &global") + + frame = thread.GetFrameAtIndex(0) + + count_p = frame.FindVariable("count_p") + count_invalid_p = frame.FindVariable("count_invalid_p") + self.assertEqual( + count_p.GetValueAsUnsigned(), count_invalid_p.GetValueAsAddress() + ) + self.assertNotEqual( + count_invalid_p.GetValueAsUnsigned(), count_invalid_p.GetValueAsAddress() + ) + self.assertEqual(5, count_p.Dereference().GetValueAsUnsigned()) + self.assertEqual(5, count_invalid_p.Dereference().GetValueAsUnsigned()) + + global_p = frame.FindVariable("global_p") + global_invalid_p = frame.FindVariable("global_invalid_p") + self.assertEqual( + global_p.GetValueAsUnsigned(), global_invalid_p.GetValueAsAddress() + ) + self.assertNotEqual( + global_invalid_p.GetValueAsUnsigned(), global_invalid_p.GetValueAsAddress() + ) + self.assertEqual(10, global_p.Dereference().GetValueAsUnsigned()) + self.assertEqual(10, global_invalid_p.Dereference().GetValueAsUnsigned()) + + main_p = frame.FindVariable("main_p") + main_invalid_p = frame.FindVariable("main_invalid_p") + self.assertEqual( + main_p.GetValueAsUnsigned(), main_invalid_p.GetValueAsAddress() + ) diff --git a/lldb/test/API/clear-sbvalue-nonaddressable-bits/main.c b/lldb/test/API/clear-sbvalue-nonaddressable-bits/main.c new file mode 100644 index 0000000000000000000000000000000000000000..1b0e42c50dd6785df304f19ca25f9f8d026bb34d --- /dev/null +++ b/lldb/test/API/clear-sbvalue-nonaddressable-bits/main.c @@ -0,0 +1,27 @@ +#include + +int global = 10; + +int main() { + int count = 5; + int *count_p = &count; + + // Add some metadata in the top byte (this will crash unless the + // test is running with TBI enabled, but we won't dereference it) + + intptr_t scratch = (intptr_t)count_p; + scratch |= (3ULL << 60); + int *count_invalid_p = (int *)scratch; + + int (*main_p)() = main; + scratch = (intptr_t)main_p; + scratch |= (3ULL << 60); + int (*main_invalid_p)() = (int (*)())scratch; + + int *global_p = &global; + scratch = (intptr_t)global_p; + scratch |= (3ULL << 60); + int *global_invalid_p = (int *)scratch; + + return count; // break here +} diff --git a/lldb/test/API/macosx/ctf/Makefile b/lldb/test/API/macosx/ctf/Makefile index afe6ab1b5db06b05b8a62b8700a60473f7f7b57f..0857e234837e543811bb2c68f7ab82c59634b587 100644 --- a/lldb/test/API/macosx/ctf/Makefile +++ b/lldb/test/API/macosx/ctf/Makefile @@ -4,7 +4,7 @@ MAKE_DSYM := YES ifeq "$(COMPRESS_CTF)" "YES" COMPRESS := -c else - COMPRESS := + COMPRESS := endif all: a.out a.ctf diff --git a/lldb/test/API/macosx/ctf/TestCTF.py b/lldb/test/API/macosx/ctf/TestCTF.py index f5fd29f6ed968f7b74102b0cde0a7435605cea51..fed3a8886dd30c4f17a9ed7ad4974edbf8368a05 100644 --- a/lldb/test/API/macosx/ctf/TestCTF.py +++ b/lldb/test/API/macosx/ctf/TestCTF.py @@ -53,6 +53,7 @@ class TestCTF(TestBase): "[2] = 'b'", "[3] = 'c'", 'u = (i = 1, s = "")', + "b = false", "f = 0x0000000000000000", ], ) diff --git a/lldb/test/API/macosx/ctf/test.c b/lldb/test/API/macosx/ctf/test.c index 358006646e766e6a7af15ca333592152eb3e765c..a15f7a5161334f098710443f98872e1dd650a60a 100644 --- a/lldb/test/API/macosx/ctf/test.c +++ b/lldb/test/API/macosx/ctf/test.c @@ -1,3 +1,4 @@ +#include #include struct ForwardDecl; @@ -24,6 +25,7 @@ typedef struct MyNestedStruct { char a[4]; MyEnumT e; MyUnionT u; + _Bool b; } MyNestedStructT; typedef struct MyStruct { @@ -54,6 +56,7 @@ void populate(MyInt i) { foo.n.a[2] = 'c'; foo.n.a[3] = 'd'; foo.n.e = eOne; + foo.n.b = false; foo.f = NULL; forward = NULL; bar.b = i; diff --git a/lldb/test/API/python_api/type/TestTypeList.py b/lldb/test/API/python_api/type/TestTypeList.py index c647c2bcdccb6f8a42cadeb27df7457c7b5a180f..81c44f7a39d61ae38e04e4cb11a74823ccc7948e 100644 --- a/lldb/test/API/python_api/type/TestTypeList.py +++ b/lldb/test/API/python_api/type/TestTypeList.py @@ -33,6 +33,32 @@ class TypeAndTypeListTestCase(TestBase): self.assertTrue(pointer_masks2_type) self.DebugSBType(pointer_masks2_type) + def _find_static_field_in_Task_pointer(self, task_pointer): + self.assertTrue(task_pointer) + self.DebugSBType(task_pointer) + + task_type = task_pointer.GetPointeeType() + self.assertTrue(task_type) + self.DebugSBType(task_type) + + static_constexpr_field = task_type.GetStaticFieldWithName( + "static_constexpr_field" + ) + self.assertTrue(static_constexpr_field) + self.assertEqual(static_constexpr_field.GetName(), "static_constexpr_field") + self.assertEqual(static_constexpr_field.GetType().GetName(), "const long") + + value = static_constexpr_field.GetConstantValue(self.target()) + self.DebugSBValue(value) + self.assertEqual(value.GetValueAsSigned(), 47) + + static_mutable_field = task_type.GetStaticFieldWithName("static_mutable_field") + self.assertTrue(static_mutable_field) + self.assertEqual(static_mutable_field.GetName(), "static_mutable_field") + self.assertEqual(static_mutable_field.GetType().GetName(), "int") + + self.assertFalse(static_mutable_field.GetConstantValue(self.target())) + @skipIf(compiler="clang", compiler_version=["<", "17.0"]) def test(self): """Exercise SBType and SBTypeList API.""" @@ -175,6 +201,13 @@ class TypeAndTypeListTestCase(TestBase): frame0.EvaluateExpression("pointer").GetType() ) + self._find_static_field_in_Task_pointer( + frame0.FindVariable("task_head").GetType() + ) + self._find_static_field_in_Task_pointer( + frame0.EvaluateExpression("task_head").GetType() + ) + # We'll now get the child member 'id' from 'task_head'. id = task_head.GetChildMemberWithName("id") self.DebugSBValue(id) diff --git a/lldb/test/API/python_api/type/main.cpp b/lldb/test/API/python_api/type/main.cpp index 391f58e3e5871c8fd7cc64220fdef14d9d126fc1..c86644d918279a4133b67fd6d9be1b8d2482a137 100644 --- a/lldb/test/API/python_api/type/main.cpp +++ b/lldb/test/API/python_api/type/main.cpp @@ -27,12 +27,15 @@ public: enum E : unsigned char {} e; union U { } u; + static constexpr long static_constexpr_field = 47; + static int static_mutable_field; Task(int i, Task *n): id(i), next(n), type(TASK_TYPE_1) {} }; +int Task::static_mutable_field = 42; template struct PointerInfo { enum Masks1 { pointer_mask }; diff --git a/lldb/test/API/tools/lldb-dap/console/TestDAP_console.py b/lldb/test/API/tools/lldb-dap/console/TestDAP_console.py index ffa0dc943e0693315fbcb4c5f63be655621628a6..8f456aaf890c7fbe23d016125e4ce29d9b957718 100644 --- a/lldb/test/API/tools/lldb-dap/console/TestDAP_console.py +++ b/lldb/test/API/tools/lldb-dap/console/TestDAP_console.py @@ -4,11 +4,23 @@ Test lldb-dap setBreakpoints request import dap_server import lldbdap_testcase +import psutil +from collections import deque from lldbsuite.test import lldbutil from lldbsuite.test.decorators import * from lldbsuite.test.lldbtest import * +def get_subprocess(process_name): + queue = deque([psutil.Process(os.getpid())]) + while queue: + process = queue.popleft() + if process.name() == process_name: + return process + queue.extend(process.children()) + + self.assertTrue(False, "No subprocess with name %s found" % process_name) + class TestDAP_console(lldbdap_testcase.DAPTestCaseBase): def check_lldb_command( self, lldb_command, contains_string, assert_msg, command_escape_prefix="`" @@ -104,3 +116,49 @@ class TestDAP_console(lldbdap_testcase.DAPTestCaseBase): "Help can be invoked", command_escape_prefix="", ) + + @skipIfWindows + @skipIfRemote + def test_exit_status_message_sigterm(self): + source = "main.cpp" + program = self.getBuildArtifact("a.out") + self.build_and_launch(program, commandEscapePrefix="") + breakpoint1_line = line_number(source, "// breakpoint 1") + breakpoint_ids = self.set_source_breakpoints(source, [breakpoint1_line]) + self.continue_to_breakpoints(breakpoint_ids) + + # Kill lldb-server process. + process_name = ( + "debugserver" if platform.system() in ["Darwin"] else "lldb-server" + ) + process = get_subprocess(process_name) + process.terminate() + process.wait() + + # Get the console output + console_output = self.collect_console(1.0) + + # Verify the exit status message is printed. + self.assertIn( + "exited with status = -1 (0xffffffff) debugserver died with signal SIGTERM", + console_output, + "Exit status does not contain message 'exited with status'", + ) + + @skipIfWindows + @skipIfRemote + def test_exit_status_message_ok(self): + source = "main.cpp" + program = self.getBuildArtifact("a.out") + self.build_and_launch(program, commandEscapePrefix="") + self.continue_to_exit() + + # Get the console output + console_output = self.collect_console(1.0) + + # Verify the exit status message is printed. + self.assertIn( + "exited with status = 0 (0x00000000)", + console_output, + "Exit status does not contain message 'exited with status'", + ) diff --git a/lldb/test/API/tools/lldb-dap/stepInTargets/Makefile b/lldb/test/API/tools/lldb-dap/stepInTargets/Makefile new file mode 100644 index 0000000000000000000000000000000000000000..f772575cd5613b9650773148604d2c1c81c6c675 --- /dev/null +++ b/lldb/test/API/tools/lldb-dap/stepInTargets/Makefile @@ -0,0 +1,6 @@ + +ENABLE_THREADS := YES + +CXX_SOURCES := main.cpp + +include Makefile.rules diff --git a/lldb/test/API/tools/lldb-dap/stepInTargets/TestDAP_stepInTargets.py b/lldb/test/API/tools/lldb-dap/stepInTargets/TestDAP_stepInTargets.py new file mode 100644 index 0000000000000000000000000000000000000000..6296f6554d07e55df76a1301ae86b203a1dd0d0b --- /dev/null +++ b/lldb/test/API/tools/lldb-dap/stepInTargets/TestDAP_stepInTargets.py @@ -0,0 +1,68 @@ +""" +Test lldb-dap stepInTargets request +""" + +import dap_server +from lldbsuite.test.decorators import * +from lldbsuite.test.lldbtest import * +import lldbdap_testcase +from lldbsuite.test import lldbutil + + +class TestDAP_stepInTargets(lldbdap_testcase.DAPTestCaseBase): + @skipIf( + archs=no_match(["x86_64"]) + ) # InstructionControlFlowKind for ARM is not supported yet. + def test_basic(self): + """ + Tests the basic stepping in targets with directly calls. + """ + program = self.getBuildArtifact("a.out") + self.build_and_launch(program) + source = "main.cpp" + + breakpoint_line = line_number(source, "// set breakpoint here") + lines = [breakpoint_line] + # Set breakpoint in the thread function so we can step the threads + breakpoint_ids = self.set_source_breakpoints(source, lines) + self.assertEqual( + len(breakpoint_ids), len(lines), "expect correct number of breakpoints" + ) + self.continue_to_breakpoints(breakpoint_ids) + + threads = self.dap_server.get_threads() + self.assertEqual(len(threads), 1, "expect one thread") + tid = threads[0]["id"] + + leaf_frame = self.dap_server.get_stackFrame() + self.assertIsNotNone(leaf_frame, "expect a leaf frame") + + # Request all step in targets list and verify the response. + step_in_targets_response = self.dap_server.request_stepInTargets( + leaf_frame["id"] + ) + self.assertEqual(step_in_targets_response["success"], True, "expect success") + self.assertIn( + "body", step_in_targets_response, "expect body field in response body" + ) + self.assertIn( + "targets", + step_in_targets_response["body"], + "expect targets field in response body", + ) + + step_in_targets = step_in_targets_response["body"]["targets"] + self.assertEqual(len(step_in_targets), 3, "expect 3 step in targets") + + # Verify the target names are correct. + self.assertEqual(step_in_targets[0]["label"], "bar()", "expect bar()") + self.assertEqual(step_in_targets[1]["label"], "bar2()", "expect bar2()") + self.assertEqual( + step_in_targets[2]["label"], "foo(int, int)", "expect foo(int, int)" + ) + + # Choose to step into second target and verify that we are in bar2() + self.stepIn(threadId=tid, targetId=step_in_targets[1]["id"], waitForStop=True) + leaf_frame = self.dap_server.get_stackFrame() + self.assertIsNotNone(leaf_frame, "expect a leaf frame") + self.assertEqual(leaf_frame["name"], "bar2()") diff --git a/lldb/test/API/tools/lldb-dap/stepInTargets/main.cpp b/lldb/test/API/tools/lldb-dap/stepInTargets/main.cpp new file mode 100644 index 0000000000000000000000000000000000000000..d3c3dbcc139ef068c4860de73c0adc60c202226f --- /dev/null +++ b/lldb/test/API/tools/lldb-dap/stepInTargets/main.cpp @@ -0,0 +1,11 @@ + +int foo(int val, int extra) { return val + extra; } + +int bar() { return 22; } + +int bar2() { return 54; } + +int main(int argc, char const *argv[]) { + foo(bar(), bar2()); // set breakpoint here + return 0; +} diff --git a/lldb/test/Shell/SymbolFile/DWARF/x86/find-basic-function.cpp b/lldb/test/Shell/SymbolFile/DWARF/x86/find-basic-function.cpp index 30143a41d5e734806d8d0699d740b1411dc7aebe..b9a63525d0711d7c31a809c2cc938f05fe067587 100644 --- a/lldb/test/Shell/SymbolFile/DWARF/x86/find-basic-function.cpp +++ b/lldb/test/Shell/SymbolFile/DWARF/x86/find-basic-function.cpp @@ -59,6 +59,11 @@ // RUN: lldb-test symbols --name=not_there --find=function %t | \ // RUN: FileCheck --check-prefix=EMPTY %s +/// Test a per-module index built by lld. +// RUN: ld.lld --debug-names %t.o -o %t +// RUN: lldb-test symbols --name=foo --find=function --function-flags=base %t | \ +// RUN: FileCheck --check-prefix=BASE %s + // NAMES: Name: .debug_names // BASE: Found 4 functions: diff --git a/lldb/test/Shell/SymbolFile/DWARF/x86/find-basic-variable.cpp b/lldb/test/Shell/SymbolFile/DWARF/x86/find-basic-variable.cpp index 98b4097cdda01fc8241640cff180b5bcf12a53b0..e46fa14489d32d2131c050acbe1beef96eac771d 100644 --- a/lldb/test/Shell/SymbolFile/DWARF/x86/find-basic-variable.cpp +++ b/lldb/test/Shell/SymbolFile/DWARF/x86/find-basic-variable.cpp @@ -33,6 +33,11 @@ // RUN: lldb-test symbols --name=not_there --find=variable %t | \ // RUN: FileCheck --check-prefix=EMPTY %s +/// Test a per-module index built by lld. +// RUN: ld.lld --debug-names %t.o -o %t +// RUN: lldb-test symbols --name=foo --find=variable --context=context %t | \ +// RUN: FileCheck --check-prefix=CONTEXT %s + // NAMES: Name: .debug_names // EMPTY: Found 0 variables: diff --git a/lldb/test/Shell/Unwind/eh-frame-dwarf-unwind-abort.test b/lldb/test/Shell/Unwind/eh-frame-dwarf-unwind-abort.test index 477a656a711f90356e8c933d88d898f0304aa5b5..d5e66ca5e263411004b67ddb73beac7122f26260 100644 --- a/lldb/test/Shell/Unwind/eh-frame-dwarf-unwind-abort.test +++ b/lldb/test/Shell/Unwind/eh-frame-dwarf-unwind-abort.test @@ -9,12 +9,12 @@ process launch # CHECK: stop reason = signal SIGTRAP thread backtrace -# CHECK: frame #0: {{.*}}`asm_main + 23 +# CHECK: frame #0: {{.*}}`asm_main + 19 # CHECK: frame #1: {{.*}}`main + {{.*}} target modules show-unwind -n asm_main # CHECK: eh_frame UnwindPlan: # CHECK: row[0]: 0: CFA=rsp +8 => rip=[CFA-8] -# CHECK: row[1]: 14: CFA=rsp+16 => rbp=[CFA-16] rip=[CFA-8] -# CHECK: row[2]: 17: CFA=rbp+16 => rbp=[CFA-16] rip=[CFA-8] -# CHECK: row[3]: 22: CFA=rsp +8 => rip=[CFA-8] +# CHECK: row[1]: 10: CFA=rsp+16 => rbp=[CFA-16] rip=[CFA-8] +# CHECK: row[2]: 13: CFA=rbp+16 => rbp=[CFA-16] rip=[CFA-8] +# CHECK: row[3]: 18: CFA=rsp +8 => rip=[CFA-8] diff --git a/lldb/tools/lldb-dap/DAP.h b/lldb/tools/lldb-dap/DAP.h index 8015dec9ba8fe634cd39f7e34d38ce6e8c108127..5c70a056fea4bf88bd9b9581f6e1b818df47f4db 100644 --- a/lldb/tools/lldb-dap/DAP.h +++ b/lldb/tools/lldb-dap/DAP.h @@ -162,6 +162,8 @@ struct DAP { std::vector exit_commands; std::vector stop_commands; std::vector terminate_commands; + // Map step in target id to list of function targets that user can choose. + llvm::DenseMap step_in_targets; // A copy of the last LaunchRequest or AttachRequest so we can reuse its // arguments if we get a RestartRequest. std::optional last_launch_or_attach_request; diff --git a/lldb/tools/lldb-dap/lldb-dap.cpp b/lldb/tools/lldb-dap/lldb-dap.cpp index 25c5ad56e3d6fed7a88cc85872686f6651fc4a83..d0fbb9155715b10f234376855cbbdd9feff459e4 100644 --- a/lldb/tools/lldb-dap/lldb-dap.cpp +++ b/lldb/tools/lldb-dap/lldb-dap.cpp @@ -50,6 +50,7 @@ #include #include +#include "lldb/API/SBStream.h" #include "lldb/Host/Config.h" #include "llvm/ADT/ArrayRef.h" #include "llvm/ADT/DenseMap.h" @@ -503,6 +504,10 @@ void EventThreadFunction() { SendContinuedEvent(); break; case lldb::eStateExited: + lldb::SBStream stream; + process.GetStatus(stream); + g_dap.SendOutput(OutputType::Console, stream.GetData()); + // When restarting, we can get an "exited" event for the process we // just killed with the old PID, or even with no PID. In that case // we don't have to terminate the session. @@ -1645,7 +1650,7 @@ void request_initialize(const llvm::json::Object &request) { // The debug adapter supports the gotoTargetsRequest. body.try_emplace("supportsGotoTargetsRequest", false); // The debug adapter supports the stepInTargetsRequest. - body.try_emplace("supportsStepInTargetsRequest", false); + body.try_emplace("supportsStepInTargetsRequest", true); // The debug adapter supports the completions request. body.try_emplace("supportsCompletionsRequest", true); // The debug adapter supports the disassembly request. @@ -3180,14 +3185,155 @@ void request_stepIn(const llvm::json::Object &request) { llvm::json::Object response; FillResponse(request, response); auto arguments = request.getObject("arguments"); + + std::string step_in_target; + uint64_t target_id = GetUnsigned(arguments, "targetId", 0); + auto it = g_dap.step_in_targets.find(target_id); + if (it != g_dap.step_in_targets.end()) + step_in_target = it->second; + + const bool single_thread = GetBoolean(arguments, "singleThread", false); + lldb::RunMode run_mode = + single_thread ? lldb::eOnlyThisThread : lldb::eOnlyDuringStepping; lldb::SBThread thread = g_dap.GetLLDBThread(*arguments); if (thread.IsValid()) { // Remember the thread ID that caused the resume so we can set the // "threadCausedFocus" boolean value in the "stopped" events. g_dap.focus_tid = thread.GetThreadID(); - thread.StepInto(); + thread.StepInto(step_in_target.c_str(), run_mode); + } else { + response["success"] = llvm::json::Value(false); + } + g_dap.SendJSON(llvm::json::Value(std::move(response))); +} + +// "StepInTargetsRequest": { +// "allOf": [ { "$ref": "#/definitions/Request" }, { +// "type": "object", +// "description": "This request retrieves the possible step-in targets for +// the specified stack frame.\nThese targets can be used in the `stepIn` +// request.\nClients should only call this request if the corresponding +// capability `supportsStepInTargetsRequest` is true.", "properties": { +// "command": { +// "type": "string", +// "enum": [ "stepInTargets" ] +// }, +// "arguments": { +// "$ref": "#/definitions/StepInTargetsArguments" +// } +// }, +// "required": [ "command", "arguments" ] +// }] +// }, +// "StepInTargetsArguments": { +// "type": "object", +// "description": "Arguments for `stepInTargets` request.", +// "properties": { +// "frameId": { +// "type": "integer", +// "description": "The stack frame for which to retrieve the possible +// step-in targets." +// } +// }, +// "required": [ "frameId" ] +// }, +// "StepInTargetsResponse": { +// "allOf": [ { "$ref": "#/definitions/Response" }, { +// "type": "object", +// "description": "Response to `stepInTargets` request.", +// "properties": { +// "body": { +// "type": "object", +// "properties": { +// "targets": { +// "type": "array", +// "items": { +// "$ref": "#/definitions/StepInTarget" +// }, +// "description": "The possible step-in targets of the specified +// source location." +// } +// }, +// "required": [ "targets" ] +// } +// }, +// "required": [ "body" ] +// }] +// } +void request_stepInTargets(const llvm::json::Object &request) { + llvm::json::Object response; + FillResponse(request, response); + auto arguments = request.getObject("arguments"); + + g_dap.step_in_targets.clear(); + lldb::SBFrame frame = g_dap.GetLLDBFrame(*arguments); + if (frame.IsValid()) { + lldb::SBAddress pc_addr = frame.GetPCAddress(); + lldb::SBAddress line_end_addr = + pc_addr.GetLineEntry().GetSameLineContiguousAddressRangeEnd(true); + lldb::SBInstructionList insts = g_dap.target.ReadInstructions( + pc_addr, line_end_addr, /*flavor_string=*/nullptr); + + if (!insts.IsValid()) { + response["success"] = false; + response["message"] = "Failed to get instructions for frame."; + g_dap.SendJSON(llvm::json::Value(std::move(response))); + return; + } + + llvm::json::Array step_in_targets; + const auto num_insts = insts.GetSize(); + for (size_t i = 0; i < num_insts; ++i) { + lldb::SBInstruction inst = insts.GetInstructionAtIndex(i); + if (!inst.IsValid()) + break; + + lldb::addr_t inst_addr = inst.GetAddress().GetLoadAddress(g_dap.target); + + // Note: currently only x86/x64 supports flow kind. + lldb::InstructionControlFlowKind flow_kind = + inst.GetControlFlowKind(g_dap.target); + if (flow_kind == lldb::eInstructionControlFlowKindCall) { + // Use call site instruction address as id which is easy to debug. + llvm::json::Object step_in_target; + step_in_target["id"] = inst_addr; + + llvm::StringRef call_operand_name = inst.GetOperands(g_dap.target); + lldb::addr_t call_target_addr; + if (call_operand_name.getAsInteger(0, call_target_addr)) + continue; + + lldb::SBAddress call_target_load_addr = + g_dap.target.ResolveLoadAddress(call_target_addr); + if (!call_target_load_addr.IsValid()) + continue; + + // The existing ThreadPlanStepInRange only accept step in target + // function with debug info. + lldb::SBSymbolContext sc = g_dap.target.ResolveSymbolContextForAddress( + call_target_load_addr, lldb::eSymbolContextFunction); + + // The existing ThreadPlanStepInRange only accept step in target + // function with debug info. + std::string step_in_target_name; + if (sc.IsValid() && sc.GetFunction().IsValid()) + step_in_target_name = sc.GetFunction().GetDisplayName(); + + // Skip call sites if we fail to resolve its symbol name. + if (step_in_target_name.empty()) + continue; + + g_dap.step_in_targets.try_emplace(inst_addr, step_in_target_name); + step_in_target.try_emplace("label", step_in_target_name); + step_in_targets.emplace_back(std::move(step_in_target)); + } + } + llvm::json::Object body; + body.try_emplace("targets", std::move(step_in_targets)); + response.try_emplace("body", std::move(body)); } else { response["success"] = llvm::json::Value(false); + response["message"] = "Failed to get frame for input frameId."; } g_dap.SendJSON(llvm::json::Value(std::move(response))); } @@ -3904,6 +4050,7 @@ void RegisterRequestCallbacks() { g_dap.RegisterRequestCallback("source", request_source); g_dap.RegisterRequestCallback("stackTrace", request_stackTrace); g_dap.RegisterRequestCallback("stepIn", request_stepIn); + g_dap.RegisterRequestCallback("stepInTargets", request_stepInTargets); g_dap.RegisterRequestCallback("stepOut", request_stepOut); g_dap.RegisterRequestCallback("threads", request_threads); g_dap.RegisterRequestCallback("variables", request_variables); diff --git a/lldb/unittests/Host/linux/HostTest.cpp b/lldb/unittests/Host/linux/HostTest.cpp index 733909902474d70864812c2e2e71eacdaf948825..8ecaf3ec0decb0505b19a137c0c96a6e5e84fc1b 100644 --- a/lldb/unittests/Host/linux/HostTest.cpp +++ b/lldb/unittests/Host/linux/HostTest.cpp @@ -69,17 +69,21 @@ TEST_F(HostTest, GetProcessInfo) { EXPECT_EQ(HostInfo::GetArchitecture(HostInfo::eArchKindDefault), Info.GetArchitecture()); // Test timings - /* - * This is flaky in the buildbots on all archs + // In some sense this is a pretty trivial test. What it is trying to + // accomplish is just to validate that these values are never decreasing + // which would be unambiguously wrong. We can not reliably show them + // to be always increasing because the microsecond granularity means that, + // with hardware variations the number of loop iterations need to always + // be increasing for faster and faster machines. ASSERT_TRUE(Host::GetProcessInfo(getpid(), Info)); ProcessInstanceInfo::timespec user_time = Info.GetUserTime(); static volatile unsigned u = 0; for (unsigned i = 0; i < 10'000'000; i++) { - u = i; + u += i; } + ASSERT_TRUE(u > 0); ASSERT_TRUE(Host::GetProcessInfo(getpid(), Info)); ProcessInstanceInfo::timespec next_user_time = Info.GetUserTime(); - ASSERT_TRUE(user_time.tv_sec < next_user_time.tv_sec || - user_time.tv_usec < next_user_time.tv_usec); - */ + ASSERT_TRUE(user_time.tv_sec <= next_user_time.tv_sec || + user_time.tv_usec <= next_user_time.tv_usec); } diff --git a/llvm/docs/AMDGPUDwarfExtensionsForHeterogeneousDebugging.rst b/llvm/docs/AMDGPUDwarfExtensionsForHeterogeneousDebugging.rst index 5dd8df231d3024250ae336247561142362eda078..7d4e06ebf0493c4ae1879576f16328a1c6eaa56b 100644 --- a/llvm/docs/AMDGPUDwarfExtensionsForHeterogeneousDebugging.rst +++ b/llvm/docs/AMDGPUDwarfExtensionsForHeterogeneousDebugging.rst @@ -2487,7 +2487,7 @@ type. .. note:: Could also consider adding ``DW_OP_LLVM_aspace_breg0, - DW_OP_LLVM_aspace_breg1, ..., DW_OP_LLVM_aspace_bref31`` which would save + DW_OP_LLVM_aspace_breg1, ..., DW_OP_LLVM_aspace_breg31`` which would save encoding size. .. _amdgpu-dwarf-register-location-description-operations: diff --git a/llvm/docs/CommandGuide/llvm-objcopy.rst b/llvm/docs/CommandGuide/llvm-objcopy.rst index 57d6280d57c8bdfaa46039b881175725fcc79a40..a62acfc8fdcd80b09a0affc050a5cf244f85e0a6 100644 --- a/llvm/docs/CommandGuide/llvm-objcopy.rst +++ b/llvm/docs/CommandGuide/llvm-objcopy.rst @@ -366,12 +366,12 @@ them. .. option:: --keep-global-symbol , -G - Make all symbols local in the output, except for symbols with the name + Mark all symbols local in the output, except for symbols with the name ````. Can be specified multiple times to ignore multiple symbols. .. option:: --keep-global-symbols - Make all symbols local in the output, except for symbols named in the file + Mark all symbols local in the output, except for symbols named in the file ````. In the file, each line represents a single symbol, with leading and trailing whitespace ignored, as is anything following a '#'. Can be specified multiple times to read names from multiple files. @@ -395,7 +395,7 @@ them. .. option:: --localize-hidden - Make all symbols with hidden or internal visibility local in the output. + Mark all symbols with hidden or internal visibility local in the output. .. option:: --localize-symbol , -L diff --git a/llvm/docs/GettingInvolved.rst b/llvm/docs/GettingInvolved.rst index a4247796cb65914c66c5df41f198dc3552496dfb..93be3bd1d8545e235ac610de95df989926f6dc0e 100644 --- a/llvm/docs/GettingInvolved.rst +++ b/llvm/docs/GettingInvolved.rst @@ -228,7 +228,8 @@ what to add to your calendar invite. - `Meeting details/agenda `__ * - Floating Point Working Group - Every 3rd Wednesday of the month - - `gcal `__ + - `ics `__ + `gcal `__ - `Meeting details/agenda: `__ .. _office-hours: diff --git a/llvm/docs/GlobalISel/MIRPatterns.rst b/llvm/docs/GlobalISel/MIRPatterns.rst index 728e32470144523052e80fb2bc131f8a8649cd96..d7dce1b978cd213856db65fb4e192da14b156f37 100644 --- a/llvm/docs/GlobalISel/MIRPatterns.rst +++ b/llvm/docs/GlobalISel/MIRPatterns.rst @@ -514,3 +514,40 @@ of operands. (match (does_not_bind $tmp, $x) (G_MUL $dst, $x, $tmp)), (apply (COPY $dst, $x))>; + + + + +Gallery +======= + +We should use precise patterns that state our intentions. Please avoid +using wip_match_opcode in patterns. + +.. code-block:: text + :caption: Example fold zext(trunc:nuw) + + // Imprecise: matches any G_ZEXT + def zext : GICombineRule< + (defs root:$root), + (match (wip_match_opcode G_ZEXT):$root, + [{ return Helper.matchZextOfTrunc(*${root}, ${matchinfo}); }]), + (apply [{ Helper.applyBuildFn(*${root}, ${matchinfo}); }])>; + + + // Imprecise: matches G_ZEXT of G_TRUNC + def zext_of_trunc : GICombineRule< + (defs root:$root), + (match (G_TRUNC $src, $x), + (G_ZEXT $root, $src), + [{ return Helper.matchZextOfTrunc(${root}, ${matchinfo}); }]), + (apply [{ Helper.applyBuildFnMO(${root}, ${matchinfo}); }])>; + + + // Precise: matches G_ZEXT of G_TRUNC with nuw flag + def zext_of_trunc_nuw : GICombineRule< + (defs root:$root), + (match (G_TRUNC $src, $x, (MIFlags NoUWrap)), + (G_ZEXT $root, $src), + [{ return Helper.matchZextOfTrunc(${root}, ${matchinfo}); }]), + (apply [{ Helper.applyBuildFnMO(${root}, ${matchinfo}); }])>; diff --git a/llvm/docs/LangRef.rst b/llvm/docs/LangRef.rst index 9592929d79feb42c90474505f0ee1f12e334d35d..f169ab941c457bd0d46980fac5a5786c6b49c31e 100644 --- a/llvm/docs/LangRef.rst +++ b/llvm/docs/LangRef.rst @@ -12517,7 +12517,7 @@ This instruction requires several arguments: ``llvm::GuaranteedTailCallOpt`` is ``true``, or the calling convention is ``tailcc`` - `Platform-specific constraints are - met. `_ + met. `_ #. The optional ``notail`` marker indicates that the optimizers should not add ``tail`` or ``musttail`` markers to the call. It is used to prevent tail @@ -14139,6 +14139,41 @@ Semantics: """""""""" See description of '``llvm.instrprof.increment``' intrinsic. +'``llvm.instrprof.callsite``' Intrinsic +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +Syntax: +""""""" + +:: + + declare void @llvm.instrprof.callsite(ptr , i64 , + i32 , + i32 , ptr ) + +Overview: +""""""""" + +.. FIXME: detail when it's emitted once the support is added + +The '``llvm.instrprof.callsite``' intrinsic should be emitted before a callsite +that's not to a "fake" callee (like another intrinsic or asm). + +Arguments: +"""""""""" +The first 4 arguments are similar to ``llvm.instrprof.increment``. The indexing +is specific to callsites, meaning callsites are indexed from 0, independent from +the indexes used by the other intrinsics (such as +``llvm.instrprof.increment[.step]``). + +The last argument is the called value of the callsite this intrinsic precedes. + +Semantics: +"""""""""" +.. FIXME: detail how when the lowering pass is added. + +This is lowered by contextual profiling. + '``llvm.instrprof.timestamp``' Intrinsic ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ diff --git a/llvm/docs/MemoryModelRelaxationAnnotations.rst b/llvm/docs/MemoryModelRelaxationAnnotations.rst new file mode 100644 index 0000000000000000000000000000000000000000..c79675d30f62083762d78c018ece1131e4320ea1 --- /dev/null +++ b/llvm/docs/MemoryModelRelaxationAnnotations.rst @@ -0,0 +1,481 @@ +=================================== +Memory Model Relaxation Annotations +=================================== + +.. contents:: + :local: + +Introduction +============ + +Memory Model Relaxation Annotations (MMRAs) are target-defined properties +on instructions that can be used to selectively relax constraints placed +by the memory model. For example: + +* The use of ``VulkanMemoryModel`` in a SPIRV program allows certain + memory operations to be reordered across ``acquire`` or ``release`` + operations. +* OpenCL APIs expose primitives to only fence a specific set of address + spaces. Carrying that information to the backend can enable the + use of faster synchronization instructions, rather than fencing all + address spaces everytime. + +MMRAs offer an opt-in system for targets to relax the default LLVM +memory model. +As such, they are attached to an operation using LLVM metadata which +can always be dropped without affecting correctness. + +Definitions +=========== + +memory operation + A load, a store, an atomic, or a function call that is marked as + accessing memory. + +synchronizing operation + An instruction that synchronizes memory with other threads (e.g. + an atomic or a fence). + +tag + Metadata attached to a memory or synchronizing operation + that represents some target-defined property regarding memory + synchronization. + + An operation may have multiple tags that each represent a different + property. + + A tag is composed of a pair of metadata string: a *prefix* and a *suffix*. + + In LLVM IR, the pair is represented using a metadata tuple. + In other cases (comments, documentation, etc.), we may use the + ``prefix:suffix`` notation. + For example: + + .. code-block:: + :caption: Example: Tags in Metadata + + !0 = !{!"scope", !"workgroup"} # scope:workgroup + !1 = !{!"scope", !"device"} # scope:device + !2 = !{!"scope", !"system"} # scope:system + + .. note:: + + The only semantics relevant to the optimizer is the + "compatibility" relation defined below. All other + semantics are target defined. + + Tags can also be organised in lists to allow operations + to specify all of the tags they belong to. Such a list + is referred to as a "set of tags". + + .. code-block:: + :caption: Example: Set of Tags in Metadata + + !0 = !{!"scope", !"workgroup"} + !1 = !{!"sync-as", !"private"} + !2 = !{!0, !2} + + .. note:: + + If an operation does not have MMRA metadata, it's treated as if + it has an empty list (``!{}``) of tags. + + Note that it is not an error if a tag is not recognized by the + instruction it is applied to, or by the current target. + Such tags are simply ignored. + + Both synchronizing operations and memory operations can have + zero or more tags attached to them using the ``!mmra`` syntax. + + For the sake of readability in examples below, + we use a (non-functional) short syntax to represent MMMRA metadata: + + .. code-block:: + :caption: Short Syntax Example + + store %ptr1 # foo:bar + store %ptr1 !mmra !{!"foo", !"bar"} + + These two notations can be used in this document and are strictly + equivalent. However, only the second version is functional. + +compatibility + Two sets of tags are said to be *compatible* iff, for every unique + tag prefix P present in at least one set: + + - the other set contains no tag with prefix P, or + - at least one tag with prefix P is common to both sets. + + The above definition implies that an empty set is always compatible + with any other set. This is an important property as it ensures that + if a transform drops the metadata on an operation, it can never affect + correctness. In other words, the memory model cannot be relaxed further + by deleting metadata from instructions. + +.. _HappensBefore: + +The *happens-before* Relation +============================== + +Compatibility checks can be used to opt out of the *happens-before* relation +established between two instructions. + +Ordering + When two instructions' metadata are not compatible, any program order + between them are not in *happens-before*. + + For example, consider two tags ``foo:bar`` and + ``foo:baz`` exposed by a target: + + .. code-block:: + + A: store %ptr1 # foo:bar + B: store %ptr2 # foo:baz + X: store atomic release %ptr3 # foo:bar + + In the above figure, ``A`` is compatible with ``X``, and hence ``A`` + happens-before ``X``. But ``B`` is not compatible with + ``X``, and hence it is not happens-before ``X``. + +Synchronization + If an synchronizing operation has one or more tags, then whether it + synchronizes-with and participates in the ``seq_cst`` order with + other operations is target dependent. + + Whether the following example synchronizes with another sequence depends + on the target-defined semantics of ``foo:bar`` and ``foo:bux``. + + .. code-block:: + + fence release # foo:bar + store atomic %ptr1 # foo:bux + +Examples +-------- + +Example 1: + .. code-block:: + + A: store ptr addrspace(1) %ptr2 # sync-as:1 vulkan:nonprivate + B: store atomic release ptr addrspace(1) %ptr3 # sync-as:0 vulkan:nonprivate + + A and B are not ordered relative to each other + (no *happens-before*) because their sets of tags are not compatible. + + Note that the ``sync-as`` value does not have to match the ``addrspace`` value. + e.g. In Example 1, a store-release to a location in ``addrspace(1)`` wants to + only synchronize with operations happening in ``addrspace(0)``. + +Example 2: + .. code-block:: + + A: store ptr addrspace(1) %ptr2 # sync-as:1 vulkan:nonprivate + B: store atomic release ptr addrspace(1) %ptr3 # sync-as:1 vulkan:nonprivate + + The ordering of A and B is unaffected because their set of tags are + compatible. + + Note that A and B may or may not be in *happens-before* due to other reasons. + +Example 3: + .. code-block:: + + A: store ptr addrspace(1) %ptr2 # sync-as:1 vulkan:nonprivate + B: store atomic release ptr addrspace(1) %ptr3 # vulkan:nonprivate + + The ordering of A and B is unaffected because their set of tags are + compatible. + +Example 4: + .. code-block:: + + A: store ptr addrspace(1) %ptr2 # sync-as:1 + B: store atomic release ptr addrspace(1) %ptr3 # sync-as:2 + + A and B do not have to be ordered relative to each other + (no *happens-before*) because their sets of tags are not compatible. + +Use-cases +========= + +SPIRV ``NonPrivatePointer`` +--------------------------- + +MMRAs can support the SPIRV capability +``VulkanMemoryModel``, where synchronizing operations only affect +memory operations that specify ``NonPrivatePointer`` semantics. + +The example below is generated from a SPIRV program using the +following recipe: + +- Add ``vulkan:nonprivate`` to every synchronizing operation. +- Add ``vulkan:nonprivate`` to every non-atomic memory operation + that is marked ``NonPrivatePointer``. +- Add ``vulkan:private`` to tags of every non-atomic memory operation + that is not marked ``NonPrivatePointer``. + +.. code-block:: + + Thread T1: + A: store %ptr1 # vulkan:nonprivate + B: store %ptr2 # vulkan:private + X: store atomic release %ptr3 # vulkan:nonprivate + + Thread T2: + Y: load atomic acquire %ptr3 # vulkan:nonprivate + C: load %ptr2 # vulkan:private + D: load %ptr1 # vulkan:nonprivate + +Compatibility ensures that operation ``A`` is ordered +relative to ``X`` while operation ``D`` is ordered relative to ``Y``. +If ``X`` synchronizes with ``Y``, then ``A`` happens-before ``D``. +No such relation can be inferred about operations ``B`` and ``C``. + +.. note:: + The `Vulkan Memory Model `_ + considers all atomic operation non-private. + + Whether ``vulkan:nonprivate`` would be specified on atomic operations is + an implementation detail, as an atomic operation is always ``nonprivate``. + The implementation may choose to be explicit and emit IR with + ``vulkan:nonprivate`` on every atomic operation, or it could choose to + only emit ``vulkan::private`` and assume ``vulkan:nonprivate`` + by default. + +Operations marked with ``vulkan:private`` effectively opt out of the +happens-before order in a SPIRV program since they are incompatible +with every synchronizing operation. Note that SPIRV operations that +are not marked ``NonPrivatePointer`` are not entirely private to the +thread --- they are implicitly synchronized at the start or end of a +thread by the Vulkan *system-synchronizes-with* relationship. This +example assumes that the target-defined semantics of +``vulkan:private`` correctly implements this property. + +This scheme is general enough to express the interoperability of SPIRV +programs with other environments. + +.. code-block:: + + Thread T1: + A: store %ptr1 # vulkan:nonprivate + X: store atomic release %ptr2 # vulkan:nonprivate + + Thread T2: + Y: load atomic acquire %ptr2 # foo:bar + B: load %ptr1 + +In the above example, thread ``T1`` originates from a SPIRV program +while thread ``T2`` originates from a non-SPIRV program. Whether ``X`` +can synchronize with ``Y`` is target defined. If ``X`` synchronizes +with ``Y``, then ``A`` happens before ``B`` (because A/X and +Y/B are compatible). + +Implementation Example +~~~~~~~~~~~~~~~~~~~~~~ + +Consider the implementation of SPIRV ``NonPrivatePointer`` on a target +where all memory operations are cached, and the entire cache is +flushed or invalidated at a ``release`` or ``acquire`` respectively. A +possible scheme is that when translating a SPIRV program, memory +operations marked ``NonPrivatePointer`` should not be cached, and the +cache contents should not be touched during an ``acquire`` and +``release`` operation. + +This could be implemented using the tags that share the ``vulkan:`` prefix, +as follows: + +- For memory operations: + + - Operations with ``vulkan:nonprivate`` should bypass the cache. + - Operations with ``vulkan:private`` should be cached. + - Operations that specify neither or both should conservatively + bypass the cache to ensure correctness. + +- For synchronizing operations: + + - Operations with ``vulkan:nonprivate`` should not flush or + invalidate the cache. + - Operations with ``vulkan:private`` should flush or invalidate the cache. + - Operations that specify neither or both should conservatively + flush or invalidate the cache to ensure correctness. + +.. note:: + In such an implementation, dropping the metadata on an operation, while + not affecting correctness, may have big performance implications. + e.g. an operation bypasses the cache when it shouldn't. + +Memory Types +------------ + +MMRAs may express the selective synchronization of +different memory types. + +As an example, a target may expose an ``sync-as:`` tag to +pass information about which address spaces are synchronized by the +execution of a synchronizing operation. + +.. note:: + Address spaces are used here as a common example, but this concept + can apply for other "memory types". What "memory types" means here is + up to the target. + +.. code-block:: + + # let 1 = global address space + # let 3 = local address space + + Thread T1: + A: store %ptr1 # sync-as:1 + B: store %ptr2 # sync-as:3 + X: store atomic release ptr addrspace(0) %ptr3 # sync-as:3 + + Thread T2: + Y: load atomic acquire ptr addrspace(0) %ptr3 # sync-as:3 + C: load %ptr2 # sync-as:3 + D: load %ptr1 # sync-as:1 + +In the above figure, ``X`` and ``Y`` are atomic operations on a +location in the ``global`` address space. If ``X`` synchronizes with +``Y``, then ``B`` happens-before ``C`` in the ``local`` address +space. But no such statement can be made about operations ``A`` and +``D``, although they are peformed on a location in the ``global`` +address space. + +Implementation Example: Adding Address Space Information to Fences +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +Languages such as OpenCL C provide fence operations such as +``atomic_work_item_fence`` that can take an explicit address +space to fence. + +By default, LLVM has no means to carry that information in the IR, so +the information is lost during lowering to LLVM IR. This means that +targets such as AMDGPU have to conservatively emit instructions to +fence all address spaces in all cases, which can have a noticeable +performance impact in high-performance applications. + +MMRAs may be used to preserve that information at the IR level, all the +way through code generation. For example, a fence that only affects the +global address space ``addrspace(1)`` may be lowered as + +.. code-block:: + + fence release # sync-as:1 + +and the target may use the presence of ``sync-as:1`` to infer that it +must only emit instruction to fence the global address space. + +Note that as MMRAs are opt in, a fence that does not have MMRA metadata +could still be lowered conservatively, so this optimization would only +apply if the front-end emits the MMRA metadata on the fence instructions. + +Additional Topics +================= + +.. note:: + + The following sections are informational. + +Performance Impact +------------------ + +MMRAs are a way to capture optimization opportunities in the program. +But when an operation mentions no tags or conflicting tags, +the target may need to produce conservative code to ensure correctness +at the cost of performance. This can happen in the following situations: + +1. When a target first introduces MMRAs, the + frontend might not have been updated to emit them. +2. An optimization may drop MMRA metadata. +3. An optimization may add arbitrary tags to an operation. + +Note that targets can always choose to ignore (or even drop) MMRAs +and revert to the default behavior/codegen heuristics without +affecting correctness. + +Consequences of the Absence of *happens-before* +----------------------------------------------- + +In the :ref:`happens-before` section, we defined how an +*happens-before* relation between two instruction can be broken +by leveraging compatibility between MMRAs. When the instructions +are incompatible and there is no *happens-before* relation, we say +that the instructions "do not have to be ordered relative to each +other". + +"Ordering" in this context is a very broad term which covers both +static and runtime aspects. + +When there is no ordering constraint, we *could* statically reorder +the instructions in an optimizer transform if the reordering does +not break other constraints as single location coherence. +Static reordering is one consequence of breaking *happens-before*, +but is not the most interesting one. + +Run-time consequences are more interesting. When there is an +*happens-before* relation between instructions, the target has to emit +synchronization code to ensure other threads will observe the effects of +the instructions in the right order. + +For instance, the target may have to wait for previous loads & stores to +finish before starting a fence-release, or there may be a need to flush a +memory cache before executing the next instruction. +In the absence of *happens-before*, there is no such requirement and +no waiting or flushing is required. This may noticeably speed up +execution in some cases. + +Combining Operations +-------------------- + +If a pass can combine multiple memory or synchronizing operations +into one, it needs to be able to combine MMRAs. One possible way to +achieve this is by doing a prefix-wise union of the tag sets. + +Let A and B be two tags set, and U be the prefix-wise union of A and B. +For every unique tag prefix P present in A or B: + +* If either A or B has no tags with prefix P, no tags with prefix + P are added to U. +* If both A and B have at least one tag with prefix P, all tags with prefix + P from both sets are added to U. + +Passes should avoid aggressively combining MMRAs, as this can result +in significant losses of information. While this cannot affect +correctness, it may affect performance. + +As a general rule of thumb, common passes such as SimplifyCFG that +aggressively combine/reorder operations should only combine +instructions that have identical sets of tags. +Passes that combine less frequently, or that are well aware of the cost +of combining the MMRAs can use the prefix-wise union described above. + +Examples: + +.. code-block:: + + A: store release %ptr1 # foo:x, foo:y, bar:x + B: store release %ptr2 # foo:x, bar:y + + # Unique prefixes P = [foo, bar] + # "foo:x" is common to A and B so it's added to U. + # "bar:x" != "bar:y" so it's not added to U. + U: store release %ptr3 # foo:x + +.. code-block:: + + A: store release %ptr1 # foo:x, foo:y + B: store release %ptr2 # foo:x, bux:y + + # Unique prefixes P = [foo, bux] + # "foo:x" is common to A and B so it's added to U. + # No tags have the prefix "bux" in A. + U: store release %ptr3 # foo:x + +.. code-block:: + + A: store release %ptr1 + B: store release %ptr2 # foo:x, bar:y + + # Unique prefixes P = [foo, bar] + # No tags with "foo" or "bar" in A, so no tags added. + U: store release %ptr3 diff --git a/llvm/docs/Reference.rst b/llvm/docs/Reference.rst index 3a1d1665be439e287460bd27547609d2671fdb08..1661c8c533db1d2cedb59800a7c1e486ff012b55 100644 --- a/llvm/docs/Reference.rst +++ b/llvm/docs/Reference.rst @@ -39,6 +39,7 @@ LLVM and API reference documentation. PDB/index PointerAuth ScudoHardenedAllocator + MemoryModelRelaxationAnnotations MemTagSanitizer Security SecurityTransparencyReports @@ -194,6 +195,9 @@ Additional Topics :doc:`ScudoHardenedAllocator` A library that implements a security-hardened `malloc()`. +:doc:`MemoryModelRelaxationAnnotations` + Target-defined relaxation to LLVM's concurrency model. + :doc:`MemTagSanitizer` Security hardening for production code aiming to mitigate memory related vulnerabilities. Based on the Armv8.5-A Memory Tagging Extension. diff --git a/llvm/docs/ReleaseNotes.rst b/llvm/docs/ReleaseNotes.rst index 580dc512d9690cbd22b536310ac2d60826826c06..a83b8bb79a1c99b3348c98052361cc43831112db 100644 --- a/llvm/docs/ReleaseNotes.rst +++ b/llvm/docs/ReleaseNotes.rst @@ -50,6 +50,8 @@ Update on required toolchains to build LLVM Changes to the LLVM IR ---------------------- +- Added Memory Model Relaxation Annotations (MMRAs). + Changes to LLVM infrastructure ------------------------------ @@ -67,7 +69,8 @@ Changes to Interprocedural Optimizations Changes to the AArch64 Backend ------------------------------ -* Added support for Cortex-A78AE, Cortex-A520AE and Cortex-A720AE CPUs. +* Added support for Cortex-A78AE, Cortex-A520AE, Cortex-A720AE, + Neoverse-N3, Neoverse-V3 and Neoverse-V3AE CPUs. Changes to the AMDGPU Backend ----------------------------- @@ -133,7 +136,7 @@ Changes to the C API functions for accessing the values in a blockaddress constant. * Added ``LLVMConstStringInContext2`` function, which better matches the C++ - API by using ``size_t`` for string length. Deprecated ``LLVMConstStringInContext``. + API by using ``size_t`` for string length. Deprecated ``LLVMConstStringInContext``. * Added the following functions for accessing a function's prefix data: diff --git a/llvm/docs/Security.rst b/llvm/docs/Security.rst index 7f3493d4563bb2ac8a5d381d601893a04f84e9d0..9140923e5e8c9d6bf02a17f0836fd455f2cd4660 100644 --- a/llvm/docs/Security.rst +++ b/llvm/docs/Security.rst @@ -53,9 +53,9 @@ username for an individual isn't available, the brackets will be empty. * Peter Smith (ARM) [@smithp35] * Pietro Albini (Ferrous Systems; Rust) [@pietroalbini] * Serge Guelton (Mozilla) [@serge-sans-paille] -* Sergey Maslov (Intel) [@smaslov-intel] * Shayne Hiet-Block (Microsoft) [@GreatKeeper] * Tim Penge (Sony) [] +* Will Huhn (Intel) [@wphuhn-intel] Criteria -------- diff --git a/llvm/examples/OrcV2Examples/LLJITWithRemoteDebugging/RemoteJITUtils.cpp b/llvm/examples/OrcV2Examples/LLJITWithRemoteDebugging/RemoteJITUtils.cpp index b11d875c6f2d06b1aedc128606cdb4bffcafb8aa..7c896ab6d88e07fb7aa54acd9bcd774b280efb8e 100644 --- a/llvm/examples/OrcV2Examples/LLJITWithRemoteDebugging/RemoteJITUtils.cpp +++ b/llvm/examples/OrcV2Examples/LLJITWithRemoteDebugging/RemoteJITUtils.cpp @@ -129,7 +129,7 @@ launchLocalExecutor(StringRef ExecutablePath) { close(FromExecutor[WriteEnd]); auto EPC = SimpleRemoteEPC::Create( - std::make_unique(), + std::make_unique(std::nullopt), SimpleRemoteEPC::Setup(), FromExecutor[ReadEnd], ToExecutor[WriteEnd]); if (!EPC) @@ -201,7 +201,7 @@ connectTCPSocket(StringRef NetworkAddress) { return CreateErr(toString(SockFD.takeError())); return SimpleRemoteEPC::Create( - std::make_unique(), + std::make_unique(std::nullopt), SimpleRemoteEPC::Setup(), *SockFD); } diff --git a/llvm/examples/SpeculativeJIT/SpeculativeJIT.cpp b/llvm/examples/SpeculativeJIT/SpeculativeJIT.cpp index 0d97d379d2279e1a68e022d006ee9379699d2825..1659e5c5c8b40bf0b8b41ea4696f5d340f563e50 100644 --- a/llvm/examples/SpeculativeJIT/SpeculativeJIT.cpp +++ b/llvm/examples/SpeculativeJIT/SpeculativeJIT.cpp @@ -49,7 +49,9 @@ public: if (!DL) return DL.takeError(); - auto EPC = SelfExecutorProcessControl::Create(); + auto EPC = SelfExecutorProcessControl::Create( + nullptr, + std::make_unique(std::nullopt)); if (!EPC) return EPC.takeError(); @@ -116,14 +118,6 @@ private: std::move(ISMBuilder)) { MainJD.addGenerator(std::move(ProcessSymbolsGenerator)); this->CODLayer.setImplMap(&Imps); - this->ES->setDispatchTask( - [this](std::unique_ptr T) { - CompileThreads.async( - [UnownedT = T.release()]() { - std::unique_ptr T(UnownedT); - T->run(); - }); - }); ExitOnErr(S.addSpeculationRuntime(MainJD, Mangle)); LocalCXXRuntimeOverrides CXXRuntimeoverrides; ExitOnErr(CXXRuntimeoverrides.enable(MainJD, Mangle)); diff --git a/llvm/include/llvm/Analysis/Loads.h b/llvm/include/llvm/Analysis/Loads.h index 0926093bba99deffaca343036800fa87e4b9216b..a8d954b9872d97b24b95b5b2453be75f93617218 100644 --- a/llvm/include/llvm/Analysis/Loads.h +++ b/llvm/include/llvm/Analysis/Loads.h @@ -173,14 +173,17 @@ Value *findAvailablePtrLoadStore(const MemoryLocation &Loc, Type *AccessTy, unsigned MaxInstsToScan, BatchAAResults *AA, bool *IsLoadCSE, unsigned *NumScanedInst); -/// Returns true if a pointer value \p A can be replace with another pointer -/// value \B if they are deemed equal through some means (e.g. information from +/// Returns true if a pointer value \p From can be replaced with another pointer +/// value \To if they are deemed equal through some means (e.g. information from /// conditions). -/// NOTE: the current implementations is incomplete and unsound. It does not -/// reject all invalid cases yet, but will be made stricter in the future. In -/// particular this means returning true means unknown if replacement is safe. -bool canReplacePointersIfEqual(Value *A, Value *B, const DataLayout &DL, - Instruction *CtxI); +/// NOTE: The current implementation allows replacement in Icmp and PtrToInt +/// instructions, as well as when we are replacing with a null pointer. +/// Additionally it also allows replacement of pointers when both pointers have +/// the same underlying object. +bool canReplacePointersIfEqual(const Value *From, const Value *To, + const DataLayout &DL); +bool canReplacePointersInUseIfEqual(const Use &U, const Value *To, + const DataLayout &DL); } #endif diff --git a/llvm/include/llvm/Analysis/TargetTransformInfo.h b/llvm/include/llvm/Analysis/TargetTransformInfo.h index 58c69ac939763a40ddda9ae07a0714cd8f1b37b0..1c76821fe5e4abf4cfc1a71e5d0abe04c6a90ce7 100644 --- a/llvm/include/llvm/Analysis/TargetTransformInfo.h +++ b/llvm/include/llvm/Analysis/TargetTransformInfo.h @@ -1267,7 +1267,7 @@ public: TTI::TargetCostKind CostKind = TTI::TCK_RecipThroughput, TTI::OperandValueInfo Opd1Info = {TTI::OK_AnyValue, TTI::OP_None}, TTI::OperandValueInfo Opd2Info = {TTI::OK_AnyValue, TTI::OP_None}, - ArrayRef Args = ArrayRef(), + ArrayRef Args = std::nullopt, const Instruction *CxtI = nullptr, const TargetLibraryInfo *TLibInfo = nullptr) const; diff --git a/llvm/include/llvm/Analysis/ValueTracking.h b/llvm/include/llvm/Analysis/ValueTracking.h index a2fa8f6064e11667ca2e260c3b59d1db1e1d309c..571e44cdac2650ae8195138e3beda2e799ed771f 100644 --- a/llvm/include/llvm/Analysis/ValueTracking.h +++ b/llvm/include/llvm/Analysis/ValueTracking.h @@ -131,7 +131,8 @@ bool isKnownNonZero(const Value *V, const SimplifyQuery &Q, unsigned Depth = 0); /// Currently can recoginze Value pair: /// 1: if X = sub (0, Y) or Y = sub (0, X) /// 2: if X = sub (A, B) and Y = sub (B, A) -bool isKnownNegation(const Value *X, const Value *Y, bool NeedNSW = false); +bool isKnownNegation(const Value *X, const Value *Y, bool NeedNSW = false, + bool AllowPoison = true); /// Returns true if the give value is known to be non-negative. bool isKnownNonNegative(const Value *V, const SimplifyQuery &SQ, diff --git a/llvm/include/llvm/Analysis/VectorUtils.h b/llvm/include/llvm/Analysis/VectorUtils.h index c6eb66cc9660ca61ec61d92972d44c033f9618b9..424b73e375b5bc82eb29605694004ba382103fc8 100644 --- a/llvm/include/llvm/Analysis/VectorUtils.h +++ b/llvm/include/llvm/Analysis/VectorUtils.h @@ -301,7 +301,7 @@ MDNode *intersectAccessGroups(const Instruction *Inst1, const Instruction *Inst2); /// Specifically, let Kinds = [MD_tbaa, MD_alias_scope, MD_noalias, MD_fpmath, -/// MD_nontemporal, MD_access_group]. +/// MD_nontemporal, MD_access_group, MD_mmra]. /// For K in Kinds, we get the MDNode for K from each of the /// elements of VL, compute their "intersection" (i.e., the most generic /// metadata value that covers all of the individual values), and set I's diff --git a/llvm/include/llvm/CodeGen/BasicTTIImpl.h b/llvm/include/llvm/CodeGen/BasicTTIImpl.h index 06a19c75cf873a340bf78573dfc40caa417229e9..4a3a03dc5ad488212d600c9bde2cce6768206fa5 100644 --- a/llvm/include/llvm/CodeGen/BasicTTIImpl.h +++ b/llvm/include/llvm/CodeGen/BasicTTIImpl.h @@ -892,7 +892,7 @@ public: unsigned Opcode, Type *Ty, TTI::TargetCostKind CostKind, TTI::OperandValueInfo Opd1Info = {TTI::OK_AnyValue, TTI::OP_None}, TTI::OperandValueInfo Opd2Info = {TTI::OK_AnyValue, TTI::OP_None}, - ArrayRef Args = ArrayRef(), + ArrayRef Args = std::nullopt, const Instruction *CxtI = nullptr) { // Check if any of the operands are vector operands. const TargetLoweringBase *TLI = getTLI(); diff --git a/llvm/include/llvm/CodeGen/GlobalISel/GIMatchTableExecutor.h b/llvm/include/llvm/CodeGen/GlobalISel/GIMatchTableExecutor.h index 29a46f04fd5de5a34e4f05432c7a278faa3d49a7..8eddc6a6a531b42ebf6d868df5ea545ef6262aeb 100644 --- a/llvm/include/llvm/CodeGen/GlobalISel/GIMatchTableExecutor.h +++ b/llvm/include/llvm/CodeGen/GlobalISel/GIMatchTableExecutor.h @@ -217,6 +217,8 @@ enum { /// - OpIdx(ULEB128) - Operand index /// - Ty(1) - Expected type GIM_CheckType, + /// GIM_CheckType but InsnID is omitted and defaults to zero. + GIM_RootCheckType, /// Check the type of a pointer to any address space. /// - InsnID(ULEB128) - Instruction ID @@ -229,6 +231,8 @@ enum { /// - OpIdx(ULEB128) - Operand index /// - RC(2) - Expected register bank (specified as a register class) GIM_CheckRegBankForClass, + /// GIM_CheckRegBankForClass but InsnID is omitted and defaults to zero. + GIM_RootCheckRegBankForClass, /// Check the operand matches a complex predicate /// - InsnID(ULEB128) - Instruction ID @@ -278,9 +282,9 @@ enum { /// - OpIdx(ULEB128) - Operand index GIM_CheckIsImm, - /// Check if the specified operand is safe to fold into the current - /// instruction. - /// - InsnID(ULEB128) - Instruction ID + /// Checks if the matched instructions numbered [1, 1+N) can + /// be folded into the root (inst 0). + /// - Num(1) GIM_CheckIsSafeToFold, /// Check the specified operands are identical. @@ -338,6 +342,8 @@ enum { /// - InsnID(ULEB128) - Instruction ID to define /// - Opcode(2) - The new opcode to use GIR_BuildMI, + /// GIR_BuildMI but InsnID is omitted and defaults to zero. + GIR_BuildRootMI, /// Builds a constant and stores its result in a TempReg. /// - TempRegID(ULEB128) - Temp Register to define. @@ -349,6 +355,8 @@ enum { /// - OldInsnID(ULEB128) - Instruction ID to copy from /// - OpIdx(ULEB128) - The operand to copy GIR_Copy, + /// GIR_Copy but with both New/OldInsnIDs omitted and defaulting to zero. + GIR_RootToRootCopy, /// Copy an operand to the specified instruction or add a zero register if the /// operand is a zero immediate. @@ -506,6 +514,9 @@ enum { /// description. /// - InsnID(ULEB128) - Instruction ID to modify GIR_ConstrainSelectedInstOperands, + /// GIR_ConstrainSelectedInstOperands but InsnID is omitted and defaults to + /// zero. + GIR_RootConstrainSelectedInstOperands, /// Merge all memory operands into instruction. /// - InsnID(ULEB128) - Instruction ID to modify @@ -518,6 +529,9 @@ enum { /// - InsnID(ULEB128) - Instruction ID to erase GIR_EraseFromParent, + /// Combines both a GIR_EraseFromParent 0 + GIR_Done + GIR_EraseRootFromParent_Done, + /// Create a new temporary register that's not constrained. /// - TempRegID(ULEB128) - The temporary register ID to initialize. /// - Ty(1) - Expected type diff --git a/llvm/include/llvm/CodeGen/GlobalISel/GIMatchTableExecutorImpl.h b/llvm/include/llvm/CodeGen/GlobalISel/GIMatchTableExecutorImpl.h index c73ac2c9f55b7b5f18f664fea952a39903b4a964..dec2d97bb1fa7e1c7d95f900902172aa2242a434 100644 --- a/llvm/include/llvm/CodeGen/GlobalISel/GIMatchTableExecutorImpl.h +++ b/llvm/include/llvm/CodeGen/GlobalISel/GIMatchTableExecutorImpl.h @@ -131,6 +131,16 @@ bool GIMatchTableExecutor::executeMatchTable( return V; }; + const auto eraseImpl = [&](MachineInstr *MI) { + // If we're erasing the insertion point, ensure we don't leave a dangling + // pointer in the builder. + if (Builder.getInsertPt() == MI) + Builder.setInsertPt(*MI->getParent(), ++MI->getIterator()); + if (Observer) + Observer->erasingInstr(*MI); + MI->eraseFromParent(); + }; + while (true) { assert(CurrentIdx != ~0u && "Invalid MatchTable index"); uint8_t MatcherOpcode = MatchTable[CurrentIdx++]; @@ -661,8 +671,9 @@ bool GIMatchTableExecutor::executeMatchTable( break; } + case GIM_RootCheckType: case GIM_CheckType: { - uint64_t InsnID = readULEB(); + uint64_t InsnID = (MatcherOpcode == GIM_RootCheckType) ? 0 : readULEB(); uint64_t OpIdx = readULEB(); int TypeID = readS8(); DEBUG_WITH_TYPE(TgtExecutor::getName(), @@ -741,8 +752,11 @@ bool GIMatchTableExecutor::executeMatchTable( State.RecordedTypes[TypeIdx] = MRI.getType(Op.getReg()); break; } + + case GIM_RootCheckRegBankForClass: case GIM_CheckRegBankForClass: { - uint64_t InsnID = readULEB(); + uint64_t InsnID = + (MatcherOpcode == GIM_RootCheckRegBankForClass) ? 0 : readULEB(); uint64_t OpIdx = readULEB(); uint16_t RCEnum = readU16(); DEBUG_WITH_TYPE(TgtExecutor::getName(), @@ -898,14 +912,16 @@ bool GIMatchTableExecutor::executeMatchTable( break; } case GIM_CheckIsSafeToFold: { - uint64_t InsnID = readULEB(); + uint64_t NumInsn = MatchTable[CurrentIdx++]; DEBUG_WITH_TYPE(TgtExecutor::getName(), - dbgs() << CurrentIdx << ": GIM_CheckIsSafeToFold(MIs[" - << InsnID << "])\n"); - assert(State.MIs[InsnID] != nullptr && "Used insn before defined"); - if (!isObviouslySafeToFold(*State.MIs[InsnID], *State.MIs[0])) { - if (handleReject() == RejectAndGiveUp) - return false; + dbgs() << CurrentIdx << ": GIM_CheckIsSafeToFold(N = " + << NumInsn << ")\n"); + MachineInstr &Root = *State.MIs[0]; + for (unsigned K = 1, E = NumInsn + 1; K < E; ++K) { + if (!isObviouslySafeToFold(*State.MIs[K], Root)) { + if (handleReject() == RejectAndGiveUp) + return false; + } } break; } @@ -1011,8 +1027,9 @@ bool GIMatchTableExecutor::executeMatchTable( break; } + case GIR_BuildRootMI: case GIR_BuildMI: { - uint64_t NewInsnID = readULEB(); + uint64_t NewInsnID = (MatcherOpcode == GIR_BuildRootMI) ? 0 : readULEB(); uint16_t Opcode = readU16(); if (NewInsnID >= OutMIs.size()) OutMIs.resize(NewInsnID + 1); @@ -1034,9 +1051,12 @@ bool GIMatchTableExecutor::executeMatchTable( break; } + case GIR_RootToRootCopy: case GIR_Copy: { - uint64_t NewInsnID = readULEB(); - uint64_t OldInsnID = readULEB(); + uint64_t NewInsnID = + (MatcherOpcode == GIR_RootToRootCopy) ? 0 : readULEB(); + uint64_t OldInsnID = + (MatcherOpcode == GIR_RootToRootCopy) ? 0 : readULEB(); uint64_t OpIdx = readULEB(); assert(OutMIs[NewInsnID] && "Attempted to add to undefined instruction"); OutMIs[NewInsnID].add(State.MIs[OldInsnID]->getOperand(OpIdx)); @@ -1361,8 +1381,11 @@ bool GIMatchTableExecutor::executeMatchTable( break; } + case GIR_RootConstrainSelectedInstOperands: case GIR_ConstrainSelectedInstOperands: { - uint64_t InsnID = readULEB(); + uint64_t InsnID = (MatcherOpcode == GIR_RootConstrainSelectedInstOperands) + ? 0 + : readULEB(); assert(OutMIs[InsnID] && "Attempted to add to undefined instruction"); constrainSelectedInstRegOperands(*OutMIs[InsnID].getInstr(), TII, TRI, RBI); @@ -1372,7 +1395,6 @@ bool GIMatchTableExecutor::executeMatchTable( << InsnID << "])\n"); break; } - case GIR_MergeMemOperands: { uint64_t InsnID = readULEB(); uint64_t NumInsn = MatchTable[CurrentIdx++]; @@ -1391,7 +1413,6 @@ bool GIMatchTableExecutor::executeMatchTable( DEBUG_WITH_TYPE(TgtExecutor::getName(), dbgs() << ")\n"); break; } - case GIR_EraseFromParent: { uint64_t InsnID = readULEB(); MachineInstr *MI = State.MIs[InsnID]; @@ -1399,16 +1420,17 @@ bool GIMatchTableExecutor::executeMatchTable( DEBUG_WITH_TYPE(TgtExecutor::getName(), dbgs() << CurrentIdx << ": GIR_EraseFromParent(MIs[" << InsnID << "])\n"); - // If we're erasing the insertion point, ensure we don't leave a dangling - // pointer in the builder. - if (Builder.getInsertPt() == MI) - Builder.setInsertPt(*MI->getParent(), ++MI->getIterator()); - if (Observer) - Observer->erasingInstr(*MI); - MI->eraseFromParent(); + eraseImpl(MI); break; } - + case GIR_EraseRootFromParent_Done: { + DEBUG_WITH_TYPE(TgtExecutor::getName(), + dbgs() + << CurrentIdx << ": GIR_EraseRootFromParent_Done\n"); + eraseImpl(State.MIs[0]); + propagateFlags(); + return true; + } case GIR_MakeTempReg: { uint64_t TempRegID = readULEB(); int TypeID = readS8(); diff --git a/llvm/include/llvm/CodeGen/GlobalISel/LegalizationArtifactCombiner.h b/llvm/include/llvm/CodeGen/GlobalISel/LegalizationArtifactCombiner.h index ca62f38061b115445bfc002ee82c0fc0e81e1eb1..305bef7dd3ea63dd1b11a92bc8e3ccc42efc4fa0 100644 --- a/llvm/include/llvm/CodeGen/GlobalISel/LegalizationArtifactCombiner.h +++ b/llvm/include/llvm/CodeGen/GlobalISel/LegalizationArtifactCombiner.h @@ -906,7 +906,8 @@ public: unsigned &DefOperandIdx) { if (Register Def = findValueFromDefImpl(Reg, 0, Size)) { if (auto *Unmerge = dyn_cast(MRI.getVRegDef(Def))) { - DefOperandIdx = Unmerge->findRegisterDefOperandIdx(Def); + DefOperandIdx = + Unmerge->findRegisterDefOperandIdx(Def, /*TRI=*/nullptr); return Unmerge; } } diff --git a/llvm/include/llvm/CodeGen/GlobalISel/MachineIRBuilder.h b/llvm/include/llvm/CodeGen/GlobalISel/MachineIRBuilder.h index be39eb7891f3bf73d0b82ae85a4cbe92c010042a..e15f7a7172e1a40a193cfe1221e221fff2e91348 100644 --- a/llvm/include/llvm/CodeGen/GlobalISel/MachineIRBuilder.h +++ b/llvm/include/llvm/CodeGen/GlobalISel/MachineIRBuilder.h @@ -53,6 +53,8 @@ struct MachineIRBuilderState { DebugLoc DL; /// PC sections metadata to be set to any instruction we create. MDNode *PCSections = nullptr; + /// MMRA Metadata to be set on any instruction we create. + MDNode *MMRA = nullptr; /// \name Fields describing the insertion point. /// @{ @@ -354,6 +356,7 @@ public: setMBB(*MI.getParent()); State.II = MI.getIterator(); setPCSections(MI.getPCSections()); + setMMRAMetadata(MI.getMMRAMetadata()); } /// @} @@ -387,6 +390,12 @@ public: /// Get the current instruction's PC sections metadata. MDNode *getPCSections() { return State.PCSections; } + /// Set the PC sections metadata to \p MD for all the next build instructions. + void setMMRAMetadata(MDNode *MMRA) { State.MMRA = MMRA; } + + /// Get the current instruction's MMRA metadata. + MDNode *getMMRAMetadata() { return State.MMRA; } + /// Build and insert = \p Opcode . /// The insertion point is the one set by the last call of either /// setBasicBlock or setMI. diff --git a/llvm/include/llvm/CodeGen/ISDOpcodes.h b/llvm/include/llvm/CodeGen/ISDOpcodes.h index 078a936b061a329fb538cf6dd7b5839cc5ca9706..6429947958ee91d0e7fa3248727070fcfa430e29 100644 --- a/llvm/include/llvm/CodeGen/ISDOpcodes.h +++ b/llvm/include/llvm/CodeGen/ISDOpcodes.h @@ -205,6 +205,7 @@ enum NodeType { /// CopyFromReg - This node indicates that the input value is a virtual or /// physical register that is defined outside of the scope of this /// SelectionDAG. The register is available from the RegisterSDNode object. + /// Note that CopyFromReg is considered as also freezing the value. CopyFromReg, /// UNDEF - An undefined node. diff --git a/llvm/include/llvm/CodeGen/MachineFunction.h b/llvm/include/llvm/CodeGen/MachineFunction.h index 470997b31fe85fe69fe0e54d86882f271fed28bd..9f8e846cac45b9d33165848da6db5f4b1c498a4e 100644 --- a/llvm/include/llvm/CodeGen/MachineFunction.h +++ b/llvm/include/llvm/CodeGen/MachineFunction.h @@ -1125,7 +1125,8 @@ public: MachineInstr::ExtraInfo *createMIExtraInfo( ArrayRef MMOs, MCSymbol *PreInstrSymbol = nullptr, MCSymbol *PostInstrSymbol = nullptr, MDNode *HeapAllocMarker = nullptr, - MDNode *PCSections = nullptr, uint32_t CFIType = 0); + MDNode *PCSections = nullptr, uint32_t CFIType = 0, + MDNode *MMRAs = nullptr); /// Allocate a string and populate it with the given external symbol name. const char *createExternalSymbolName(StringRef Name); diff --git a/llvm/include/llvm/CodeGen/MachineInstr.h b/llvm/include/llvm/CodeGen/MachineInstr.h index 7249f812d2cc4cf498acc6ceda615ac6500d4814..2b0c5d166d88b06187f0c53dcd55cbb08ad26e0b 100644 --- a/llvm/include/llvm/CodeGen/MachineInstr.h +++ b/llvm/include/llvm/CodeGen/MachineInstr.h @@ -160,37 +160,41 @@ private: MCSymbol *PreInstrSymbol = nullptr, MCSymbol *PostInstrSymbol = nullptr, MDNode *HeapAllocMarker = nullptr, - MDNode *PCSections = nullptr, - uint32_t CFIType = 0) { + MDNode *PCSections = nullptr, uint32_t CFIType = 0, + MDNode *MMRAs = nullptr) { bool HasPreInstrSymbol = PreInstrSymbol != nullptr; bool HasPostInstrSymbol = PostInstrSymbol != nullptr; bool HasHeapAllocMarker = HeapAllocMarker != nullptr; + bool HasMMRAs = MMRAs != nullptr; bool HasCFIType = CFIType != 0; bool HasPCSections = PCSections != nullptr; auto *Result = new (Allocator.Allocate( totalSizeToAlloc( MMOs.size(), HasPreInstrSymbol + HasPostInstrSymbol, - HasHeapAllocMarker + HasPCSections, HasCFIType), + HasHeapAllocMarker + HasPCSections + HasMMRAs, HasCFIType), alignof(ExtraInfo))) ExtraInfo(MMOs.size(), HasPreInstrSymbol, HasPostInstrSymbol, - HasHeapAllocMarker, HasPCSections, HasCFIType); + HasHeapAllocMarker, HasPCSections, HasCFIType, HasMMRAs); // Copy the actual data into the trailing objects. std::copy(MMOs.begin(), MMOs.end(), Result->getTrailingObjects()); + unsigned MDNodeIdx = 0; + if (HasPreInstrSymbol) Result->getTrailingObjects()[0] = PreInstrSymbol; if (HasPostInstrSymbol) Result->getTrailingObjects()[HasPreInstrSymbol] = PostInstrSymbol; if (HasHeapAllocMarker) - Result->getTrailingObjects()[0] = HeapAllocMarker; + Result->getTrailingObjects()[MDNodeIdx++] = HeapAllocMarker; if (HasPCSections) - Result->getTrailingObjects()[HasHeapAllocMarker] = - PCSections; + Result->getTrailingObjects()[MDNodeIdx++] = PCSections; if (HasCFIType) Result->getTrailingObjects()[0] = CFIType; + if (HasMMRAs) + Result->getTrailingObjects()[MDNodeIdx++] = MMRAs; return Result; } @@ -223,6 +227,12 @@ private: return HasCFIType ? getTrailingObjects()[0] : 0; } + MDNode *getMMRAMetadata() const { + return HasMMRAs ? getTrailingObjects()[HasHeapAllocMarker + + HasPCSections] + : nullptr; + } + private: friend TrailingObjects; @@ -237,6 +247,7 @@ private: const bool HasHeapAllocMarker; const bool HasPCSections; const bool HasCFIType; + const bool HasMMRAs; // Implement the `TrailingObjects` internal API. size_t numTrailingObjects(OverloadToken) const { @@ -255,11 +266,12 @@ private: // Just a boring constructor to allow us to initialize the sizes. Always use // the `create` routine above. ExtraInfo(int NumMMOs, bool HasPreInstrSymbol, bool HasPostInstrSymbol, - bool HasHeapAllocMarker, bool HasPCSections, bool HasCFIType) + bool HasHeapAllocMarker, bool HasPCSections, bool HasCFIType, + bool HasMMRAs) : NumMMOs(NumMMOs), HasPreInstrSymbol(HasPreInstrSymbol), HasPostInstrSymbol(HasPostInstrSymbol), HasHeapAllocMarker(HasHeapAllocMarker), HasPCSections(HasPCSections), - HasCFIType(HasCFIType) {} + HasCFIType(HasCFIType), HasMMRAs(HasMMRAs) {} }; /// Enumeration of the kinds of inline extra info available. It is important @@ -838,6 +850,15 @@ public: return nullptr; } + /// Helper to extract mmra.op metadata. + MDNode *getMMRAMetadata() const { + if (!Info) + return nullptr; + if (ExtraInfo *EI = Info.get()) + return EI->getMMRAMetadata(); + return nullptr; + } + /// Helper to extract a CFI type hash if one has been added. uint32_t getCFIType() const { if (!Info) @@ -1445,9 +1466,8 @@ public: /// is a read of a super-register. /// This does not count partial redefines of virtual registers as reads: /// %reg1024:6 = OP. - bool readsRegister(Register Reg, - const TargetRegisterInfo *TRI = nullptr) const { - return findRegisterUseOperandIdx(Reg, false, TRI) != -1; + bool readsRegister(Register Reg, const TargetRegisterInfo *TRI) const { + return findRegisterUseOperandIdx(Reg, TRI, false) != -1; } /// Return true if the MachineInstr reads the specified virtual register. @@ -1466,34 +1486,30 @@ public: /// Return true if the MachineInstr kills the specified register. /// If TargetRegisterInfo is non-null, then it also checks if there is /// a kill of a super-register. - bool killsRegister(Register Reg, - const TargetRegisterInfo *TRI = nullptr) const { - return findRegisterUseOperandIdx(Reg, true, TRI) != -1; + bool killsRegister(Register Reg, const TargetRegisterInfo *TRI) const { + return findRegisterUseOperandIdx(Reg, TRI, true) != -1; } /// Return true if the MachineInstr fully defines the specified register. /// If TargetRegisterInfo is non-null, then it also checks /// if there is a def of a super-register. /// NOTE: It's ignoring subreg indices on virtual registers. - bool definesRegister(Register Reg, - const TargetRegisterInfo *TRI = nullptr) const { - return findRegisterDefOperandIdx(Reg, false, false, TRI) != -1; + bool definesRegister(Register Reg, const TargetRegisterInfo *TRI) const { + return findRegisterDefOperandIdx(Reg, TRI, false, false) != -1; } /// Return true if the MachineInstr modifies (fully define or partially /// define) the specified register. /// NOTE: It's ignoring subreg indices on virtual registers. - bool modifiesRegister(Register Reg, - const TargetRegisterInfo *TRI = nullptr) const { - return findRegisterDefOperandIdx(Reg, false, true, TRI) != -1; + bool modifiesRegister(Register Reg, const TargetRegisterInfo *TRI) const { + return findRegisterDefOperandIdx(Reg, TRI, false, true) != -1; } /// Returns true if the register is dead in this machine instruction. /// If TargetRegisterInfo is non-null, then it also checks /// if there is a dead def of a super-register. - bool registerDefIsDead(Register Reg, - const TargetRegisterInfo *TRI = nullptr) const { - return findRegisterDefOperandIdx(Reg, true, false, TRI) != -1; + bool registerDefIsDead(Register Reg, const TargetRegisterInfo *TRI) const { + return findRegisterDefOperandIdx(Reg, TRI, true, false) != -1; } /// Returns true if the MachineInstr has an implicit-use operand of exactly @@ -1503,22 +1519,23 @@ public: /// Returns the operand index that is a use of the specific register or -1 /// if it is not found. It further tightens the search criteria to a use /// that kills the register if isKill is true. - int findRegisterUseOperandIdx(Register Reg, bool isKill = false, - const TargetRegisterInfo *TRI = nullptr) const; + int findRegisterUseOperandIdx(Register Reg, const TargetRegisterInfo *TRI, + bool isKill = false) const; /// Wrapper for findRegisterUseOperandIdx, it returns /// a pointer to the MachineOperand rather than an index. - MachineOperand *findRegisterUseOperand(Register Reg, bool isKill = false, - const TargetRegisterInfo *TRI = nullptr) { - int Idx = findRegisterUseOperandIdx(Reg, isKill, TRI); + MachineOperand *findRegisterUseOperand(Register Reg, + const TargetRegisterInfo *TRI, + bool isKill = false) { + int Idx = findRegisterUseOperandIdx(Reg, TRI, isKill); return (Idx == -1) ? nullptr : &getOperand(Idx); } - const MachineOperand *findRegisterUseOperand( - Register Reg, bool isKill = false, - const TargetRegisterInfo *TRI = nullptr) const { - return const_cast(this)-> - findRegisterUseOperand(Reg, isKill, TRI); + const MachineOperand *findRegisterUseOperand(Register Reg, + const TargetRegisterInfo *TRI, + bool isKill = false) const { + return const_cast(this)->findRegisterUseOperand(Reg, TRI, + isKill); } /// Returns the operand index that is a def of the specified register or @@ -1527,26 +1544,26 @@ public: /// overlap the specified register. If TargetRegisterInfo is non-null, /// then it also checks if there is a def of a super-register. /// This may also return a register mask operand when Overlap is true. - int findRegisterDefOperandIdx(Register Reg, - bool isDead = false, bool Overlap = false, - const TargetRegisterInfo *TRI = nullptr) const; + int findRegisterDefOperandIdx(Register Reg, const TargetRegisterInfo *TRI, + bool isDead = false, + bool Overlap = false) const; /// Wrapper for findRegisterDefOperandIdx, it returns /// a pointer to the MachineOperand rather than an index. - MachineOperand * - findRegisterDefOperand(Register Reg, bool isDead = false, - bool Overlap = false, - const TargetRegisterInfo *TRI = nullptr) { - int Idx = findRegisterDefOperandIdx(Reg, isDead, Overlap, TRI); + MachineOperand *findRegisterDefOperand(Register Reg, + const TargetRegisterInfo *TRI, + bool isDead = false, + bool Overlap = false) { + int Idx = findRegisterDefOperandIdx(Reg, TRI, isDead, Overlap); return (Idx == -1) ? nullptr : &getOperand(Idx); } - const MachineOperand * - findRegisterDefOperand(Register Reg, bool isDead = false, - bool Overlap = false, - const TargetRegisterInfo *TRI = nullptr) const { + const MachineOperand *findRegisterDefOperand(Register Reg, + const TargetRegisterInfo *TRI, + bool isDead = false, + bool Overlap = false) const { return const_cast(this)->findRegisterDefOperand( - Reg, isDead, Overlap, TRI); + Reg, TRI, isDead, Overlap); } /// Find the index of the first operand in the @@ -1902,6 +1919,8 @@ public: // addresses into. void setPCSections(MachineFunction &MF, MDNode *MD); + void setMMRAMetadata(MachineFunction &MF, MDNode *MMRAs); + /// Set the CFI type for the instruction. void setCFIType(MachineFunction &MF, uint32_t Type); @@ -2014,7 +2033,7 @@ private: void setExtraInfo(MachineFunction &MF, ArrayRef MMOs, MCSymbol *PreInstrSymbol, MCSymbol *PostInstrSymbol, MDNode *HeapAllocMarker, MDNode *PCSections, - uint32_t CFIType); + uint32_t CFIType, MDNode *MMRAs); }; /// Special DenseMapInfo traits to compare MachineInstr* by *value* of the diff --git a/llvm/include/llvm/CodeGen/MachineInstrBuilder.h b/llvm/include/llvm/CodeGen/MachineInstrBuilder.h index 954d8e6770a294f481a0913b67ef3f8e9556db2c..a5b8d3af3cc9b703e8facb5886ad20c16fb2a63b 100644 --- a/llvm/include/llvm/CodeGen/MachineInstrBuilder.h +++ b/llvm/include/llvm/CodeGen/MachineInstrBuilder.h @@ -322,6 +322,12 @@ public: return *this; } + const MachineInstrBuilder &setMMRAMetadata(MDNode *MMRA) const { + if (MMRA) + MI->setMMRAMetadata(*MF, MMRA); + return *this; + } + /// Copy all the implicit operands from OtherMI onto this one. const MachineInstrBuilder & copyImplicitOps(const MachineInstr &OtherMI) const { @@ -337,14 +343,15 @@ public: }; /// Set of metadata that should be preserved when using BuildMI(). This provides -/// a more convenient way of preserving DebugLoc and PCSections. +/// a more convenient way of preserving DebugLoc, PCSections and MMRA. class MIMetadata { public: MIMetadata() = default; - MIMetadata(DebugLoc DL, MDNode *PCSections = nullptr) - : DL(std::move(DL)), PCSections(PCSections) {} - MIMetadata(const DILocation *DI, MDNode *PCSections = nullptr) - : DL(DI), PCSections(PCSections) {} + MIMetadata(DebugLoc DL, MDNode *PCSections = nullptr, MDNode *MMRA = nullptr) + : DL(std::move(DL)), PCSections(PCSections), MMRA(MMRA) {} + MIMetadata(const DILocation *DI, MDNode *PCSections = nullptr, + MDNode *MMRA = nullptr) + : DL(DI), PCSections(PCSections), MMRA(MMRA) {} explicit MIMetadata(const Instruction &From) : DL(From.getDebugLoc()), PCSections(From.getMetadata(LLVMContext::MD_pcsections)) {} @@ -353,17 +360,20 @@ public: const DebugLoc &getDL() const { return DL; } MDNode *getPCSections() const { return PCSections; } + MDNode *getMMRAMetadata() const { return MMRA; } private: DebugLoc DL; MDNode *PCSections = nullptr; + MDNode *MMRA = nullptr; }; /// Builder interface. Specify how to create the initial instruction itself. inline MachineInstrBuilder BuildMI(MachineFunction &MF, const MIMetadata &MIMD, const MCInstrDesc &MCID) { return MachineInstrBuilder(MF, MF.CreateMachineInstr(MCID, MIMD.getDL())) - .setPCSections(MIMD.getPCSections()); + .setPCSections(MIMD.getPCSections()) + .setMMRAMetadata(MIMD.getMMRAMetadata()); } /// This version of the builder sets up the first operand as a @@ -371,8 +381,9 @@ inline MachineInstrBuilder BuildMI(MachineFunction &MF, const MIMetadata &MIMD, inline MachineInstrBuilder BuildMI(MachineFunction &MF, const MIMetadata &MIMD, const MCInstrDesc &MCID, Register DestReg) { return MachineInstrBuilder(MF, MF.CreateMachineInstr(MCID, MIMD.getDL())) - .setPCSections(MIMD.getPCSections()) - .addReg(DestReg, RegState::Define); + .setPCSections(MIMD.getPCSections()) + .setMMRAMetadata(MIMD.getMMRAMetadata()) + .addReg(DestReg, RegState::Define); } /// This version of the builder inserts the newly-built instruction before @@ -386,8 +397,9 @@ inline MachineInstrBuilder BuildMI(MachineBasicBlock &BB, MachineInstr *MI = MF.CreateMachineInstr(MCID, MIMD.getDL()); BB.insert(I, MI); return MachineInstrBuilder(MF, MI) - .setPCSections(MIMD.getPCSections()) - .addReg(DestReg, RegState::Define); + .setPCSections(MIMD.getPCSections()) + .setMMRAMetadata(MIMD.getMMRAMetadata()) + .addReg(DestReg, RegState::Define); } /// This version of the builder inserts the newly-built instruction before @@ -404,8 +416,9 @@ inline MachineInstrBuilder BuildMI(MachineBasicBlock &BB, MachineInstr *MI = MF.CreateMachineInstr(MCID, MIMD.getDL()); BB.insert(I, MI); return MachineInstrBuilder(MF, MI) - .setPCSections(MIMD.getPCSections()) - .addReg(DestReg, RegState::Define); + .setPCSections(MIMD.getPCSections()) + .setMMRAMetadata(MIMD.getMMRAMetadata()) + .addReg(DestReg, RegState::Define); } inline MachineInstrBuilder BuildMI(MachineBasicBlock &BB, MachineInstr &I, @@ -435,7 +448,9 @@ inline MachineInstrBuilder BuildMI(MachineBasicBlock &BB, MachineFunction &MF = *BB.getParent(); MachineInstr *MI = MF.CreateMachineInstr(MCID, MIMD.getDL()); BB.insert(I, MI); - return MachineInstrBuilder(MF, MI).setPCSections(MIMD.getPCSections()); + return MachineInstrBuilder(MF, MI) + .setPCSections(MIMD.getPCSections()) + .setMMRAMetadata(MIMD.getMMRAMetadata()); } inline MachineInstrBuilder BuildMI(MachineBasicBlock &BB, @@ -445,7 +460,9 @@ inline MachineInstrBuilder BuildMI(MachineBasicBlock &BB, MachineFunction &MF = *BB.getParent(); MachineInstr *MI = MF.CreateMachineInstr(MCID, MIMD.getDL()); BB.insert(I, MI); - return MachineInstrBuilder(MF, MI).setPCSections(MIMD.getPCSections()); + return MachineInstrBuilder(MF, MI) + .setPCSections(MIMD.getPCSections()) + .setMMRAMetadata(MIMD.getMMRAMetadata()); } inline MachineInstrBuilder BuildMI(MachineBasicBlock &BB, MachineInstr &I, diff --git a/llvm/include/llvm/CodeGen/SelectionDAG.h b/llvm/include/llvm/CodeGen/SelectionDAG.h index f347131be080f63fb2b9ac6a97d19b86ac090ac4..f353aef1f446ff206d8fc4855c898a68d771e6d4 100644 --- a/llvm/include/llvm/CodeGen/SelectionDAG.h +++ b/llvm/include/llvm/CodeGen/SelectionDAG.h @@ -284,6 +284,7 @@ class SelectionDAG { CallSiteInfo CSInfo; MDNode *HeapAllocSite = nullptr; MDNode *PCSections = nullptr; + MDNode *MMRA = nullptr; bool NoMerge = false; }; /// Out-of-line extra information for SDNodes. @@ -2145,18 +2146,32 @@ public: const APInt *getValidShiftAmountConstant(SDValue V, const APInt &DemandedElts) const; + /// If a SHL/SRA/SRL node \p V has a constant or splat constant shift amount + /// that is less than the element bit-width of the shift node, return it. + const APInt *getValidShiftAmountConstant(SDValue V) const; + /// If a SHL/SRA/SRL node \p V has constant shift amounts that are all less /// than the element bit-width of the shift node, return the minimum value. const APInt * getValidMinimumShiftAmountConstant(SDValue V, const APInt &DemandedElts) const; + /// If a SHL/SRA/SRL node \p V has constant shift amounts that are all less + /// than the element bit-width of the shift node, return the minimum value. + const APInt * + getValidMinimumShiftAmountConstant(SDValue V) const; + /// If a SHL/SRA/SRL node \p V has constant shift amounts that are all less /// than the element bit-width of the shift node, return the maximum value. const APInt * getValidMaximumShiftAmountConstant(SDValue V, const APInt &DemandedElts) const; + /// If a SHL/SRA/SRL node \p V has constant shift amounts that are all less + /// than the element bit-width of the shift node, return the maximum value. + const APInt * + getValidMaximumShiftAmountConstant(SDValue V) const; + /// Match a binop + shuffle pyramid that represents a horizontal reduction /// over the elements of a vector starting from the EXTRACT_VECTOR_ELT node /p /// Extract. The reduction must use one of the opcodes listed in /p @@ -2279,11 +2294,21 @@ public: void addPCSections(const SDNode *Node, MDNode *MD) { SDEI[Node].PCSections = MD; } + /// Set MMRAMetadata to be associated with Node. + void addMMRAMetadata(const SDNode *Node, MDNode *MMRA) { + SDEI[Node].MMRA = MMRA; + } /// Return PCSections associated with Node, or nullptr if none exists. MDNode *getPCSections(const SDNode *Node) const { auto It = SDEI.find(Node); return It != SDEI.end() ? It->second.PCSections : nullptr; } + /// Return the MMRA MDNode associated with Node, or nullptr if none + /// exists. + MDNode *getMMRAMetadata(const SDNode *Node) const { + auto It = SDEI.find(Node); + return It != SDEI.end() ? It->second.MMRA : nullptr; + } /// Set NoMergeSiteInfo to be associated with Node if NoMerge is true. void addNoMergeSiteInfo(const SDNode *Node, bool NoMerge) { if (NoMerge) diff --git a/llvm/include/llvm/CodeGen/SelectionDAGNodes.h b/llvm/include/llvm/CodeGen/SelectionDAGNodes.h index 261f7e49e5c8ca6e60e75d4be31bce3b651abe4d..e7c71041454557eb139ae50db6560781073ce787 100644 --- a/llvm/include/llvm/CodeGen/SelectionDAGNodes.h +++ b/llvm/include/llvm/CodeGen/SelectionDAGNodes.h @@ -999,6 +999,13 @@ public: /// If Flags is not in a defined state then this has no effect. void intersectFlagsWith(const SDNodeFlags Flags); + bool hasPoisonGeneratingFlags() const { + SDNodeFlags Flags = getFlags(); + return Flags.hasNoUnsignedWrap() || Flags.hasNoSignedWrap() || + Flags.hasExact() || Flags.hasDisjoint() || Flags.hasNonNeg() || + Flags.hasNoNaNs() || Flags.hasNoInfs(); + } + void setCFIType(uint32_t Type) { CFIType = Type; } uint32_t getCFIType() const { return CFIType; } @@ -1283,8 +1290,10 @@ private: unsigned DestAddrSpace; public: - AddrSpaceCastSDNode(unsigned Order, const DebugLoc &dl, EVT VT, - unsigned SrcAS, unsigned DestAS); + AddrSpaceCastSDNode(unsigned Order, const DebugLoc &dl, SDVTList VTs, + unsigned SrcAS, unsigned DestAS) + : SDNode(ISD::ADDRSPACECAST, Order, dl, VTs), SrcAddrSpace(SrcAS), + DestAddrSpace(DestAS) {} unsigned getSrcAddressSpace() const { return SrcAddrSpace; } unsigned getDestAddressSpace() const { return DestAddrSpace; } @@ -1573,8 +1582,9 @@ class ShuffleVectorSDNode : public SDNode { protected: friend class SelectionDAG; - ShuffleVectorSDNode(EVT VT, unsigned Order, const DebugLoc &dl, const int *M) - : SDNode(ISD::VECTOR_SHUFFLE, Order, dl, getSDVTList(VT)), Mask(M) {} + ShuffleVectorSDNode(SDVTList VTs, unsigned Order, const DebugLoc &dl, + const int *M) + : SDNode(ISD::VECTOR_SHUFFLE, Order, dl, VTs), Mask(M) {} public: ArrayRef getMask() const { @@ -1628,9 +1638,10 @@ class ConstantSDNode : public SDNode { const ConstantInt *Value; - ConstantSDNode(bool isTarget, bool isOpaque, const ConstantInt *val, EVT VT) + ConstantSDNode(bool isTarget, bool isOpaque, const ConstantInt *val, + SDVTList VTs) : SDNode(isTarget ? ISD::TargetConstant : ISD::Constant, 0, DebugLoc(), - getSDVTList(VT)), + VTs), Value(val) { ConstantSDNodeBits.IsOpaque = isOpaque; } @@ -1681,9 +1692,9 @@ class ConstantFPSDNode : public SDNode { const ConstantFP *Value; - ConstantFPSDNode(bool isTarget, const ConstantFP *val, EVT VT) + ConstantFPSDNode(bool isTarget, const ConstantFP *val, SDVTList VTs) : SDNode(isTarget ? ISD::TargetConstantFP : ISD::ConstantFP, 0, - DebugLoc(), getSDVTList(VT)), + DebugLoc(), VTs), Value(val) {} public: @@ -1816,8 +1827,10 @@ class GlobalAddressSDNode : public SDNode { unsigned TargetFlags; GlobalAddressSDNode(unsigned Opc, unsigned Order, const DebugLoc &DL, - const GlobalValue *GA, EVT VT, int64_t o, - unsigned TF); + const GlobalValue *GA, SDVTList VTs, int64_t o, + unsigned TF) + : SDNode(Opc, Order, DL, VTs), TheGlobal(GA), Offset(o), TargetFlags(TF) { + } public: const GlobalValue *getGlobal() const { return TheGlobal; } @@ -1839,10 +1852,10 @@ class FrameIndexSDNode : public SDNode { int FI; - FrameIndexSDNode(int fi, EVT VT, bool isTarg) - : SDNode(isTarg ? ISD::TargetFrameIndex : ISD::FrameIndex, - 0, DebugLoc(), getSDVTList(VT)), FI(fi) { - } + FrameIndexSDNode(int fi, SDVTList VTs, bool isTarg) + : SDNode(isTarg ? ISD::TargetFrameIndex : ISD::FrameIndex, 0, DebugLoc(), + VTs), + FI(fi) {} public: int getIndex() const { return FI; } @@ -1917,10 +1930,10 @@ class JumpTableSDNode : public SDNode { int JTI; unsigned TargetFlags; - JumpTableSDNode(int jti, EVT VT, bool isTarg, unsigned TF) - : SDNode(isTarg ? ISD::TargetJumpTable : ISD::JumpTable, - 0, DebugLoc(), getSDVTList(VT)), JTI(jti), TargetFlags(TF) { - } + JumpTableSDNode(int jti, SDVTList VTs, bool isTarg, unsigned TF) + : SDNode(isTarg ? ISD::TargetJumpTable : ISD::JumpTable, 0, DebugLoc(), + VTs), + JTI(jti), TargetFlags(TF) {} public: int getIndex() const { return JTI; } @@ -1943,19 +1956,19 @@ class ConstantPoolSDNode : public SDNode { Align Alignment; // Minimum alignment requirement of CP. unsigned TargetFlags; - ConstantPoolSDNode(bool isTarget, const Constant *c, EVT VT, int o, + ConstantPoolSDNode(bool isTarget, const Constant *c, SDVTList VTs, int o, Align Alignment, unsigned TF) : SDNode(isTarget ? ISD::TargetConstantPool : ISD::ConstantPool, 0, - DebugLoc(), getSDVTList(VT)), + DebugLoc(), VTs), Offset(o), Alignment(Alignment), TargetFlags(TF) { assert(Offset >= 0 && "Offset is too large"); Val.ConstVal = c; } - ConstantPoolSDNode(bool isTarget, MachineConstantPoolValue *v, EVT VT, int o, - Align Alignment, unsigned TF) + ConstantPoolSDNode(bool isTarget, MachineConstantPoolValue *v, SDVTList VTs, + int o, Align Alignment, unsigned TF) : SDNode(isTarget ? ISD::TargetConstantPool : ISD::ConstantPool, 0, - DebugLoc(), getSDVTList(VT)), + DebugLoc(), VTs), Offset(o), Alignment(Alignment), TargetFlags(TF) { assert(Offset >= 0 && "Offset is too large"); Val.MachineCPVal = v; @@ -2003,9 +2016,9 @@ class TargetIndexSDNode : public SDNode { int64_t Offset; public: - TargetIndexSDNode(int Idx, EVT VT, int64_t Ofs, unsigned TF) - : SDNode(ISD::TargetIndex, 0, DebugLoc(), getSDVTList(VT)), - TargetFlags(TF), Index(Idx), Offset(Ofs) {} + TargetIndexSDNode(int Idx, SDVTList VTs, int64_t Ofs, unsigned TF) + : SDNode(ISD::TargetIndex, 0, DebugLoc(), VTs), TargetFlags(TF), + Index(Idx), Offset(Ofs) {} unsigned getTargetFlags() const { return TargetFlags; } int getIndex() const { return Index; } @@ -2215,8 +2228,8 @@ class RegisterSDNode : public SDNode { Register Reg; - RegisterSDNode(Register reg, EVT VT) - : SDNode(ISD::Register, 0, DebugLoc(), getSDVTList(VT)), Reg(reg) {} + RegisterSDNode(Register reg, SDVTList VTs) + : SDNode(ISD::Register, 0, DebugLoc(), VTs), Reg(reg) {} public: Register getReg() const { return Reg; } @@ -2251,10 +2264,10 @@ class BlockAddressSDNode : public SDNode { int64_t Offset; unsigned TargetFlags; - BlockAddressSDNode(unsigned NodeTy, EVT VT, const BlockAddress *ba, + BlockAddressSDNode(unsigned NodeTy, SDVTList VTs, const BlockAddress *ba, int64_t o, unsigned Flags) - : SDNode(NodeTy, 0, DebugLoc(), getSDVTList(VT)), - BA(ba), Offset(o), TargetFlags(Flags) {} + : SDNode(NodeTy, 0, DebugLoc(), VTs), BA(ba), Offset(o), + TargetFlags(Flags) {} public: const BlockAddress *getBlockAddress() const { return BA; } @@ -2292,9 +2305,10 @@ class ExternalSymbolSDNode : public SDNode { const char *Symbol; unsigned TargetFlags; - ExternalSymbolSDNode(bool isTarget, const char *Sym, unsigned TF, EVT VT) + ExternalSymbolSDNode(bool isTarget, const char *Sym, unsigned TF, + SDVTList VTs) : SDNode(isTarget ? ISD::TargetExternalSymbol : ISD::ExternalSymbol, 0, - DebugLoc(), getSDVTList(VT)), + DebugLoc(), VTs), Symbol(Sym), TargetFlags(TF) {} public: @@ -2312,8 +2326,8 @@ class MCSymbolSDNode : public SDNode { MCSymbol *Symbol; - MCSymbolSDNode(MCSymbol *Symbol, EVT VT) - : SDNode(ISD::MCSymbol, 0, DebugLoc(), getSDVTList(VT)), Symbol(Symbol) {} + MCSymbolSDNode(MCSymbol *Symbol, SDVTList VTs) + : SDNode(ISD::MCSymbol, 0, DebugLoc(), VTs), Symbol(Symbol) {} public: MCSymbol *getMCSymbol() const { return Symbol; } @@ -3026,8 +3040,8 @@ class AssertAlignSDNode : public SDNode { Align Alignment; public: - AssertAlignSDNode(unsigned Order, const DebugLoc &DL, EVT VT, Align A) - : SDNode(ISD::AssertAlign, Order, DL, getSDVTList(VT)), Alignment(A) {} + AssertAlignSDNode(unsigned Order, const DebugLoc &DL, SDVTList VTs, Align A) + : SDNode(ISD::AssertAlign, Order, DL, VTs), Alignment(A) {} Align getAlign() const { return Alignment; } diff --git a/llvm/include/llvm/CodeGen/TargetInstrInfo.h b/llvm/include/llvm/CodeGen/TargetInstrInfo.h index d4a83e3753d980a6211c96b7e1b4426f7d6a3f47..d5b1df2114e9e7967bced88fe4b688b0a5f47e27 100644 --- a/llvm/include/llvm/CodeGen/TargetInstrInfo.h +++ b/llvm/include/llvm/CodeGen/TargetInstrInfo.h @@ -31,6 +31,7 @@ #include "llvm/MC/MCInstrInfo.h" #include "llvm/Support/BranchProbability.h" #include "llvm/Support/ErrorHandling.h" +#include #include #include #include @@ -1271,11 +1272,20 @@ public: return true; } + /// The returned array encodes the operand index for each parameter because + /// the operands may be commuted; the operand indices for associative + /// operations might also be target-specific. Each element specifies the index + /// of {Prev, A, B, X, Y}. + virtual void + getReassociateOperandIndices(const MachineInstr &Root, unsigned Pattern, + std::array &OperandIndices) const; + /// Attempt to reassociate \P Root and \P Prev according to \P Pattern to /// reduce critical path length. void reassociateOps(MachineInstr &Root, MachineInstr &Prev, unsigned Pattern, SmallVectorImpl &InsInstrs, SmallVectorImpl &DelInstrs, + ArrayRef OperandIndices, DenseMap &InstrIdxForVirtReg) const; /// Reassociation of some instructions requires inverse operations (e.g. diff --git a/llvm/include/llvm/DebugInfo/DWARF/DWARFUnit.h b/llvm/include/llvm/DebugInfo/DWARF/DWARFUnit.h index f20e71781f46be94995d224e03b4fcab4c82b4da..80c27aea893123860d06226295899eb32842bd2f 100644 --- a/llvm/include/llvm/DebugInfo/DWARF/DWARFUnit.h +++ b/llvm/include/llvm/DebugInfo/DWARF/DWARFUnit.h @@ -85,7 +85,7 @@ public: uint64_t *offset_ptr, DWARFSectionKind SectionKind); // For units in DWARF Package File, remember the index entry and update // the abbreviation offset read by extract(). - bool applyIndexEntry(const DWARFUnitIndex::Entry *Entry); + Error applyIndexEntry(const DWARFUnitIndex::Entry *Entry); uint64_t getOffset() const { return Offset; } const dwarf::FormParams &getFormParams() const { return FormParams; } uint16_t getVersion() const { return FormParams.Version; } diff --git a/llvm/include/llvm/ExecutionEngine/Orc/Core.h b/llvm/include/llvm/ExecutionEngine/Orc/Core.h index 7121b3fe762748897398c98c03947a8f98c0a073..bac923aba02afdf5ce32c916b7e4c360019b1782 100644 --- a/llvm/include/llvm/ExecutionEngine/Orc/Core.h +++ b/llvm/include/llvm/ExecutionEngine/Orc/Core.h @@ -1443,9 +1443,6 @@ public: /// Send a result to the remote. using SendResultFunction = unique_function; - /// For dispatching ORC tasks (typically materialization tasks). - using DispatchTaskFunction = unique_function T)>; - /// An asynchronous wrapper-function callable from the executor via /// jit-dispatch. using JITDispatchHandlerFunction = unique_functionDispatchTask = std::move(DispatchTask); - return *this; - } - /// Search the given JITDylibs to find the flags associated with each of the /// given symbols. void lookupFlags(LookupKind K, JITDylibSearchOrder SearchOrder, @@ -1648,7 +1639,7 @@ public: void dispatchTask(std::unique_ptr T) { assert(T && "T must be non-null"); DEBUG_WITH_TYPE("orc", dumpDispatchInfo(*T)); - DispatchTask(std::move(T)); + EPC->getDispatcher().dispatch(std::move(T)); } /// Run a wrapper function in the executor. @@ -1762,8 +1753,6 @@ private: logAllUnhandledErrors(std::move(Err), errs(), "JIT session error: "); } - static void runOnCurrentThread(std::unique_ptr T) { T->run(); } - void dispatchOutstandingMUs(); static std::unique_ptr @@ -1869,7 +1858,6 @@ private: std::unique_ptr EPC; std::unique_ptr P; ErrorReporter ReportError = logErrorsToStdErr; - DispatchTaskFunction DispatchTask = runOnCurrentThread; std::vector ResourceManagers; diff --git a/llvm/include/llvm/ExecutionEngine/Orc/LLJIT.h b/llvm/include/llvm/ExecutionEngine/Orc/LLJIT.h index 810a38f4a6acb88691ee6079b4d2a013b4e1a445..3a71ddc88ce95631517a6cbf32e510ebbff053a6 100644 --- a/llvm/include/llvm/ExecutionEngine/Orc/LLJIT.h +++ b/llvm/include/llvm/ExecutionEngine/Orc/LLJIT.h @@ -254,7 +254,6 @@ protected: DataLayout DL; Triple TT; - std::unique_ptr CompileThreads; std::unique_ptr ObjLinkingLayer; std::unique_ptr ObjTransformLayer; @@ -325,6 +324,7 @@ public: PlatformSetupFunction SetUpPlatform; NotifyCreatedFunction NotifyCreated; unsigned NumCompileThreads = 0; + std::optional SupportConcurrentCompilation; /// Called prior to JIT class construcion to fix up defaults. Error prepareForConstruction(); @@ -333,7 +333,7 @@ public: template class LLJITBuilderSetters { public: - /// Set a ExecutorProcessControl for this instance. + /// Set an ExecutorProcessControl for this instance. /// This should not be called if ExecutionSession has already been set. SetterImpl & setExecutorProcessControl(std::unique_ptr EPC) { @@ -462,19 +462,26 @@ public: /// /// If this method is not called, behavior will be as if it were called with /// a zero argument. + /// + /// This setting should not be used if a custom ExecutionSession or + /// ExecutorProcessControl object is set: in those cases a custom + /// TaskDispatcher should be used instead. SetterImpl &setNumCompileThreads(unsigned NumCompileThreads) { impl().NumCompileThreads = NumCompileThreads; return impl(); } - /// Set an ExecutorProcessControl object. + /// If set, this forces LLJIT concurrent compilation support to be either on + /// or off. This controls the selection of compile function (concurrent vs + /// single threaded) and whether or not sub-modules are cloned to new + /// contexts for lazy emission. /// - /// If the platform uses ObjectLinkingLayer by default and no - /// ObjectLinkingLayerCreator has been set then the ExecutorProcessControl - /// object will be used to supply the memory manager for the - /// ObjectLinkingLayer. - SetterImpl &setExecutorProcessControl(ExecutorProcessControl &EPC) { - impl().EPC = &EPC; + /// If not explicitly set then concurrency support will be turned on if + /// NumCompileThreads is set to a non-zero value, or if a custom + /// ExecutionSession or ExecutorProcessControl instance is provided. + SetterImpl &setSupportConcurrentCompilation( + std::optional SupportConcurrentCompilation) { + impl().SupportConcurrentCompilation = SupportConcurrentCompilation; return impl(); } diff --git a/llvm/include/llvm/ExecutionEngine/Orc/TaskDispatch.h b/llvm/include/llvm/ExecutionEngine/Orc/TaskDispatch.h index 8c287f9fec0e89807524a88672340b08f347b632..8c65677aae25a47aad7fd2e9878dba812029e2d5 100644 --- a/llvm/include/llvm/ExecutionEngine/Orc/TaskDispatch.h +++ b/llvm/include/llvm/ExecutionEngine/Orc/TaskDispatch.h @@ -23,6 +23,7 @@ #if LLVM_ENABLE_THREADS #include +#include #include #include #endif @@ -114,6 +115,9 @@ public: class DynamicThreadPoolTaskDispatcher : public TaskDispatcher { public: + DynamicThreadPoolTaskDispatcher( + std::optional MaxMaterializationThreads) + : MaxMaterializationThreads(MaxMaterializationThreads) {} void dispatch(std::unique_ptr T) override; void shutdown() override; private: @@ -121,6 +125,10 @@ private: bool Running = true; size_t Outstanding = 0; std::condition_variable OutstandingCV; + + std::optional MaxMaterializationThreads; + size_t NumMaterializationThreads = 0; + std::deque> MaterializationTaskQueue; }; #endif // LLVM_ENABLE_THREADS diff --git a/llvm/include/llvm/Frontend/OpenMP/OMP.h b/llvm/include/llvm/Frontend/OpenMP/OMP.h index ec8ae68f1c2ca0e7137128e3315b5a19996bd189..6f7a39acac1d319a82c9bc6766d52c26bf5cb201 100644 --- a/llvm/include/llvm/Frontend/OpenMP/OMP.h +++ b/llvm/include/llvm/Frontend/OpenMP/OMP.h @@ -16,9 +16,15 @@ #include "llvm/Frontend/OpenMP/OMP.h.inc" #include "llvm/ADT/ArrayRef.h" +#include "llvm/ADT/SmallVector.h" namespace llvm::omp { ArrayRef getLeafConstructs(Directive D); +ArrayRef getLeafConstructsOrSelf(Directive D); + +ArrayRef +getLeafOrCompositeConstructs(Directive D, SmallVectorImpl &Output); + Directive getCompoundConstruct(ArrayRef Parts); bool isLeafConstruct(Directive D); diff --git a/llvm/include/llvm/Frontend/OpenMP/OMPKinds.def b/llvm/include/llvm/Frontend/OpenMP/OMPKinds.def index d22d2a8e948b00ed04a70e72a0ad0853ae18af6b..fe09bb8177c28eba171641a9d35f8f72cd846e43 100644 --- a/llvm/include/llvm/Frontend/OpenMP/OMPKinds.def +++ b/llvm/include/llvm/Frontend/OpenMP/OMPKinds.def @@ -436,7 +436,6 @@ __OMP_RTL(__tgt_target_kernel, false, Int32, IdentPtr, Int64, Int32, Int32, VoidPtr, KernelArgsPtr) __OMP_RTL(__tgt_target_kernel_nowait, false, Int32, IdentPtr, Int64, Int32, Int32, VoidPtr, KernelArgsPtr, Int32, VoidPtr, Int32, VoidPtr) -__OMP_RTL(__tgt_register_requires, false, Void, Int64) __OMP_RTL(__tgt_target_data_begin_mapper, false, Void, IdentPtr, Int64, Int32, VoidPtrPtr, VoidPtrPtr, Int64Ptr, Int64Ptr, VoidPtrPtr, VoidPtrPtr) __OMP_RTL(__tgt_target_data_begin_nowait_mapper, false, Void, IdentPtr, Int64, Int32, @@ -1025,8 +1024,6 @@ __OMP_RTL_ATTRS(__tgt_target_kernel_nowait, ForkAttrs, SExt, ParamAttrs(AttributeSet(), AttributeSet(), SExt, SExt, AttributeSet(), AttributeSet(), SExt, AttributeSet(), SExt)) -__OMP_RTL_ATTRS(__tgt_register_requires, ForkAttrs, AttributeSet(), - ParamAttrs()) __OMP_RTL_ATTRS(__tgt_target_data_begin_mapper, ForkAttrs, AttributeSet(), ParamAttrs(AttributeSet(), AttributeSet(), SExt)) __OMP_RTL_ATTRS(__tgt_target_data_begin_nowait_mapper, ForkAttrs, AttributeSet(), diff --git a/llvm/include/llvm/IR/Attributes.h b/llvm/include/llvm/IR/Attributes.h index 7dd8a329029a3420a5ae9b78a0bd57688813df86..5e3ba1f32e6ab0c0756c1e200c238235064da60c 100644 --- a/llvm/include/llvm/IR/Attributes.h +++ b/llvm/include/llvm/IR/Attributes.h @@ -747,6 +747,11 @@ public: addDereferenceableOrNullParamAttr(LLVMContext &C, unsigned ArgNo, uint64_t Bytes) const; + /// Add the range attribute to the attribute set at the return value index. + /// Returns a new list because attribute lists are immutable. + [[nodiscard]] AttributeList addRangeRetAttr(LLVMContext &C, + const ConstantRange &CR) const; + /// Add the allocsize attribute to the attribute set at the given arg index. /// Returns a new list because attribute lists are immutable. [[nodiscard]] AttributeList diff --git a/llvm/include/llvm/IR/FixedMetadataKinds.def b/llvm/include/llvm/IR/FixedMetadataKinds.def index b375d0f0912060fc84fe5d58d42263bf075f17a7..5f4cc230a0f5ff1112f2ea00d4c08b4e5b5297ec 100644 --- a/llvm/include/llvm/IR/FixedMetadataKinds.def +++ b/llvm/include/llvm/IR/FixedMetadataKinds.def @@ -51,3 +51,4 @@ LLVM_FIXED_MD_KIND(MD_kcfi_type, "kcfi_type", 36) LLVM_FIXED_MD_KIND(MD_pcsections, "pcsections", 37) LLVM_FIXED_MD_KIND(MD_DIAssignID, "DIAssignID", 38) LLVM_FIXED_MD_KIND(MD_coro_outside_frame, "coro.outside.frame", 39) +LLVM_FIXED_MD_KIND(MD_mmra, "mmra", 40) diff --git a/llvm/include/llvm/IR/Function.h b/llvm/include/llvm/IR/Function.h index 60f41b30e91c24c62a1d1357acd21dd4dc1d2c55..cb514cde95b51ac64dd844c12c936db9995428a4 100644 --- a/llvm/include/llvm/IR/Function.h +++ b/llvm/include/llvm/IR/Function.h @@ -46,6 +46,7 @@ typedef unsigned ID; class AssemblyAnnotationWriter; class Constant; +class ConstantRange; struct DenormalMode; class DISubprogram; enum LibFunc : unsigned; @@ -462,6 +463,9 @@ public: /// attributes for the given arg. void addDereferenceableOrNullParamAttr(unsigned ArgNo, uint64_t Bytes); + /// adds the range attribute to the list of attributes for the return value. + void addRangeRetAttr(const ConstantRange &CR); + MaybeAlign getParamAlign(unsigned ArgNo) const { return AttributeSets.getParamAlignment(ArgNo); } diff --git a/llvm/include/llvm/IR/GenericConvergenceVerifierImpl.h b/llvm/include/llvm/IR/GenericConvergenceVerifierImpl.h index a3ebde709ae6e1cfe8d79c6153304e83f4b93778..7525c9eb758bef39febc539e9dd2413fd205bcc4 100644 --- a/llvm/include/llvm/IR/GenericConvergenceVerifierImpl.h +++ b/llvm/include/llvm/IR/GenericConvergenceVerifierImpl.h @@ -76,7 +76,7 @@ void GenericConvergenceVerifier::visit(const InstructionT &I) { "Entry intrinsic cannot be preceded by a convergent operation in the " "same basic block.", {Context.print(&I)}); - LLVM_FALLTHROUGH; + [[fallthrough]]; case CONV_ANCHOR: Check(!TokenDef, "Entry or anchor intrinsic cannot have a convergencectrl token " diff --git a/llvm/include/llvm/IR/InstrTypes.h b/llvm/include/llvm/IR/InstrTypes.h index 8e6bef69218c2b1f03399b42b5def311503de46b..b9af3a6ca42c06dc65e9f70a65adc29043a234d8 100644 --- a/llvm/include/llvm/IR/InstrTypes.h +++ b/llvm/include/llvm/IR/InstrTypes.h @@ -1941,6 +1941,11 @@ public: Attrs = Attrs.addDereferenceableRetAttr(getContext(), Bytes); } + /// adds the range attribute to the list of attributes. + void addRangeRetAttr(const ConstantRange &CR) { + Attrs = Attrs.addRangeRetAttr(getContext(), CR); + } + /// Determine whether the return value has the given attribute. bool hasRetAttr(Attribute::AttrKind Kind) const { return hasRetAttrImpl(Kind); diff --git a/llvm/include/llvm/IR/IntrinsicInst.h b/llvm/include/llvm/IR/IntrinsicInst.h index 4f22720f1c558d9a27cc90b402ef592de528b3a3..2e99c9e2ee3e6f75987f93ac3a2441ebf026bdb2 100644 --- a/llvm/include/llvm/IR/IntrinsicInst.h +++ b/llvm/include/llvm/IR/IntrinsicInst.h @@ -311,7 +311,8 @@ public: Value *getVariableLocationOp(unsigned OpIdx) const; - void replaceVariableLocationOp(Value *OldValue, Value *NewValue); + void replaceVariableLocationOp(Value *OldValue, Value *NewValue, + bool AllowEmpty = false); void replaceVariableLocationOp(unsigned OpIdx, Value *NewValue); /// Adding a new location operand will always result in this intrinsic using /// an ArgList, and must always be accompanied by a new expression that uses @@ -1435,6 +1436,7 @@ protected: case Intrinsic::instrprof_cover: case Intrinsic::instrprof_increment: case Intrinsic::instrprof_increment_step: + case Intrinsic::instrprof_callsite: case Intrinsic::instrprof_timestamp: case Intrinsic::instrprof_value_profile: return true; @@ -1519,6 +1521,21 @@ public: } }; +/// This represents the llvm.instrprof.callsite intrinsic. +/// It is structurally like the increment or step counters, hence the +/// inheritance relationship, albeit somewhat tenuous (it's not 'counting' per +/// se) +class InstrProfCallsite : public InstrProfCntrInstBase { +public: + static bool classof(const IntrinsicInst *I) { + return I->getIntrinsicID() == Intrinsic::instrprof_callsite; + } + static bool classof(const Value *V) { + return isa(V) && classof(cast(V)); + } + Value *getCallee() const; +}; + /// This represents the llvm.instrprof.timestamp intrinsic. class InstrProfTimestampInst : public InstrProfCntrInstBase { public: diff --git a/llvm/include/llvm/IR/Intrinsics.td b/llvm/include/llvm/IR/Intrinsics.td index 1d20f7e1b19854f20798ce74314d25adccbe5b1b..a14e9dedef8c9eeaa8431bbeb665d6efdd0d0560 100644 --- a/llvm/include/llvm/IR/Intrinsics.td +++ b/llvm/include/llvm/IR/Intrinsics.td @@ -914,6 +914,11 @@ def int_instrprof_increment_step : Intrinsic<[], [llvm_ptr_ty, llvm_i64_ty, llvm_i32_ty, llvm_i32_ty, llvm_i64_ty]>; +// Callsite instrumentation for contextual profiling +def int_instrprof_callsite : Intrinsic<[], + [llvm_ptr_ty, llvm_i64_ty, + llvm_i32_ty, llvm_i32_ty, llvm_ptr_ty]>; + // A timestamp for instrumentation based profiling. def int_instrprof_timestamp : Intrinsic<[], [llvm_ptr_ty, llvm_i64_ty, llvm_i32_ty, llvm_i32_ty]>; diff --git a/llvm/include/llvm/IR/IntrinsicsAArch64.td b/llvm/include/llvm/IR/IntrinsicsAArch64.td index bcaa37de74b630986484c703e0c1bf88c76381e0..e31e00a9c76f31078e8cf2b5e6c264397ee6dab5 100644 --- a/llvm/include/llvm/IR/IntrinsicsAArch64.td +++ b/llvm/include/llvm/IR/IntrinsicsAArch64.td @@ -1762,6 +1762,7 @@ def int_aarch64_sve_uqsub_x : AdvSIMD_2VectorArg_Intrinsic; def int_aarch64_sve_orqv : AdvSIMD_SVE_V128_Reduce_Intrinsic; def int_aarch64_sve_eorqv : AdvSIMD_SVE_V128_Reduce_Intrinsic; def int_aarch64_sve_andqv : AdvSIMD_SVE_V128_Reduce_Intrinsic; +def int_aarch64_sve_addqv : AdvSIMD_SVE_V128_Reduce_Intrinsic; def int_aarch64_sve_smaxqv : AdvSIMD_SVE_V128_Reduce_Intrinsic; def int_aarch64_sve_umaxqv : AdvSIMD_SVE_V128_Reduce_Intrinsic; def int_aarch64_sve_sminqv : AdvSIMD_SVE_V128_Reduce_Intrinsic; @@ -2079,11 +2080,12 @@ def int_aarch64_sve_fmaxv : AdvSIMD_SVE_Reduce_Intrinsic; def int_aarch64_sve_fmaxnmv : AdvSIMD_SVE_Reduce_Intrinsic; def int_aarch64_sve_fminv : AdvSIMD_SVE_Reduce_Intrinsic; def int_aarch64_sve_fminnmv : AdvSIMD_SVE_Reduce_Intrinsic; -def int_aarch64_sve_addqv : AdvSIMD_SVE_V128_Reduce_Intrinsic; + +def int_aarch64_sve_faddqv : AdvSIMD_SVE_V128_Reduce_Intrinsic; def int_aarch64_sve_fmaxnmqv : AdvSIMD_SVE_V128_Reduce_Intrinsic; def int_aarch64_sve_fminnmqv : AdvSIMD_SVE_V128_Reduce_Intrinsic; -def int_aarch64_sve_fmaxqv : AdvSIMD_SVE_V128_Reduce_Intrinsic; -def int_aarch64_sve_fminqv : AdvSIMD_SVE_V128_Reduce_Intrinsic; +def int_aarch64_sve_fmaxqv : AdvSIMD_SVE_V128_Reduce_Intrinsic; +def int_aarch64_sve_fminqv : AdvSIMD_SVE_V128_Reduce_Intrinsic; // // Floating-point conversions @@ -3646,4 +3648,4 @@ def int_aarch64_sve_pmov_to_pred_lane_zero : SVE2_1VectorArg_Pred_Intrinsic; def int_aarch64_sve_pmov_to_vector_lane_merging : SVE2_Pred_1VectorArgIndexed_Intrinsic; -def int_aarch64_sve_pmov_to_vector_lane_zeroing : SVE2_Pred_1VectorArg_Intrinsic; \ No newline at end of file +def int_aarch64_sve_pmov_to_vector_lane_zeroing : SVE2_Pred_1VectorArg_Intrinsic; diff --git a/llvm/include/llvm/IR/IntrinsicsNVVM.td b/llvm/include/llvm/IR/IntrinsicsNVVM.td index 726cea004606e2503da7d2742af90cbbeb0bc8fc..0a9139e0062ba3c1cb3d746e2f004a077d3a212f 100644 --- a/llvm/include/llvm/IR/IntrinsicsNVVM.td +++ b/llvm/include/llvm/IR/IntrinsicsNVVM.td @@ -1003,6 +1003,8 @@ let TargetPrefix = "nvvm" in { def int_nvvm_rsqrt_approx_ftz_f : ClangBuiltin<"__nvvm_rsqrt_approx_ftz_f">, DefaultAttrsIntrinsic<[llvm_float_ty], [llvm_float_ty], [IntrNoMem]>; + def int_nvvm_rsqrt_approx_ftz_d : ClangBuiltin<"__nvvm_rsqrt_approx_ftz_d">, + DefaultAttrsIntrinsic<[llvm_double_ty], [llvm_double_ty], [IntrNoMem]>; def int_nvvm_rsqrt_approx_f : ClangBuiltin<"__nvvm_rsqrt_approx_f">, DefaultAttrsIntrinsic<[llvm_float_ty], [llvm_float_ty], [IntrNoMem]>; def int_nvvm_rsqrt_approx_d : ClangBuiltin<"__nvvm_rsqrt_approx_d">, diff --git a/llvm/include/llvm/IR/MemoryModelRelaxationAnnotations.h b/llvm/include/llvm/IR/MemoryModelRelaxationAnnotations.h new file mode 100644 index 0000000000000000000000000000000000000000..a9ded6034d0b4e7e9d84699c50cf006fef6ca10d --- /dev/null +++ b/llvm/include/llvm/IR/MemoryModelRelaxationAnnotations.h @@ -0,0 +1,132 @@ +//===- MemoryModelRelaxationAnnotations.h -----------------------*- C++ -*-===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// +// +/// \file +/// This file provides utility for Memory Model Relaxation Annotations (MMRAs). +/// Those annotations are represented using Metadata. The MMRATagSet class +/// offers a simple API to parse the metadata and perform common operations on +/// it. The MMRAMetadata class is a simple tuple of MDNode that provides easy +/// access to all MMRA annotations on an instruction. +// +//===----------------------------------------------------------------------===// + +#ifndef LLVM_IR_MEMORYMODELRELAXATIONANNOTATIONS_H +#define LLVM_IR_MEMORYMODELRELAXATIONANNOTATIONS_H + +#include "llvm/ADT/DenseSet.h" +#include "llvm/ADT/StringRef.h" +#include // for std::pair + +namespace llvm { + +template class ArrayRef; + +class MDNode; +class MDTuple; +class Metadata; +class raw_ostream; +class LLVMContext; +class Instruction; + +/// Helper class to manipulate `!mmra` metadata nodes. +/// +/// This can be visualized as a set of "tags", with each tag +/// representing a particular property of an instruction, as +/// explained in the MemoryModelRelaxationAnnotations docs. +/// +/// This class (and the optimizer in general) does not reason +/// about the exact nature of the tags and the properties they +/// imply. It just sees the metadata as a collection of tags, which +/// are a prefix/suffix pair of strings. +class MMRAMetadata { +public: + using TagT = std::pair; + using SetT = DenseSet; + using const_iterator = SetT::const_iterator; + + /// \name Constructors + /// @{ + MMRAMetadata() = default; + MMRAMetadata(const Instruction &I); + MMRAMetadata(MDNode *MD); + /// @} + + /// \name Metadata Helpers & Builders + /// @{ + + /// Combines \p A and \p B according to MMRA semantics. + /// \returns !mmra metadata for the combined MMRAs. + static MDNode *combine(LLVMContext &Ctx, const MMRAMetadata &A, + const MMRAMetadata &B); + + /// Creates !mmra metadata for a single tag. + /// + /// !mmra metadata can either be a single tag, or a MDTuple containing + /// multiple tags. + static MDTuple *getTagMD(LLVMContext &Ctx, StringRef Prefix, + StringRef Suffix); + static MDTuple *getTagMD(LLVMContext &Ctx, const TagT &T) { + return getTagMD(Ctx, T.first, T.second); + } + + /// Creates !mmra metadata from \p Tags. + /// \returns nullptr or a MDTuple* from \p Tags. + static MDTuple *getMD(LLVMContext &Ctx, ArrayRef Tags); + + /// \returns true if \p MD is a well-formed MMRA tag. + static bool isTagMD(const Metadata *MD); + + /// @} + + /// \name Compatibility Helpers + /// @{ + + /// \returns whether the MMRAs on \p A and \p B are compatible. + static bool checkCompatibility(const Instruction &A, const Instruction &B) { + return MMRAMetadata(A).isCompatibleWith(B); + } + + /// \returns whether this set of tags is compatible with \p Other. + bool isCompatibleWith(const MMRAMetadata &Other) const; + + /// @} + + /// \name Content Queries + /// @{ + + bool hasTag(StringRef Prefix, StringRef Suffix) const; + bool hasTagWithPrefix(StringRef Prefix) const; + + const_iterator begin() const; + const_iterator end() const; + bool empty() const; + unsigned size() const; + + /// @} + + void print(raw_ostream &OS) const; + void dump() const; + + operator bool() const { return !Tags.empty(); } + bool operator==(const MMRAMetadata &Other) const { + return Tags == Other.Tags; + } + bool operator!=(const MMRAMetadata &Other) const { + return Tags != Other.Tags; + } + +private: + SetT Tags; +}; + +/// \returns true if \p I can have !mmra metadata. +bool canInstructionHaveMMRAs(const Instruction &I); + +} // namespace llvm + +#endif diff --git a/llvm/include/llvm/IR/PatternMatch.h b/llvm/include/llvm/IR/PatternMatch.h index 1fee1901fabb65d8798a311966bc9036bae31e4b..0b13b4aad9c326aa8ee20d5e392f87583c4907af 100644 --- a/llvm/include/llvm/IR/PatternMatch.h +++ b/llvm/include/llvm/IR/PatternMatch.h @@ -350,8 +350,9 @@ template inline constantint_match m_ConstantInt() { /// This helper class is used to match constant scalars, vector splats, /// and fixed width vectors that satisfy a specified predicate. -/// For fixed width vector constants, poison elements are ignored. -template +/// For fixed width vector constants, poison elements are ignored if AllowPoison +/// is true. +template struct cstval_pred_ty : public Predicate { template bool match(ITy *V) { if (const auto *CV = dyn_cast(V)) @@ -374,7 +375,7 @@ struct cstval_pred_ty : public Predicate { Constant *Elt = C->getAggregateElement(i); if (!Elt) return false; - if (isa(Elt)) + if (AllowPoison && isa(Elt)) continue; auto *CV = dyn_cast(Elt); if (!CV || !this->isValue(CV->getValue())) @@ -389,12 +390,13 @@ struct cstval_pred_ty : public Predicate { }; /// specialization of cstval_pred_ty for ConstantInt -template -using cst_pred_ty = cstval_pred_ty; +template +using cst_pred_ty = cstval_pred_ty; /// specialization of cstval_pred_ty for ConstantFP template -using cstfp_pred_ty = cstval_pred_ty; +using cstfp_pred_ty = cstval_pred_ty; /// This helper class is used to match scalar and vector constants that /// satisfy a specified predicate, and bind them to an APInt. @@ -484,6 +486,10 @@ inline cst_pred_ty m_AllOnes() { return cst_pred_ty(); } +inline cst_pred_ty m_AllOnesForbidPoison() { + return cst_pred_ty(); +} + struct is_maxsignedvalue { bool isValue(const APInt &C) { return C.isMaxSignedValue(); } }; @@ -2596,6 +2602,13 @@ m_Not(const ValTy &V) { return m_c_Xor(m_AllOnes(), V); } +template +inline BinaryOp_match, ValTy, Instruction::Xor, + true> +m_NotForbidPoison(const ValTy &V) { + return m_c_Xor(m_AllOnesForbidPoison(), V); +} + /// Matches an SMin with LHS and RHS in either order. template inline MaxMin_match diff --git a/llvm/include/llvm/MC/MCELFStreamer.h b/llvm/include/llvm/MC/MCELFStreamer.h index 1309b17bff9c14b8c469b3465a63d3b5d73aa68c..1ff029d44d376c9e5387ab61cd0832b403b4bb38 100644 --- a/llvm/include/llvm/MC/MCELFStreamer.h +++ b/llvm/include/llvm/MC/MCELFStreamer.h @@ -156,7 +156,7 @@ MCELFStreamer *createARMELFStreamer(MCContext &Context, std::unique_ptr TAB, std::unique_ptr OW, std::unique_ptr Emitter, - bool RelaxAll, bool IsThumb, bool IsAndroid); + bool IsThumb, bool IsAndroid); } // end namespace llvm diff --git a/llvm/include/llvm/MC/TargetRegistry.h b/llvm/include/llvm/MC/TargetRegistry.h index 47051447404d00f83e48588ab53c57c6f30b86f1..5038b87cd1dc90e8d4ad29cf503384f2713f4736 100644 --- a/llvm/include/llvm/MC/TargetRegistry.h +++ b/llvm/include/llvm/MC/TargetRegistry.h @@ -92,39 +92,33 @@ createAsmStreamer(MCContext &Ctx, std::unique_ptr OS, MCStreamer *createELFStreamer(MCContext &Ctx, std::unique_ptr &&TAB, std::unique_ptr &&OW, - std::unique_ptr &&CE, - bool RelaxAll); + std::unique_ptr &&CE); MCStreamer *createGOFFStreamer(MCContext &Ctx, std::unique_ptr &&TAB, std::unique_ptr &&OW, - std::unique_ptr &&CE, - bool RelaxAll); + std::unique_ptr &&CE); MCStreamer *createMachOStreamer(MCContext &Ctx, std::unique_ptr &&TAB, std::unique_ptr &&OW, std::unique_ptr &&CE, - bool RelaxAll, bool DWARFMustBeAtTheEnd, + bool DWARFMustBeAtTheEnd, bool LabelSections = false); MCStreamer *createWasmStreamer(MCContext &Ctx, std::unique_ptr &&TAB, std::unique_ptr &&OW, - std::unique_ptr &&CE, - bool RelaxAll); + std::unique_ptr &&CE); MCStreamer *createXCOFFStreamer(MCContext &Ctx, std::unique_ptr &&TAB, std::unique_ptr &&OW, - std::unique_ptr &&CE, - bool RelaxAll); + std::unique_ptr &&CE); MCStreamer *createSPIRVStreamer(MCContext &Ctx, std::unique_ptr &&TAB, std::unique_ptr &&OW, - std::unique_ptr &&CE, - bool RelaxAll); + std::unique_ptr &&CE); MCStreamer *createDXContainerStreamer(MCContext &Ctx, std::unique_ptr &&TAB, std::unique_ptr &&OW, - std::unique_ptr &&CE, - bool RelaxAll); + std::unique_ptr &&CE); MCRelocationInfo *createMCRelocationInfo(const Triple &TT, MCContext &Ctx); @@ -199,42 +193,42 @@ public: MCStreamer *(*)(const Triple &T, MCContext &Ctx, std::unique_ptr &&TAB, std::unique_ptr &&OW, - std::unique_ptr &&Emitter, bool RelaxAll); + std::unique_ptr &&Emitter); using GOFFStreamerCtorTy = MCStreamer *(*)(MCContext &Ctx, std::unique_ptr &&TAB, std::unique_ptr &&OW, - std::unique_ptr &&Emitter, bool RelaxAll); + std::unique_ptr &&Emitter); using MachOStreamerCtorTy = MCStreamer *(*)(MCContext &Ctx, std::unique_ptr &&TAB, std::unique_ptr &&OW, - std::unique_ptr &&Emitter, bool RelaxAll, + std::unique_ptr &&Emitter, bool DWARFMustBeAtTheEnd); using COFFStreamerCtorTy = MCStreamer *(*)(MCContext &Ctx, std::unique_ptr &&TAB, std::unique_ptr &&OW, - std::unique_ptr &&Emitter, bool RelaxAll, + std::unique_ptr &&Emitter, bool IncrementalLinkerCompatible); using WasmStreamerCtorTy = MCStreamer *(*)(const Triple &T, MCContext &Ctx, std::unique_ptr &&TAB, std::unique_ptr &&OW, - std::unique_ptr &&Emitter, bool RelaxAll); + std::unique_ptr &&Emitter); using XCOFFStreamerCtorTy = MCStreamer *(*)(const Triple &T, MCContext &Ctx, std::unique_ptr &&TAB, std::unique_ptr &&OW, - std::unique_ptr &&Emitter, bool RelaxAll); + std::unique_ptr &&Emitter); using SPIRVStreamerCtorTy = MCStreamer *(*)(const Triple &T, MCContext &Ctx, std::unique_ptr &&TAB, std::unique_ptr &&OW, - std::unique_ptr &&Emitter, bool RelaxAll); - + std::unique_ptr &&Emitter); + using DXContainerStreamerCtorTy = MCStreamer *(*)(const Triple &T, MCContext &Ctx, std::unique_ptr &&TAB, std::unique_ptr &&OW, - std::unique_ptr &&Emitter, bool RelaxAll); + std::unique_ptr &&Emitter); using NullTargetStreamerCtorTy = MCTargetStreamer *(*)(MCStreamer &S); using AsmTargetStreamerCtorTy = MCTargetStreamer *(*)( @@ -566,7 +560,7 @@ public: std::unique_ptr &&TAB, std::unique_ptr &&OW, std::unique_ptr &&Emitter, - const MCSubtargetInfo &STI, bool RelaxAll, + const MCSubtargetInfo &STI, bool, bool IncrementalLinkerCompatible, bool DWARFMustBeAtTheEnd) const { MCStreamer *S = nullptr; @@ -577,66 +571,63 @@ public: assert((T.isOSWindows() || T.isUEFI()) && "only Windows and UEFI COFF are supported"); S = COFFStreamerCtorFn(Ctx, std::move(TAB), std::move(OW), - std::move(Emitter), RelaxAll, - IncrementalLinkerCompatible); + std::move(Emitter), IncrementalLinkerCompatible); break; case Triple::MachO: if (MachOStreamerCtorFn) S = MachOStreamerCtorFn(Ctx, std::move(TAB), std::move(OW), - std::move(Emitter), RelaxAll, - DWARFMustBeAtTheEnd); + std::move(Emitter), DWARFMustBeAtTheEnd); else S = createMachOStreamer(Ctx, std::move(TAB), std::move(OW), - std::move(Emitter), RelaxAll, - DWARFMustBeAtTheEnd); + std::move(Emitter), DWARFMustBeAtTheEnd); break; case Triple::ELF: if (ELFStreamerCtorFn) S = ELFStreamerCtorFn(T, Ctx, std::move(TAB), std::move(OW), - std::move(Emitter), RelaxAll); + std::move(Emitter)); else S = createELFStreamer(Ctx, std::move(TAB), std::move(OW), - std::move(Emitter), RelaxAll); + std::move(Emitter)); break; case Triple::Wasm: if (WasmStreamerCtorFn) S = WasmStreamerCtorFn(T, Ctx, std::move(TAB), std::move(OW), - std::move(Emitter), RelaxAll); + std::move(Emitter)); else S = createWasmStreamer(Ctx, std::move(TAB), std::move(OW), - std::move(Emitter), RelaxAll); + std::move(Emitter)); break; case Triple::GOFF: if (GOFFStreamerCtorFn) S = GOFFStreamerCtorFn(Ctx, std::move(TAB), std::move(OW), - std::move(Emitter), RelaxAll); + std::move(Emitter)); else S = createGOFFStreamer(Ctx, std::move(TAB), std::move(OW), - std::move(Emitter), RelaxAll); + std::move(Emitter)); break; case Triple::XCOFF: if (XCOFFStreamerCtorFn) S = XCOFFStreamerCtorFn(T, Ctx, std::move(TAB), std::move(OW), - std::move(Emitter), RelaxAll); + std::move(Emitter)); else S = createXCOFFStreamer(Ctx, std::move(TAB), std::move(OW), - std::move(Emitter), RelaxAll); + std::move(Emitter)); break; case Triple::SPIRV: if (SPIRVStreamerCtorFn) S = SPIRVStreamerCtorFn(T, Ctx, std::move(TAB), std::move(OW), - std::move(Emitter), RelaxAll); + std::move(Emitter)); else S = createSPIRVStreamer(Ctx, std::move(TAB), std::move(OW), - std::move(Emitter), RelaxAll); + std::move(Emitter)); break; case Triple::DXContainer: if (DXContainerStreamerCtorFn) S = DXContainerStreamerCtorFn(T, Ctx, std::move(TAB), std::move(OW), - std::move(Emitter), RelaxAll); + std::move(Emitter)); else S = createDXContainerStreamer(Ctx, std::move(TAB), std::move(OW), - std::move(Emitter), RelaxAll); + std::move(Emitter)); break; } if (ObjectTargetStreamerCtorFn) diff --git a/llvm/include/llvm/ProfileData/InstrProfWriter.h b/llvm/include/llvm/ProfileData/InstrProfWriter.h index b0ae8f364fcafb91f7729c424bbca05daa4f76a4..08db8fa6e7ef2cd40814f137a22f70df6cea044c 100644 --- a/llvm/include/llvm/ProfileData/InstrProfWriter.h +++ b/llvm/include/llvm/ProfileData/InstrProfWriter.h @@ -85,11 +85,15 @@ private: // The MemProf version we should write. memprof::IndexedVersion MemProfVersionRequested; + // Whether to serialize the full schema. + bool MemProfFullSchema; + public: InstrProfWriter( bool Sparse = false, uint64_t TemporalProfTraceReservoirSize = 0, uint64_t MaxTemporalProfTraceLength = 0, bool WritePrevVersion = false, - memprof::IndexedVersion MemProfVersionRequested = memprof::Version0); + memprof::IndexedVersion MemProfVersionRequested = memprof::Version0, + bool MemProfFullSchema = false); ~InstrProfWriter(); StringMap &getProfileData() { return FunctionData; } @@ -203,6 +207,7 @@ public: void setMemProfVersionRequested(memprof::IndexedVersion Version) { MemProfVersionRequested = Version; } + void setMemProfFullSchema(bool Full) { MemProfFullSchema = Full; } // Compute the overlap b/w this object and Other. Program level result is // stored in Overlap and function level result is stored in FuncLevelOverlap. void overlapRecord(NamedInstrProfRecord &&Other, OverlapStats &Overlap, diff --git a/llvm/include/llvm/ProfileData/MemProf.h b/llvm/include/llvm/ProfileData/MemProf.h index aa6cdf198485b03a935b02d85182f3bbbdb66cea..d378c3696f8d0bbd368a6a0518eba59a1e6571cf 100644 --- a/llvm/include/llvm/ProfileData/MemProf.h +++ b/llvm/include/llvm/ProfileData/MemProf.h @@ -44,6 +44,12 @@ enum class Meta : uint64_t { using MemProfSchema = llvm::SmallVector(Meta::Size)>; +// Returns the full schema currently in use. +MemProfSchema getFullSchema(); + +// Returns the schema consisting of the fields used for hot cold memory hinting. +MemProfSchema getHotColdSchema(); + // Holds the actual MemInfoBlock data with all fields. Contents may be read or // written partially by providing an appropriate schema to the serialize and // deserialize methods. @@ -116,15 +122,6 @@ struct PortableMemInfoBlock { void clear() { *this = PortableMemInfoBlock(); } - // Returns the full schema currently in use. - static MemProfSchema getSchema() { - MemProfSchema List; -#define MIBEntryDef(NameTag, Name, Type) List.push_back(Meta::Name); -#include "llvm/ProfileData/MIBEntryDef.inc" -#undef MIBEntryDef - return List; - } - bool operator==(const PortableMemInfoBlock &Other) const { #define MIBEntryDef(NameTag, Name, Type) \ if (Other.get##Name() != get##Name()) \ @@ -138,11 +135,22 @@ struct PortableMemInfoBlock { return !operator==(Other); } - static constexpr size_t serializedSize() { + static size_t serializedSize(const MemProfSchema &Schema) { size_t Result = 0; -#define MIBEntryDef(NameTag, Name, Type) Result += sizeof(Type); + + for (const Meta Id : Schema) { + switch (Id) { +#define MIBEntryDef(NameTag, Name, Type) \ + case Meta::Name: { \ + Result += sizeof(Type); \ + } break; #include "llvm/ProfileData/MIBEntryDef.inc" #undef MIBEntryDef + default: + llvm_unreachable("Unknown meta type id, invalid input?"); + } + } + return Result; } @@ -292,7 +300,8 @@ struct IndexedAllocationInfo { : CallStack(CS.begin(), CS.end()), CSId(CSId), Info(MB) {} // Returns the size in bytes when this allocation info struct is serialized. - size_t serializedSize(IndexedVersion Version) const; + size_t serializedSize(const MemProfSchema &Schema, + IndexedVersion Version) const; bool operator==(const IndexedAllocationInfo &Other) const { if (Other.Info != Info) @@ -367,7 +376,8 @@ struct IndexedMemProfRecord { CallSites.append(Other.CallSites); } - size_t serializedSize(IndexedVersion Version) const; + size_t serializedSize(const MemProfSchema &Schema, + IndexedVersion Version) const; bool operator==(const IndexedMemProfRecord &Other) const { if (Other.AllocSites != AllocSites) @@ -535,7 +545,7 @@ public: endian::Writer LE(Out, llvm::endianness::little); offset_type N = sizeof(K); LE.write(N); - offset_type M = V.serializedSize(Version); + offset_type M = V.serializedSize(*Schema, Version); LE.write(M); return std::make_pair(N, M); } diff --git a/llvm/include/llvm/Support/RISCVISAUtils.h b/llvm/include/llvm/Support/RISCVISAUtils.h new file mode 100644 index 0000000000000000000000000000000000000000..94aedb75faa2567730eca23349ec7210b6c63c57 --- /dev/null +++ b/llvm/include/llvm/Support/RISCVISAUtils.h @@ -0,0 +1,42 @@ +//===-- RISCVISAUtils.h - RISC-V ISA Utilities ------------------*- C++ -*-===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// +// +// Utilities shared by TableGen and RISCVISAInfo. +// +//===----------------------------------------------------------------------===// + +#ifndef LLVM_SUPPORT_RISCVISAUTILS_H +#define LLVM_SUPPORT_RISCVISAUTILS_H + +#include "llvm/ADT/StringRef.h" +#include + +namespace llvm { + +namespace RISCVISAUtils { +constexpr StringLiteral AllStdExts = "mafdqlcbkjtpvnh"; + +/// Represents the major and version number components of a RISC-V extension. +struct ExtensionVersion { + unsigned Major; + unsigned Minor; +}; + +bool compareExtension(const std::string &LHS, const std::string &RHS); + +/// Helper class for OrderedExtensionMap. +struct ExtensionComparator { + bool operator()(const std::string &LHS, const std::string &RHS) const { + return compareExtension(LHS, RHS); + } +}; +} // namespace RISCVISAUtils + +} // namespace llvm + +#endif diff --git a/llvm/include/llvm/Target/TargetSelectionDAG.td b/llvm/include/llvm/Target/TargetSelectionDAG.td index ea3520835fa07d6b5690976c1024cfcff9f07f61..1684b424e3b44292b6db907c9799cb243d37ca57 100644 --- a/llvm/include/llvm/Target/TargetSelectionDAG.td +++ b/llvm/include/llvm/Target/TargetSelectionDAG.td @@ -1979,6 +1979,7 @@ class Pattern resultInstrs> { list ResultInstrs = resultInstrs; list Predicates = []; // See class Instruction in Target.td. int AddedComplexity = 0; // See class Instruction in Target.td. + bit GISelShouldIgnore = 0; } // Pat - A simple (but common) form of a pattern, which produces a simple result diff --git a/llvm/include/llvm/TargetParser/AArch64TargetParser.h b/llvm/include/llvm/TargetParser/AArch64TargetParser.h index 805b963a7a13c7c0d6847038f29e9fb70c45393c..0d1cfd152151aaa88344c0219ca43b4d75f19f40 100644 --- a/llvm/include/llvm/TargetParser/AArch64TargetParser.h +++ b/llvm/include/llvm/TargetParser/AArch64TargetParser.h @@ -268,7 +268,7 @@ inline constexpr ExtensionInfo Extensions[] = { {"sha3", AArch64::AEK_SHA3, "+sha3", "-sha3", FEAT_SHA3, "+sha3,+sha2,+fp-armv8,+neon", 140}, {"simd", AArch64::AEK_SIMD, "+neon", "-neon", FEAT_SIMD, "+fp-armv8,+neon", 100}, {"sm4", AArch64::AEK_SM4, "+sm4", "-sm4", FEAT_SM4, "+sm4,+fp-armv8,+neon", 106}, - {"sme-f16f16", AArch64::AEK_SMEF16F16, "+sme-f16f16", "-sme-f16f16", FEAT_INIT, "", 0}, + {"sme-f16f16", AArch64::AEK_SMEF16F16, "+sme-f16f16", "-sme-f16f16", FEAT_INIT, "+sme2,+sme-f16f16", 0}, {"sme-f64f64", AArch64::AEK_SMEF64F64, "+sme-f64f64", "-sme-f64f64", FEAT_SME_F64, "+sme,+sme-f64f64,+bf16", 560}, {"sme-i16i64", AArch64::AEK_SMEI16I64, "+sme-i16i64", "-sme-i16i64", FEAT_SME_I64, "+sme,+sme-i16i64,+bf16", 570}, {"sme", AArch64::AEK_SME, "+sme", "-sme", FEAT_SME, "+sme,+bf16", 430}, @@ -302,7 +302,7 @@ inline constexpr ExtensionInfo Extensions[] = { {"ssve-fp8dot4", AArch64::AEK_SSVE_FP8DOT4, "+ssve-fp8dot4", "-ssve-fp8dot4", FEAT_INIT, "+sme2", 0}, {"lut", AArch64::AEK_LUT, "+lut", "-lut", FEAT_INIT, "", 0}, {"sme-lutv2", AArch64::AEK_SME_LUTv2, "+sme-lutv2", "-sme-lutv2", FEAT_INIT, "", 0}, - {"sme-f8f16", AArch64::AEK_SMEF8F16, "+sme-f8f16", "-sme-f8f16", FEAT_INIT, "+sme2,+fp8", 0}, + {"sme-f8f16", AArch64::AEK_SMEF8F16, "+sme-f8f16", "-sme-f8f16", FEAT_INIT, "+fp8,+sme2", 0}, {"sme-f8f32", AArch64::AEK_SMEF8F32, "+sme-f8f32", "-sme-f8f32", FEAT_INIT, "+sme2,+fp8", 0}, {"sme-fa64", AArch64::AEK_SMEFA64, "+sme-fa64", "-sme-fa64", FEAT_INIT, "", 0}, {"cpa", AArch64::AEK_CPA, "+cpa", "-cpa", FEAT_INIT, "", 0}, @@ -677,6 +677,13 @@ inline constexpr CpuInfo CpuInfos[] = { AArch64::AEK_FP16FML, AArch64::AEK_I8MM, AArch64::AEK_MTE, AArch64::AEK_SB, AArch64::AEK_SSBS, AArch64::AEK_SVE, AArch64::AEK_SVE2, AArch64::AEK_SVE2BITPERM})}, + {"neoverse-n3", ARMV9_2A, + AArch64::ExtensionBitset({AArch64::AEK_MTE, AArch64::AEK_SSBS, + AArch64::AEK_SB, AArch64::AEK_PREDRES, + AArch64::AEK_FP16FML, AArch64::AEK_PAUTH, + AArch64::AEK_FLAGM, AArch64::AEK_PERFMON, + AArch64::AEK_RAND, AArch64::AEK_SVE2BITPERM, + AArch64::AEK_PROFILE, AArch64::AEK_PERFMON})}, {"neoverse-512tvb", ARMV8_4A, AArch64::ExtensionBitset( {AArch64::AEK_AES, AArch64::AEK_SHA2, AArch64::AEK_SHA3, @@ -697,6 +704,20 @@ inline constexpr CpuInfo CpuInfos[] = { AArch64::AEK_FP16, AArch64::AEK_BF16, AArch64::AEK_RAND, AArch64::AEK_DOTPROD, AArch64::AEK_PROFILE, AArch64::AEK_SVE2BITPERM, AArch64::AEK_FP16FML, AArch64::AEK_I8MM, AArch64::AEK_MTE})}, + {"neoverse-v3", ARMV9_2A, + AArch64::ExtensionBitset( + {AArch64::AEK_PROFILE, AArch64::AEK_MTE, AArch64::AEK_SSBS, + AArch64::AEK_SB, AArch64::AEK_PREDRES, AArch64::AEK_LS64, + AArch64::AEK_BRBE, AArch64::AEK_PAUTH, AArch64::AEK_FLAGM, + AArch64::AEK_PERFMON, AArch64::AEK_RAND, AArch64::AEK_SVE2BITPERM, + AArch64::AEK_FP16FML})}, + {"neoverse-v3ae", ARMV9_2A, + (AArch64::ExtensionBitset( + {AArch64::AEK_PROFILE, AArch64::AEK_MTE, AArch64::AEK_SSBS, + AArch64::AEK_SB, AArch64::AEK_PREDRES, AArch64::AEK_LS64, + AArch64::AEK_BRBE, AArch64::AEK_PAUTH, AArch64::AEK_FLAGM, + AArch64::AEK_PERFMON, AArch64::AEK_RAND, AArch64::AEK_SVE2BITPERM, + AArch64::AEK_FP16FML}))}, {"cyclone", ARMV8A, AArch64::ExtensionBitset( {AArch64::AEK_AES, AArch64::AEK_SHA2, AArch64::AEK_NONE})}, diff --git a/llvm/include/llvm/TargetParser/CMakeLists.txt b/llvm/include/llvm/TargetParser/CMakeLists.txt index 7f080e01548c7cc9f98fd02f3a488d1c7c59e1b7..f89d4eb5ea1638b02ddaf2e54168e63f8a3b0705 100644 --- a/llvm/include/llvm/TargetParser/CMakeLists.txt +++ b/llvm/include/llvm/TargetParser/CMakeLists.txt @@ -1,3 +1,12 @@ +set(LLVM_TARGET_DEFINITIONS ${PROJECT_SOURCE_DIR}/lib/Target/ARM/ARM.td) +tablegen(LLVM ARMTargetParserDef.inc -gen-arm-target-def -I ${PROJECT_SOURCE_DIR}/lib/Target/ARM/) +add_public_tablegen_target(ARMTargetParserTableGen) + +set(LLVM_TARGET_DEFINITIONS ${PROJECT_SOURCE_DIR}/lib/Target/AArch64/AArch64.td) +tablegen(LLVM AArch64TargetParserDef.inc -gen-arm-target-def -I ${PROJECT_SOURCE_DIR}/lib/Target/AArch64/) +add_public_tablegen_target(AArch64TargetParserTableGen) + set(LLVM_TARGET_DEFINITIONS ${PROJECT_SOURCE_DIR}/lib/Target/RISCV/RISCV.td) tablegen(LLVM RISCVTargetParserDef.inc -gen-riscv-target-def -I ${PROJECT_SOURCE_DIR}/lib/Target/RISCV/) add_public_tablegen_target(RISCVTargetParserTableGen) + diff --git a/llvm/include/llvm/Support/RISCVISAInfo.h b/llvm/include/llvm/TargetParser/RISCVISAInfo.h similarity index 86% rename from llvm/include/llvm/Support/RISCVISAInfo.h rename to llvm/include/llvm/TargetParser/RISCVISAInfo.h index 46df93d7522602f4477ff63f4dc5285cc09a6538..83c4f1e620fc85dbba7f5df77ba4d5f3271f4749 100644 --- a/llvm/include/llvm/Support/RISCVISAInfo.h +++ b/llvm/include/llvm/TargetParser/RISCVISAInfo.h @@ -12,6 +12,7 @@ #include "llvm/ADT/StringMap.h" #include "llvm/ADT/StringRef.h" #include "llvm/Support/Error.h" +#include "llvm/Support/RISCVISAUtils.h" #include #include @@ -25,24 +26,10 @@ public: RISCVISAInfo(const RISCVISAInfo &) = delete; RISCVISAInfo &operator=(const RISCVISAInfo &) = delete; - /// Represents the major and version number components of a RISC-V extension. - struct ExtensionVersion { - unsigned Major; - unsigned Minor; - }; - - static bool compareExtension(const std::string &LHS, const std::string &RHS); - - /// Helper class for OrderedExtensionMap. - struct ExtensionComparator { - bool operator()(const std::string &LHS, const std::string &RHS) const { - return compareExtension(LHS, RHS); - } - }; - /// OrderedExtensionMap is std::map, it's specialized to keep entries /// in canonical order of extension. - typedef std::map + typedef std::map OrderedExtensionMap; RISCVISAInfo(unsigned XLen, OrderedExtensionMap &Exts) @@ -105,7 +92,7 @@ private: OrderedExtensionMap Exts; - void addExtension(StringRef ExtName, ExtensionVersion Version); + void addExtension(StringRef ExtName, RISCVISAUtils::ExtensionVersion Version); Error checkDependency(); diff --git a/llvm/include/llvm/Transforms/Scalar/GVN.h b/llvm/include/llvm/Transforms/Scalar/GVN.h index 4ba9b74ccb005d43d32ea2a9dd0030e9626f608d..debe2ee7991728ee1cdad3358f7b8fe790a202f5 100644 --- a/llvm/include/llvm/Transforms/Scalar/GVN.h +++ b/llvm/include/llvm/Transforms/Scalar/GVN.h @@ -232,13 +232,67 @@ private: /// A mapping from value numbers to lists of Value*'s that /// have that value number. Use findLeader to query it. - struct LeaderTableEntry { - Value *Val; - const BasicBlock *BB; - LeaderTableEntry *Next; + class LeaderMap { + public: + struct LeaderTableEntry { + Value *Val; + const BasicBlock *BB; + }; + + private: + struct LeaderListNode { + LeaderTableEntry Entry; + LeaderListNode *Next; + }; + DenseMap NumToLeaders; + BumpPtrAllocator TableAllocator; + + public: + class leader_iterator { + const LeaderListNode *Current; + + public: + using iterator_category = std::forward_iterator_tag; + using value_type = const LeaderTableEntry; + using difference_type = std::ptrdiff_t; + using pointer = value_type *; + using reference = value_type &; + + leader_iterator(const LeaderListNode *C) : Current(C) {} + leader_iterator &operator++() { + assert(Current && "Dereferenced end of leader list!"); + Current = Current->Next; + return *this; + } + bool operator==(const leader_iterator &Other) const { + return Current == Other.Current; + } + bool operator!=(const leader_iterator &Other) const { + return Current != Other.Current; + } + reference operator*() const { return Current->Entry; } + }; + + iterator_range getLeaders(uint32_t N) { + auto I = NumToLeaders.find(N); + if (I == NumToLeaders.end()) { + return iterator_range(leader_iterator(nullptr), + leader_iterator(nullptr)); + } + + return iterator_range(leader_iterator(&I->second), + leader_iterator(nullptr)); + } + + void insert(uint32_t N, Value *V, const BasicBlock *BB); + void erase(uint32_t N, Instruction *I, const BasicBlock *BB); + void verifyRemoved(const Value *Inst) const; + void clear() { + NumToLeaders.clear(); + TableAllocator.Reset(); + } }; - DenseMap LeaderTable; - BumpPtrAllocator TableAllocator; + LeaderMap LeaderTable; // Block-local map of equivalent values to their leader, does not // propagate to any successors. Entries added mid-block are applied @@ -264,51 +318,6 @@ private: MemoryDependenceResults *RunMD, LoopInfo &LI, OptimizationRemarkEmitter *ORE, MemorySSA *MSSA = nullptr); - /// Push a new Value to the LeaderTable onto the list for its value number. - void addToLeaderTable(uint32_t N, Value *V, const BasicBlock *BB) { - LeaderTableEntry &Curr = LeaderTable[N]; - if (!Curr.Val) { - Curr.Val = V; - Curr.BB = BB; - return; - } - - LeaderTableEntry *Node = TableAllocator.Allocate(); - Node->Val = V; - Node->BB = BB; - Node->Next = Curr.Next; - Curr.Next = Node; - } - - /// Scan the list of values corresponding to a given - /// value number, and remove the given instruction if encountered. - void removeFromLeaderTable(uint32_t N, Instruction *I, BasicBlock *BB) { - LeaderTableEntry *Prev = nullptr; - LeaderTableEntry *Curr = &LeaderTable[N]; - - while (Curr && (Curr->Val != I || Curr->BB != BB)) { - Prev = Curr; - Curr = Curr->Next; - } - - if (!Curr) - return; - - if (Prev) { - Prev->Next = Curr->Next; - } else { - if (!Curr->Next) { - Curr->Val = nullptr; - Curr->BB = nullptr; - } else { - LeaderTableEntry *Next = Curr->Next; - Curr->Val = Next->Val; - Curr->BB = Next->BB; - Curr->Next = Next->Next; - } - } - } - // List of critical edges to be split between iterations. SmallVector, 4> toSplit; diff --git a/llvm/include/llvm/Transforms/Scalar/JumpThreading.h b/llvm/include/llvm/Transforms/Scalar/JumpThreading.h index 3364d7eaee42476c5018cf1a0bb51b8e3950e5f5..f7358ac9b1ee0a41a282426185d7a08d6bc4cc0f 100644 --- a/llvm/include/llvm/Transforms/Scalar/JumpThreading.h +++ b/llvm/include/llvm/Transforms/Scalar/JumpThreading.h @@ -22,6 +22,7 @@ #include "llvm/Analysis/BranchProbabilityInfo.h" #include "llvm/Analysis/DomTreeUpdater.h" #include "llvm/IR/ValueHandle.h" +#include "llvm/Transforms/Utils/ValueMapper.h" #include #include @@ -114,11 +115,10 @@ public: bool processBlock(BasicBlock *BB); bool maybeMergeBasicBlockIntoOnlyPred(BasicBlock *BB); void updateSSA(BasicBlock *BB, BasicBlock *NewBB, - DenseMap &ValueMapping); - DenseMap cloneInstructions(BasicBlock::iterator BI, - BasicBlock::iterator BE, - BasicBlock *NewBB, - BasicBlock *PredBB); + ValueToValueMapTy &ValueMapping); + void cloneInstructions(ValueToValueMapTy &ValueMapping, + BasicBlock::iterator BI, BasicBlock::iterator BE, + BasicBlock *NewBB, BasicBlock *PredBB); bool tryThreadEdge(BasicBlock *BB, const SmallVectorImpl &PredBBs, BasicBlock *SuccBB); diff --git a/llvm/include/llvm/Transforms/Utils/Local.h b/llvm/include/llvm/Transforms/Utils/Local.h index 9ae026fa95d21ad1e0786100182e30c5af390ab7..6937ec8dfd21c74e2e67879b236dda05442be5d5 100644 --- a/llvm/include/llvm/Transforms/Utils/Local.h +++ b/llvm/include/llvm/Transforms/Utils/Local.h @@ -18,6 +18,7 @@ #include "llvm/IR/Dominators.h" #include "llvm/Support/CommandLine.h" #include "llvm/Transforms/Utils/SimplifyCFGOptions.h" +#include "llvm/Transforms/Utils/ValueMapper.h" #include namespace llvm { @@ -439,6 +440,18 @@ unsigned replaceDominatedUsesWith(Value *From, Value *To, DominatorTree &DT, /// the end of the given BasicBlock. Returns the number of replacements made. unsigned replaceDominatedUsesWith(Value *From, Value *To, DominatorTree &DT, const BasicBlock *BB); +/// Replace each use of 'From' with 'To' if that use is dominated by +/// the given edge and the callback ShouldReplace returns true. Returns the +/// number of replacements made. +unsigned replaceDominatedUsesWithIf( + Value *From, Value *To, DominatorTree &DT, const BasicBlockEdge &Edge, + function_ref ShouldReplace); +/// Replace each use of 'From' with 'To' if that use is dominated by +/// the end of the given BasicBlock and the callback ShouldReplace returns true. +/// Returns the number of replacements made. +unsigned replaceDominatedUsesWithIf( + Value *From, Value *To, DominatorTree &DT, const BasicBlock *BB, + function_ref ShouldReplace); /// Return true if this call calls a gc leaf function. /// @@ -478,6 +491,10 @@ void hoistAllInstructionsInto(BasicBlock *DomBlock, Instruction *InsertPt, DIExpression *getExpressionForConstant(DIBuilder &DIB, const Constant &C, Type &Ty); +/// Remap the operands of the debug records attached to \p Inst, and the +/// operands of \p Inst itself if it's a debug intrinsic. +void remapDebugVariable(ValueToValueMapTy &Mapping, Instruction *Inst); + //===----------------------------------------------------------------------===// // Intrinsic pattern matching // diff --git a/llvm/include/llvm/Transforms/Vectorize/SLPVectorizer.h b/llvm/include/llvm/Transforms/Vectorize/SLPVectorizer.h index 326006fbb88039d7c240ff407dae70c765a9470f..4f99d171469e49838d2ae975cd80b8ae7b4293a8 100644 --- a/llvm/include/llvm/Transforms/Vectorize/SLPVectorizer.h +++ b/llvm/include/llvm/Transforms/Vectorize/SLPVectorizer.h @@ -153,10 +153,15 @@ private: /// a vectorization chain. bool vectorizeChainsInBlock(BasicBlock *BB, slpvectorizer::BoUpSLP &R); - bool vectorizeStoreChain(ArrayRef Chain, slpvectorizer::BoUpSLP &R, - unsigned Idx, unsigned MinVF); - - bool vectorizeStores(ArrayRef Stores, slpvectorizer::BoUpSLP &R); + std::optional vectorizeStoreChain(ArrayRef Chain, + slpvectorizer::BoUpSLP &R, + unsigned Idx, unsigned MinVF, + unsigned &Size); + + bool vectorizeStores( + ArrayRef Stores, slpvectorizer::BoUpSLP &R, + DenseSet> + &Visited); /// The store instructions in a basic block organized by base pointer. StoreListMap Stores; diff --git a/llvm/lib/Analysis/Loads.cpp b/llvm/lib/Analysis/Loads.cpp index ac508e19c9e0145d14d747196dc285358e86ef6b..478302d687b534fd9b8619ef6b3d93b894393f97 100644 --- a/llvm/lib/Analysis/Loads.cpp +++ b/llvm/lib/Analysis/Loads.cpp @@ -710,22 +710,62 @@ Value *llvm::FindAvailableLoadedValue(LoadInst *Load, BatchAAResults &AA, return Available; } -bool llvm::canReplacePointersIfEqual(Value *A, Value *B, const DataLayout &DL, - Instruction *CtxI) { - Type *Ty = A->getType(); - assert(Ty == B->getType() && Ty->isPointerTy() && - "values must have matching pointer types"); - - // NOTE: The checks in the function are incomplete and currently miss illegal - // cases! The current implementation is a starting point and the - // implementation should be made stricter over time. - if (auto *C = dyn_cast(B)) { - // Do not allow replacing a pointer with a constant pointer, unless it is - // either null or at least one byte is dereferenceable. - APInt OneByte(DL.getPointerTypeSizeInBits(Ty), 1); - return C->isNullValue() || - isDereferenceableAndAlignedPointer(B, Align(1), OneByte, DL, CtxI); +// Returns true if a use is either in an ICmp/PtrToInt or a Phi/Select that only +// feeds into them. +static bool isPointerUseReplacable(const Use &U) { + unsigned Limit = 40; + SmallVector Worklist({U.getUser()}); + SmallPtrSet Visited; + + while (!Worklist.empty() && --Limit) { + auto *User = Worklist.pop_back_val(); + if (!Visited.insert(User).second) + continue; + if (isa(User)) + continue; + if (isa(User)) + Worklist.append(User->user_begin(), User->user_end()); + else + return false; } - return true; + return Limit != 0; +} + +// Returns true if `To` is a null pointer, constant dereferenceable pointer or +// both pointers have the same underlying objects. +static bool isPointerAlwaysReplaceable(const Value *From, const Value *To, + const DataLayout &DL) { + // This is not strictly correct, but we do it for now to retain important + // optimizations. + if (isa(To)) + return true; + if (isa(To) && + isDereferenceablePointer(To, Type::getInt8Ty(To->getContext()), DL)) + return true; + if (getUnderlyingObject(From) == getUnderlyingObject(To)) + return true; + return false; +} + +bool llvm::canReplacePointersInUseIfEqual(const Use &U, const Value *To, + const DataLayout &DL) { + assert(U->getType() == To->getType() && "values must have matching types"); + // Not a pointer, just return true. + if (!To->getType()->isPointerTy()) + return true; + + if (isPointerAlwaysReplaceable(&*U, To, DL)) + return true; + return isPointerUseReplacable(U); +} + +bool llvm::canReplacePointersIfEqual(const Value *From, const Value *To, + const DataLayout &DL) { + assert(From->getType() == To->getType() && "values must have matching types"); + // Not a pointer, just return true. + if (!From->getType()->isPointerTy()) + return true; + + return isPointerAlwaysReplaceable(From, To, DL); } diff --git a/llvm/lib/Analysis/LoopAccessAnalysis.cpp b/llvm/lib/Analysis/LoopAccessAnalysis.cpp index b1ba8e7c0f6014525d94d76fe00fe6fbe0ba6031..f65515ca387229d9c8cf88242fc96719dda13f11 100644 --- a/llvm/lib/Analysis/LoopAccessAnalysis.cpp +++ b/llvm/lib/Analysis/LoopAccessAnalysis.cpp @@ -1920,20 +1920,21 @@ isLoopVariantIndirectAddress(ArrayRef UnderlyingObjects, namespace { struct DepDistanceStrideAndSizeInfo { const SCEV *Dist; - uint64_t Stride; + uint64_t StrideA; + uint64_t StrideB; uint64_t TypeByteSize; bool AIsWrite; bool BIsWrite; - DepDistanceStrideAndSizeInfo(const SCEV *Dist, uint64_t Stride, - uint64_t TypeByteSize, bool AIsWrite, - bool BIsWrite) - : Dist(Dist), Stride(Stride), TypeByteSize(TypeByteSize), - AIsWrite(AIsWrite), BIsWrite(BIsWrite) {} + DepDistanceStrideAndSizeInfo(const SCEV *Dist, uint64_t StrideA, + uint64_t StrideB, uint64_t TypeByteSize, + bool AIsWrite, bool BIsWrite) + : Dist(Dist), StrideA(StrideA), StrideB(StrideB), + TypeByteSize(TypeByteSize), AIsWrite(AIsWrite), BIsWrite(BIsWrite) {} }; } // namespace -// Get the dependence distance, stride, type size and whether it is a write for +// Get the dependence distance, strides, type size and whether it is a write for // the dependence between A and B. Returns a DepType, if we can prove there's // no dependence or the analysis fails. Outlined to lambda to limit he scope // of various temporary variables, like A/BPtr, StrideA/BPtr and others. @@ -1995,10 +1996,11 @@ getDependenceDistanceStrideAndSize( InnermostLoop)) return MemoryDepChecker::Dependence::IndirectUnsafe; - // Need accesses with constant stride. We don't want to vectorize - // "A[B[i]] += ..." and similar code or pointer arithmetic that could wrap - // in the address space. - if (!StrideAPtr || !StrideBPtr || StrideAPtr != StrideBPtr) { + // Need accesses with constant strides and the same direction. We don't want + // to vectorize "A[B[i]] += ..." and similar code or pointer arithmetic that + // could wrap in the address space. + if (!StrideAPtr || !StrideBPtr || (StrideAPtr > 0 && StrideBPtr < 0) || + (StrideAPtr < 0 && StrideBPtr > 0)) { LLVM_DEBUG(dbgs() << "Pointer access with non-constant stride\n"); return MemoryDepChecker::Dependence::Unknown; } @@ -2008,9 +2010,9 @@ getDependenceDistanceStrideAndSize( DL.getTypeStoreSizeInBits(ATy) == DL.getTypeStoreSizeInBits(BTy); if (!HasSameSize) TypeByteSize = 0; - uint64_t Stride = std::abs(StrideAPtr); - return DepDistanceStrideAndSizeInfo(Dist, Stride, TypeByteSize, AIsWrite, - BIsWrite); + return DepDistanceStrideAndSizeInfo(Dist, std::abs(StrideAPtr), + std::abs(StrideBPtr), TypeByteSize, + AIsWrite, BIsWrite); } MemoryDepChecker::Dependence::DepType MemoryDepChecker::isDependent( @@ -2028,41 +2030,63 @@ MemoryDepChecker::Dependence::DepType MemoryDepChecker::isDependent( if (std::holds_alternative(Res)) return std::get(Res); - const auto &[Dist, Stride, TypeByteSize, AIsWrite, BIsWrite] = + const auto &[Dist, StrideA, StrideB, TypeByteSize, AIsWrite, BIsWrite] = std::get(Res); bool HasSameSize = TypeByteSize > 0; + std::optional CommonStride = + StrideA == StrideB ? std::make_optional(StrideA) : std::nullopt; + if (isa(Dist)) { + // TODO: Relax requirement that there is a common stride to retry with + // non-constant distance dependencies. + FoundNonConstantDistanceDependence |= !!CommonStride; + LLVM_DEBUG(dbgs() << "LAA: Dependence because of uncomputable distance.\n"); + return Dependence::Unknown; + } + ScalarEvolution &SE = *PSE.getSE(); auto &DL = InnermostLoop->getHeader()->getModule()->getDataLayout(); + // If the distance between the acecsses is larger than their absolute stride // multiplied by the backedge taken count, the accesses are independet, i.e. // they are far enough appart that accesses won't access the same location // across all loop ierations. - if (!isa(Dist) && HasSameSize && + if (HasSameSize && CommonStride && isSafeDependenceDistance(DL, SE, *(PSE.getBackedgeTakenCount()), *Dist, - Stride, TypeByteSize)) + *CommonStride, TypeByteSize)) return Dependence::NoDep; const SCEVConstant *C = dyn_cast(Dist); - if (!C) { - LLVM_DEBUG(dbgs() << "LAA: Dependence because of non-constant distance\n"); - FoundNonConstantDistanceDependence = true; - return Dependence::Unknown; - } - const APInt &Val = C->getAPInt(); - int64_t Distance = Val.getSExtValue(); - - // If the distance between accesses and their strides are known constants, - // check whether the accesses interlace each other. - if (std::abs(Distance) > 0 && Stride > 1 && HasSameSize && - areStridedAccessesIndependent(std::abs(Distance), Stride, TypeByteSize)) { - LLVM_DEBUG(dbgs() << "LAA: Strided accesses are independent\n"); - return Dependence::NoDep; + // Attempt to prove strided accesses independent. + if (C) { + const APInt &Val = C->getAPInt(); + int64_t Distance = Val.getSExtValue(); + + // If the distance between accesses and their strides are known constants, + // check whether the accesses interlace each other. + if (std::abs(Distance) > 0 && CommonStride && *CommonStride > 1 && + HasSameSize && + areStridedAccessesIndependent(std::abs(Distance), *CommonStride, + TypeByteSize)) { + LLVM_DEBUG(dbgs() << "LAA: Strided accesses are independent\n"); + return Dependence::NoDep; + } } // Negative distances are not plausible dependencies. - if (Val.isNegative()) { + if (SE.isKnownNonPositive(Dist)) { + if (SE.isKnownNonNegative(Dist)) { + if (HasSameSize) { + // Write to the same location with the same size. + return Dependence::Forward; + } else { + LLVM_DEBUG(dbgs() << "LAA: possibly zero dependence difference but " + "different type sizes\n"); + return Dependence::Unknown; + } + } + bool IsTrueDataDependence = (AIsWrite && !BIsWrite); // Check if the first access writes to a location that is read in a later // iteration, where the distance between them is not a multiple of a vector @@ -2071,27 +2095,40 @@ MemoryDepChecker::Dependence::DepType MemoryDepChecker::isDependent( // NOTE: There is no need to update MaxSafeVectorWidthInBits after call to // couldPreventStoreLoadForward, even if it changed MinDepDistBytes, since a // forward dependency will allow vectorization using any width. - if (IsTrueDataDependence && EnableForwardingConflictDetection && - (!HasSameSize || couldPreventStoreLoadForward(Val.abs().getZExtValue(), - TypeByteSize))) { - LLVM_DEBUG(dbgs() << "LAA: Forward but may prevent st->ld forwarding\n"); - return Dependence::ForwardButPreventsForwarding; + + if (IsTrueDataDependence && EnableForwardingConflictDetection) { + if (!C) { + // TODO: FoundNonConstantDistanceDependence is used as a necessary + // condition to consider retrying with runtime checks. Historically, we + // did not set it when strides were different but there is no inherent + // reason to. + FoundNonConstantDistanceDependence |= CommonStride.has_value(); + return Dependence::Unknown; + } + if (!HasSameSize || + couldPreventStoreLoadForward(C->getAPInt().abs().getZExtValue(), + TypeByteSize)) { + LLVM_DEBUG( + dbgs() << "LAA: Forward but may prevent st->ld forwarding\n"); + return Dependence::ForwardButPreventsForwarding; + } } LLVM_DEBUG(dbgs() << "LAA: Dependence is negative\n"); return Dependence::Forward; } - // Write to the same location with the same size. - if (Val == 0) { - if (HasSameSize) - return Dependence::Forward; - LLVM_DEBUG( - dbgs() << "LAA: Zero dependence difference but different type sizes\n"); + if (!C) { + // TODO: FoundNonConstantDistanceDependence is used as a necessary condition + // to consider retrying with runtime checks. Historically, we did not set it + // when strides were different but there is no inherent reason to. + FoundNonConstantDistanceDependence |= CommonStride.has_value(); + LLVM_DEBUG(dbgs() << "LAA: Dependence because of non-constant distance\n"); return Dependence::Unknown; } - assert(Val.isStrictlyPositive() && "Expect a positive value"); + if (!SE.isKnownPositive(Dist)) + return Dependence::Unknown; if (!HasSameSize) { LLVM_DEBUG(dbgs() << "LAA: ReadWrite-Write positive dependency with " @@ -2099,6 +2136,14 @@ MemoryDepChecker::Dependence::DepType MemoryDepChecker::isDependent( return Dependence::Unknown; } + // The logic below currently only supports StrideA == StrideB, i.e. there's a + // common stride. + if (!CommonStride) + return Dependence::Unknown; + + const APInt &Val = C->getAPInt(); + int64_t Distance = Val.getSExtValue(); + // Bail out early if passed-in parameters make vectorization not feasible. unsigned ForcedFactor = (VectorizerParams::VectorizationFactor ? VectorizerParams::VectorizationFactor : 1); @@ -2134,7 +2179,7 @@ MemoryDepChecker::Dependence::DepType MemoryDepChecker::isDependent( // the minimum distance needed is 28, which is greater than distance. It is // not safe to do vectorization. uint64_t MinDistanceNeeded = - TypeByteSize * Stride * (MinNumIter - 1) + TypeByteSize; + TypeByteSize * (*CommonStride) * (MinNumIter - 1) + TypeByteSize; if (MinDistanceNeeded > static_cast(Distance)) { LLVM_DEBUG(dbgs() << "LAA: Failure because of positive distance " << Distance << '\n'); @@ -2183,7 +2228,7 @@ MemoryDepChecker::Dependence::DepType MemoryDepChecker::isDependent( // An update to MinDepDistBytes requires an update to MaxSafeVectorWidthInBits // since there is a backwards dependency. - uint64_t MaxVF = MinDepDistBytes / (TypeByteSize * Stride); + uint64_t MaxVF = MinDepDistBytes / (TypeByteSize * (*CommonStride)); LLVM_DEBUG(dbgs() << "LAA: Positive distance " << Val.getSExtValue() << " with max VF = " << MaxVF << '\n'); uint64_t MaxVFInBits = MaxVF * TypeByteSize * 8; diff --git a/llvm/lib/Analysis/ValueTracking.cpp b/llvm/lib/Analysis/ValueTracking.cpp index 21e3f8a4cc52c713d53de3c8d5ebdf8b06125141..de38eddaa98feffc2c69182be6d2358fb73418c2 100644 --- a/llvm/lib/Analysis/ValueTracking.cpp +++ b/llvm/lib/Analysis/ValueTracking.cpp @@ -2632,6 +2632,13 @@ static bool isKnownNonZeroFromOperator(const Operator *I, Q.DL.getTypeSizeInBits(I->getType()).getFixedValue()) return isKnownNonZero(I->getOperand(0), Q, Depth); break; + case Instruction::Trunc: + // nuw/nsw trunc preserves zero/non-zero status of input. + if (auto *TI = dyn_cast(I)) + if (TI->hasNoSignedWrap() || TI->hasNoUnsignedWrap()) + return isKnownNonZero(TI->getOperand(0), Q, Depth); + break; + case Instruction::Sub: return isNonZeroSub(DemandedElts, Depth, Q, BitWidth, I->getOperand(0), I->getOperand(1)); @@ -8042,17 +8049,27 @@ static SelectPatternResult matchMinMax(CmpInst::Predicate Pred, return {SPF_UNKNOWN, SPNB_NA, false}; } -bool llvm::isKnownNegation(const Value *X, const Value *Y, bool NeedNSW) { +bool llvm::isKnownNegation(const Value *X, const Value *Y, bool NeedNSW, + bool AllowPoison) { assert(X && Y && "Invalid operand"); - // X = sub (0, Y) || X = sub nsw (0, Y) - if ((!NeedNSW && match(X, m_Sub(m_ZeroInt(), m_Specific(Y)))) || - (NeedNSW && match(X, m_NSWNeg(m_Specific(Y))))) + auto IsNegationOf = [&](const Value *X, const Value *Y) { + if (!match(X, m_Neg(m_Specific(Y)))) + return false; + + auto *BO = cast(X); + if (NeedNSW && !BO->hasNoSignedWrap()) + return false; + + auto *Zero = cast(BO->getOperand(0)); + if (!AllowPoison && !Zero->isNullValue()) + return false; + return true; + }; - // Y = sub (0, X) || Y = sub nsw (0, X) - if ((!NeedNSW && match(Y, m_Sub(m_ZeroInt(), m_Specific(X)))) || - (NeedNSW && match(Y, m_NSWNeg(m_Specific(X))))) + // X = -Y or Y = -X + if (IsNegationOf(X, Y) || IsNegationOf(Y, X)) return true; // X = sub (A, B), Y = sub (B, A) || X = sub nsw (A, B), Y = sub nsw (B, A) diff --git a/llvm/lib/Analysis/VectorUtils.cpp b/llvm/lib/Analysis/VectorUtils.cpp index bf7bc0ba84a03362fe908ae47853d9594d7186c8..917094267d05ae425a2ca837cc1a464af51e6351 100644 --- a/llvm/lib/Analysis/VectorUtils.cpp +++ b/llvm/lib/Analysis/VectorUtils.cpp @@ -23,6 +23,7 @@ #include "llvm/IR/Constants.h" #include "llvm/IR/DerivedTypes.h" #include "llvm/IR/IRBuilder.h" +#include "llvm/IR/MemoryModelRelaxationAnnotations.h" #include "llvm/IR/PatternMatch.h" #include "llvm/IR/Value.h" #include "llvm/Support/CommandLine.h" @@ -793,13 +794,17 @@ Instruction *llvm::propagateMetadata(Instruction *Inst, ArrayRef VL) { for (auto Kind : {LLVMContext::MD_tbaa, LLVMContext::MD_alias_scope, LLVMContext::MD_noalias, LLVMContext::MD_fpmath, LLVMContext::MD_nontemporal, LLVMContext::MD_invariant_load, - LLVMContext::MD_access_group}) { + LLVMContext::MD_access_group, LLVMContext::MD_mmra}) { MDNode *MD = I0->getMetadata(Kind); - for (int J = 1, E = VL.size(); MD && J != E; ++J) { const Instruction *IJ = cast(VL[J]); MDNode *IMD = IJ->getMetadata(Kind); + switch (Kind) { + case LLVMContext::MD_mmra: { + MD = MMRAMetadata::combine(Inst->getContext(), MD, IMD); + break; + } case LLVMContext::MD_tbaa: MD = MDNode::getMostGenericTBAA(MD, IMD); break; diff --git a/llvm/lib/CodeGen/AggressiveAntiDepBreaker.cpp b/llvm/lib/CodeGen/AggressiveAntiDepBreaker.cpp index ed6ce6bc73d38c9675c1f840eee02b5cb924f094..e91750afd281719a3e9014fabfa97f72bbd6e106 100644 --- a/llvm/lib/CodeGen/AggressiveAntiDepBreaker.cpp +++ b/llvm/lib/CodeGen/AggressiveAntiDepBreaker.cpp @@ -231,9 +231,9 @@ bool AggressiveAntiDepBreaker::IsImplicitDefUse(MachineInstr &MI, MachineOperand *Op = nullptr; if (MO.isDef()) - Op = MI.findRegisterUseOperand(Reg, true); + Op = MI.findRegisterUseOperand(Reg, /*TRI=*/nullptr, true); else - Op = MI.findRegisterDefOperand(Reg); + Op = MI.findRegisterDefOperand(Reg, /*TRI=*/nullptr); return(Op && Op->isImplicit()); } @@ -679,7 +679,7 @@ bool AggressiveAntiDepBreaker::FindSuitableFreeRegisters( // defines 'NewReg' via an early-clobber operand. for (const auto &Q : make_range(RegRefs.equal_range(Reg))) { MachineInstr *UseMI = Q.second.Operand->getParent(); - int Idx = UseMI->findRegisterDefOperandIdx(NewReg, false, true, TRI); + int Idx = UseMI->findRegisterDefOperandIdx(NewReg, TRI, false, true); if (Idx == -1) continue; @@ -846,7 +846,8 @@ unsigned AggressiveAntiDepBreaker::BreakAntiDependencies( continue; } else { // No anti-dep breaking for implicit deps - MachineOperand *AntiDepOp = MI.findRegisterDefOperand(AntiDepReg); + MachineOperand *AntiDepOp = + MI.findRegisterDefOperand(AntiDepReg, /*TRI=*/nullptr); assert(AntiDepOp && "Can't find index for defined register operand"); if (!AntiDepOp || AntiDepOp->isImplicit()) { LLVM_DEBUG(dbgs() << " (implicit)\n"); diff --git a/llvm/lib/CodeGen/AtomicExpandPass.cpp b/llvm/lib/CodeGen/AtomicExpandPass.cpp index e5496c0e31c1c02674af90ce1865dcdd8df1c6e4..f3b8097396e266ad3830cdfcc4d5a9d88314ec5e 100644 --- a/llvm/lib/CodeGen/AtomicExpandPass.cpp +++ b/llvm/lib/CodeGen/AtomicExpandPass.cpp @@ -37,6 +37,7 @@ #include "llvm/IR/InstIterator.h" #include "llvm/IR/Instruction.h" #include "llvm/IR/Instructions.h" +#include "llvm/IR/MemoryModelRelaxationAnnotations.h" #include "llvm/IR/Module.h" #include "llvm/IR/Type.h" #include "llvm/IR/User.h" @@ -133,15 +134,27 @@ public: }; // IRBuilder to be used for replacement atomic instructions. -struct ReplacementIRBuilder : IRBuilder { +struct ReplacementIRBuilder + : IRBuilder { + MDNode *MMRAMD = nullptr; + // Preserves the DebugLoc from I, and preserves still valid metadata. // Enable StrictFP builder mode when appropriate. explicit ReplacementIRBuilder(Instruction *I, const DataLayout &DL) - : IRBuilder(I->getContext(), DL) { + : IRBuilder(I->getContext(), DL, + IRBuilderCallbackInserter( + [this](Instruction *I) { addMMRAMD(I); })) { SetInsertPoint(I); this->CollectMetadataToCopy(I, {LLVMContext::MD_pcsections}); if (BB->getParent()->getAttributes().hasFnAttr(Attribute::StrictFP)) this->setIsFPConstrained(true); + + MMRAMD = I->getMetadata(LLVMContext::MD_mmra); + } + + void addMMRAMD(Instruction *I) { + if (canInstructionHaveMMRAs(*I)) + I->setMetadata(LLVMContext::MD_mmra, MMRAMD); } }; @@ -421,8 +434,9 @@ AtomicExpandImpl::convertAtomicXchgToIntegerType(AtomicRMWInst *RMWI) { ? Builder.CreatePtrToInt(Val, NewTy) : Builder.CreateBitCast(Val, NewTy); - auto *NewRMWI = Builder.CreateAtomicRMW( - AtomicRMWInst::Xchg, Addr, NewVal, RMWI->getAlign(), RMWI->getOrdering()); + auto *NewRMWI = Builder.CreateAtomicRMW(AtomicRMWInst::Xchg, Addr, NewVal, + RMWI->getAlign(), RMWI->getOrdering(), + RMWI->getSyncScopeID()); NewRMWI->setVolatile(RMWI->isVolatile()); LLVM_DEBUG(dbgs() << "Replaced " << *RMWI << " with " << *NewRMWI << "\n"); diff --git a/llvm/lib/CodeGen/CalcSpillWeights.cpp b/llvm/lib/CodeGen/CalcSpillWeights.cpp index f3cb7fa5af61481df1ffed2a5a06d3e42bb097cd..1d767a3484bcadbf2339636aa2690c1f6ae1a955 100644 --- a/llvm/lib/CodeGen/CalcSpillWeights.cpp +++ b/llvm/lib/CodeGen/CalcSpillWeights.cpp @@ -251,7 +251,8 @@ float VirtRegAuxInfo::weightCalcHelper(LiveInterval &LI, SlotIndex *Start, // For terminators that produce values, ask the backend if the register is // not spillable. - if (TII.isUnspillableTerminator(MI) && MI->definesRegister(LI.reg())) { + if (TII.isUnspillableTerminator(MI) && + MI->definesRegister(LI.reg(), /*TRI=*/nullptr)) { LI.markNotSpillable(); return -1.0f; } diff --git a/llvm/lib/CodeGen/CodeGenCommonISel.cpp b/llvm/lib/CodeGen/CodeGenCommonISel.cpp index 577c5dbc8e2da8e855edfb579dd684bdfbd9298f..fe144d3c1820390e824867d161870a3a8f9a05d6 100644 --- a/llvm/lib/CodeGen/CodeGenCommonISel.cpp +++ b/llvm/lib/CodeGen/CodeGenCommonISel.cpp @@ -260,7 +260,8 @@ void llvm::salvageDebugInfoForDbgValue(const MachineRegisterInfo &MRI, continue; } - int UseMOIdx = DbgMI->findRegisterUseOperandIdx(DefMO->getReg()); + int UseMOIdx = + DbgMI->findRegisterUseOperandIdx(DefMO->getReg(), /*TRI=*/nullptr); assert(UseMOIdx != -1 && DbgMI->hasDebugOperandForReg(DefMO->getReg()) && "Must use salvaged instruction as its location"); diff --git a/llvm/lib/CodeGen/CodeGenPrepare.cpp b/llvm/lib/CodeGen/CodeGenPrepare.cpp index 22a766f8d62524e3f3dd3d73e9ebd7092abebfb8..8eaf78157550ee35ac0ee7290d42e56de22daae0 100644 --- a/llvm/lib/CodeGen/CodeGenPrepare.cpp +++ b/llvm/lib/CodeGen/CodeGenPrepare.cpp @@ -1431,10 +1431,8 @@ static bool SinkCast(CastInst *CI) { if (!InsertedCast) { BasicBlock::iterator InsertPt = UserBB->getFirstInsertionPt(); assert(InsertPt != UserBB->end()); - InsertedCast = CastInst::Create(CI->getOpcode(), CI->getOperand(0), - CI->getType(), ""); + InsertedCast = cast(CI->clone()); InsertedCast->insertBefore(*UserBB, InsertPt); - InsertedCast->setDebugLoc(CI->getDebugLoc()); } // Replace a use of the cast with a use of the new cast. diff --git a/llvm/lib/CodeGen/EarlyIfConversion.cpp b/llvm/lib/CodeGen/EarlyIfConversion.cpp index 31e107ade1ccbb00784e4325d15a5b6e8e05b0ab..2a7bee1618deb25acb93898b76b3962368779c8c 100644 --- a/llvm/lib/CodeGen/EarlyIfConversion.cpp +++ b/llvm/lib/CodeGen/EarlyIfConversion.cpp @@ -599,8 +599,8 @@ static bool hasSameValue(const MachineRegisterInfo &MRI, return false; // Further, check that the two defs come from corresponding operands. - int TIdx = TDef->findRegisterDefOperandIdx(TReg); - int FIdx = FDef->findRegisterDefOperandIdx(FReg); + int TIdx = TDef->findRegisterDefOperandIdx(TReg, /*TRI=*/nullptr); + int FIdx = FDef->findRegisterDefOperandIdx(FReg, /*TRI=*/nullptr); if (TIdx == -1 || FIdx == -1) return false; diff --git a/llvm/lib/CodeGen/FixupStatepointCallerSaved.cpp b/llvm/lib/CodeGen/FixupStatepointCallerSaved.cpp index 4d668c53f7156b8de85c92db0f6abaf2f8573d3b..3bb9da5f1a37bb42f3b70eec1c2627aee1520ece 100644 --- a/llvm/lib/CodeGen/FixupStatepointCallerSaved.cpp +++ b/llvm/lib/CodeGen/FixupStatepointCallerSaved.cpp @@ -112,7 +112,7 @@ static Register performCopyPropagation(Register Reg, bool &IsKill, const TargetInstrInfo &TII, const TargetRegisterInfo &TRI) { // First check if statepoint itself uses Reg in non-meta operands. - int Idx = RI->findRegisterUseOperandIdx(Reg, false, &TRI); + int Idx = RI->findRegisterUseOperandIdx(Reg, &TRI, false); if (Idx >= 0 && (unsigned)Idx < StatepointOpers(&*RI).getNumDeoptArgsIdx()) { IsKill = false; return Reg; diff --git a/llvm/lib/CodeGen/GlobalISel/CombinerHelper.cpp b/llvm/lib/CodeGen/GlobalISel/CombinerHelper.cpp index 5545ec3b3ed0c661dd72d3a93dfe39e560134eb3..653e7689b577435e07618a6fd05c3dad371e14c8 100644 --- a/llvm/lib/CodeGen/GlobalISel/CombinerHelper.cpp +++ b/llvm/lib/CodeGen/GlobalISel/CombinerHelper.cpp @@ -2800,8 +2800,8 @@ bool CombinerHelper::matchEqualDefs(const MachineOperand &MOP1, // %5:_(s8), %6:_(s8), %7:_(s8), %8:_(s8) = G_UNMERGE_VALUES %4:_(<4 x s8>) // I1 and I2 are different instructions but produce same values, // %1 and %6 are same, %1 and %7 are not the same value. - return I1->findRegisterDefOperandIdx(InstAndDef1->Reg) == - I2->findRegisterDefOperandIdx(InstAndDef2->Reg); + return I1->findRegisterDefOperandIdx(InstAndDef1->Reg, /*TRI=*/nullptr) == + I2->findRegisterDefOperandIdx(InstAndDef2->Reg, /*TRI=*/nullptr); } return false; } @@ -5069,6 +5069,9 @@ MachineInstr *CombinerHelper::buildUDivUsingMul(MachineInstr &MI) { const unsigned EltBits = ScalarTy.getScalarSizeInBits(); LLT ShiftAmtTy = getTargetLowering().getPreferredShiftAmountTy(Ty); LLT ScalarShiftAmtTy = ShiftAmtTy.getScalarType(); + + unsigned KnownLeadingZeros = + KB ? KB->getKnownBits(LHS).countMinLeadingZeros() : 0; auto &MIB = Builder; bool UseNPQ = false; @@ -5086,8 +5089,12 @@ MachineInstr *CombinerHelper::buildUDivUsingMul(MachineInstr &MI) { // at the end. // TODO: Use undef values for divisor of 1. if (!Divisor.isOne()) { + + // UnsignedDivisionByConstantInfo doesn't work correctly if leading zeros + // in the dividend exceeds the leading zeros for the divisor. UnsignedDivisionByConstantInfo magics = - UnsignedDivisionByConstantInfo::get(Divisor); + UnsignedDivisionByConstantInfo::get( + Divisor, std::min(KnownLeadingZeros, Divisor.countl_zero())); Magic = std::move(magics.Magic); diff --git a/llvm/lib/CodeGen/GlobalISel/IRTranslator.cpp b/llvm/lib/CodeGen/GlobalISel/IRTranslator.cpp index 0b6aae3759756f35c116f7a9c7229a4615b5ce03..d7b0c9aa1667359b88186108b1dbda0ad98c51aa 100644 --- a/llvm/lib/CodeGen/GlobalISel/IRTranslator.cpp +++ b/llvm/lib/CodeGen/GlobalISel/IRTranslator.cpp @@ -2223,7 +2223,7 @@ bool IRTranslator::translateKnownIntrinsic(const CallInst &CI, Intrinsic::ID ID, // addresses. We can treat it like a normal dbg_value intrinsic here; to // benefit from the full analysis of stack/SSA locations, GlobalISel would // need to register for and use the AssignmentTrackingAnalysis pass. - LLVM_FALLTHROUGH; + [[fallthrough]]; case Intrinsic::dbg_value: { // This form of DBG_VALUE is target-independent. const DbgValueInst &DI = cast(CI); @@ -3446,6 +3446,7 @@ void IRTranslator::translateDbgInfo(const Instruction &Inst, bool IRTranslator::translate(const Instruction &Inst) { CurBuilder->setDebugLoc(Inst.getDebugLoc()); CurBuilder->setPCSections(Inst.getMetadata(LLVMContext::MD_pcsections)); + CurBuilder->setMMRAMetadata(Inst.getMetadata(LLVMContext::MD_mmra)); if (TLI->fallBackToDAGISel(Inst)) return false; diff --git a/llvm/lib/CodeGen/GlobalISel/LegalizerHelper.cpp b/llvm/lib/CodeGen/GlobalISel/LegalizerHelper.cpp index d55091e2e717395abfb4fbb8ce281e0bb3509116..6a76ad7f5db749bdc2ff22db2b7e842cd37aeeb3 100644 --- a/llvm/lib/CodeGen/GlobalISel/LegalizerHelper.cpp +++ b/llvm/lib/CodeGen/GlobalISel/LegalizerHelper.cpp @@ -4764,6 +4764,8 @@ LegalizerHelper::fewerElementsVector(MachineInstr &MI, unsigned TypeIdx, return fewerElementsVectorMultiEltType(GMI, NumElts, {2 /*pow*/}); case G_BITCAST: return fewerElementsBitcast(MI, TypeIdx, NarrowTy); + case G_INTRINSIC_FPTRUNC_ROUND: + return fewerElementsVectorMultiEltType(GMI, NumElts, {2}); default: return UnableToLegalize; } diff --git a/llvm/lib/CodeGen/GlobalISel/MachineIRBuilder.cpp b/llvm/lib/CodeGen/GlobalISel/MachineIRBuilder.cpp index 6b35caf834918bbb90684ef937a7fbafafac8025..2e8407813ba641605a4138c3e62a0392df6c3fb8 100644 --- a/llvm/lib/CodeGen/GlobalISel/MachineIRBuilder.cpp +++ b/llvm/lib/CodeGen/GlobalISel/MachineIRBuilder.cpp @@ -28,6 +28,7 @@ void MachineIRBuilder::setMF(MachineFunction &MF) { State.TII = MF.getSubtarget().getInstrInfo(); State.DL = DebugLoc(); State.PCSections = nullptr; + State.MMRA = nullptr; State.II = MachineBasicBlock::iterator(); State.Observer = nullptr; } @@ -37,7 +38,8 @@ void MachineIRBuilder::setMF(MachineFunction &MF) { //------------------------------------------------------------------------------ MachineInstrBuilder MachineIRBuilder::buildInstrNoInsert(unsigned Opcode) { - return BuildMI(getMF(), {getDL(), getPCSections()}, getTII().get(Opcode)); + return BuildMI(getMF(), {getDL(), getPCSections(), getMMRAMetadata()}, + getTII().get(Opcode)); } MachineInstrBuilder MachineIRBuilder::insertInstr(MachineInstrBuilder MIB) { diff --git a/llvm/lib/CodeGen/GlobalISel/RegBankSelect.cpp b/llvm/lib/CodeGen/GlobalISel/RegBankSelect.cpp index bb5363fb2527b58d6cf9e4402497f048b86458a2..383cb61aed41073c659dff9a401cc25de260fea9 100644 --- a/llvm/lib/CodeGen/GlobalISel/RegBankSelect.cpp +++ b/llvm/lib/CodeGen/GlobalISel/RegBankSelect.cpp @@ -420,7 +420,8 @@ void RegBankSelect::tryAvoidingSplit( // If the next terminator uses Reg, this means we have // to split right after MI and thus we need a way to ask // which outgoing edges are affected. - assert(!Next->readsRegister(Reg) && "Need to split between terminators"); + assert(!Next->readsRegister(Reg, /*TRI=*/nullptr) && + "Need to split between terminators"); // We will split all the edges and repair there. } else { // This is a virtual register defined by a terminator. diff --git a/llvm/lib/CodeGen/InlineSpiller.cpp b/llvm/lib/CodeGen/InlineSpiller.cpp index c46b1fe18ca7434ca8119ddfe8f18a4046cc2375..69c671220db35374f845ba42495c3173a882eaee 100644 --- a/llvm/lib/CodeGen/InlineSpiller.cpp +++ b/llvm/lib/CodeGen/InlineSpiller.cpp @@ -869,7 +869,7 @@ static void dumpMachineInstrRangeWithSlotIndex(MachineBasicBlock::iterator B, // destination that is marked as an early clobber, print the // early-clobber slot index. if (VReg) { - MachineOperand *MO = I->findRegisterDefOperand(VReg); + MachineOperand *MO = I->findRegisterDefOperand(VReg, /*TRI=*/nullptr); if (MO && MO->isEarlyClobber()) Idx = Idx.getRegSlot(true); } diff --git a/llvm/lib/CodeGen/LiveVariables.cpp b/llvm/lib/CodeGen/LiveVariables.cpp index b85526cfb380b6a6bafee4eea2f3163f29a912d5..f44db575a92506b17fa6464b2a1b9e0c395c28e3 100644 --- a/llvm/lib/CodeGen/LiveVariables.cpp +++ b/llvm/lib/CodeGen/LiveVariables.cpp @@ -258,7 +258,7 @@ void LiveVariables::HandlePhysRegUse(Register Reg, MachineInstr &MI) { } } } else if (LastDef && !PhysRegUse[Reg] && - !LastDef->findRegisterDefOperand(Reg)) + !LastDef->findRegisterDefOperand(Reg, /*TRI=*/nullptr)) // Last def defines the super register, add an implicit def of reg. LastDef->addOperand(MachineOperand::CreateReg(Reg, true/*IsDef*/, true/*IsImp*/)); @@ -361,7 +361,8 @@ bool LiveVariables::HandlePhysRegKill(Register Reg, MachineInstr *MI) { continue; bool NeedDef = true; if (PhysRegDef[Reg] == PhysRegDef[SubReg]) { - MachineOperand *MO = PhysRegDef[Reg]->findRegisterDefOperand(SubReg); + MachineOperand *MO = + PhysRegDef[Reg]->findRegisterDefOperand(SubReg, /*TRI=*/nullptr); if (MO) { NeedDef = false; assert(!MO->isDead()); @@ -388,7 +389,7 @@ bool LiveVariables::HandlePhysRegKill(Register Reg, MachineInstr *MI) { true/*IsImp*/, true/*IsKill*/)); else { MachineOperand *MO = - LastRefOrPartRef->findRegisterDefOperand(Reg, false, false, TRI); + LastRefOrPartRef->findRegisterDefOperand(Reg, TRI, false, false); bool NeedEC = MO->isEarlyClobber() && MO->getReg() != Reg; // If the last reference is the last def, then it's not used at all. // That is, unless we are currently processing the last reference itself. @@ -396,7 +397,7 @@ bool LiveVariables::HandlePhysRegKill(Register Reg, MachineInstr *MI) { if (NeedEC) { // If we are adding a subreg def and the superreg def is marked early // clobber, add an early clobber marker to the subreg def. - MO = LastRefOrPartRef->findRegisterDefOperand(Reg); + MO = LastRefOrPartRef->findRegisterDefOperand(Reg, /*TRI=*/nullptr); if (MO) MO->setIsEarlyClobber(); } @@ -727,7 +728,7 @@ void LiveVariables::recomputeForSingleDefVirtReg(Register Reg) { if (MI.isPHI()) break; if (MI.readsVirtualRegister(Reg)) { - assert(!MI.killsRegister(Reg)); + assert(!MI.killsRegister(Reg, /*TRI=*/nullptr)); MI.addRegisterKilled(Reg, nullptr); VI.Kills.push_back(&MI); break; diff --git a/llvm/lib/CodeGen/MIRPrinter.cpp b/llvm/lib/CodeGen/MIRPrinter.cpp index bf3aee67ec00285c9e5fa7521bf938f4094984d2..6751fcf97087c74d84d1b2e75538c5fc87e34c90 100644 --- a/llvm/lib/CodeGen/MIRPrinter.cpp +++ b/llvm/lib/CodeGen/MIRPrinter.cpp @@ -856,6 +856,13 @@ void MIPrinter::print(const MachineInstr &MI) { PCSections->printAsOperand(OS, MST); NeedComma = true; } + if (MDNode *MMRA = MI.getMMRAMetadata()) { + if (NeedComma) + OS << ','; + OS << " mmra "; + MMRA->printAsOperand(OS, MST); + NeedComma = true; + } if (uint32_t CFIType = MI.getCFIType()) { if (NeedComma) OS << ','; diff --git a/llvm/lib/CodeGen/MachineCSE.cpp b/llvm/lib/CodeGen/MachineCSE.cpp index 26a8d00e6626519ee4fb2d9f2194cf950eb556f4..42cdcaa5bbf4f23c80bde6f275bb09191bc408d8 100644 --- a/llvm/lib/CodeGen/MachineCSE.cpp +++ b/llvm/lib/CodeGen/MachineCSE.cpp @@ -709,7 +709,7 @@ bool MachineCSE::ProcessBlockCSE(MachineBasicBlock *MBB) { for (MachineBasicBlock::iterator II = CSMI, IE = &MI; II != IE; ++II) for (auto ImplicitDef : ImplicitDefs) if (MachineOperand *MO = II->findRegisterUseOperand( - ImplicitDef, /*isKill=*/true, TRI)) + ImplicitDef, TRI, /*isKill=*/true)) MO->setIsKill(false); } else { // If the instructions aren't in the same BB, bail out and clear the diff --git a/llvm/lib/CodeGen/MachineCombiner.cpp b/llvm/lib/CodeGen/MachineCombiner.cpp index ac58162bbfb4208756579d1277a9f21a62a6b196..c11263163a34ff9a240d24e1f7d0a42cb1b0cba1 100644 --- a/llvm/lib/CodeGen/MachineCombiner.cpp +++ b/llvm/lib/CodeGen/MachineCombiner.cpp @@ -229,8 +229,10 @@ MachineCombiner::getDepth(SmallVectorImpl &InsInstrs, assert(DefInstr && "There must be a definition for a new virtual register"); DepthOp = InstrDepth[II->second]; - int DefIdx = DefInstr->findRegisterDefOperandIdx(MO.getReg()); - int UseIdx = InstrPtr->findRegisterUseOperandIdx(MO.getReg()); + int DefIdx = + DefInstr->findRegisterDefOperandIdx(MO.getReg(), /*TRI=*/nullptr); + int UseIdx = + InstrPtr->findRegisterUseOperandIdx(MO.getReg(), /*TRI=*/nullptr); LatencyOp = TSchedModel.computeOperandLatency(DefInstr, DefIdx, InstrPtr, UseIdx); } else { @@ -241,8 +243,12 @@ MachineCombiner::getDepth(SmallVectorImpl &InsInstrs, DepthOp = BlockTrace.getInstrCycles(*DefInstr).Depth; if (!isTransientMI(DefInstr)) LatencyOp = TSchedModel.computeOperandLatency( - DefInstr, DefInstr->findRegisterDefOperandIdx(MO.getReg()), - InstrPtr, InstrPtr->findRegisterUseOperandIdx(MO.getReg())); + DefInstr, + DefInstr->findRegisterDefOperandIdx(MO.getReg(), + /*TRI=*/nullptr), + InstrPtr, + InstrPtr->findRegisterUseOperandIdx(MO.getReg(), + /*TRI=*/nullptr)); } } IDepth = std::max(IDepth, DepthOp + LatencyOp); @@ -280,8 +286,10 @@ unsigned MachineCombiner::getLatency(MachineInstr *Root, MachineInstr *NewRoot, unsigned LatencyOp = 0; if (UseMO && BlockTrace.isDepInTrace(*Root, *UseMO)) { LatencyOp = TSchedModel.computeOperandLatency( - NewRoot, NewRoot->findRegisterDefOperandIdx(MO.getReg()), UseMO, - UseMO->findRegisterUseOperandIdx(MO.getReg())); + NewRoot, + NewRoot->findRegisterDefOperandIdx(MO.getReg(), /*TRI=*/nullptr), + UseMO, + UseMO->findRegisterUseOperandIdx(MO.getReg(), /*TRI=*/nullptr)); } else { LatencyOp = TSchedModel.computeInstrLatency(NewRoot); } diff --git a/llvm/lib/CodeGen/MachineCopyPropagation.cpp b/llvm/lib/CodeGen/MachineCopyPropagation.cpp index 8dc6781fcb018f1ff01ef32a5b64abd0c065345a..c82f00316147bc056b58b3e86e07a063f20c7767 100644 --- a/llvm/lib/CodeGen/MachineCopyPropagation.cpp +++ b/llvm/lib/CodeGen/MachineCopyPropagation.cpp @@ -737,7 +737,7 @@ void MachineCopyPropagation::forwardUses(MachineInstr &MI) { // cannot cope with that. if (isCopyInstr(MI, *TII, UseCopyInstr) && MI.modifiesRegister(CopySrcReg, TRI) && - !MI.definesRegister(CopySrcReg)) { + !MI.definesRegister(CopySrcReg, /*TRI=*/nullptr)) { LLVM_DEBUG(dbgs() << "MCP: Copy source overlap with dest in " << MI); continue; } diff --git a/llvm/lib/CodeGen/MachineFunction.cpp b/llvm/lib/CodeGen/MachineFunction.cpp index ad532149926670949f09d213f56c42e5419c9175..8366ad2859069fe73a6c8e749678869b3027b227 100644 --- a/llvm/lib/CodeGen/MachineFunction.cpp +++ b/llvm/lib/CodeGen/MachineFunction.cpp @@ -573,10 +573,10 @@ MachineFunction::getMachineMemOperand(const MachineMemOperand *MMO, MachineInstr::ExtraInfo *MachineFunction::createMIExtraInfo( ArrayRef MMOs, MCSymbol *PreInstrSymbol, MCSymbol *PostInstrSymbol, MDNode *HeapAllocMarker, MDNode *PCSections, - uint32_t CFIType) { + uint32_t CFIType, MDNode *MMRAs) { return MachineInstr::ExtraInfo::create(Allocator, MMOs, PreInstrSymbol, PostInstrSymbol, HeapAllocMarker, - PCSections, CFIType); + PCSections, CFIType, MMRAs); } const char *MachineFunction::createExternalSymbolName(StringRef Name) { diff --git a/llvm/lib/CodeGen/MachineInstr.cpp b/llvm/lib/CodeGen/MachineInstr.cpp index 83604003a038bd78da3497b08f240da15f0f72f6..02479f31f0b692bf6282452f1489c24a6d5c3bc0 100644 --- a/llvm/lib/CodeGen/MachineInstr.cpp +++ b/llvm/lib/CodeGen/MachineInstr.cpp @@ -318,14 +318,15 @@ void MachineInstr::setExtraInfo(MachineFunction &MF, MCSymbol *PreInstrSymbol, MCSymbol *PostInstrSymbol, MDNode *HeapAllocMarker, MDNode *PCSections, - uint32_t CFIType) { + uint32_t CFIType, MDNode *MMRAs) { bool HasPreInstrSymbol = PreInstrSymbol != nullptr; bool HasPostInstrSymbol = PostInstrSymbol != nullptr; bool HasHeapAllocMarker = HeapAllocMarker != nullptr; bool HasPCSections = PCSections != nullptr; bool HasCFIType = CFIType != 0; + bool HasMMRAs = MMRAs != nullptr; int NumPointers = MMOs.size() + HasPreInstrSymbol + HasPostInstrSymbol + - HasHeapAllocMarker + HasPCSections + HasCFIType; + HasHeapAllocMarker + HasPCSections + HasCFIType + HasMMRAs; // Drop all extra info if there is none. if (NumPointers <= 0) { @@ -337,11 +338,11 @@ void MachineInstr::setExtraInfo(MachineFunction &MF, // out of line because PointerSumType cannot hold more than 4 tag types with // 32-bit pointers. // FIXME: Maybe we should make the symbols in the extra info mutable? - else if (NumPointers > 1 || HasHeapAllocMarker || HasPCSections || + else if (NumPointers > 1 || HasMMRAs || HasHeapAllocMarker || HasPCSections || HasCFIType) { Info.set( MF.createMIExtraInfo(MMOs, PreInstrSymbol, PostInstrSymbol, - HeapAllocMarker, PCSections, CFIType)); + HeapAllocMarker, PCSections, CFIType, MMRAs)); return; } @@ -359,7 +360,8 @@ void MachineInstr::dropMemRefs(MachineFunction &MF) { return; setExtraInfo(MF, {}, getPreInstrSymbol(), getPostInstrSymbol(), - getHeapAllocMarker(), getPCSections(), getCFIType()); + getHeapAllocMarker(), getPCSections(), getCFIType(), + getMMRAMetadata()); } void MachineInstr::setMemRefs(MachineFunction &MF, @@ -370,7 +372,8 @@ void MachineInstr::setMemRefs(MachineFunction &MF, } setExtraInfo(MF, MMOs, getPreInstrSymbol(), getPostInstrSymbol(), - getHeapAllocMarker(), getPCSections(), getCFIType()); + getHeapAllocMarker(), getPCSections(), getCFIType(), + getMMRAMetadata()); } void MachineInstr::addMemOperand(MachineFunction &MF, @@ -394,7 +397,8 @@ void MachineInstr::cloneMemRefs(MachineFunction &MF, const MachineInstr &MI) { if (getPreInstrSymbol() == MI.getPreInstrSymbol() && getPostInstrSymbol() == MI.getPostInstrSymbol() && getHeapAllocMarker() == MI.getHeapAllocMarker() && - getPCSections() == MI.getPCSections()) { + getPCSections() == MI.getPCSections() && getMMRAMetadata() && + MI.getMMRAMetadata()) { Info = MI.Info; return; } @@ -479,7 +483,8 @@ void MachineInstr::setPreInstrSymbol(MachineFunction &MF, MCSymbol *Symbol) { } setExtraInfo(MF, memoperands(), Symbol, getPostInstrSymbol(), - getHeapAllocMarker(), getPCSections(), getCFIType()); + getHeapAllocMarker(), getPCSections(), getCFIType(), + getMMRAMetadata()); } void MachineInstr::setPostInstrSymbol(MachineFunction &MF, MCSymbol *Symbol) { @@ -494,7 +499,8 @@ void MachineInstr::setPostInstrSymbol(MachineFunction &MF, MCSymbol *Symbol) { } setExtraInfo(MF, memoperands(), getPreInstrSymbol(), Symbol, - getHeapAllocMarker(), getPCSections(), getCFIType()); + getHeapAllocMarker(), getPCSections(), getCFIType(), + getMMRAMetadata()); } void MachineInstr::setHeapAllocMarker(MachineFunction &MF, MDNode *Marker) { @@ -503,7 +509,7 @@ void MachineInstr::setHeapAllocMarker(MachineFunction &MF, MDNode *Marker) { return; setExtraInfo(MF, memoperands(), getPreInstrSymbol(), getPostInstrSymbol(), - Marker, getPCSections(), getCFIType()); + Marker, getPCSections(), getCFIType(), getMMRAMetadata()); } void MachineInstr::setPCSections(MachineFunction &MF, MDNode *PCSections) { @@ -512,7 +518,8 @@ void MachineInstr::setPCSections(MachineFunction &MF, MDNode *PCSections) { return; setExtraInfo(MF, memoperands(), getPreInstrSymbol(), getPostInstrSymbol(), - getHeapAllocMarker(), PCSections, getCFIType()); + getHeapAllocMarker(), PCSections, getCFIType(), + getMMRAMetadata()); } void MachineInstr::setCFIType(MachineFunction &MF, uint32_t Type) { @@ -521,7 +528,16 @@ void MachineInstr::setCFIType(MachineFunction &MF, uint32_t Type) { return; setExtraInfo(MF, memoperands(), getPreInstrSymbol(), getPostInstrSymbol(), - getHeapAllocMarker(), getPCSections(), Type); + getHeapAllocMarker(), getPCSections(), Type, getMMRAMetadata()); +} + +void MachineInstr::setMMRAMetadata(MachineFunction &MF, MDNode *MMRAs) { + // Do nothing if old and new symbols are the same. + if (MMRAs == getMMRAMetadata()) + return; + + setExtraInfo(MF, memoperands(), getPreInstrSymbol(), getPostInstrSymbol(), + getHeapAllocMarker(), getPCSections(), getCFIType(), MMRAs); } void MachineInstr::cloneInstrSymbols(MachineFunction &MF, @@ -537,6 +553,7 @@ void MachineInstr::cloneInstrSymbols(MachineFunction &MF, setPostInstrSymbol(MF, MI.getPostInstrSymbol()); setHeapAllocMarker(MF, MI.getHeapAllocMarker()); setPCSections(MF, MI.getPCSections()); + setMMRAMetadata(MF, MI.getMMRAMetadata()); } uint32_t MachineInstr::mergeFlagsWith(const MachineInstr &Other) const { @@ -1028,8 +1045,9 @@ bool MachineInstr::hasRegisterImplicitUseOperand(Register Reg) const { /// findRegisterUseOperandIdx() - Returns the MachineOperand that is a use of /// the specific register or -1 if it is not found. It further tightens /// the search criteria to a use that kills the register if isKill is true. -int MachineInstr::findRegisterUseOperandIdx( - Register Reg, bool isKill, const TargetRegisterInfo *TRI) const { +int MachineInstr::findRegisterUseOperandIdx(Register Reg, + const TargetRegisterInfo *TRI, + bool isKill) const { for (unsigned i = 0, e = getNumOperands(); i != e; ++i) { const MachineOperand &MO = getOperand(i); if (!MO.isReg() || !MO.isUse()) @@ -1076,9 +1094,9 @@ MachineInstr::readsWritesVirtualRegister(Register Reg, /// the specified register or -1 if it is not found. If isDead is true, defs /// that are not dead are skipped. If TargetRegisterInfo is non-null, then it /// also checks if there is a def of a super-register. -int -MachineInstr::findRegisterDefOperandIdx(Register Reg, bool isDead, bool Overlap, - const TargetRegisterInfo *TRI) const { +int MachineInstr::findRegisterDefOperandIdx(Register Reg, + const TargetRegisterInfo *TRI, + bool isDead, bool Overlap) const { bool isPhys = Reg.isPhysical(); for (unsigned i = 0, e = getNumOperands(); i != e; ++i) { const MachineOperand &MO = getOperand(i); @@ -1881,6 +1899,14 @@ void MachineInstr::print(raw_ostream &OS, ModuleSlotTracker &MST, OS << " pcsections "; PCSections->printAsOperand(OS, MST); } + if (MDNode *MMRA = getMMRAMetadata()) { + if (!FirstOp) { + FirstOp = false; + OS << ','; + } + OS << " mmra "; + MMRA->printAsOperand(OS, MST); + } if (uint32_t CFIType = getCFIType()) { if (!FirstOp) OS << ','; @@ -2111,7 +2137,7 @@ void MachineInstr::setRegisterDefReadUndef(Register Reg, bool IsUndef) { void MachineInstr::addRegisterDefined(Register Reg, const TargetRegisterInfo *RegInfo) { if (Reg.isPhysical()) { - MachineOperand *MO = findRegisterDefOperand(Reg, false, false, RegInfo); + MachineOperand *MO = findRegisterDefOperand(Reg, RegInfo, false, false); if (MO) return; } else { diff --git a/llvm/lib/CodeGen/MachineLateInstrsCleanup.cpp b/llvm/lib/CodeGen/MachineLateInstrsCleanup.cpp index aa1eb7c354255d962eb9b55e387082979a7977a2..1f596cd1bd2ec1e06abf35af167a6c744cf338a4 100644 --- a/llvm/lib/CodeGen/MachineLateInstrsCleanup.cpp +++ b/llvm/lib/CodeGen/MachineLateInstrsCleanup.cpp @@ -230,7 +230,7 @@ bool MachineLateInstrsCleanup::processBlock(MachineBasicBlock *MBB) { if (MI.modifiesRegister(Reg, TRI)) { MBBDefs.erase(Reg); MBBKills.erase(Reg); - } else if (MI.findRegisterUseOperandIdx(Reg, true /*isKill*/, TRI) != -1) + } else if (MI.findRegisterUseOperandIdx(Reg, TRI, true /*isKill*/) != -1) // Keep track of register kills. MBBKills[Reg] = &MI; } diff --git a/llvm/lib/CodeGen/MachineSink.cpp b/llvm/lib/CodeGen/MachineSink.cpp index c3a1d3759882d8d97beeb0cda05bc7f48e010f55..3d40130b92c443e25b9160784a579e13cc884ee0 100644 --- a/llvm/lib/CodeGen/MachineSink.cpp +++ b/llvm/lib/CodeGen/MachineSink.cpp @@ -309,7 +309,7 @@ static bool blockPrologueInterferes(const MachineBasicBlock *BB, if (PI->readsRegister(Reg, TRI)) return true; // Check for interference with non-dead defs - auto *DefOp = PI->findRegisterDefOperand(Reg, false, true, TRI); + auto *DefOp = PI->findRegisterDefOperand(Reg, TRI, false, true); if (DefOp && !DefOp->isDead()) return true; } diff --git a/llvm/lib/CodeGen/ModuloSchedule.cpp b/llvm/lib/CodeGen/ModuloSchedule.cpp index bdae94c4e6f885c69782f46474d81cd180bd7fca..b912112b16362e13fed1de8819c49cf0d8981a35 100644 --- a/llvm/lib/CodeGen/ModuloSchedule.cpp +++ b/llvm/lib/CodeGen/ModuloSchedule.cpp @@ -814,7 +814,7 @@ void ModuloScheduleExpander::splitLifetimes(MachineBasicBlock *KernelBB, unsigned SplitReg = 0; for (auto &BBJ : make_range(MachineBasicBlock::instr_iterator(MI), KernelBB->instr_end())) - if (BBJ.readsRegister(Def)) { + if (BBJ.readsRegister(Def, /*TRI=*/nullptr)) { // We split the lifetime when we find the first use. if (SplitReg == 0) { SplitReg = MRI.createVirtualRegister(MRI.getRegClass(Def)); @@ -829,7 +829,7 @@ void ModuloScheduleExpander::splitLifetimes(MachineBasicBlock *KernelBB, // Search through each of the epilog blocks for any uses to be renamed. for (auto &Epilog : EpilogBBs) for (auto &I : *Epilog) - if (I.readsRegister(Def)) + if (I.readsRegister(Def, /*TRI=*/nullptr)) I.substituteRegister(Def, SplitReg, 0, *TRI); break; } @@ -1673,7 +1673,8 @@ void PeelingModuloScheduleExpander::moveStageBetweenBlocks( // we don't need the phi anymore. if (getStage(Def) == Stage) { Register PhiReg = MI.getOperand(0).getReg(); - assert(Def->findRegisterDefOperandIdx(MI.getOperand(1).getReg()) != -1); + assert(Def->findRegisterDefOperandIdx(MI.getOperand(1).getReg(), + /*TRI=*/nullptr) != -1); MRI.replaceRegWith(MI.getOperand(0).getReg(), MI.getOperand(1).getReg()); MI.getOperand(0).setReg(PhiReg); PhiToDelete.push_back(&MI); @@ -1899,7 +1900,7 @@ Register PeelingModuloScheduleExpander::getEquivalentRegisterIn(Register Reg, MachineBasicBlock *BB) { MachineInstr *MI = MRI.getUniqueVRegDef(Reg); - unsigned OpIdx = MI->findRegisterDefOperandIdx(Reg); + unsigned OpIdx = MI->findRegisterDefOperandIdx(Reg, /*TRI=*/nullptr); return BlockMIs[{BB, CanonicalMIs[MI]}]->getOperand(OpIdx).getReg(); } diff --git a/llvm/lib/CodeGen/PHIElimination.cpp b/llvm/lib/CodeGen/PHIElimination.cpp index 18f8c001bd789aca4e356df606b0088c5be39019..3254ec0b77fe7889b728621cc1dd306e7238e75f 100644 --- a/llvm/lib/CodeGen/PHIElimination.cpp +++ b/llvm/lib/CodeGen/PHIElimination.cpp @@ -549,7 +549,7 @@ void PHIElimination::LowerPHINode(MachineBasicBlock &MBB, MachineBasicBlock::iterator KillInst = opBlock.end(); for (MachineBasicBlock::iterator Term = InsertPos; Term != opBlock.end(); ++Term) { - if (Term->readsRegister(SrcReg)) + if (Term->readsRegister(SrcReg, /*TRI=*/nullptr)) KillInst = Term; } @@ -563,7 +563,7 @@ void PHIElimination::LowerPHINode(MachineBasicBlock &MBB, --KillInst; if (KillInst->isDebugInstr()) continue; - if (KillInst->readsRegister(SrcReg)) + if (KillInst->readsRegister(SrcReg, /*TRI=*/nullptr)) break; } } else { @@ -571,7 +571,8 @@ void PHIElimination::LowerPHINode(MachineBasicBlock &MBB, KillInst = NewSrcInstr; } } - assert(KillInst->readsRegister(SrcReg) && "Cannot find kill instruction"); + assert(KillInst->readsRegister(SrcReg, /*TRI=*/nullptr) && + "Cannot find kill instruction"); // Finally, mark it killed. LV->addVirtualRegisterKilled(SrcReg, *KillInst); @@ -607,7 +608,7 @@ void PHIElimination::LowerPHINode(MachineBasicBlock &MBB, MachineBasicBlock::iterator KillInst = opBlock.end(); for (MachineBasicBlock::iterator Term = InsertPos; Term != opBlock.end(); ++Term) { - if (Term->readsRegister(SrcReg)) + if (Term->readsRegister(SrcReg, /*TRI=*/nullptr)) KillInst = Term; } @@ -621,7 +622,7 @@ void PHIElimination::LowerPHINode(MachineBasicBlock &MBB, --KillInst; if (KillInst->isDebugInstr()) continue; - if (KillInst->readsRegister(SrcReg)) + if (KillInst->readsRegister(SrcReg, /*TRI=*/nullptr)) break; } } else { @@ -629,7 +630,7 @@ void PHIElimination::LowerPHINode(MachineBasicBlock &MBB, KillInst = std::prev(InsertPos); } } - assert(KillInst->readsRegister(SrcReg) && + assert(KillInst->readsRegister(SrcReg, /*TRI=*/nullptr) && "Cannot find kill instruction"); SlotIndex LastUseIndex = LIS->getInstructionIndex(*KillInst); diff --git a/llvm/lib/CodeGen/PeepholeOptimizer.cpp b/llvm/lib/CodeGen/PeepholeOptimizer.cpp index 1b1f22e827cb1e2e2f11ee613d7fef53156a53a1..477a86dbe3f8c4c8000ab808d3d284add271797c 100644 --- a/llvm/lib/CodeGen/PeepholeOptimizer.cpp +++ b/llvm/lib/CodeGen/PeepholeOptimizer.cpp @@ -1577,7 +1577,7 @@ bool PeepholeOptimizer::findTargetRecurrence( return false; MachineInstr &MI = *(MRI->use_instr_nodbg_begin(Reg)); - unsigned Idx = MI.findRegisterUseOperandIdx(Reg); + unsigned Idx = MI.findRegisterUseOperandIdx(Reg, /*TRI=*/nullptr); // Only interested in recurrences whose instructions have only one def, which // is a virtual register. diff --git a/llvm/lib/CodeGen/RegisterCoalescer.cpp b/llvm/lib/CodeGen/RegisterCoalescer.cpp index 7e9c992031f8d3fc061a35d024da8787be6b86cb..3397bd0a6060311daddbfdcca3632fbdad2b0ff5 100644 --- a/llvm/lib/CodeGen/RegisterCoalescer.cpp +++ b/llvm/lib/CodeGen/RegisterCoalescer.cpp @@ -723,7 +723,8 @@ bool RegisterCoalescer::adjustCopiesBackFrom(const CoalescerPair &CP, // If the source instruction was killing the source register before the // merge, unset the isKill marker given the live range has been extended. - int UIdx = ValSEndInst->findRegisterUseOperandIdx(IntB.reg(), true); + int UIdx = + ValSEndInst->findRegisterUseOperandIdx(IntB.reg(), /*TRI=*/nullptr, true); if (UIdx != -1) { ValSEndInst->getOperand(UIdx).setIsKill(false); } @@ -848,7 +849,7 @@ RegisterCoalescer::removeCopyByCommutingDef(const CoalescerPair &CP, return { false, false }; // If DefMI is a two-address instruction then commuting it will change the // destination register. - int DefIdx = DefMI->findRegisterDefOperandIdx(IntA.reg()); + int DefIdx = DefMI->findRegisterDefOperandIdx(IntA.reg(), /*TRI=*/nullptr); assert(DefIdx != -1); unsigned UseOpIdx; if (!DefMI->isRegTiedToUseOperand(DefIdx, &UseOpIdx)) diff --git a/llvm/lib/CodeGen/SelectionDAG/DAGCombiner.cpp b/llvm/lib/CodeGen/SelectionDAG/DAGCombiner.cpp index fd265b12d73ca4d4c1c972d7f1115d25343101b7..b6d5b309ceb92de7571a72fade649e4b0513f034 100644 --- a/llvm/lib/CodeGen/SelectionDAG/DAGCombiner.cpp +++ b/llvm/lib/CodeGen/SelectionDAG/DAGCombiner.cpp @@ -530,6 +530,7 @@ namespace { bool refineExtractVectorEltIntoMultipleNarrowExtractVectorElts(SDNode *N); SDValue visitSTORE(SDNode *N); + SDValue visitATOMIC_STORE(SDNode *N); SDValue visitLIFETIME_END(SDNode *N); SDValue visitINSERT_VECTOR_ELT(SDNode *N); SDValue visitEXTRACT_VECTOR_ELT(SDNode *N); @@ -1909,6 +1910,7 @@ SDValue DAGCombiner::visit(SDNode *N) { case ISD::BR_CC: return visitBR_CC(N); case ISD::LOAD: return visitLOAD(N); case ISD::STORE: return visitSTORE(N); + case ISD::ATOMIC_STORE: return visitATOMIC_STORE(N); case ISD::INSERT_VECTOR_ELT: return visitINSERT_VECTOR_ELT(N); case ISD::EXTRACT_VECTOR_ELT: return visitEXTRACT_VECTOR_ELT(N); case ISD::BUILD_VECTOR: return visitBUILD_VECTOR(N); @@ -7620,6 +7622,8 @@ SDValue DAGCombiner::visitORLike(SDValue N0, SDValue N1, const SDLoc &DL) { static SDValue visitORCommutative(SelectionDAG &DAG, SDValue N0, SDValue N1, SDNode *N) { EVT VT = N0.getValueType(); + unsigned BW = VT.getScalarSizeInBits(); + SDLoc DL(N); auto peekThroughResize = [](SDValue V) { if (V->getOpcode() == ISD::ZERO_EXTEND || V->getOpcode() == ISD::TRUNCATE) @@ -7642,16 +7646,16 @@ static SDValue visitORCommutative(SelectionDAG &DAG, SDValue N0, SDValue N1, if (SDValue NotOperand = getBitwiseNotOperand(N01, N00, /* AllowUndefs */ false)) { if (peekThroughResize(NotOperand) == N1Resized) - return DAG.getNode(ISD::OR, SDLoc(N), VT, - DAG.getZExtOrTrunc(N00, SDLoc(N), VT), N1); + return DAG.getNode(ISD::OR, DL, VT, DAG.getZExtOrTrunc(N00, DL, VT), + N1); } // fold (or (and (xor Y, -1), X), Y) -> (or X, Y) if (SDValue NotOperand = getBitwiseNotOperand(N00, N01, /* AllowUndefs */ false)) { if (peekThroughResize(NotOperand) == N1Resized) - return DAG.getNode(ISD::OR, SDLoc(N), VT, - DAG.getZExtOrTrunc(N01, SDLoc(N), VT), N1); + return DAG.getNode(ISD::OR, DL, VT, DAG.getZExtOrTrunc(N01, DL, VT), + N1); } } @@ -7659,13 +7663,13 @@ static SDValue visitORCommutative(SelectionDAG &DAG, SDValue N0, SDValue N1, // fold or (xor X, N1), N1 --> or X, N1 if (sd_match(N0, m_Xor(m_Value(X), m_Specific(N1)))) - return DAG.getNode(ISD::OR, SDLoc(N), VT, X, N1); + return DAG.getNode(ISD::OR, DL, VT, X, N1); // fold or (xor x, y), (x and/or y) --> or x, y if (sd_match(N0, m_Xor(m_Value(X), m_Value(Y))) && (sd_match(N1, m_And(m_Specific(X), m_Specific(Y))) || sd_match(N1, m_Or(m_Specific(X), m_Specific(Y))))) - return DAG.getNode(ISD::OR, SDLoc(N), VT, X, Y); + return DAG.getNode(ISD::OR, DL, VT, X, Y); if (SDValue R = foldLogicOfShifts(N, N0, N1, DAG)) return R; @@ -7688,6 +7692,26 @@ static SDValue visitORCommutative(SelectionDAG &DAG, SDValue N0, SDValue N1, peekThroughZext(N0.getOperand(2)) == peekThroughZext(N1.getOperand(1))) return N0; + // Attempt to match a legalized build_pair-esque pattern: + // or(shl(aext(Hi),BW/2),zext(Lo)) + SDValue Lo, Hi; + if (sd_match(N0, + m_OneUse(m_Shl(m_AnyExt(m_Value(Hi)), m_SpecificInt(BW / 2)))) && + sd_match(N1, m_ZExt(m_Value(Lo))) && + Lo.getScalarValueSizeInBits() == (BW / 2) && + Lo.getValueType() == Hi.getValueType()) { + // Fold build_pair(not(Lo),not(Hi)) -> not(build_pair(Lo,Hi)). + SDValue NotLo, NotHi; + if (sd_match(Lo, m_OneUse(m_Not(m_Value(NotLo)))) && + sd_match(Hi, m_OneUse(m_Not(m_Value(NotHi))))) { + Lo = DAG.getNode(ISD::ZERO_EXTEND, DL, VT, NotLo); + Hi = DAG.getNode(ISD::ANY_EXTEND, DL, VT, NotHi); + Hi = DAG.getNode(ISD::SHL, DL, VT, Hi, + DAG.getShiftAmountConstant(BW / 2, VT, DL)); + return DAG.getNOT(DL, DAG.getNode(ISD::OR, DL, VT, Lo, Hi), VT); + } + } + return SDValue(); } @@ -15451,6 +15475,26 @@ SDValue DAGCombiner::visitFREEZE(SDNode *N) { N0.getOpcode() == ISD::BUILD_PAIR || N0.getOpcode() == ISD::CONCAT_VECTORS; + // Avoid turning a BUILD_VECTOR that can be recognized as "all zeros", "all + // ones" or "constant" into something that depends on FrozenUndef. We can + // instead pick undef values to keep those properties, while at the same time + // folding away the freeze. + // If we implement a more general solution for folding away freeze(undef) in + // the future, then this special handling can be removed. + if (N0.getOpcode() == ISD::BUILD_VECTOR) { + SDLoc DL(N0); + MVT VT = N0.getSimpleValueType(); + if (llvm::ISD::isBuildVectorAllOnes(N0.getNode())) + return DAG.getAllOnesConstant(DL, VT); + if (llvm::ISD::isBuildVectorOfConstantSDNodes(N0.getNode())) { + SmallVector NewVecC; + for (const SDValue &Op : N0->op_values()) + NewVecC.push_back( + Op.isUndef() ? DAG.getConstant(0, DL, Op.getValueType()) : Op); + return DAG.getBuildVector(VT, DL, NewVecC); + } + } + SmallSetVector MaybePoisonOperands; for (SDValue Op : N0->ops()) { if (DAG.isGuaranteedNotToBeUndefOrPoison(Op, /*PoisonOnly*/ false, @@ -21095,6 +21139,24 @@ SDValue DAGCombiner::replaceStoreOfInsertLoad(StoreSDNode *ST) { ST->getMemOperand()->getFlags()); } +SDValue DAGCombiner::visitATOMIC_STORE(SDNode *N) { + AtomicSDNode *ST = cast(N); + SDValue Val = ST->getVal(); + EVT VT = Val.getValueType(); + EVT MemVT = ST->getMemoryVT(); + + if (MemVT.bitsLT(VT)) { // Is truncating store + APInt TruncDemandedBits = APInt::getLowBitsSet(VT.getScalarSizeInBits(), + MemVT.getScalarSizeInBits()); + // See if we can simplify the operation with SimplifyDemandedBits, which + // only works if the value has a single use. + if (SimplifyDemandedBits(Val, TruncDemandedBits)) + return SDValue(N, 0); + } + + return SDValue(); +} + SDValue DAGCombiner::visitSTORE(SDNode *N) { StoreSDNode *ST = cast(N); SDValue Chain = ST->getChain(); diff --git a/llvm/lib/CodeGen/SelectionDAG/FastISel.cpp b/llvm/lib/CodeGen/SelectionDAG/FastISel.cpp index aefedd060f897dfb527931ef15fb715090828cfa..ef9f7833551905404c9b37649358ea54116951c4 100644 --- a/llvm/lib/CodeGen/SelectionDAG/FastISel.cpp +++ b/llvm/lib/CodeGen/SelectionDAG/FastISel.cpp @@ -1424,7 +1424,7 @@ bool FastISel::selectIntrinsicCall(const IntrinsicInst *II) { // happened (such as an optimised function being always-inlined into an // optnone function). We will not be using the extra information in the // dbg.assign in that case, just use its dbg.value fields. - LLVM_FALLTHROUGH; + [[fallthrough]]; case Intrinsic::dbg_value: { // This form of DBG_VALUE is target-independent. const DbgValueInst *DI = cast(II); diff --git a/llvm/lib/CodeGen/SelectionDAG/InstrEmitter.cpp b/llvm/lib/CodeGen/SelectionDAG/InstrEmitter.cpp index 54409cbf91f1f7a895ccdaafb8edd715f99bfffe..759368a67a16cf3574859f76481c25f0634080c1 100644 --- a/llvm/lib/CodeGen/SelectionDAG/InstrEmitter.cpp +++ b/llvm/lib/CodeGen/SelectionDAG/InstrEmitter.cpp @@ -1420,7 +1420,7 @@ EmitSpecialNode(SDNode *Node, bool IsClone, bool IsCloned, for (unsigned Reg : ECRegs) { if (MIB->readsRegister(Reg, TRI)) { MachineOperand *MO = - MIB->findRegisterDefOperand(Reg, false, false, TRI); + MIB->findRegisterDefOperand(Reg, TRI, false, false); assert(MO && "No def operand for clobbered register?"); MO->setIsEarlyClobber(false); } diff --git a/llvm/lib/CodeGen/SelectionDAG/LegalizeDAG.cpp b/llvm/lib/CodeGen/SelectionDAG/LegalizeDAG.cpp index 24f69ea1b742a67e6dd8f1204896ebdb74d8ee02..c381870ae5f41b485efdde61f9712fd10632ed5d 100644 --- a/llvm/lib/CodeGen/SelectionDAG/LegalizeDAG.cpp +++ b/llvm/lib/CodeGen/SelectionDAG/LegalizeDAG.cpp @@ -3195,7 +3195,7 @@ bool SelectionDAGLegalize::ExpandNode(SDNode *Node) { break; } - LLVM_FALLTHROUGH; + [[fallthrough]]; } case ISD::BITCAST: if ((Tmp1 = EmitStackConvert(Node->getOperand(0), Node->getValueType(0), @@ -5575,6 +5575,21 @@ void SelectionDAGLegalize::PromoteNode(SDNode *Node) { Results.push_back(NewAtomic.getValue(1)); break; } + case ISD::ATOMIC_LOAD: { + AtomicSDNode *AM = cast(Node); + SDLoc SL(Node); + assert(NVT.getSizeInBits() == OVT.getSizeInBits() && + "unexpected promotion type"); + assert(AM->getMemoryVT().getSizeInBits() == NVT.getSizeInBits() && + "unexpected atomic_load with illegal type"); + + SDValue NewAtomic = + DAG.getAtomic(ISD::ATOMIC_LOAD, SL, NVT, DAG.getVTList(NVT, MVT::Other), + {AM->getChain(), AM->getBasePtr()}, AM->getMemOperand()); + Results.push_back(DAG.getNode(ISD::BITCAST, SL, OVT, NewAtomic)); + Results.push_back(NewAtomic.getValue(1)); + break; + } case ISD::SPLAT_VECTOR: { SDValue Scalar = Node->getOperand(0); MVT ScalarType = Scalar.getSimpleValueType(); diff --git a/llvm/lib/CodeGen/SelectionDAG/LegalizeFloatTypes.cpp b/llvm/lib/CodeGen/SelectionDAG/LegalizeFloatTypes.cpp index 7685bc73cf965242f749ea758c90825ca2200815..abe5be76382556ec8a3471eb3922823b713c5256 100644 --- a/llvm/lib/CodeGen/SelectionDAG/LegalizeFloatTypes.cpp +++ b/llvm/lib/CodeGen/SelectionDAG/LegalizeFloatTypes.cpp @@ -2449,6 +2449,9 @@ void DAGTypeLegalizer::PromoteFloatResult(SDNode *N, unsigned ResNo) { R = PromoteFloatRes_STRICT_FP_ROUND(N); break; case ISD::LOAD: R = PromoteFloatRes_LOAD(N); break; + case ISD::ATOMIC_LOAD: + R = PromoteFloatRes_ATOMIC_LOAD(N); + break; case ISD::SELECT: R = PromoteFloatRes_SELECT(N); break; case ISD::SELECT_CC: R = PromoteFloatRes_SELECT_CC(N); break; @@ -2695,6 +2698,25 @@ SDValue DAGTypeLegalizer::PromoteFloatRes_LOAD(SDNode *N) { return DAG.getNode(GetPromotionOpcode(VT, NVT), SDLoc(N), NVT, newL); } +SDValue DAGTypeLegalizer::PromoteFloatRes_ATOMIC_LOAD(SDNode *N) { + AtomicSDNode *AM = cast(N); + EVT VT = AM->getValueType(0); + + // Load the value as an integer value with the same number of bits. + EVT IVT = EVT::getIntegerVT(*DAG.getContext(), VT.getSizeInBits()); + SDValue newL = DAG.getAtomic( + ISD::ATOMIC_LOAD, SDLoc(N), IVT, DAG.getVTList(IVT, MVT::Other), + {AM->getChain(), AM->getBasePtr()}, AM->getMemOperand()); + + // Legalize the chain result by replacing uses of the old value chain with the + // new one + ReplaceValueWith(SDValue(N, 1), newL.getValue(1)); + + // Convert the integer value to the desired FP type + EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), VT); + return DAG.getNode(GetPromotionOpcode(VT, IVT), SDLoc(N), NVT, newL); +} + // Construct a new SELECT node with the promoted true- and false- values. SDValue DAGTypeLegalizer::PromoteFloatRes_SELECT(SDNode *N) { SDValue TrueVal = GetPromotedFloat(N->getOperand(1)); @@ -2855,6 +2877,9 @@ void DAGTypeLegalizer::SoftPromoteHalfResult(SDNode *N, unsigned ResNo) { case ISD::FFREXP: R = SoftPromoteHalfRes_FFREXP(N); break; case ISD::LOAD: R = SoftPromoteHalfRes_LOAD(N); break; + case ISD::ATOMIC_LOAD: + R = SoftPromoteHalfRes_ATOMIC_LOAD(N); + break; case ISD::SELECT: R = SoftPromoteHalfRes_SELECT(N); break; case ISD::SELECT_CC: R = SoftPromoteHalfRes_SELECT_CC(N); break; case ISD::SINT_TO_FP: @@ -3039,6 +3064,20 @@ SDValue DAGTypeLegalizer::SoftPromoteHalfRes_LOAD(SDNode *N) { return NewL; } +SDValue DAGTypeLegalizer::SoftPromoteHalfRes_ATOMIC_LOAD(SDNode *N) { + AtomicSDNode *AM = cast(N); + + // Load the value as an integer value with the same number of bits. + SDValue NewL = DAG.getAtomic( + ISD::ATOMIC_LOAD, SDLoc(N), MVT::i16, DAG.getVTList(MVT::i16, MVT::Other), + {AM->getChain(), AM->getBasePtr()}, AM->getMemOperand()); + + // Legalize the chain result by replacing uses of the old value chain with the + // new one + ReplaceValueWith(SDValue(N, 1), NewL.getValue(1)); + return NewL; +} + SDValue DAGTypeLegalizer::SoftPromoteHalfRes_SELECT(SDNode *N) { SDValue Op1 = GetSoftPromotedHalf(N->getOperand(1)); SDValue Op2 = GetSoftPromotedHalf(N->getOperand(2)); diff --git a/llvm/lib/CodeGen/SelectionDAG/LegalizeTypes.h b/llvm/lib/CodeGen/SelectionDAG/LegalizeTypes.h index 0483f7c74f91a2e36eb0b78c540d534c1e7b60c1..4a2c7b355eb528a2bff9d902b55922ffd3a89766 100644 --- a/llvm/lib/CodeGen/SelectionDAG/LegalizeTypes.h +++ b/llvm/lib/CodeGen/SelectionDAG/LegalizeTypes.h @@ -691,6 +691,7 @@ private: SDValue PromoteFloatRes_FP_ROUND(SDNode *N); SDValue PromoteFloatRes_STRICT_FP_ROUND(SDNode *N); SDValue PromoteFloatRes_LOAD(SDNode *N); + SDValue PromoteFloatRes_ATOMIC_LOAD(SDNode *N); SDValue PromoteFloatRes_SELECT(SDNode *N); SDValue PromoteFloatRes_SELECT_CC(SDNode *N); SDValue PromoteFloatRes_UnaryOp(SDNode *N); @@ -734,6 +735,7 @@ private: SDValue SoftPromoteHalfRes_FFREXP(SDNode *N); SDValue SoftPromoteHalfRes_FP_ROUND(SDNode *N); SDValue SoftPromoteHalfRes_LOAD(SDNode *N); + SDValue SoftPromoteHalfRes_ATOMIC_LOAD(SDNode *N); SDValue SoftPromoteHalfRes_SELECT(SDNode *N); SDValue SoftPromoteHalfRes_SELECT_CC(SDNode *N); SDValue SoftPromoteHalfRes_UnaryOp(SDNode *N); @@ -984,7 +986,7 @@ private: SDValue WidenVecRes_FP_TO_XINT_SAT(SDNode *N); SDValue WidenVecRes_XRINT(SDNode *N); SDValue WidenVecRes_FCOPYSIGN(SDNode *N); - SDValue WidenVecRes_IS_FPCLASS(SDNode *N); + SDValue WidenVecRes_UnarySameEltsWithScalarArg(SDNode *N); SDValue WidenVecRes_ExpOp(SDNode *N); SDValue WidenVecRes_Unary(SDNode *N); SDValue WidenVecRes_InregOp(SDNode *N); diff --git a/llvm/lib/CodeGen/SelectionDAG/LegalizeVectorOps.cpp b/llvm/lib/CodeGen/SelectionDAG/LegalizeVectorOps.cpp index 7a9cfdf5c3fda9e678924ca06bfaa2119e6858e1..1de43a4f60e3a2bb54778e61f0109df0e7656584 100644 --- a/llvm/lib/CodeGen/SelectionDAG/LegalizeVectorOps.cpp +++ b/llvm/lib/CodeGen/SelectionDAG/LegalizeVectorOps.cpp @@ -420,6 +420,7 @@ SDValue VectorLegalizer::LegalizeOp(SDValue Op) { case ISD::FFLOOR: case ISD::FP_ROUND: case ISD::FP_EXTEND: + case ISD::FPTRUNC_ROUND: case ISD::FMA: case ISD::SIGN_EXTEND_INREG: case ISD::ANY_EXTEND_VECTOR_INREG: diff --git a/llvm/lib/CodeGen/SelectionDAG/LegalizeVectorTypes.cpp b/llvm/lib/CodeGen/SelectionDAG/LegalizeVectorTypes.cpp index 8776d89f4c5bd9dc2f135c024e099f73af3c9557..985c9f16ab97cdf805dfe7b2bed462fd495d12da 100644 --- a/llvm/lib/CodeGen/SelectionDAG/LegalizeVectorTypes.cpp +++ b/llvm/lib/CodeGen/SelectionDAG/LegalizeVectorTypes.cpp @@ -4242,7 +4242,8 @@ void DAGTypeLegalizer::WidenVectorResult(SDNode *N, unsigned ResNo) { break; case ISD::IS_FPCLASS: - Res = WidenVecRes_IS_FPCLASS(N); + case ISD::FPTRUNC_ROUND: + Res = WidenVecRes_UnarySameEltsWithScalarArg(N); break; case ISD::FLDEXP: @@ -5004,7 +5005,10 @@ SDValue DAGTypeLegalizer::WidenVecRes_FCOPYSIGN(SDNode *N) { return DAG.UnrollVectorOp(N, WidenVT.getVectorNumElements()); } -SDValue DAGTypeLegalizer::WidenVecRes_IS_FPCLASS(SDNode *N) { +/// Result and first source operand are different scalar types, but must have +/// the same number of elements. There is an additional control argument which +/// should be passed through unchanged. +SDValue DAGTypeLegalizer::WidenVecRes_UnarySameEltsWithScalarArg(SDNode *N) { SDValue FpValue = N->getOperand(0); EVT WidenVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0)); if (getTypeAction(FpValue.getValueType()) != TargetLowering::TypeWidenVector) diff --git a/llvm/lib/CodeGen/SelectionDAG/ScheduleDAGSDNodes.cpp b/llvm/lib/CodeGen/SelectionDAG/ScheduleDAGSDNodes.cpp index 379456e3a9b6c013a8d48a978282095aae7bd72b..f44added89a72838a0bef7110eee034d4da045e2 100644 --- a/llvm/lib/CodeGen/SelectionDAG/ScheduleDAGSDNodes.cpp +++ b/llvm/lib/CodeGen/SelectionDAG/ScheduleDAGSDNodes.cpp @@ -27,6 +27,7 @@ #include "llvm/CodeGen/TargetRegisterInfo.h" #include "llvm/CodeGen/TargetSubtargetInfo.h" #include "llvm/Config/llvm-config.h" +#include "llvm/IR/MemoryModelRelaxationAnnotations.h" #include "llvm/MC/MCInstrItineraries.h" #include "llvm/Support/CommandLine.h" #include "llvm/Support/Debug.h" @@ -899,6 +900,14 @@ EmitSchedule(MachineBasicBlock::iterator &InsertPos) { if (MDNode *MD = DAG->getPCSections(Node)) MI->setPCSections(MF, MD); + // Set MMRAs on _all_ added instructions. + if (MDNode *MMRA = DAG->getMMRAMetadata(Node)) { + for (MachineBasicBlock::iterator It = MI->getIterator(), + End = std::next(After); + It != End; ++It) + It->setMMRAMetadata(MF, MMRA); + } + return MI; }; diff --git a/llvm/lib/CodeGen/SelectionDAG/SelectionDAG.cpp b/llvm/lib/CodeGen/SelectionDAG/SelectionDAG.cpp index b63b8b893fdbf1c98b8815c304a545b2202b37f7..dde10fd4b8c8afe8f1f5244e3f5cdbbe44ddf953 100644 --- a/llvm/lib/CodeGen/SelectionDAG/SelectionDAG.cpp +++ b/llvm/lib/CodeGen/SelectionDAG/SelectionDAG.cpp @@ -1418,10 +1418,8 @@ void SelectionDAG::clear() { TargetExternalSymbols.clear(); MCSymbols.clear(); SDEI.clear(); - std::fill(CondCodeNodes.begin(), CondCodeNodes.end(), - static_cast(nullptr)); - std::fill(ValueTypeNodes.begin(), ValueTypeNodes.end(), - static_cast(nullptr)); + std::fill(CondCodeNodes.begin(), CondCodeNodes.end(), nullptr); + std::fill(ValueTypeNodes.begin(), ValueTypeNodes.end(), nullptr); EntryNode.UseList = nullptr; InsertNode(&EntryNode); @@ -1703,8 +1701,9 @@ SDValue SelectionDAG::getConstant(const ConstantInt &Val, const SDLoc &DL, assert(Elt->getBitWidth() == EltVT.getSizeInBits() && "APInt size does not match type size!"); unsigned Opc = isT ? ISD::TargetConstant : ISD::Constant; + SDVTList VTs = getVTList(EltVT); FoldingSetNodeID ID; - AddNodeIDNode(ID, Opc, getVTList(EltVT), std::nullopt); + AddNodeIDNode(ID, Opc, VTs, std::nullopt); ID.AddPointer(Elt); ID.AddBoolean(isO); void *IP = nullptr; @@ -1714,7 +1713,7 @@ SDValue SelectionDAG::getConstant(const ConstantInt &Val, const SDLoc &DL, return SDValue(N, 0); if (!N) { - N = newSDNode(isT, isO, Elt, EltVT); + N = newSDNode(isT, isO, Elt, VTs); CSEMap.InsertNode(N, IP); InsertNode(N); NewSDValueDbgMsg(SDValue(N, 0), "Creating constant: ", this); @@ -1764,8 +1763,9 @@ SDValue SelectionDAG::getConstantFP(const ConstantFP &V, const SDLoc &DL, // value, so that we don't have problems with 0.0 comparing equal to -0.0, and // we don't have issues with SNANs. unsigned Opc = isTarget ? ISD::TargetConstantFP : ISD::ConstantFP; + SDVTList VTs = getVTList(EltVT); FoldingSetNodeID ID; - AddNodeIDNode(ID, Opc, getVTList(EltVT), std::nullopt); + AddNodeIDNode(ID, Opc, VTs, std::nullopt); ID.AddPointer(&V); void *IP = nullptr; SDNode *N = nullptr; @@ -1774,7 +1774,7 @@ SDValue SelectionDAG::getConstantFP(const ConstantFP &V, const SDLoc &DL, return SDValue(N, 0); if (!N) { - N = newSDNode(isTarget, &V, EltVT); + N = newSDNode(isTarget, &V, VTs); CSEMap.InsertNode(N, IP); InsertNode(N); } @@ -1821,8 +1821,9 @@ SDValue SelectionDAG::getGlobalAddress(const GlobalValue *GV, const SDLoc &DL, else Opc = isTargetGA ? ISD::TargetGlobalAddress : ISD::GlobalAddress; + SDVTList VTs = getVTList(VT); FoldingSetNodeID ID; - AddNodeIDNode(ID, Opc, getVTList(VT), std::nullopt); + AddNodeIDNode(ID, Opc, VTs, std::nullopt); ID.AddPointer(GV); ID.AddInteger(Offset); ID.AddInteger(TargetFlags); @@ -1831,7 +1832,7 @@ SDValue SelectionDAG::getGlobalAddress(const GlobalValue *GV, const SDLoc &DL, return SDValue(E, 0); auto *N = newSDNode( - Opc, DL.getIROrder(), DL.getDebugLoc(), GV, VT, Offset, TargetFlags); + Opc, DL.getIROrder(), DL.getDebugLoc(), GV, VTs, Offset, TargetFlags); CSEMap.InsertNode(N, IP); InsertNode(N); return SDValue(N, 0); @@ -1839,14 +1840,15 @@ SDValue SelectionDAG::getGlobalAddress(const GlobalValue *GV, const SDLoc &DL, SDValue SelectionDAG::getFrameIndex(int FI, EVT VT, bool isTarget) { unsigned Opc = isTarget ? ISD::TargetFrameIndex : ISD::FrameIndex; + SDVTList VTs = getVTList(VT); FoldingSetNodeID ID; - AddNodeIDNode(ID, Opc, getVTList(VT), std::nullopt); + AddNodeIDNode(ID, Opc, VTs, std::nullopt); ID.AddInteger(FI); void *IP = nullptr; if (SDNode *E = FindNodeOrInsertPos(ID, IP)) return SDValue(E, 0); - auto *N = newSDNode(FI, VT, isTarget); + auto *N = newSDNode(FI, VTs, isTarget); CSEMap.InsertNode(N, IP); InsertNode(N); return SDValue(N, 0); @@ -1857,15 +1859,16 @@ SDValue SelectionDAG::getJumpTable(int JTI, EVT VT, bool isTarget, assert((TargetFlags == 0 || isTarget) && "Cannot set target flags on target-independent jump tables"); unsigned Opc = isTarget ? ISD::TargetJumpTable : ISD::JumpTable; + SDVTList VTs = getVTList(VT); FoldingSetNodeID ID; - AddNodeIDNode(ID, Opc, getVTList(VT), std::nullopt); + AddNodeIDNode(ID, Opc, VTs, std::nullopt); ID.AddInteger(JTI); ID.AddInteger(TargetFlags); void *IP = nullptr; if (SDNode *E = FindNodeOrInsertPos(ID, IP)) return SDValue(E, 0); - auto *N = newSDNode(JTI, VT, isTarget, TargetFlags); + auto *N = newSDNode(JTI, VTs, isTarget, TargetFlags); CSEMap.InsertNode(N, IP); InsertNode(N); return SDValue(N, 0); @@ -1888,8 +1891,9 @@ SDValue SelectionDAG::getConstantPool(const Constant *C, EVT VT, ? getDataLayout().getABITypeAlign(C->getType()) : getDataLayout().getPrefTypeAlign(C->getType()); unsigned Opc = isTarget ? ISD::TargetConstantPool : ISD::ConstantPool; + SDVTList VTs = getVTList(VT); FoldingSetNodeID ID; - AddNodeIDNode(ID, Opc, getVTList(VT), std::nullopt); + AddNodeIDNode(ID, Opc, VTs, std::nullopt); ID.AddInteger(Alignment->value()); ID.AddInteger(Offset); ID.AddPointer(C); @@ -1898,7 +1902,7 @@ SDValue SelectionDAG::getConstantPool(const Constant *C, EVT VT, if (SDNode *E = FindNodeOrInsertPos(ID, IP)) return SDValue(E, 0); - auto *N = newSDNode(isTarget, C, VT, Offset, *Alignment, + auto *N = newSDNode(isTarget, C, VTs, Offset, *Alignment, TargetFlags); CSEMap.InsertNode(N, IP); InsertNode(N); @@ -1915,8 +1919,9 @@ SDValue SelectionDAG::getConstantPool(MachineConstantPoolValue *C, EVT VT, if (!Alignment) Alignment = getDataLayout().getPrefTypeAlign(C->getType()); unsigned Opc = isTarget ? ISD::TargetConstantPool : ISD::ConstantPool; + SDVTList VTs = getVTList(VT); FoldingSetNodeID ID; - AddNodeIDNode(ID, Opc, getVTList(VT), std::nullopt); + AddNodeIDNode(ID, Opc, VTs, std::nullopt); ID.AddInteger(Alignment->value()); ID.AddInteger(Offset); C->addSelectionDAGCSEId(ID); @@ -1925,7 +1930,7 @@ SDValue SelectionDAG::getConstantPool(MachineConstantPoolValue *C, EVT VT, if (SDNode *E = FindNodeOrInsertPos(ID, IP)) return SDValue(E, 0); - auto *N = newSDNode(isTarget, C, VT, Offset, *Alignment, + auto *N = newSDNode(isTarget, C, VTs, Offset, *Alignment, TargetFlags); CSEMap.InsertNode(N, IP); InsertNode(N); @@ -1963,7 +1968,7 @@ SDValue SelectionDAG::getValueType(EVT VT) { SDValue SelectionDAG::getExternalSymbol(const char *Sym, EVT VT) { SDNode *&N = ExternalSymbols[Sym]; if (N) return SDValue(N, 0); - N = newSDNode(false, Sym, 0, VT); + N = newSDNode(false, Sym, 0, getVTList(VT)); InsertNode(N); return SDValue(N, 0); } @@ -1972,7 +1977,7 @@ SDValue SelectionDAG::getMCSymbol(MCSymbol *Sym, EVT VT) { SDNode *&N = MCSymbols[Sym]; if (N) return SDValue(N, 0); - N = newSDNode(Sym, VT); + N = newSDNode(Sym, getVTList(VT)); InsertNode(N); return SDValue(N, 0); } @@ -1982,7 +1987,7 @@ SDValue SelectionDAG::getTargetExternalSymbol(const char *Sym, EVT VT, SDNode *&N = TargetExternalSymbols[std::pair(Sym, TargetFlags)]; if (N) return SDValue(N, 0); - N = newSDNode(true, Sym, TargetFlags, VT); + N = newSDNode(true, Sym, TargetFlags, getVTList(VT)); InsertNode(N); return SDValue(N, 0); } @@ -2198,9 +2203,10 @@ SDValue SelectionDAG::getVectorShuffle(EVT VT, const SDLoc &dl, SDValue N1, } } + SDVTList VTs = getVTList(VT); FoldingSetNodeID ID; SDValue Ops[2] = { N1, N2 }; - AddNodeIDNode(ID, ISD::VECTOR_SHUFFLE, getVTList(VT), Ops); + AddNodeIDNode(ID, ISD::VECTOR_SHUFFLE, VTs, Ops); for (int i = 0; i != NElts; ++i) ID.AddInteger(MaskVec[i]); @@ -2214,7 +2220,7 @@ SDValue SelectionDAG::getVectorShuffle(EVT VT, const SDLoc &dl, SDValue N1, int *MaskAlloc = OperandAllocator.Allocate(NElts); llvm::copy(MaskVec, MaskAlloc); - auto *N = newSDNode(VT, dl.getIROrder(), + auto *N = newSDNode(VTs, dl.getIROrder(), dl.getDebugLoc(), MaskAlloc); createOperands(N, Ops); @@ -2236,14 +2242,15 @@ SDValue SelectionDAG::getCommutedVectorShuffle(const ShuffleVectorSDNode &SV) { } SDValue SelectionDAG::getRegister(unsigned RegNo, EVT VT) { + SDVTList VTs = getVTList(VT); FoldingSetNodeID ID; - AddNodeIDNode(ID, ISD::Register, getVTList(VT), std::nullopt); + AddNodeIDNode(ID, ISD::Register, VTs, std::nullopt); ID.AddInteger(RegNo); void *IP = nullptr; if (SDNode *E = FindNodeOrInsertPos(ID, IP)) return SDValue(E, 0); - auto *N = newSDNode(RegNo, VT); + auto *N = newSDNode(RegNo, VTs); N->SDNodeBits.IsDivergent = TLI->isSDNodeSourceOfDivergence(N, FLI, UA); CSEMap.InsertNode(N, IP); InsertNode(N); @@ -2292,9 +2299,10 @@ SDValue SelectionDAG::getBlockAddress(const BlockAddress *BA, EVT VT, int64_t Offset, bool isTarget, unsigned TargetFlags) { unsigned Opc = isTarget ? ISD::TargetBlockAddress : ISD::BlockAddress; + SDVTList VTs = getVTList(VT); FoldingSetNodeID ID; - AddNodeIDNode(ID, Opc, getVTList(VT), std::nullopt); + AddNodeIDNode(ID, Opc, VTs, std::nullopt); ID.AddPointer(BA); ID.AddInteger(Offset); ID.AddInteger(TargetFlags); @@ -2302,7 +2310,7 @@ SDValue SelectionDAG::getBlockAddress(const BlockAddress *BA, EVT VT, if (SDNode *E = FindNodeOrInsertPos(ID, IP)) return SDValue(E, 0); - auto *N = newSDNode(Opc, VT, BA, Offset, TargetFlags); + auto *N = newSDNode(Opc, VTs, BA, Offset, TargetFlags); CSEMap.InsertNode(N, IP); InsertNode(N); return SDValue(N, 0); @@ -2347,9 +2355,10 @@ SDValue SelectionDAG::getBitcast(EVT VT, SDValue V) { SDValue SelectionDAG::getAddrSpaceCast(const SDLoc &dl, EVT VT, SDValue Ptr, unsigned SrcAS, unsigned DestAS) { + SDVTList VTs = getVTList(VT); SDValue Ops[] = {Ptr}; FoldingSetNodeID ID; - AddNodeIDNode(ID, ISD::ADDRSPACECAST, getVTList(VT), Ops); + AddNodeIDNode(ID, ISD::ADDRSPACECAST, VTs, Ops); ID.AddInteger(SrcAS); ID.AddInteger(DestAS); @@ -2358,7 +2367,7 @@ SDValue SelectionDAG::getAddrSpaceCast(const SDLoc &dl, EVT VT, SDValue Ptr, return SDValue(E, 0); auto *N = newSDNode(dl.getIROrder(), dl.getDebugLoc(), - VT, SrcAS, DestAS); + VTs, SrcAS, DestAS); createOperands(N, Ops); CSEMap.InsertNode(N, IP); @@ -2995,6 +3004,14 @@ SelectionDAG::getValidShiftAmountConstant(SDValue V, return nullptr; } +const APInt *SelectionDAG::getValidShiftAmountConstant(SDValue V) const { + EVT VT = V.getValueType(); + APInt DemandedElts = VT.isFixedLengthVector() + ? APInt::getAllOnes(VT.getVectorNumElements()) + : APInt(1, 1); + return getValidShiftAmountConstant(V, DemandedElts); +} + const APInt *SelectionDAG::getValidMinimumShiftAmountConstant( SDValue V, const APInt &DemandedElts) const { assert((V.getOpcode() == ISD::SHL || V.getOpcode() == ISD::SRL || @@ -3024,6 +3041,14 @@ const APInt *SelectionDAG::getValidMinimumShiftAmountConstant( return MinShAmt; } +const APInt *SelectionDAG::getValidMinimumShiftAmountConstant(SDValue V) const { + EVT VT = V.getValueType(); + APInt DemandedElts = VT.isFixedLengthVector() + ? APInt::getAllOnes(VT.getVectorNumElements()) + : APInt(1, 1); + return getValidMinimumShiftAmountConstant(V, DemandedElts); +} + const APInt *SelectionDAG::getValidMaximumShiftAmountConstant( SDValue V, const APInt &DemandedElts) const { assert((V.getOpcode() == ISD::SHL || V.getOpcode() == ISD::SRL || @@ -3053,6 +3078,14 @@ const APInt *SelectionDAG::getValidMaximumShiftAmountConstant( return MaxShAmt; } +const APInt *SelectionDAG::getValidMaximumShiftAmountConstant(SDValue V) const { + EVT VT = V.getValueType(); + APInt DemandedElts = VT.isFixedLengthVector() + ? APInt::getAllOnes(VT.getVectorNumElements()) + : APInt(1, 1); + return getValidMaximumShiftAmountConstant(V, DemandedElts); +} + /// Determine which bits of Op are known to be either zero or one and return /// them in Known. For vectors, the known bits are those that are shared by /// every vector element. @@ -5030,6 +5063,7 @@ bool SelectionDAG::isGuaranteedNotToBeUndefOrPoison(SDValue Op, case ISD::VALUETYPE: case ISD::FrameIndex: case ISD::TargetFrameIndex: + case ISD::CopyFromReg: return true; case ISD::UNDEF: @@ -5095,6 +5129,9 @@ bool SelectionDAG::canCreateUndefOrPoison(SDValue Op, const APInt &DemandedElts, if (VT.isScalableVector()) return true; + if (ConsiderFlags && Op->hasPoisonGeneratingFlags()) + return true; + unsigned Opcode = Op.getOpcode(); switch (Opcode) { case ISD::FREEZE: @@ -5134,34 +5171,20 @@ bool SelectionDAG::canCreateUndefOrPoison(SDValue Op, const APInt &DemandedElts, return true; const TargetOptions &Options = getTarget().Options; - return Options.NoNaNsFPMath || Options.NoInfsFPMath || - (ConsiderFlags && - (Op->getFlags().hasNoNaNs() || Op->getFlags().hasNoInfs())); + return Options.NoNaNsFPMath || Options.NoInfsFPMath; } - // Matches hasPoisonGeneratingFlags(). + case ISD::OR: case ISD::ZERO_EXTEND: - return ConsiderFlags && Op->getFlags().hasNonNeg(); - case ISD::ADD: case ISD::SUB: case ISD::MUL: - // Matches hasPoisonGeneratingFlags(). - return ConsiderFlags && (Op->getFlags().hasNoSignedWrap() || - Op->getFlags().hasNoUnsignedWrap()); + // No poison except from flags (which is handled above) + return false; case ISD::SHL: // If the max shift amount isn't in range, then the shift can create poison. - if (!getValidMaximumShiftAmountConstant(Op, DemandedElts)) - return true; - - // Matches hasPoisonGeneratingFlags(). - return ConsiderFlags && (Op->getFlags().hasNoSignedWrap() || - Op->getFlags().hasNoUnsignedWrap()); - - // Matches hasPoisonGeneratingFlags(). - case ISD::OR: - return ConsiderFlags && Op->getFlags().hasDisjoint(); + return !getValidMaximumShiftAmountConstant(Op, DemandedElts); case ISD::SCALAR_TO_VECTOR: // Check if we demand any upper (undef) elements. @@ -5691,14 +5714,14 @@ static SDValue foldCONCAT_VECTORS(const SDLoc &DL, EVT VT, /// Gets or creates the specified node. SDValue SelectionDAG::getNode(unsigned Opcode, const SDLoc &DL, EVT VT) { + SDVTList VTs = getVTList(VT); FoldingSetNodeID ID; - AddNodeIDNode(ID, Opcode, getVTList(VT), std::nullopt); + AddNodeIDNode(ID, Opcode, VTs, std::nullopt); void *IP = nullptr; if (SDNode *E = FindNodeOrInsertPos(ID, DL, IP)) return SDValue(E, 0); - auto *N = newSDNode(Opcode, DL.getIROrder(), DL.getDebugLoc(), - getVTList(VT)); + auto *N = newSDNode(Opcode, DL.getIROrder(), DL.getDebugLoc(), VTs); CSEMap.InsertNode(N, IP); InsertNode(N); @@ -6645,16 +6668,17 @@ SDValue SelectionDAG::getAssertAlign(const SDLoc &DL, SDValue Val, Align A) { if (A == Align(1)) return Val; + SDVTList VTs = getVTList(Val.getValueType()); FoldingSetNodeID ID; - AddNodeIDNode(ID, ISD::AssertAlign, getVTList(Val.getValueType()), {Val}); + AddNodeIDNode(ID, ISD::AssertAlign, VTs, {Val}); ID.AddInteger(A.value()); void *IP = nullptr; if (SDNode *E = FindNodeOrInsertPos(ID, DL, IP)) return SDValue(E, 0); - auto *N = newSDNode(DL.getIROrder(), DL.getDebugLoc(), - Val.getValueType(), A); + auto *N = + newSDNode(DL.getIROrder(), DL.getDebugLoc(), VTs, A); createOperands(N, {Val}); CSEMap.InsertNode(N, IP); @@ -11773,20 +11797,6 @@ HandleSDNode::~HandleSDNode() { DropOperands(); } -GlobalAddressSDNode::GlobalAddressSDNode(unsigned Opc, unsigned Order, - const DebugLoc &DL, - const GlobalValue *GA, EVT VT, - int64_t o, unsigned TF) - : SDNode(Opc, Order, DL, getSDVTList(VT)), Offset(o), TargetFlags(TF) { - TheGlobal = GA; -} - -AddrSpaceCastSDNode::AddrSpaceCastSDNode(unsigned Order, const DebugLoc &dl, - EVT VT, unsigned SrcAS, - unsigned DestAS) - : SDNode(ISD::ADDRSPACECAST, Order, dl, getSDVTList(VT)), - SrcAddrSpace(SrcAS), DestAddrSpace(DestAS) {} - MemSDNode::MemSDNode(unsigned Opc, unsigned Order, const DebugLoc &dl, SDVTList VTs, EVT memvt, MachineMemOperand *mmo) : SDNode(Opc, Order, dl, VTs), MemoryVT(memvt), MMO(mmo) { @@ -12946,7 +12956,7 @@ void SelectionDAG::copyExtraInfo(SDNode *From, SDNode *To) { // Use of operator[] on the DenseMap may cause an insertion, which invalidates // the iterator, hence the need to make a copy to prevent a use-after-free. NodeExtraInfo NEI = I->second; - if (LLVM_LIKELY(!NEI.PCSections)) { + if (LLVM_LIKELY(!NEI.PCSections) && LLVM_LIKELY(!NEI.MMRA)) { // No deep copy required for the types of extra info set. // // FIXME: Investigate if other types of extra info also need deep copy. This diff --git a/llvm/lib/CodeGen/SelectionDAG/SelectionDAGBuilder.cpp b/llvm/lib/CodeGen/SelectionDAG/SelectionDAGBuilder.cpp index 319465865fb1d18c11ac437d71a36771afd6cf66..0db484a5e06bcdcc254c94756c31131beefa9398 100644 --- a/llvm/lib/CodeGen/SelectionDAG/SelectionDAGBuilder.cpp +++ b/llvm/lib/CodeGen/SelectionDAG/SelectionDAGBuilder.cpp @@ -80,6 +80,7 @@ #include "llvm/IR/IntrinsicsAMDGPU.h" #include "llvm/IR/IntrinsicsWebAssembly.h" #include "llvm/IR/LLVMContext.h" +#include "llvm/IR/MemoryModelRelaxationAnnotations.h" #include "llvm/IR/Metadata.h" #include "llvm/IR/Module.h" #include "llvm/IR/Operator.h" @@ -1326,7 +1327,8 @@ void SelectionDAGBuilder::visit(const Instruction &I) { bool NodeInserted = false; std::unique_ptr InsertedListener; MDNode *PCSectionsMD = I.getMetadata(LLVMContext::MD_pcsections); - if (PCSectionsMD) { + MDNode *MMRA = I.getMetadata(LLVMContext::MD_mmra); + if (PCSectionsMD || MMRA) { InsertedListener = std::make_unique( DAG, [&](SDNode *) { NodeInserted = true; }); } @@ -1338,14 +1340,17 @@ void SelectionDAGBuilder::visit(const Instruction &I) { CopyToExportRegsIfNeeded(&I); // Handle metadata. - if (PCSectionsMD) { + if (PCSectionsMD || MMRA) { auto It = NodeMap.find(&I); if (It != NodeMap.end()) { - DAG.addPCSections(It->second.getNode(), PCSectionsMD); + if (PCSectionsMD) + DAG.addPCSections(It->second.getNode(), PCSectionsMD); + if (MMRA) + DAG.addMMRAMetadata(It->second.getNode(), MMRA); } else if (NodeInserted) { // This should not happen; if it does, don't let it go unnoticed so we can // fix it. Relevant visit*() function is probably missing a setValue(). - errs() << "warning: loosing !pcsections metadata [" + errs() << "warning: loosing !pcsections and/or !mmra metadata [" << I.getModule()->getName() << "]\n"; LLVM_DEBUG(I.dump()); assert(false); @@ -5294,9 +5299,9 @@ void SelectionDAGBuilder::visitTargetIntrinsic(const CallInst &I, Result = DAG.getAssertAlign(getCurSDLoc(), Result, Alignment.valueOrOne()); } - - setValue(&I, Result); } + + setValue(&I, Result); } /// GetSignificand - Get the significand and build it into a floating-point diff --git a/llvm/lib/CodeGen/SelectionDAG/SelectionDAGDumper.cpp b/llvm/lib/CodeGen/SelectionDAG/SelectionDAGDumper.cpp index 6691aa41face39aa6c0c24fa4c392dfedb3b2a20..4ad4a938ca97f2f3c37cf18f6a3e0e3124181a9d 100644 --- a/llvm/lib/CodeGen/SelectionDAG/SelectionDAGDumper.cpp +++ b/llvm/lib/CodeGen/SelectionDAG/SelectionDAGDumper.cpp @@ -299,6 +299,7 @@ std::string SDNode::getOperationName(const SelectionDAG *G) const { case ISD::SETCCCARRY: return "setcccarry"; case ISD::STRICT_FSETCC: return "strict_fsetcc"; case ISD::STRICT_FSETCCS: return "strict_fsetccs"; + case ISD::FPTRUNC_ROUND: return "fptrunc_round"; case ISD::SELECT: return "select"; case ISD::VSELECT: return "vselect"; case ISD::SELECT_CC: return "select_cc"; @@ -905,6 +906,13 @@ void SDNode::print_details(raw_ostream &OS, const SelectionDAG *G) const { MD->printAsOperand(OS, G->getMachineFunction().getFunction().getParent()); OS << ']'; } + + if (MDNode *MMRA = G ? G->getMMRAMetadata(this) : nullptr) { + OS << " [mmra "; + MMRA->printAsOperand(OS, + G->getMachineFunction().getFunction().getParent()); + OS << ']'; + } } } diff --git a/llvm/lib/CodeGen/SelectionDAG/SelectionDAGISel.cpp b/llvm/lib/CodeGen/SelectionDAG/SelectionDAGISel.cpp index d629c36bc792e32835718304e495ed1b1ad07920..b5694c955b8c8fbf730efde8111537c4145637b7 100644 --- a/llvm/lib/CodeGen/SelectionDAG/SelectionDAGISel.cpp +++ b/llvm/lib/CodeGen/SelectionDAG/SelectionDAGISel.cpp @@ -1059,6 +1059,8 @@ public: SDNode *CurNode = &*ISelPosition; if (MDNode *MD = DAG.getPCSections(CurNode)) DAG.addPCSections(N, MD); + if (MDNode *MMRA = DAG.getMMRAMetadata(CurNode)) + DAG.addMMRAMetadata(N, MMRA); } }; diff --git a/llvm/lib/CodeGen/StackSlotColoring.cpp b/llvm/lib/CodeGen/StackSlotColoring.cpp index 6d3fc740b292a8c26f27a6aafaabdd1e5332029c..9fdc8a338b52a5d2c08a54ede68f17090ae89506 100644 --- a/llvm/lib/CodeGen/StackSlotColoring.cpp +++ b/llvm/lib/CodeGen/StackSlotColoring.cpp @@ -486,7 +486,8 @@ bool StackSlotColoring::RemoveDeadStores(MachineBasicBlock* MBB) { ++NumDead; changed = true; - if (NextMI->findRegisterUseOperandIdx(LoadReg, true, nullptr) != -1) { + if (NextMI->findRegisterUseOperandIdx(LoadReg, /*TRI=*/nullptr, true) != + -1) { ++NumDead; toErase.push_back(&*ProbableLoadMI); } diff --git a/llvm/lib/CodeGen/TargetInstrInfo.cpp b/llvm/lib/CodeGen/TargetInstrInfo.cpp index 14b2e4268eb0fbf0e295a2e75555486311acea38..e01e7b3888915b72b26d00444d5c11980cd52b98 100644 --- a/llvm/lib/CodeGen/TargetInstrInfo.cpp +++ b/llvm/lib/CodeGen/TargetInstrInfo.cpp @@ -1055,12 +1055,34 @@ static std::pair mustSwapOperands(unsigned Pattern) { } } +void TargetInstrInfo::getReassociateOperandIndices( + const MachineInstr &Root, unsigned Pattern, + std::array &OperandIndices) const { + switch (Pattern) { + case MachineCombinerPattern::REASSOC_AX_BY: + OperandIndices = {1, 1, 1, 2, 2}; + break; + case MachineCombinerPattern::REASSOC_AX_YB: + OperandIndices = {2, 1, 2, 2, 1}; + break; + case MachineCombinerPattern::REASSOC_XA_BY: + OperandIndices = {1, 2, 1, 1, 2}; + break; + case MachineCombinerPattern::REASSOC_XA_YB: + OperandIndices = {2, 2, 2, 1, 1}; + break; + default: + llvm_unreachable("unexpected MachineCombinerPattern"); + } +} + /// Attempt the reassociation transformation to reduce critical path length. /// See the above comments before getMachineCombinerPatterns(). void TargetInstrInfo::reassociateOps( MachineInstr &Root, MachineInstr &Prev, unsigned Pattern, SmallVectorImpl &InsInstrs, SmallVectorImpl &DelInstrs, + ArrayRef OperandIndices, DenseMap &InstrIdxForVirtReg) const { MachineFunction *MF = Root.getMF(); MachineRegisterInfo &MRI = MF->getRegInfo(); @@ -1068,29 +1090,10 @@ void TargetInstrInfo::reassociateOps( const TargetRegisterInfo *TRI = MF->getSubtarget().getRegisterInfo(); const TargetRegisterClass *RC = Root.getRegClassConstraint(0, TII, TRI); - // This array encodes the operand index for each parameter because the - // operands may be commuted. Each row corresponds to a pattern value, - // and each column specifies the index of A, B, X, Y. - unsigned OpIdx[4][4] = { - { 1, 1, 2, 2 }, - { 1, 2, 2, 1 }, - { 2, 1, 1, 2 }, - { 2, 2, 1, 1 } - }; - - int Row; - switch (Pattern) { - case MachineCombinerPattern::REASSOC_AX_BY: Row = 0; break; - case MachineCombinerPattern::REASSOC_AX_YB: Row = 1; break; - case MachineCombinerPattern::REASSOC_XA_BY: Row = 2; break; - case MachineCombinerPattern::REASSOC_XA_YB: Row = 3; break; - default: llvm_unreachable("unexpected MachineCombinerPattern"); - } - - MachineOperand &OpA = Prev.getOperand(OpIdx[Row][0]); - MachineOperand &OpB = Root.getOperand(OpIdx[Row][1]); - MachineOperand &OpX = Prev.getOperand(OpIdx[Row][2]); - MachineOperand &OpY = Root.getOperand(OpIdx[Row][3]); + MachineOperand &OpA = Prev.getOperand(OperandIndices[1]); + MachineOperand &OpB = Root.getOperand(OperandIndices[2]); + MachineOperand &OpX = Prev.getOperand(OperandIndices[3]); + MachineOperand &OpY = Root.getOperand(OperandIndices[4]); MachineOperand &OpC = Root.getOperand(0); Register RegA = OpA.getReg(); @@ -1129,11 +1132,62 @@ void TargetInstrInfo::reassociateOps( std::swap(KillX, KillY); } + unsigned PrevFirstOpIdx, PrevSecondOpIdx; + unsigned RootFirstOpIdx, RootSecondOpIdx; + switch (Pattern) { + case MachineCombinerPattern::REASSOC_AX_BY: + PrevFirstOpIdx = OperandIndices[1]; + PrevSecondOpIdx = OperandIndices[3]; + RootFirstOpIdx = OperandIndices[2]; + RootSecondOpIdx = OperandIndices[4]; + break; + case MachineCombinerPattern::REASSOC_AX_YB: + PrevFirstOpIdx = OperandIndices[1]; + PrevSecondOpIdx = OperandIndices[3]; + RootFirstOpIdx = OperandIndices[4]; + RootSecondOpIdx = OperandIndices[2]; + break; + case MachineCombinerPattern::REASSOC_XA_BY: + PrevFirstOpIdx = OperandIndices[3]; + PrevSecondOpIdx = OperandIndices[1]; + RootFirstOpIdx = OperandIndices[2]; + RootSecondOpIdx = OperandIndices[4]; + break; + case MachineCombinerPattern::REASSOC_XA_YB: + PrevFirstOpIdx = OperandIndices[3]; + PrevSecondOpIdx = OperandIndices[1]; + RootFirstOpIdx = OperandIndices[4]; + RootSecondOpIdx = OperandIndices[2]; + break; + default: + llvm_unreachable("unexpected MachineCombinerPattern"); + } + + // Basically BuildMI but doesn't add implicit operands by default. + auto buildMINoImplicit = [](MachineFunction &MF, const MIMetadata &MIMD, + const MCInstrDesc &MCID, Register DestReg) { + return MachineInstrBuilder( + MF, MF.CreateMachineInstr(MCID, MIMD.getDL(), /*NoImpl=*/true)) + .setPCSections(MIMD.getPCSections()) + .addReg(DestReg, RegState::Define); + }; + // Create new instructions for insertion. MachineInstrBuilder MIB1 = - BuildMI(*MF, MIMetadata(Prev), TII->get(NewPrevOpc), NewVR) - .addReg(RegX, getKillRegState(KillX)) - .addReg(RegY, getKillRegState(KillY)); + buildMINoImplicit(*MF, MIMetadata(Prev), TII->get(NewPrevOpc), NewVR); + for (const auto &MO : Prev.explicit_operands()) { + unsigned Idx = MO.getOperandNo(); + // Skip the result operand we'd already added. + if (Idx == 0) + continue; + if (Idx == PrevFirstOpIdx) + MIB1.addReg(RegX, getKillRegState(KillX)); + else if (Idx == PrevSecondOpIdx) + MIB1.addReg(RegY, getKillRegState(KillY)); + else + MIB1.add(MO); + } + MIB1.copyImplicitOps(Prev); if (SwapRootOperands) { std::swap(RegA, NewVR); @@ -1141,9 +1195,20 @@ void TargetInstrInfo::reassociateOps( } MachineInstrBuilder MIB2 = - BuildMI(*MF, MIMetadata(Root), TII->get(NewRootOpc), RegC) - .addReg(RegA, getKillRegState(KillA)) - .addReg(NewVR, getKillRegState(KillNewVR)); + buildMINoImplicit(*MF, MIMetadata(Root), TII->get(NewRootOpc), RegC); + for (const auto &MO : Root.explicit_operands()) { + unsigned Idx = MO.getOperandNo(); + // Skip the result operand. + if (Idx == 0) + continue; + if (Idx == RootFirstOpIdx) + MIB2 = MIB2.addReg(RegA, getKillRegState(KillA)); + else if (Idx == RootSecondOpIdx) + MIB2 = MIB2.addReg(NewVR, getKillRegState(KillNewVR)); + else + MIB2 = MIB2.add(MO); + } + MIB2.copyImplicitOps(Root); // Propagate FP flags from the original instructions. // But clear poison-generating flags because those may not be valid now. @@ -1187,25 +1252,17 @@ void TargetInstrInfo::genAlternativeCodeSequence( MachineRegisterInfo &MRI = Root.getMF()->getRegInfo(); // Select the previous instruction in the sequence based on the input pattern. - MachineInstr *Prev = nullptr; - switch (Pattern) { - case MachineCombinerPattern::REASSOC_AX_BY: - case MachineCombinerPattern::REASSOC_XA_BY: - Prev = MRI.getUniqueVRegDef(Root.getOperand(1).getReg()); - break; - case MachineCombinerPattern::REASSOC_AX_YB: - case MachineCombinerPattern::REASSOC_XA_YB: - Prev = MRI.getUniqueVRegDef(Root.getOperand(2).getReg()); - break; - default: - llvm_unreachable("Unknown pattern for machine combiner"); - } + std::array OperandIndices; + getReassociateOperandIndices(Root, Pattern, OperandIndices); + MachineInstr *Prev = + MRI.getUniqueVRegDef(Root.getOperand(OperandIndices[0]).getReg()); // Don't reassociate if Prev and Root are in different blocks. if (Prev->getParent() != Root.getParent()) return; - reassociateOps(Root, *Prev, Pattern, InsInstrs, DelInstrs, InstIdxForVirtReg); + reassociateOps(Root, *Prev, Pattern, InsInstrs, DelInstrs, OperandIndices, + InstIdxForVirtReg); } MachineTraceStrategy TargetInstrInfo::getMachineCombinerTraceStrategy() const { diff --git a/llvm/lib/CodeGen/TwoAddressInstructionPass.cpp b/llvm/lib/CodeGen/TwoAddressInstructionPass.cpp index ebacbc420f8580a8189a083fc8fcdb206f154075..b9b2841e7c9ee40a54b5b902014a0a6c9694c8a1 100644 --- a/llvm/lib/CodeGen/TwoAddressInstructionPass.cpp +++ b/llvm/lib/CodeGen/TwoAddressInstructionPass.cpp @@ -339,7 +339,7 @@ bool TwoAddressInstructionPass::isPlainlyKilled(const MachineInstr *MI, }); } - return MI->killsRegister(Reg); + return MI->killsRegister(Reg, /*TRI=*/nullptr); } /// Test if the register used by the given operand is killed by the operand's @@ -1355,8 +1355,10 @@ tryInstructionTransform(MachineBasicBlock::iterator &mi, << "2addr: NEW INST: " << *NewMIs[1]); // Transform the instruction, now that it no longer has a load. - unsigned NewDstIdx = NewMIs[1]->findRegisterDefOperandIdx(regA); - unsigned NewSrcIdx = NewMIs[1]->findRegisterUseOperandIdx(regB); + unsigned NewDstIdx = + NewMIs[1]->findRegisterDefOperandIdx(regA, /*TRI=*/nullptr); + unsigned NewSrcIdx = + NewMIs[1]->findRegisterUseOperandIdx(regB, /*TRI=*/nullptr); MachineBasicBlock::iterator NewMI = NewMIs[1]; bool TransformResult = tryInstructionTransform(NewMI, mi, NewSrcIdx, NewDstIdx, Dist, true); @@ -1371,19 +1373,22 @@ tryInstructionTransform(MachineBasicBlock::iterator &mi, if (MO.isReg() && MO.getReg().isVirtual()) { if (MO.isUse()) { if (MO.isKill()) { - if (NewMIs[0]->killsRegister(MO.getReg())) + if (NewMIs[0]->killsRegister(MO.getReg(), /*TRI=*/nullptr)) LV->replaceKillInstruction(MO.getReg(), MI, *NewMIs[0]); else { - assert(NewMIs[1]->killsRegister(MO.getReg()) && + assert(NewMIs[1]->killsRegister(MO.getReg(), + /*TRI=*/nullptr) && "Kill missing after load unfold!"); LV->replaceKillInstruction(MO.getReg(), MI, *NewMIs[1]); } } } else if (LV->removeVirtualRegisterDead(MO.getReg(), MI)) { - if (NewMIs[1]->registerDefIsDead(MO.getReg())) + if (NewMIs[1]->registerDefIsDead(MO.getReg(), + /*TRI=*/nullptr)) LV->addVirtualRegisterDead(MO.getReg(), *NewMIs[1]); else { - assert(NewMIs[0]->registerDefIsDead(MO.getReg()) && + assert(NewMIs[0]->registerDefIsDead(MO.getReg(), + /*TRI=*/nullptr) && "Dead flag missing after load unfold!"); LV->addVirtualRegisterDead(MO.getReg(), *NewMIs[0]); } diff --git a/llvm/lib/DebugInfo/DWARF/DWARFUnit.cpp b/llvm/lib/DebugInfo/DWARF/DWARFUnit.cpp index 9f455fa7e96a7efb050a3eb3b56050c38f73e4fb..bdd04b00f557bd5d43c5000af0be528eac0baca0 100644 --- a/llvm/lib/DebugInfo/DWARF/DWARFUnit.cpp +++ b/llvm/lib/DebugInfo/DWARF/DWARFUnit.cpp @@ -98,8 +98,12 @@ void DWARFUnitVector::addUnitsImpl( if (!IndexEntry) IndexEntry = Index.getFromOffset(Header.getOffset()); } - if (IndexEntry && !Header.applyIndexEntry(IndexEntry)) - return nullptr; + if (IndexEntry) { + if (Error ApplicationErr = Header.applyIndexEntry(IndexEntry)) { + Context.getWarningHandler()(std::move(ApplicationErr)); + return nullptr; + } + } std::unique_ptr U; if (Header.isTypeUnit()) U = std::make_unique(Context, InfoSection, Header, DA, @@ -334,21 +338,40 @@ Error DWARFUnitHeader::extract(DWARFContext &Context, return Error::success(); } -bool DWARFUnitHeader::applyIndexEntry(const DWARFUnitIndex::Entry *Entry) { +Error DWARFUnitHeader::applyIndexEntry(const DWARFUnitIndex::Entry *Entry) { assert(Entry); assert(!IndexEntry); IndexEntry = Entry; if (AbbrOffset) - return false; + return createStringError(errc::invalid_argument, + "DWARF package unit at offset 0x%8.8" PRIx64 + " has a non-zero abbreviation offset", + Offset); + auto *UnitContrib = IndexEntry->getContribution(); - if (!UnitContrib || - UnitContrib->getLength() != (getLength() + getUnitLengthFieldByteSize())) - return false; + if (!UnitContrib) + return createStringError(errc::invalid_argument, + "DWARF package unit at offset 0x%8.8" PRIx64 + " has no contribution index", + Offset); + + uint64_t IndexLength = getLength() + getUnitLengthFieldByteSize(); + if (UnitContrib->getLength() != IndexLength) + return createStringError(errc::invalid_argument, + "DWARF package unit at offset 0x%8.8" PRIx64 + " has an inconsistent index (expected: %" PRIu64 + ", actual: %" PRIu64 ")", + Offset, UnitContrib->getLength(), IndexLength); + auto *AbbrEntry = IndexEntry->getContribution(DW_SECT_ABBREV); if (!AbbrEntry) - return false; + return createStringError(errc::invalid_argument, + "DWARF package unit at offset 0x%8.8" PRIx64 + " missing abbreviation column", + Offset); + AbbrOffset = AbbrEntry->getOffset(); - return true; + return Error::success(); } Error DWARFUnit::extractRangeList(uint64_t RangeListOffset, diff --git a/llvm/lib/ExecutionEngine/Orc/ExecutorProcessControl.cpp b/llvm/lib/ExecutionEngine/Orc/ExecutorProcessControl.cpp index efafca949e61efbccad4685bd45bc3f105d0fa4c..0df7c4f25eb82c7cca9a6ca3cd8bdab09925fe2d 100644 --- a/llvm/lib/ExecutionEngine/Orc/ExecutorProcessControl.cpp +++ b/llvm/lib/ExecutionEngine/Orc/ExecutorProcessControl.cpp @@ -61,13 +61,8 @@ SelfExecutorProcessControl::Create( if (!SSP) SSP = std::make_shared(); - if (!D) { -#if LLVM_ENABLE_THREADS - D = std::make_unique(); -#else + if (!D) D = std::make_unique(); -#endif - } auto PageSize = sys::Process::getPageSize(); if (!PageSize) diff --git a/llvm/lib/ExecutionEngine/Orc/LLJIT.cpp b/llvm/lib/ExecutionEngine/Orc/LLJIT.cpp index 79adda5b7bc0341b6cdd5458e3b42457c57c257b..568b2ececaa09a6648ab879bc4da4e4ca17f7710 100644 --- a/llvm/lib/ExecutionEngine/Orc/LLJIT.cpp +++ b/llvm/lib/ExecutionEngine/Orc/LLJIT.cpp @@ -667,6 +667,40 @@ Error LLJITBuilderState::prepareForConstruction() { return JTMBOrErr.takeError(); } + if ((ES || EPC) && NumCompileThreads) + return make_error( + "NumCompileThreads cannot be used with a custom ExecutionSession or " + "ExecutorProcessControl", + inconvertibleErrorCode()); + +#if !LLVM_ENABLE_THREADS + if (NumCompileThreads) + return make_error( + "LLJIT num-compile-threads is " + Twine(NumCompileThreads) + + " but LLVM was compiled with LLVM_ENABLE_THREADS=Off", + inconvertibleErrorCode()); +#endif // !LLVM_ENABLE_THREADS + + // Only used in debug builds. + [[maybe_unused]] bool ConcurrentCompilationSettingDefaulted = + !SupportConcurrentCompilation; + + if (!SupportConcurrentCompilation) { +#if LLVM_ENABLE_THREADS + SupportConcurrentCompilation = NumCompileThreads || ES || EPC; +#else + SupportConcurrentCompilation = false; +#endif // LLVM_ENABLE_THREADS + } else { +#if !LLVM_ENABLE_THREADS + if (*SupportConcurrentCompilation) + return make_error( + "LLJIT concurrent compilation support requested, but LLVM was built " + "with LLVM_ENABLE_THREADS=Off", + inconvertibleErrorCode()); +#endif // !LLVM_ENABLE_THREADS + } + LLVM_DEBUG({ dbgs() << " JITTargetMachineBuilder is " << JITTargetMachineBuilderPrinter(*JTMB, " ") @@ -684,11 +718,13 @@ Error LLJITBuilderState::prepareForConstruction() { << (CreateCompileFunction ? "Yes" : "No") << "\n" << " Custom platform-setup function: " << (SetUpPlatform ? "Yes" : "No") << "\n" - << " Number of compile threads: " << NumCompileThreads; - if (!NumCompileThreads) - dbgs() << " (code will be compiled on the execution thread)\n"; + << " Support concurrent compilation: " + << (*SupportConcurrentCompilation ? "Yes" : "No"); + if (ConcurrentCompilationSettingDefaulted) + dbgs() << " (defaulted based on ES / EPC / NumCompileThreads)\n"; else dbgs() << "\n"; + dbgs() << " Number of compile threads: " << NumCompileThreads << "\n"; }); // Create DL if not specified. @@ -705,7 +741,19 @@ Error LLJITBuilderState::prepareForConstruction() { dbgs() << "ExecutorProcessControl not specified, " "Creating SelfExecutorProcessControl instance\n"; }); - if (auto EPCOrErr = SelfExecutorProcessControl::Create()) + + std::unique_ptr D = nullptr; +#if LLVM_ENABLE_THREADS + if (*SupportConcurrentCompilation) { + std::optional NumThreads = std ::nullopt; + if (NumCompileThreads) + NumThreads = NumCompileThreads; + D = std::make_unique(NumThreads); + } else + D = std::make_unique(); +#endif // LLVM_ENABLE_THREADS + if (auto EPCOrErr = + SelfExecutorProcessControl::Create(nullptr, std::move(D), nullptr)) EPC = std::move(*EPCOrErr); else return EPCOrErr.takeError(); @@ -790,8 +838,6 @@ Error LLJITBuilderState::prepareForConstruction() { } LLJIT::~LLJIT() { - if (CompileThreads) - CompileThreads->wait(); if (auto Err = ES->endSession()) ES->reportError(std::move(Err)); } @@ -916,9 +962,8 @@ LLJIT::createCompileFunction(LLJITBuilderState &S, if (S.CreateCompileFunction) return S.CreateCompileFunction(std::move(JTMB)); - // Otherwise default to creating a SimpleCompiler, or ConcurrentIRCompiler, - // depending on the number of threads requested. - if (S.NumCompileThreads > 0) + // If using a custom EPC then use a ConcurrentIRCompiler by default. + if (*S.SupportConcurrentCompilation) return std::make_unique(std::move(JTMB)); auto TM = JTMB.createTargetMachine(); @@ -970,21 +1015,8 @@ LLJIT::LLJIT(LLJITBuilderState &S, Error &Err) std::make_unique(*ES, *TransformLayer); } - if (S.NumCompileThreads > 0) { + if (*S.SupportConcurrentCompilation) InitHelperTransformLayer->setCloneToNewContextOnEmit(true); - CompileThreads = std::make_unique( - hardware_concurrency(S.NumCompileThreads)); - ES->setDispatchTask([this](std::unique_ptr T) { - // FIXME: We should be able to use move-capture here, but ThreadPool's - // AsyncTaskTys are std::functions rather than unique_functions - // (because MSVC's std::packaged_tasks don't support move-only types). - // Fix this when all the above gets sorted out. - CompileThreads->async([UnownedT = T.release()]() mutable { - std::unique_ptr T(UnownedT); - T->run(); - }); - }); - } if (S.SetupProcessSymbolsJITDylib) { if (auto ProcSymsJD = S.SetupProcessSymbolsJITDylib(*this)) { @@ -1240,7 +1272,7 @@ LLLazyJIT::LLLazyJIT(LLLazyJITBuilderState &S, Error &Err) : LLJIT(S, Err) { CODLayer = std::make_unique( *ES, *InitHelperTransformLayer, *LCTMgr, std::move(ISMBuilder)); - if (S.NumCompileThreads > 0) + if (*S.SupportConcurrentCompilation) CODLayer->setCloneToNewContextOnEmit(true); } diff --git a/llvm/lib/ExecutionEngine/Orc/MemoryMapper.cpp b/llvm/lib/ExecutionEngine/Orc/MemoryMapper.cpp index 2c87b344083edbdffe681c8b6d67a2332549dd7b..bba3329e8cc26929953d04c56998f985913609ab 100644 --- a/llvm/lib/ExecutionEngine/Orc/MemoryMapper.cpp +++ b/llvm/lib/ExecutionEngine/Orc/MemoryMapper.cpp @@ -16,6 +16,10 @@ #if defined(LLVM_ON_UNIX) && !defined(__ANDROID__) #include #include +#if defined(__MVS__) +#include "llvm/Support/BLAKE3.h" +#include +#endif #include #elif defined(_WIN32) #include @@ -239,6 +243,24 @@ void SharedMemoryMapper::reserve(size_t NumBytes, #if defined(LLVM_ON_UNIX) +#if defined(__MVS__) + ArrayRef Data( + reinterpret_cast(SharedMemoryName.c_str()), + SharedMemoryName.size()); + auto HashedName = BLAKE3::hash(Data); + key_t Key = *reinterpret_cast(HashedName.data()); + int SharedMemoryId = + shmget(Key, NumBytes, IPC_CREAT | __IPC_SHAREAS | 0700); + if (SharedMemoryId < 0) { + return OnReserved(errorCodeToError( + std::error_code(errno, std::generic_category()))); + } + LocalAddr = shmat(SharedMemoryId, nullptr, 0); + if (LocalAddr == reinterpret_cast(-1)) { + return OnReserved(errorCodeToError( + std::error_code(errno, std::generic_category()))); + } +#else int SharedMemoryFile = shm_open(SharedMemoryName.c_str(), O_RDWR, 0700); if (SharedMemoryFile < 0) { return OnReserved(errorCodeToError(errnoAsErrorCode())); @@ -254,6 +276,7 @@ void SharedMemoryMapper::reserve(size_t NumBytes, } close(SharedMemoryFile); +#endif #elif defined(_WIN32) @@ -373,8 +396,13 @@ void SharedMemoryMapper::release(ArrayRef Bases, #if defined(LLVM_ON_UNIX) +#if defined(__MVS__) + if (shmdt(Reservations[Base].LocalAddr) < 0) + Err = joinErrors(std::move(Err), errorCodeToError(errnoAsErrorCode())); +#else if (munmap(Reservations[Base].LocalAddr, Reservations[Base].Size) != 0) Err = joinErrors(std::move(Err), errorCodeToError(errnoAsErrorCode())); +#endif #elif defined(_WIN32) @@ -415,7 +443,11 @@ SharedMemoryMapper::~SharedMemoryMapper() { #if defined(LLVM_ON_UNIX) && !defined(__ANDROID__) +#if defined(__MVS__) + shmdt(R.second.LocalAddr); +#else munmap(R.second.LocalAddr, R.second.Size); +#endif #elif defined(_WIN32) diff --git a/llvm/lib/ExecutionEngine/Orc/TargetProcess/ExecutorSharedMemoryMapperService.cpp b/llvm/lib/ExecutionEngine/Orc/TargetProcess/ExecutorSharedMemoryMapperService.cpp index 6614beec760fb327c38f1a8d4a5149cb47b751a9..f5118c0f2bfa43c916971c4c5843b27207cc85dd 100644 --- a/llvm/lib/ExecutionEngine/Orc/TargetProcess/ExecutorSharedMemoryMapperService.cpp +++ b/llvm/lib/ExecutionEngine/Orc/TargetProcess/ExecutorSharedMemoryMapperService.cpp @@ -18,6 +18,10 @@ #include #include #include +#if defined(__MVS__) +#include "llvm/Support/BLAKE3.h" +#include +#endif #include #endif @@ -59,6 +63,21 @@ ExecutorSharedMemoryMapperService::reserve(uint64_t Size) { SharedMemoryName = SharedMemoryNameStream.str(); } +#if defined(__MVS__) + ArrayRef Data( + reinterpret_cast(SharedMemoryName.c_str()), + SharedMemoryName.size()); + auto HashedName = BLAKE3::hash(Data); + key_t Key = *reinterpret_cast(HashedName.data()); + int SharedMemoryId = + shmget(Key, Size, IPC_CREAT | IPC_EXCL | __IPC_SHAREAS | 0700); + if (SharedMemoryId < 0) + return errorCodeToError(errnoAsErrorCode()); + + void *Addr = shmat(SharedMemoryId, nullptr, 0); + if (Addr == reinterpret_cast(-1)) + return errorCodeToError(errnoAsErrorCode()); +#else int SharedMemoryFile = shm_open(SharedMemoryName.c_str(), O_RDWR | O_CREAT | O_EXCL, 0700); if (SharedMemoryFile < 0) @@ -73,6 +92,7 @@ ExecutorSharedMemoryMapperService::reserve(uint64_t Size) { return errorCodeToError(errnoAsErrorCode()); close(SharedMemoryFile); +#endif #elif defined(_WIN32) @@ -131,6 +151,9 @@ Expected ExecutorSharedMemoryMapperService::initialize( #if defined(LLVM_ON_UNIX) +#if defined(__MVS__) + // TODO Is it possible to change the protection level? +#else int NativeProt = 0; if ((Segment.RAG.Prot & MemProt::Read) == MemProt::Read) NativeProt |= PROT_READ; @@ -141,6 +164,7 @@ Expected ExecutorSharedMemoryMapperService::initialize( if (mprotect(Segment.Addr.toPtr(), Segment.Size, NativeProt)) return errorCodeToError(errnoAsErrorCode()); +#endif #elif defined(_WIN32) @@ -239,8 +263,15 @@ Error ExecutorSharedMemoryMapperService::release( #if defined(LLVM_ON_UNIX) +#if defined(__MVS__) + (void)Size; + + if (shmdt(Base.toPtr()) < 0) + Err = joinErrors(std::move(Err), errorCodeToError(errnoAsErrorCode())); +#else if (munmap(Base.toPtr(), Size) != 0) Err = joinErrors(std::move(Err), errorCodeToError(errnoAsErrorCode())); +#endif #elif defined(_WIN32) (void)Size; diff --git a/llvm/lib/ExecutionEngine/Orc/TaskDispatch.cpp b/llvm/lib/ExecutionEngine/Orc/TaskDispatch.cpp index 11a99986f2ee92e0bb35f6cf663d4bf28b034126..4ac2a42091858e6ca4a85e4a3698e82d91683315 100644 --- a/llvm/lib/ExecutionEngine/Orc/TaskDispatch.cpp +++ b/llvm/lib/ExecutionEngine/Orc/TaskDispatch.cpp @@ -7,6 +7,7 @@ //===----------------------------------------------------------------------===// #include "llvm/ExecutionEngine/Orc/TaskDispatch.h" +#include "llvm/ExecutionEngine/Orc/Core.h" namespace llvm { namespace orc { @@ -24,16 +25,52 @@ void InPlaceTaskDispatcher::shutdown() {} #if LLVM_ENABLE_THREADS void DynamicThreadPoolTaskDispatcher::dispatch(std::unique_ptr T) { + bool IsMaterializationTask = isa(*T); + { std::lock_guard Lock(DispatchMutex); + + if (IsMaterializationTask) { + + // If this is a materialization task and there are too many running + // already then queue this one up and return early. + if (MaxMaterializationThreads && + NumMaterializationThreads == *MaxMaterializationThreads) { + MaterializationTaskQueue.push_back(std::move(T)); + return; + } + + // Otherwise record that we have a materialization task running. + ++NumMaterializationThreads; + } + ++Outstanding; } - std::thread([this, T = std::move(T)]() mutable { - T->run(); - std::lock_guard Lock(DispatchMutex); - --Outstanding; - OutstandingCV.notify_all(); + std::thread([this, T = std::move(T), IsMaterializationTask]() mutable { + while (true) { + + // Run the task. + T->run(); + + std::lock_guard Lock(DispatchMutex); + if (!MaterializationTaskQueue.empty()) { + // If there are any materialization tasks running then steal that work. + T = std::move(MaterializationTaskQueue.front()); + MaterializationTaskQueue.pop_front(); + if (!IsMaterializationTask) { + ++NumMaterializationThreads; + IsMaterializationTask = true; + } + } else { + // Otherwise decrement work counters. + if (IsMaterializationTask) + --NumMaterializationThreads; + --Outstanding; + OutstandingCV.notify_all(); + return; + } + } }).detach(); } diff --git a/llvm/lib/Frontend/OpenMP/OMP.cpp b/llvm/lib/Frontend/OpenMP/OMP.cpp index 1ffc38b63b0a52a518aae98837d4c03acc9a55d2..c1556ff3c74d72c2e9731dd6281a32697b03e161 100644 --- a/llvm/lib/Frontend/OpenMP/OMP.cpp +++ b/llvm/lib/Frontend/OpenMP/OMP.cpp @@ -25,6 +25,54 @@ using namespace llvm::omp; #define GEN_DIRECTIVES_IMPL #include "llvm/Frontend/OpenMP/OMP.inc" +static iterator_range::iterator> +getFirstCompositeRange(iterator_range::iterator> Leafs) { + // OpenMP Spec 5.2: [17.3, 8-9] + // If directive-name-A and directive-name-B both correspond to loop- + // associated constructs then directive-name is a composite construct + // otherwise directive-name is a combined construct. + // + // In the list of leaf constructs, find the first loop-associated construct, + // this is the beginning of the returned range. Then, starting from the + // immediately following leaf construct, find the first sequence of adjacent + // loop-associated constructs. The last of those is the last one of the + // range, that is, the end of the range is one past that element. + // If such a sequence of adjacent loop-associated directives does not exist, + // return an empty range. + // + // The end of the returned range (including empty range) is intended to be + // a point from which the search for the next range could resume. + // + // Consequently, this function can't return a range with a single leaf + // construct in it. + + auto firstLoopAssociated = + [](iterator_range::iterator> List) { + for (auto It = List.begin(), End = List.end(); It != End; ++It) { + if (getDirectiveAssociation(*It) == Association::Loop) + return It; + } + return List.end(); + }; + + auto Empty = llvm::make_range(Leafs.end(), Leafs.end()); + + auto Begin = firstLoopAssociated(Leafs); + if (Begin == Leafs.end()) + return Empty; + + auto End = + firstLoopAssociated(llvm::make_range(std::next(Begin), Leafs.end())); + if (End == Leafs.end()) + return Empty; + + for (; End != Leafs.end(); ++End) { + if (getDirectiveAssociation(*End) != Association::Loop) + break; + } + return llvm::make_range(Begin, End); +} + namespace llvm::omp { ArrayRef getLeafConstructs(Directive D) { auto Idx = static_cast(D); @@ -34,6 +82,44 @@ ArrayRef getLeafConstructs(Directive D) { return ArrayRef(&Row[2], static_cast(Row[1])); } +ArrayRef getLeafConstructsOrSelf(Directive D) { + if (auto Leafs = getLeafConstructs(D); !Leafs.empty()) + return Leafs; + auto Idx = static_cast(D); + assert(Idx < Directive_enumSize && "Invalid directive"); + const auto *Row = LeafConstructTable[LeafConstructTableOrdering[Idx]]; + // The first entry in the row is the directive itself. + return ArrayRef(&Row[0], &Row[0] + 1); +} + +ArrayRef +getLeafOrCompositeConstructs(Directive D, SmallVectorImpl &Output) { + using ArrayTy = ArrayRef; + using IteratorTy = ArrayTy::iterator; + ArrayRef Leafs = getLeafConstructsOrSelf(D); + + IteratorTy Iter = Leafs.begin(); + do { + auto Range = getFirstCompositeRange(llvm::make_range(Iter, Leafs.end())); + // All directives before the range are leaf constructs. + for (; Iter != Range.begin(); ++Iter) + Output.push_back(*Iter); + if (!Range.empty()) { + Directive Comp = + getCompoundConstruct(ArrayTy(Range.begin(), Range.end())); + assert(Comp != OMPD_unknown); + Output.push_back(Comp); + Iter = Range.end(); + // As of now, a composite construct must contain all constituent leaf + // constructs from some point until the end of all constituent leaf + // constructs. + assert(Iter == Leafs.end() && "Malformed directive"); + } + } while (Iter != Leafs.end()); + + return Output; +} + Directive getCompoundConstruct(ArrayRef Parts) { if (Parts.empty()) return OMPD_unknown; @@ -88,20 +174,11 @@ Directive getCompoundConstruct(ArrayRef Parts) { bool isLeafConstruct(Directive D) { return getLeafConstructs(D).empty(); } bool isCompositeConstruct(Directive D) { - // OpenMP Spec 5.2: [17.3, 8-9] - // If directive-name-A and directive-name-B both correspond to loop- - // associated constructs then directive-name is a composite construct - llvm::ArrayRef Leafs{getLeafConstructs(D)}; - if (Leafs.empty()) - return false; - if (getDirectiveAssociation(Leafs.front()) != Association::Loop) + ArrayRef Leafs = getLeafConstructsOrSelf(D); + if (Leafs.size() <= 1) return false; - - size_t numLoopConstructs = - llvm::count_if(Leafs.drop_front(), [](Directive L) { - return getDirectiveAssociation(L) == Association::Loop; - }); - return numLoopConstructs != 0; + auto Range = getFirstCompositeRange(Leafs); + return Range.begin() == Leafs.begin() && Range.end() == Leafs.end(); } bool isCombinedConstruct(Directive D) { diff --git a/llvm/lib/IR/Attributes.cpp b/llvm/lib/IR/Attributes.cpp index b2d9992cdc025812c5de8161f8a92abe5224f436..9c48a481de1ff69b84686f47d9c6baed726437dd 100644 --- a/llvm/lib/IR/Attributes.cpp +++ b/llvm/lib/IR/Attributes.cpp @@ -1530,6 +1530,13 @@ AttributeList::addDereferenceableOrNullParamAttr(LLVMContext &C, unsigned Index, return addParamAttributes(C, Index, B); } +AttributeList AttributeList::addRangeRetAttr(LLVMContext &C, + const ConstantRange &CR) const { + AttrBuilder B(C); + B.addRangeAttr(CR); + return addRetAttributes(C, B); +} + AttributeList AttributeList::addAllocSizeParamAttr( LLVMContext &C, unsigned Index, unsigned ElemSizeArg, const std::optional &NumElemsArg) { diff --git a/llvm/lib/IR/AutoUpgrade.cpp b/llvm/lib/IR/AutoUpgrade.cpp index 634b2dd5119e8d7e4b60d45aab165ee0e89f3c8b..6dc5b9aae769966b953881b606971138626af343 100644 --- a/llvm/lib/IR/AutoUpgrade.cpp +++ b/llvm/lib/IR/AutoUpgrade.cpp @@ -846,6 +846,18 @@ static bool upgradeArmOrAarch64IntrinsicFunction(bool IsArm, Function *F, return false; // No other 'aarch64.sve.bf*'. } + if (Name.consume_front("addqv")) { + // 'aarch64.sve.addqv'. + if (!F->getReturnType()->isFPOrFPVectorTy()) + return false; + + auto Args = F->getFunctionType()->params(); + Type *Tys[] = {F->getReturnType(), Args[1]}; + NewFn = Intrinsic::getDeclaration(F->getParent(), + Intrinsic::aarch64_sve_faddqv, Tys); + return true; + } + if (Name.consume_front("ld")) { // 'aarch64.sve.ld*'. static const Regex LdRegex("^[234](.nxv[a-z0-9]+|$)"); diff --git a/llvm/lib/IR/CMakeLists.txt b/llvm/lib/IR/CMakeLists.txt index f1668ee3be63b5d4ff3f2fc50bd553cf161a6ad7..b5fb7409d8e88e0b676750e48bcb05b2c58a2894 100644 --- a/llvm/lib/IR/CMakeLists.txt +++ b/llvm/lib/IR/CMakeLists.txt @@ -41,6 +41,7 @@ add_llvm_component_library(LLVMCore LLVMRemarkStreamer.cpp LegacyPassManager.cpp MDBuilder.cpp + MemoryModelRelaxationAnnotations.cpp Mangler.cpp Metadata.cpp Module.cpp diff --git a/llvm/lib/IR/Function.cpp b/llvm/lib/IR/Function.cpp index e66fe73425e86313434906199a0dcbc8974f9f1c..545940dd86f90f1af18f824098e292f414b64ac2 100644 --- a/llvm/lib/IR/Function.cpp +++ b/llvm/lib/IR/Function.cpp @@ -735,6 +735,10 @@ void Function::addDereferenceableOrNullParamAttr(unsigned ArgNo, ArgNo, Bytes); } +void Function::addRangeRetAttr(const ConstantRange &CR) { + AttributeSets = AttributeSets.addRangeRetAttr(getContext(), CR); +} + DenormalMode Function::getDenormalMode(const fltSemantics &FPType) const { if (&FPType == &APFloat::IEEEsingle()) { DenormalMode Mode = getDenormalModeF32Raw(); diff --git a/llvm/lib/IR/Instruction.cpp b/llvm/lib/IR/Instruction.cpp index eb1c5f445eb8b5e8ca55bd2df9cb7e733892ea48..678edc58ad848dfe15367acf72c31b955b1e1f5f 100644 --- a/llvm/lib/IR/Instruction.cpp +++ b/llvm/lib/IR/Instruction.cpp @@ -19,6 +19,7 @@ #include "llvm/IR/Instructions.h" #include "llvm/IR/IntrinsicInst.h" #include "llvm/IR/Intrinsics.h" +#include "llvm/IR/MemoryModelRelaxationAnnotations.h" #include "llvm/IR/Operator.h" #include "llvm/IR/ProfDataUtils.h" #include "llvm/IR/Type.h" diff --git a/llvm/lib/IR/IntrinsicInst.cpp b/llvm/lib/IR/IntrinsicInst.cpp index 89403e1d7fcb4dee63c5d626661d8ca46905a6cf..6b6420ae41c92d1a53124ab59c1c24f238625381 100644 --- a/llvm/lib/IR/IntrinsicInst.cpp +++ b/llvm/lib/IR/IntrinsicInst.cpp @@ -119,7 +119,8 @@ static ValueAsMetadata *getAsMetadata(Value *V) { } void DbgVariableIntrinsic::replaceVariableLocationOp(Value *OldValue, - Value *NewValue) { + Value *NewValue, + bool AllowEmpty) { // If OldValue is used as the address part of a dbg.assign intrinsic replace // it with NewValue and return true. auto ReplaceDbgAssignAddress = [this, OldValue, NewValue]() -> bool { @@ -136,6 +137,8 @@ void DbgVariableIntrinsic::replaceVariableLocationOp(Value *OldValue, auto Locations = location_ops(); auto OldIt = find(Locations, OldValue); if (OldIt == Locations.end()) { + if (AllowEmpty || DbgAssignAddrReplaced) + return; assert(DbgAssignAddrReplaced && "OldValue must be dbg.assign addr if unused in DIArgList"); return; @@ -291,6 +294,12 @@ Value *InstrProfIncrementInst::getStep() const { return ConstantInt::get(Type::getInt64Ty(Context), 1); } +Value *InstrProfCallsite::getCallee() const { + if (isa(this)) + return getArgOperand(4); + return nullptr; +} + std::optional ConstrainedFPIntrinsic::getRoundingMode() const { unsigned NumOperands = arg_size(); Metadata *MD = nullptr; diff --git a/llvm/lib/IR/MemoryModelRelaxationAnnotations.cpp b/llvm/lib/IR/MemoryModelRelaxationAnnotations.cpp new file mode 100644 index 0000000000000000000000000000000000000000..19f438d890aee843b4ee64851f69158969017395 --- /dev/null +++ b/llvm/lib/IR/MemoryModelRelaxationAnnotations.cpp @@ -0,0 +1,170 @@ +//===- MemoryModelRelaxationAnnotations.cpp ---------------------*- C++ -*-===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#include "llvm/IR/MemoryModelRelaxationAnnotations.h" +#include "llvm/ADT/StringSet.h" +#include "llvm/IR/Instructions.h" +#include "llvm/IR/Metadata.h" +#include "llvm/Support/Debug.h" +#include "llvm/Support/raw_ostream.h" + +using namespace llvm; + +//===- MMRAMetadata -------------------------------------------------------===// + +MMRAMetadata::MMRAMetadata(const Instruction &I) + : MMRAMetadata(I.getMetadata(LLVMContext::MD_mmra)) {} + +MMRAMetadata::MMRAMetadata(MDNode *MD) { + if (!MD) + return; + + // TODO: Split this into a "tryParse" function that can return an err. + // CTor can use the tryParse & just fatal on err. + + MDTuple *Tuple = dyn_cast(MD); + assert(Tuple && "Invalid MMRA structure"); + + const auto HandleTagMD = [this](MDNode *TagMD) { + Tags.insert({cast(TagMD->getOperand(0))->getString(), + cast(TagMD->getOperand(1))->getString()}); + }; + + if (isTagMD(Tuple)) { + HandleTagMD(Tuple); + return; + } + + for (const MDOperand &Op : Tuple->operands()) { + MDNode *MDOp = cast(Op.get()); + assert(isTagMD(MDOp)); + HandleTagMD(MDOp); + } +} + +bool MMRAMetadata::isTagMD(const Metadata *MD) { + if (auto *Tuple = dyn_cast(MD)) { + return Tuple->getNumOperands() == 2 && + isa(Tuple->getOperand(0)) && + isa(Tuple->getOperand(1)); + } + return false; +} + +MDTuple *MMRAMetadata::getTagMD(LLVMContext &Ctx, StringRef Prefix, + StringRef Suffix) { + return MDTuple::get(Ctx, + {MDString::get(Ctx, Prefix), MDString::get(Ctx, Suffix)}); +} + +MDTuple *MMRAMetadata::getMD(LLVMContext &Ctx, + ArrayRef Tags) { + if (Tags.empty()) + return nullptr; + + if (Tags.size() == 1) + return getTagMD(Ctx, Tags.front()); + + SmallVector MMRAs; + for (const auto &Tag : Tags) + MMRAs.push_back(getTagMD(Ctx, Tag)); + return MDTuple::get(Ctx, MMRAs); +} + +MDNode *MMRAMetadata::combine(LLVMContext &Ctx, const MMRAMetadata &A, + const MMRAMetadata &B) { + // Let A and B be two tags set, and U be the prefix-wise union of A and B. + // For every unique tag prefix P present in A or B: + // * If either A or B has no tags with prefix P, no tags with prefix + // P are added to U. + // * If both A and B have at least one tag with prefix P, all tags with prefix + // P from both sets are added to U. + + SmallVector Result; + + for (const auto &[P, S] : A) { + if (B.hasTagWithPrefix(P)) + Result.push_back(getTagMD(Ctx, P, S)); + } + for (const auto &[P, S] : B) { + if (A.hasTagWithPrefix(P)) + Result.push_back(getTagMD(Ctx, P, S)); + } + + return MDTuple::get(Ctx, Result); +} + +bool MMRAMetadata::hasTag(StringRef Prefix, StringRef Suffix) const { + return Tags.count({Prefix, Suffix}); +} + +bool MMRAMetadata::isCompatibleWith(const MMRAMetadata &Other) const { + // Two sets of tags are compatible iff, for every unique tag prefix P + // present in at least one set: + // - the other set contains no tag with prefix P, or + // - at least one tag with prefix P is common to both sets. + + StringMap PrefixStatuses; + for (const auto &[P, S] : Tags) + PrefixStatuses[P] |= (Other.hasTag(P, S) || !Other.hasTagWithPrefix(P)); + for (const auto &[P, S] : Other) + PrefixStatuses[P] |= (hasTag(P, S) || !hasTagWithPrefix(P)); + + for (auto &[Prefix, Status] : PrefixStatuses) { + if (!Status) + return false; + } + + return true; +} + +bool MMRAMetadata::hasTagWithPrefix(StringRef Prefix) const { + for (const auto &[P, S] : Tags) + if (P == Prefix) + return true; + return false; +} + +MMRAMetadata::const_iterator MMRAMetadata::begin() const { + return Tags.begin(); +} + +MMRAMetadata::const_iterator MMRAMetadata::end() const { return Tags.end(); } + +bool MMRAMetadata::empty() const { return Tags.empty(); } + +unsigned MMRAMetadata::size() const { return Tags.size(); } + +void MMRAMetadata::print(raw_ostream &OS) const { + bool IsFirst = true; + // TODO: use map_iter + join + for (const auto &[P, S] : Tags) { + if (IsFirst) + IsFirst = false; + else + OS << ", "; + OS << P << ":" << S; + } +} + +LLVM_DUMP_METHOD +void MMRAMetadata::dump() const { print(dbgs()); } + +//===- Helpers ------------------------------------------------------------===// + +static bool isReadWriteMemCall(const Instruction &I) { + if (const auto *C = dyn_cast(&I)) + return C->mayReadOrWriteMemory() || + !C->getMemoryEffects().doesNotAccessMemory(); + return false; +} + +bool llvm::canInstructionHaveMMRAs(const Instruction &I) { + return isa(I) || isa(I) || isa(I) || + isa(I) || isa(I) || isReadWriteMemCall(I); +} diff --git a/llvm/lib/IR/Verifier.cpp b/llvm/lib/IR/Verifier.cpp index edad3be9a3e09819368c381a3b938bdb1fc81afd..e42cc7e260ef108bf7b96622cf858ee9b685d615 100644 --- a/llvm/lib/IR/Verifier.cpp +++ b/llvm/lib/IR/Verifier.cpp @@ -99,6 +99,7 @@ #include "llvm/IR/IntrinsicsNVPTX.h" #include "llvm/IR/IntrinsicsWebAssembly.h" #include "llvm/IR/LLVMContext.h" +#include "llvm/IR/MemoryModelRelaxationAnnotations.h" #include "llvm/IR/Metadata.h" #include "llvm/IR/Module.h" #include "llvm/IR/ModuleSlotTracker.h" @@ -116,6 +117,7 @@ #include "llvm/Support/CommandLine.h" #include "llvm/Support/ErrorHandling.h" #include "llvm/Support/MathExtras.h" +#include "llvm/Support/ModRef.h" #include "llvm/Support/raw_ostream.h" #include #include @@ -529,6 +531,7 @@ private: void visitMemProfMetadata(Instruction &I, MDNode *MD); void visitCallsiteMetadata(Instruction &I, MDNode *MD); void visitDIAssignIDMetadata(Instruction &I, MDNode *MD); + void visitMMRAMetadata(Instruction &I, MDNode *MD); void visitAnnotationMetadata(MDNode *Annotation); void visitAliasScopeMetadata(const MDNode *MD); void visitAliasScopeListMetadata(const MDNode *MD); @@ -4844,6 +4847,24 @@ void Verifier::visitDIAssignIDMetadata(Instruction &I, MDNode *MD) { } } +void Verifier::visitMMRAMetadata(Instruction &I, MDNode *MD) { + Check(canInstructionHaveMMRAs(I), + "!mmra metadata attached to unexpected instruction kind", I, MD); + + // MMRA Metadata should either be a tag, e.g. !{!"foo", !"bar"}, or a + // list of tags such as !2 in the following example: + // !0 = !{!"a", !"b"} + // !1 = !{!"c", !"d"} + // !2 = !{!0, !1} + if (MMRAMetadata::isTagMD(MD)) + return; + + Check(isa(MD), "!mmra expected to be a metadata tuple", I, MD); + for (const MDOperand &MDOp : MD->operands()) + Check(MMRAMetadata::isTagMD(MDOp.get()), + "!mmra metadata tuple operand is not an MMRA tag", I, MDOp.get()); +} + void Verifier::visitCallStackMetadata(MDNode *MD) { // Call stack metadata should consist of a list of at least 1 constant int // (representing a hash of the location). @@ -5161,6 +5182,9 @@ void Verifier::visitInstruction(Instruction &I) { if (MDNode *MD = I.getMetadata(LLVMContext::MD_DIAssignID)) visitDIAssignIDMetadata(I, MD); + if (MDNode *MMRA = I.getMetadata(LLVMContext::MD_mmra)) + visitMMRAMetadata(I, MMRA); + if (MDNode *Annotation = I.getMetadata(LLVMContext::MD_annotation)) visitAnnotationMetadata(Annotation); @@ -6202,7 +6226,6 @@ void Verifier::visitIntrinsicCall(Intrinsic::ID ID, CallBase &Call) { break; } case Intrinsic::experimental_convergence_entry: - LLVM_FALLTHROUGH; case Intrinsic::experimental_convergence_anchor: break; case Intrinsic::experimental_convergence_loop: diff --git a/llvm/lib/MC/MCDXContainerStreamer.cpp b/llvm/lib/MC/MCDXContainerStreamer.cpp index 3cb452f3dfa5546ff779eccf1d0f9d1fb086451b..a596c9a16d498dad64b07a9316e0e29dd39161c1 100644 --- a/llvm/lib/MC/MCDXContainerStreamer.cpp +++ b/llvm/lib/MC/MCDXContainerStreamer.cpp @@ -21,11 +21,8 @@ void MCDXContainerStreamer::emitInstToData(const MCInst &, MCStreamer *llvm::createDXContainerStreamer( MCContext &Context, std::unique_ptr &&MAB, - std::unique_ptr &&OW, std::unique_ptr &&CE, - bool RelaxAll) { + std::unique_ptr &&OW, std::unique_ptr &&CE) { auto *S = new MCDXContainerStreamer(Context, std::move(MAB), std::move(OW), std::move(CE)); - if (RelaxAll) - S->getAssembler().setRelaxAll(true); return S; } diff --git a/llvm/lib/MC/MCELFStreamer.cpp b/llvm/lib/MC/MCELFStreamer.cpp index e541090769e9e5c7b9fc3a8b286a119b44eee4da..23e926c3a9d14b546d8ed805242f5b7d46fa004f 100644 --- a/llvm/lib/MC/MCELFStreamer.cpp +++ b/llvm/lib/MC/MCELFStreamer.cpp @@ -892,11 +892,8 @@ void MCELFStreamer::createAttributesSection( MCStreamer *llvm::createELFStreamer(MCContext &Context, std::unique_ptr &&MAB, std::unique_ptr &&OW, - std::unique_ptr &&CE, - bool RelaxAll) { + std::unique_ptr &&CE) { MCELFStreamer *S = new MCELFStreamer(Context, std::move(MAB), std::move(OW), std::move(CE)); - if (RelaxAll) - S->getAssembler().setRelaxAll(true); return S; } diff --git a/llvm/lib/MC/MCGOFFStreamer.cpp b/llvm/lib/MC/MCGOFFStreamer.cpp index 58d13c9f3788534f2b1b5a9b41ca7b3c70b6f1d4..2b6d5c8e75a706a6e5e8803424900ef042b515b0 100644 --- a/llvm/lib/MC/MCGOFFStreamer.cpp +++ b/llvm/lib/MC/MCGOFFStreamer.cpp @@ -24,11 +24,8 @@ MCGOFFStreamer::~MCGOFFStreamer() {} MCStreamer *llvm::createGOFFStreamer(MCContext &Context, std::unique_ptr &&MAB, std::unique_ptr &&OW, - std::unique_ptr &&CE, - bool RelaxAll) { + std::unique_ptr &&CE) { MCGOFFStreamer *S = new MCGOFFStreamer(Context, std::move(MAB), std::move(OW), std::move(CE)); - if (RelaxAll) - S->getAssembler().setRelaxAll(true); return S; } diff --git a/llvm/lib/MC/MCMachOStreamer.cpp b/llvm/lib/MC/MCMachOStreamer.cpp index d7d343f15eaa611b90d22dabe8f50c03208047a2..10f9988b9d16a0bce0170f386859eaf695275e7a 100644 --- a/llvm/lib/MC/MCMachOStreamer.cpp +++ b/llvm/lib/MC/MCMachOStreamer.cpp @@ -564,7 +564,7 @@ MCStreamer *llvm::createMachOStreamer(MCContext &Context, std::unique_ptr &&MAB, std::unique_ptr &&OW, std::unique_ptr &&CE, - bool RelaxAll, bool DWARFMustBeAtTheEnd, + bool DWARFMustBeAtTheEnd, bool LabelSections) { MCMachOStreamer *S = new MCMachOStreamer(Context, std::move(MAB), std::move(OW), std::move(CE), @@ -574,8 +574,6 @@ MCStreamer *llvm::createMachOStreamer(MCContext &Context, Target, Context.getObjectFileInfo()->getSDKVersion(), Context.getObjectFileInfo()->getDarwinTargetVariantTriple(), Context.getObjectFileInfo()->getDarwinTargetVariantSDKVersion()); - if (RelaxAll) - S->getAssembler().setRelaxAll(true); return S; } diff --git a/llvm/lib/MC/MCObjectStreamer.cpp b/llvm/lib/MC/MCObjectStreamer.cpp index 490e0a4dd404178742ef3c4f15161697cc0c869a..d2da5d0d3f90f2b13041755941931095e794bc5f 100644 --- a/llvm/lib/MC/MCObjectStreamer.cpp +++ b/llvm/lib/MC/MCObjectStreamer.cpp @@ -34,6 +34,8 @@ MCObjectStreamer::MCObjectStreamer(MCContext &Context, EmitEHFrame(true), EmitDebugFrame(false) { if (Assembler->getBackendPtr()) setAllowAutoPadding(Assembler->getBackend().allowAutoPadding()); + if (Context.getTargetOptions() && Context.getTargetOptions()->MCRelaxAll) + Assembler->setRelaxAll(true); } MCObjectStreamer::~MCObjectStreamer() = default; diff --git a/llvm/lib/MC/MCSPIRVStreamer.cpp b/llvm/lib/MC/MCSPIRVStreamer.cpp index 0bb73c7ff7ee2ddc8772ccc584668e8a393c9aab..3b75a2e17a4a9846d525e854965c71aaac15a8e0 100644 --- a/llvm/lib/MC/MCSPIRVStreamer.cpp +++ b/llvm/lib/MC/MCSPIRVStreamer.cpp @@ -34,11 +34,8 @@ void MCSPIRVStreamer::emitInstToData(const MCInst &Inst, MCStreamer *llvm::createSPIRVStreamer(MCContext &Context, std::unique_ptr &&MAB, std::unique_ptr &&OW, - std::unique_ptr &&CE, - bool RelaxAll) { + std::unique_ptr &&CE) { MCSPIRVStreamer *S = new MCSPIRVStreamer(Context, std::move(MAB), std::move(OW), std::move(CE)); - if (RelaxAll) - S->getAssembler().setRelaxAll(true); return S; } diff --git a/llvm/lib/MC/MCWasmStreamer.cpp b/llvm/lib/MC/MCWasmStreamer.cpp index fbab72fb5f3d36fb9e10c74fe54090931140ab52..c553ede77555a54329208fb25af9ccc40a5a94b4 100644 --- a/llvm/lib/MC/MCWasmStreamer.cpp +++ b/llvm/lib/MC/MCWasmStreamer.cpp @@ -275,11 +275,8 @@ void MCWasmStreamer::emitTBSSSymbol(MCSection *Section, MCSymbol *Symbol, MCStreamer *llvm::createWasmStreamer(MCContext &Context, std::unique_ptr &&MAB, std::unique_ptr &&OW, - std::unique_ptr &&CE, - bool RelaxAll) { + std::unique_ptr &&CE) { MCWasmStreamer *S = new MCWasmStreamer(Context, std::move(MAB), std::move(OW), std::move(CE)); - if (RelaxAll) - S->getAssembler().setRelaxAll(true); return S; } diff --git a/llvm/lib/MC/MCXCOFFStreamer.cpp b/llvm/lib/MC/MCXCOFFStreamer.cpp index 458b4be6198387cce3a0723d69ef256259367797..175d7d6b6c31a63cfa40ecf467962bcf088b6bfa 100644 --- a/llvm/lib/MC/MCXCOFFStreamer.cpp +++ b/llvm/lib/MC/MCXCOFFStreamer.cpp @@ -162,12 +162,9 @@ void MCXCOFFStreamer::emitInstToData(const MCInst &Inst, MCStreamer *llvm::createXCOFFStreamer(MCContext &Context, std::unique_ptr &&MAB, std::unique_ptr &&OW, - std::unique_ptr &&CE, - bool RelaxAll) { + std::unique_ptr &&CE) { MCXCOFFStreamer *S = new MCXCOFFStreamer(Context, std::move(MAB), std::move(OW), std::move(CE)); - if (RelaxAll) - S->getAssembler().setRelaxAll(true); return S; } diff --git a/llvm/lib/Object/ELFObjectFile.cpp b/llvm/lib/Object/ELFObjectFile.cpp index efec612957de33352ce64ee0d62559c2826254ad..24d7a7a280fd9a8e8733f5e5496c4e4526134534 100644 --- a/llvm/lib/Object/ELFObjectFile.cpp +++ b/llvm/lib/Object/ELFObjectFile.cpp @@ -24,7 +24,7 @@ #include "llvm/Support/MathExtras.h" #include "llvm/Support/RISCVAttributeParser.h" #include "llvm/Support/RISCVAttributes.h" -#include "llvm/Support/RISCVISAInfo.h" +#include "llvm/TargetParser/RISCVISAInfo.h" #include "llvm/TargetParser/SubtargetFeature.h" #include "llvm/TargetParser/Triple.h" #include diff --git a/llvm/lib/Object/ModuleSymbolTable.cpp b/llvm/lib/Object/ModuleSymbolTable.cpp index 07f76688fa43e7954cbab885b5ae234448fbd455..d8f520ad02c2f2cd63d6a72d7073dea0213c8a10 100644 --- a/llvm/lib/Object/ModuleSymbolTable.cpp +++ b/llvm/lib/Object/ModuleSymbolTable.cpp @@ -175,6 +175,20 @@ void ModuleSymbolTable::CollectAsmSymbols( AsmSymbol(Key, BasicSymbolRef::Flags(Res)); } }); + + // In ELF, object code generated for x86-32 and some code models of x86-64 may + // reference the special symbol _GLOBAL_OFFSET_TABLE_ that is not used in the + // IR. Record it like inline asm symbols. + Triple TT(M.getTargetTriple()); + if (!TT.isOSBinFormatELF() || !TT.isX86()) + return; + auto CM = M.getCodeModel(); + if (TT.getArch() == Triple::x86 || CM == CodeModel::Medium || + CM == CodeModel::Large) { + AsmSymbol("_GLOBAL_OFFSET_TABLE_", + BasicSymbolRef::Flags(BasicSymbolRef::SF_Undefined | + BasicSymbolRef::SF_Global)); + } } void ModuleSymbolTable::CollectAsmSymvers( diff --git a/llvm/lib/ProfileData/InstrProfWriter.cpp b/llvm/lib/ProfileData/InstrProfWriter.cpp index 4a6fc9d64b6900319fcdfd28e2307886e98d04a5..e1846fcbffee52e2ed5a315e79df7966b83d309c 100644 --- a/llvm/lib/ProfileData/InstrProfWriter.cpp +++ b/llvm/lib/ProfileData/InstrProfWriter.cpp @@ -184,12 +184,13 @@ public: InstrProfWriter::InstrProfWriter( bool Sparse, uint64_t TemporalProfTraceReservoirSize, uint64_t MaxTemporalProfTraceLength, bool WritePrevVersion, - memprof::IndexedVersion MemProfVersionRequested) + memprof::IndexedVersion MemProfVersionRequested, bool MemProfFullSchema) : Sparse(Sparse), MaxTemporalProfTraceLength(MaxTemporalProfTraceLength), TemporalProfTraceReservoirSize(TemporalProfTraceReservoirSize), InfoObj(new InstrProfRecordWriterTrait()), WritePrevVersion(WritePrevVersion), - MemProfVersionRequested(MemProfVersionRequested) {} + MemProfVersionRequested(MemProfVersionRequested), + MemProfFullSchema(MemProfFullSchema) {} InstrProfWriter::~InstrProfWriter() { delete InfoObj; } @@ -507,7 +508,7 @@ static Error writeMemProfV0( OS.write(0ULL); // Reserve space for the memprof frame payload offset. OS.write(0ULL); // Reserve space for the memprof frame table offset. - auto Schema = memprof::PortableMemInfoBlock::getSchema(); + auto Schema = memprof::getFullSchema(); writeMemProfSchema(OS, Schema); uint64_t RecordTableOffset = @@ -533,7 +534,7 @@ static Error writeMemProfV1( OS.write(0ULL); // Reserve space for the memprof frame payload offset. OS.write(0ULL); // Reserve space for the memprof frame table offset. - auto Schema = memprof::PortableMemInfoBlock::getSchema(); + auto Schema = memprof::getFullSchema(); writeMemProfSchema(OS, Schema); uint64_t RecordTableOffset = @@ -554,7 +555,8 @@ static Error writeMemProfV2( &MemProfRecordData, llvm::MapVector &MemProfFrameData, llvm::MapVector> - &MemProfCallStackData) { + &MemProfCallStackData, + bool MemProfFullSchema) { OS.write(memprof::Version2); uint64_t HeaderUpdatePos = OS.tell(); OS.write(0ULL); // Reserve space for the memprof record table offset. @@ -563,7 +565,9 @@ static Error writeMemProfV2( OS.write(0ULL); // Reserve space for the memprof call stack payload offset. OS.write(0ULL); // Reserve space for the memprof call stack table offset. - auto Schema = memprof::PortableMemInfoBlock::getSchema(); + auto Schema = memprof::getHotColdSchema(); + if (MemProfFullSchema) + Schema = memprof::getFullSchema(); writeMemProfSchema(OS, Schema); uint64_t RecordTableOffset = @@ -605,7 +609,7 @@ static Error writeMemProf( llvm::MapVector &MemProfFrameData, llvm::MapVector> &MemProfCallStackData, - memprof::IndexedVersion MemProfVersionRequested) { + memprof::IndexedVersion MemProfVersionRequested, bool MemProfFullSchema) { switch (MemProfVersionRequested) { case memprof::Version0: @@ -614,7 +618,7 @@ static Error writeMemProf( return writeMemProfV1(OS, MemProfRecordData, MemProfFrameData); case memprof::Version2: return writeMemProfV2(OS, MemProfRecordData, MemProfFrameData, - MemProfCallStackData); + MemProfCallStackData, MemProfFullSchema); } return make_error( @@ -733,7 +737,8 @@ Error InstrProfWriter::writeImpl(ProfOStream &OS) { if (static_cast(ProfileKind & InstrProfKind::MemProf)) { MemProfSectionStart = OS.tell(); if (auto E = writeMemProf(OS, MemProfRecordData, MemProfFrameData, - MemProfCallStackData, MemProfVersionRequested)) + MemProfCallStackData, MemProfVersionRequested, + MemProfFullSchema)) return E; } diff --git a/llvm/lib/ProfileData/MemProf.cpp b/llvm/lib/ProfileData/MemProf.cpp index 8e0402dd16e680ea994b79f23d6b437c384842b9..4667778ca11dd0c1485290a9ed515d9058ec804d 100644 --- a/llvm/lib/ProfileData/MemProf.cpp +++ b/llvm/lib/ProfileData/MemProf.cpp @@ -10,42 +10,59 @@ namespace llvm { namespace memprof { -static size_t serializedSizeV0(const IndexedAllocationInfo &IAI) { +MemProfSchema getFullSchema() { + MemProfSchema List; +#define MIBEntryDef(NameTag, Name, Type) List.push_back(Meta::Name); +#include "llvm/ProfileData/MIBEntryDef.inc" +#undef MIBEntryDef + return List; +} + +MemProfSchema getHotColdSchema() { + return {Meta::AllocCount, Meta::TotalSize, Meta::TotalLifetime, + Meta::TotalLifetimeAccessDensity}; +} + +static size_t serializedSizeV0(const IndexedAllocationInfo &IAI, + const MemProfSchema &Schema) { size_t Size = 0; // The number of frames to serialize. Size += sizeof(uint64_t); // The callstack frame ids. Size += sizeof(FrameId) * IAI.CallStack.size(); // The size of the payload. - Size += PortableMemInfoBlock::serializedSize(); + Size += PortableMemInfoBlock::serializedSize(Schema); return Size; } -static size_t serializedSizeV2(const IndexedAllocationInfo &IAI) { +static size_t serializedSizeV2(const IndexedAllocationInfo &IAI, + const MemProfSchema &Schema) { size_t Size = 0; // The CallStackId Size += sizeof(CallStackId); // The size of the payload. - Size += PortableMemInfoBlock::serializedSize(); + Size += PortableMemInfoBlock::serializedSize(Schema); return Size; } -size_t IndexedAllocationInfo::serializedSize(IndexedVersion Version) const { +size_t IndexedAllocationInfo::serializedSize(const MemProfSchema &Schema, + IndexedVersion Version) const { switch (Version) { case Version0: case Version1: - return serializedSizeV0(*this); + return serializedSizeV0(*this, Schema); case Version2: - return serializedSizeV2(*this); + return serializedSizeV2(*this, Schema); } llvm_unreachable("unsupported MemProf version"); } -static size_t serializedSizeV0(const IndexedMemProfRecord &Record) { +static size_t serializedSizeV0(const IndexedMemProfRecord &Record, + const MemProfSchema &Schema) { // The number of alloc sites to serialize. size_t Result = sizeof(uint64_t); for (const IndexedAllocationInfo &N : Record.AllocSites) - Result += N.serializedSize(Version0); + Result += N.serializedSize(Schema, Version0); // The number of callsites we have information for. Result += sizeof(uint64_t); @@ -57,11 +74,12 @@ static size_t serializedSizeV0(const IndexedMemProfRecord &Record) { return Result; } -static size_t serializedSizeV2(const IndexedMemProfRecord &Record) { +static size_t serializedSizeV2(const IndexedMemProfRecord &Record, + const MemProfSchema &Schema) { // The number of alloc sites to serialize. size_t Result = sizeof(uint64_t); for (const IndexedAllocationInfo &N : Record.AllocSites) - Result += N.serializedSize(Version2); + Result += N.serializedSize(Schema, Version2); // The number of callsites we have information for. Result += sizeof(uint64_t); @@ -70,13 +88,14 @@ static size_t serializedSizeV2(const IndexedMemProfRecord &Record) { return Result; } -size_t IndexedMemProfRecord::serializedSize(IndexedVersion Version) const { +size_t IndexedMemProfRecord::serializedSize(const MemProfSchema &Schema, + IndexedVersion Version) const { switch (Version) { case Version0: case Version1: - return serializedSizeV0(*this); + return serializedSizeV0(*this, Schema); case Version2: - return serializedSizeV2(*this); + return serializedSizeV2(*this, Schema); } llvm_unreachable("unsupported MemProf version"); } @@ -156,7 +175,7 @@ static IndexedMemProfRecord deserializeV0(const MemProfSchema &Schema, } Node.CSId = hashCallStack(Node.CallStack); Node.Info.deserialize(Schema, Ptr); - Ptr += PortableMemInfoBlock::serializedSize(); + Ptr += PortableMemInfoBlock::serializedSize(Schema); Record.AllocSites.push_back(Node); } @@ -193,7 +212,7 @@ static IndexedMemProfRecord deserializeV2(const MemProfSchema &Schema, IndexedAllocationInfo Node; Node.CSId = endian::readNext(Ptr); Node.Info.deserialize(Schema, Ptr); - Ptr += PortableMemInfoBlock::serializedSize(); + Ptr += PortableMemInfoBlock::serializedSize(Schema); Record.AllocSites.push_back(Node); } diff --git a/llvm/lib/Support/CMakeLists.txt b/llvm/lib/Support/CMakeLists.txt index e18beddf7bc5b7f77aad45511fbf4fbde86535ff..03e888958a0711a54d3949e083b14c3612009f3e 100644 --- a/llvm/lib/Support/CMakeLists.txt +++ b/llvm/lib/Support/CMakeLists.txt @@ -219,7 +219,7 @@ add_llvm_component_library(LLVMSupport Regex.cpp RISCVAttributes.cpp RISCVAttributeParser.cpp - RISCVISAInfo.cpp + RISCVISAUtils.cpp ScaledNumber.cpp ScopedPrinter.cpp SHA1.cpp diff --git a/llvm/lib/Support/RISCVISAUtils.cpp b/llvm/lib/Support/RISCVISAUtils.cpp new file mode 100644 index 0000000000000000000000000000000000000000..ca7518f71907b5a0d448d48f3f20e3af105ecf0e --- /dev/null +++ b/llvm/lib/Support/RISCVISAUtils.cpp @@ -0,0 +1,88 @@ +//===-- RISCVISAUtils.cpp - RISC-V ISA Utilities --------------------------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// +// +// Utilities shared by TableGen and RISCVISAInfo. +// +//===----------------------------------------------------------------------===// + +#include "llvm/Support/RISCVISAUtils.h" +#include + +using namespace llvm; + +// We rank extensions in the following order: +// -Single letter extensions in canonical order. +// -Unknown single letter extensions in alphabetical order. +// -Multi-letter extensions starting with 'z' sorted by canonical order of +// the second letter then sorted alphabetically. +// -Multi-letter extensions starting with 's' in alphabetical order. +// -(TODO) Multi-letter extensions starting with 'zxm' in alphabetical order. +// -X extensions in alphabetical order. +// These flags are used to indicate the category. The first 6 bits store the +// single letter extension rank for single letter and multi-letter extensions +// starting with 'z'. +enum RankFlags { + RF_Z_EXTENSION = 1 << 6, + RF_S_EXTENSION = 1 << 7, + RF_X_EXTENSION = 1 << 8, +}; + +// Get the rank for single-letter extension, lower value meaning higher +// priority. +static unsigned singleLetterExtensionRank(char Ext) { + assert(Ext >= 'a' && Ext <= 'z'); + switch (Ext) { + case 'i': + return 0; + case 'e': + return 1; + } + + size_t Pos = RISCVISAUtils::AllStdExts.find(Ext); + if (Pos != StringRef::npos) + return Pos + 2; // Skip 'e' and 'i' from above. + + // If we got an unknown extension letter, then give it an alphabetical + // order, but after all known standard extensions. + return 2 + RISCVISAUtils::AllStdExts.size() + (Ext - 'a'); +} + +// Get the rank for multi-letter extension, lower value meaning higher +// priority/order in canonical order. +static unsigned getExtensionRank(const std::string &ExtName) { + assert(ExtName.size() >= 1); + switch (ExtName[0]) { + case 's': + return RF_S_EXTENSION; + case 'z': + assert(ExtName.size() >= 2); + // `z` extension must be sorted by canonical order of second letter. + // e.g. zmx has higher rank than zax. + return RF_Z_EXTENSION | singleLetterExtensionRank(ExtName[1]); + case 'x': + return RF_X_EXTENSION; + default: + assert(ExtName.size() == 1); + return singleLetterExtensionRank(ExtName[0]); + } +} + +// Compare function for extension. +// Only compare the extension name, ignore version comparison. +bool llvm::RISCVISAUtils::compareExtension(const std::string &LHS, + const std::string &RHS) { + unsigned LHSRank = getExtensionRank(LHS); + unsigned RHSRank = getExtensionRank(RHS); + + // If the ranks differ, pick the lower rank. + if (LHSRank != RHSRank) + return LHSRank < RHSRank; + + // If the rank is same, it must be sorted by lexicographic order. + return LHS < RHS; +} diff --git a/llvm/lib/Target/AArch64/AArch64.td b/llvm/lib/Target/AArch64/AArch64.td index f2f1c93ea225c825b9e7c7b2917daf3191095d32..4b2ce0d73949cb38623a785bf89fac59c7bf8b4e 100644 --- a/llvm/lib/Target/AArch64/AArch64.td +++ b/llvm/lib/Target/AArch64/AArch64.td @@ -76,7 +76,7 @@ def SME2p1Unsupported : AArch64Unsupported; def SME2Unsupported : AArch64Unsupported { let F = !listconcat([HasSME2, HasSVE2orSME2, HasSVE2p1_or_HasSME2, HasSSVE_FP8FMA, - HasSMEF8F16, HasSMEF8F32], + HasSMEF8F16, HasSMEF8F32, HasSMEF16F16orSMEF8F16], SME2p1Unsupported.F); } diff --git a/llvm/lib/Target/AArch64/AArch64ConditionOptimizer.cpp b/llvm/lib/Target/AArch64/AArch64ConditionOptimizer.cpp index 1c20e24e41d7eacf23593c26ea5214225ce80701..2a4a3c0df08f9c3eb6b188731ebc1f9031e7f8f8 100644 --- a/llvm/lib/Target/AArch64/AArch64ConditionOptimizer.cpp +++ b/llvm/lib/Target/AArch64/AArch64ConditionOptimizer.cpp @@ -163,7 +163,7 @@ MachineInstr *AArch64ConditionOptimizer::findSuitableCompare( MachineInstr &I = *It; assert(!I.isTerminator() && "Spurious terminator"); // Check if there is any use of NZCV between CMP and Bcc. - if (I.readsRegister(AArch64::NZCV)) + if (I.readsRegister(AArch64::NZCV, /*TRI=*/nullptr)) return nullptr; switch (I.getOpcode()) { // cmp is an alias for subs with a dead destination register. diff --git a/llvm/lib/Target/AArch64/AArch64ConditionalCompares.cpp b/llvm/lib/Target/AArch64/AArch64ConditionalCompares.cpp index 17e0e3072db6ffc674d9872b7070ec731a2f67d5..8c16a88a13a408ab3ed9781852f16c799fc39d4c 100644 --- a/llvm/lib/Target/AArch64/AArch64ConditionalCompares.cpp +++ b/llvm/lib/Target/AArch64/AArch64ConditionalCompares.cpp @@ -299,7 +299,7 @@ MachineInstr *SSACCmpConv::findConvertibleCompare(MachineBasicBlock *MBB) { if (I == MBB->end()) return nullptr; // The terminator must be controlled by the flags. - if (!I->readsRegister(AArch64::NZCV)) { + if (!I->readsRegister(AArch64::NZCV, /*TRI=*/nullptr)) { switch (I->getOpcode()) { case AArch64::CBZW: case AArch64::CBZX: diff --git a/llvm/lib/Target/AArch64/AArch64DeadRegisterDefinitionsPass.cpp b/llvm/lib/Target/AArch64/AArch64DeadRegisterDefinitionsPass.cpp index 3e04cbae8acf18a10487782a47dcc31f5110b090..2bc14f9821e63973eb90f095d2485d0a4a83f86f 100644 --- a/llvm/lib/Target/AArch64/AArch64DeadRegisterDefinitionsPass.cpp +++ b/llvm/lib/Target/AArch64/AArch64DeadRegisterDefinitionsPass.cpp @@ -124,7 +124,8 @@ void AArch64DeadRegisterDefinitions::processMachineBasicBlock( LLVM_DEBUG(dbgs() << " Ignoring, operand is frame index\n"); continue; } - if (MI.definesRegister(AArch64::XZR) || MI.definesRegister(AArch64::WZR)) { + if (MI.definesRegister(AArch64::XZR, /*TRI=*/nullptr) || + MI.definesRegister(AArch64::WZR, /*TRI=*/nullptr)) { // It is not allowed to write to the same register (not even the zero // register) twice in a single instruction. LLVM_DEBUG( diff --git a/llvm/lib/Target/AArch64/AArch64Features.td b/llvm/lib/Target/AArch64/AArch64Features.td index efda45a72ef4245cbcead062607b7e12f030c75f..3a3751a85afd1ea6ee9f5eecf7fff7bd969f1717 100644 --- a/llvm/lib/Target/AArch64/AArch64Features.td +++ b/llvm/lib/Target/AArch64/AArch64Features.td @@ -505,15 +505,15 @@ def FeatureSMEF64F64 : SubtargetFeature<"sme-f64f64", "HasSMEF64F64", "true", def FeatureSMEI16I64 : SubtargetFeature<"sme-i16i64", "HasSMEI16I64", "true", "Enable Scalable Matrix Extension (SME) I16I64 instructions (FEAT_SME_I16I64)", [FeatureSME]>; -def FeatureSMEF16F16 : SubtargetFeature<"sme-f16f16", "HasSMEF16F16", "true", - "Enable SME2.1 non-widening Float16 instructions (FEAT_SME_F16F16)", []>; - def FeatureSMEFA64 : SubtargetFeature<"sme-fa64", "HasSMEFA64", "true", "Enable the full A64 instruction set in streaming SVE mode (FEAT_SME_FA64)", [FeatureSME, FeatureSVE2]>; def FeatureSME2 : SubtargetFeature<"sme2", "HasSME2", "true", "Enable Scalable Matrix Extension 2 (SME2) instructions", [FeatureSME]>; +def FeatureSMEF16F16 : SubtargetFeature<"sme-f16f16", "HasSMEF16F16", "true", + "Enable SME non-widening Float16 instructions (FEAT_SME_F16F16)", [FeatureSME2]>; + def FeatureSME2p1 : SubtargetFeature<"sme2p1", "HasSME2p1", "true", "Enable Scalable Matrix Extension 2.1 (FEAT_SME2p1) instructions", [FeatureSME2]>; diff --git a/llvm/lib/Target/AArch64/AArch64FrameLowering.cpp b/llvm/lib/Target/AArch64/AArch64FrameLowering.cpp index 419c141121c32535c7e07ec4a9923f07403725ff..c86c98eed24f0825904c0d177edae5e5b7b3e60d 100644 --- a/llvm/lib/Target/AArch64/AArch64FrameLowering.cpp +++ b/llvm/lib/Target/AArch64/AArch64FrameLowering.cpp @@ -1296,7 +1296,7 @@ static MachineBasicBlock::iterator InsertSEH(MachineBasicBlock::iterator MBBI, } case AArch64::LDPQpost: Imm = -Imm; - LLVM_FALLTHROUGH; + [[fallthrough]]; case AArch64::STPQpre: { unsigned Reg0 = RegInfo->getSEHRegNum(MBBI->getOperand(1).getReg()); unsigned Reg1 = RegInfo->getSEHRegNum(MBBI->getOperand(2).getReg()); diff --git a/llvm/lib/Target/AArch64/AArch64ISelLowering.cpp b/llvm/lib/Target/AArch64/AArch64ISelLowering.cpp index 2238015e43b1732e253b746dc3e1a6e554513bc0..8e9782c1930c3c5e169e7fd68ed444afe479080c 100644 --- a/llvm/lib/Target/AArch64/AArch64ISelLowering.cpp +++ b/llvm/lib/Target/AArch64/AArch64ISelLowering.cpp @@ -1603,39 +1603,19 @@ AArch64TargetLowering::AArch64TargetLowering(const TargetMachine &TM, setOperationAction(ISD::VECREDUCE_SEQ_FADD, VT, Custom); } - if (!Subtarget->isNeonAvailable()) { - setTruncStoreAction(MVT::v2f32, MVT::v2bf16, Custom); - setTruncStoreAction(MVT::v4f32, MVT::v4bf16, Custom); - setTruncStoreAction(MVT::v8f32, MVT::v8bf16, Custom); - setTruncStoreAction(MVT::v2f64, MVT::v2bf16, Custom); - setTruncStoreAction(MVT::v4f64, MVT::v4bf16, Custom); - setTruncStoreAction(MVT::v2f32, MVT::v2f16, Custom); - setTruncStoreAction(MVT::v4f32, MVT::v4f16, Custom); - setTruncStoreAction(MVT::v8f32, MVT::v8f16, Custom); - setTruncStoreAction(MVT::v1f64, MVT::v1f16, Custom); - setTruncStoreAction(MVT::v2f64, MVT::v2f16, Custom); - setTruncStoreAction(MVT::v4f64, MVT::v4f16, Custom); - setTruncStoreAction(MVT::v1f64, MVT::v1f32, Custom); - setTruncStoreAction(MVT::v2f64, MVT::v2f32, Custom); - setTruncStoreAction(MVT::v4f64, MVT::v4f32, Custom); - for (MVT VT : {MVT::v8i8, MVT::v16i8, MVT::v4i16, MVT::v8i16, MVT::v2i32, - MVT::v4i32, MVT::v1i64, MVT::v2i64}) - addTypeForFixedLengthSVE(VT, /*StreamingSVE=*/ true); - - for (MVT VT : - {MVT::v4f16, MVT::v8f16, MVT::v2f32, MVT::v4f32, MVT::v2f64}) - addTypeForFixedLengthSVE(VT, /*StreamingSVE=*/ true); - } - // NOTE: Currently this has to happen after computeRegisterProperties rather // than the preferred option of combining it with the addRegisterClass call. if (Subtarget->useSVEForFixedLengthVectors()) { - for (MVT VT : MVT::integer_fixedlen_vector_valuetypes()) - if (useSVEForFixedLengthVectorVT(VT)) - addTypeForFixedLengthSVE(VT, /*StreamingSVE=*/ false); - for (MVT VT : MVT::fp_fixedlen_vector_valuetypes()) - if (useSVEForFixedLengthVectorVT(VT)) - addTypeForFixedLengthSVE(VT, /*StreamingSVE=*/ false); + for (MVT VT : MVT::integer_fixedlen_vector_valuetypes()) { + if (useSVEForFixedLengthVectorVT( + VT, /*OverrideNEON=*/!Subtarget->isNeonAvailable())) + addTypeForFixedLengthSVE(VT); + } + for (MVT VT : MVT::fp_fixedlen_vector_valuetypes()) { + if (useSVEForFixedLengthVectorVT( + VT, /*OverrideNEON=*/!Subtarget->isNeonAvailable())) + addTypeForFixedLengthSVE(VT); + } // 64bit results can mean a bigger than NEON input. for (auto VT : {MVT::v8i8, MVT::v4i16}) @@ -1869,8 +1849,7 @@ bool AArch64TargetLowering::shouldExpandCttzElements(EVT VT) const { return !Subtarget->hasSVEorSME() || VT != MVT::nxv16i1; } -void AArch64TargetLowering::addTypeForFixedLengthSVE(MVT VT, - bool StreamingSVE) { +void AArch64TargetLowering::addTypeForFixedLengthSVE(MVT VT) { assert(VT.isFixedLengthVector() && "Expected fixed length vector type!"); // By default everything must be expanded. @@ -1889,13 +1868,17 @@ void AArch64TargetLowering::addTypeForFixedLengthSVE(MVT VT, setCondCodeAction(ISD::SETONE, VT, Expand); } + TargetLoweringBase::LegalizeAction Default = + VT == MVT::v1f64 ? Expand : Custom; + // Mark integer truncating stores/extending loads as having custom lowering if (VT.isInteger()) { MVT InnerVT = VT.changeVectorElementType(MVT::i8); while (InnerVT != VT) { - setTruncStoreAction(VT, InnerVT, Custom); - setLoadExtAction(ISD::ZEXTLOAD, VT, InnerVT, Custom); - setLoadExtAction(ISD::SEXTLOAD, VT, InnerVT, Custom); + setTruncStoreAction(VT, InnerVT, Default); + setLoadExtAction(ISD::ZEXTLOAD, VT, InnerVT, Default); + setLoadExtAction(ISD::SEXTLOAD, VT, InnerVT, Default); + setLoadExtAction(ISD::EXTLOAD, VT, InnerVT, Default); InnerVT = InnerVT.changeVectorElementType( MVT::getIntegerVT(2 * InnerVT.getScalarSizeInBits())); } @@ -1907,101 +1890,103 @@ void AArch64TargetLowering::addTypeForFixedLengthSVE(MVT VT, MVT InnerVT = VT.changeVectorElementType(MVT::f16); while (InnerVT != VT) { setTruncStoreAction(VT, InnerVT, Custom); - setLoadExtAction(ISD::EXTLOAD, VT, InnerVT, Custom); + setLoadExtAction(ISD::EXTLOAD, VT, InnerVT, Default); InnerVT = InnerVT.changeVectorElementType( MVT::getFloatingPointVT(2 * InnerVT.getScalarSizeInBits())); } } + bool PreferNEON = VT.is64BitVector() || VT.is128BitVector(); + bool PreferSVE = !PreferNEON && Subtarget->isSVEAvailable(); + // Lower fixed length vector operations to scalable equivalents. - setOperationAction(ISD::ABS, VT, Custom); - setOperationAction(ISD::ADD, VT, Custom); - setOperationAction(ISD::AND, VT, Custom); - setOperationAction(ISD::ANY_EXTEND, VT, Custom); - setOperationAction(ISD::BITCAST, VT, StreamingSVE ? Legal : Custom); - setOperationAction(ISD::BITREVERSE, VT, Custom); - setOperationAction(ISD::BSWAP, VT, Custom); - setOperationAction(ISD::BUILD_VECTOR, VT, Custom); - setOperationAction(ISD::CONCAT_VECTORS, VT, Custom); - setOperationAction(ISD::CTLZ, VT, Custom); - setOperationAction(ISD::CTPOP, VT, Custom); - setOperationAction(ISD::CTTZ, VT, Custom); - setOperationAction(ISD::EXTRACT_SUBVECTOR, VT, Custom); - setOperationAction(ISD::EXTRACT_VECTOR_ELT, VT, Custom); - setOperationAction(ISD::FABS, VT, Custom); - setOperationAction(ISD::FADD, VT, Custom); - setOperationAction(ISD::FCEIL, VT, Custom); - setOperationAction(ISD::FCOPYSIGN, VT, Custom); - setOperationAction(ISD::FDIV, VT, Custom); - setOperationAction(ISD::FFLOOR, VT, Custom); - setOperationAction(ISD::FMA, VT, Custom); - setOperationAction(ISD::FMAXIMUM, VT, Custom); - setOperationAction(ISD::FMAXNUM, VT, Custom); - setOperationAction(ISD::FMINIMUM, VT, Custom); - setOperationAction(ISD::FMINNUM, VT, Custom); - setOperationAction(ISD::FMUL, VT, Custom); - setOperationAction(ISD::FNEARBYINT, VT, Custom); - setOperationAction(ISD::FNEG, VT, Custom); - setOperationAction(ISD::FP_EXTEND, VT, Custom); - setOperationAction(ISD::FP_ROUND, VT, Custom); - setOperationAction(ISD::FP_TO_SINT, VT, Custom); - setOperationAction(ISD::FP_TO_UINT, VT, Custom); - setOperationAction(ISD::FRINT, VT, Custom); - setOperationAction(ISD::FROUND, VT, Custom); - setOperationAction(ISD::FROUNDEVEN, VT, Custom); - setOperationAction(ISD::FSQRT, VT, Custom); - setOperationAction(ISD::FSUB, VT, Custom); - setOperationAction(ISD::FTRUNC, VT, Custom); - setOperationAction(ISD::INSERT_VECTOR_ELT, VT, Custom); - setOperationAction(ISD::LOAD, VT, StreamingSVE ? Legal : Custom); - setOperationAction(ISD::MGATHER, VT, StreamingSVE ? Expand : Custom); - setOperationAction(ISD::MLOAD, VT, Custom); - setOperationAction(ISD::MSCATTER, VT, StreamingSVE ? Expand : Custom); - setOperationAction(ISD::MSTORE, VT, Custom); - setOperationAction(ISD::MUL, VT, Custom); - setOperationAction(ISD::MULHS, VT, Custom); - setOperationAction(ISD::MULHU, VT, Custom); - setOperationAction(ISD::OR, VT, Custom); - setOperationAction(ISD::SCALAR_TO_VECTOR, VT, StreamingSVE ? Legal : Expand); - setOperationAction(ISD::SDIV, VT, Custom); - setOperationAction(ISD::SELECT, VT, Custom); - setOperationAction(ISD::SETCC, VT, Custom); - setOperationAction(ISD::SHL, VT, Custom); - setOperationAction(ISD::SIGN_EXTEND, VT, Custom); - setOperationAction(ISD::SIGN_EXTEND_INREG, VT, Custom); - setOperationAction(ISD::SINT_TO_FP, VT, Custom); - setOperationAction(ISD::SMAX, VT, Custom); - setOperationAction(ISD::SMIN, VT, Custom); - setOperationAction(ISD::SPLAT_VECTOR, VT, Custom); - setOperationAction(ISD::SRA, VT, Custom); - setOperationAction(ISD::SRL, VT, Custom); - setOperationAction(ISD::STORE, VT, StreamingSVE ? Legal : Custom); - setOperationAction(ISD::SUB, VT, Custom); - setOperationAction(ISD::TRUNCATE, VT, Custom); - setOperationAction(ISD::UDIV, VT, Custom); - setOperationAction(ISD::UINT_TO_FP, VT, Custom); - setOperationAction(ISD::UMAX, VT, Custom); - setOperationAction(ISD::UMIN, VT, Custom); - setOperationAction(ISD::VECREDUCE_ADD, VT, Custom); - setOperationAction(ISD::VECREDUCE_AND, VT, Custom); - setOperationAction(ISD::VECREDUCE_FADD, VT, Custom); - setOperationAction(ISD::VECREDUCE_FMAX, VT, Custom); - setOperationAction(ISD::VECREDUCE_FMIN, VT, Custom); - setOperationAction(ISD::VECREDUCE_FMAXIMUM, VT, Custom); - setOperationAction(ISD::VECREDUCE_FMINIMUM, VT, Custom); - setOperationAction(ISD::VECREDUCE_OR, VT, Custom); - setOperationAction(ISD::VECREDUCE_SEQ_FADD, VT, - StreamingSVE ? Expand : Custom); - setOperationAction(ISD::VECREDUCE_SMAX, VT, Custom); - setOperationAction(ISD::VECREDUCE_SMIN, VT, Custom); - setOperationAction(ISD::VECREDUCE_UMAX, VT, Custom); - setOperationAction(ISD::VECREDUCE_UMIN, VT, Custom); - setOperationAction(ISD::VECREDUCE_XOR, VT, Custom); - setOperationAction(ISD::VECTOR_SHUFFLE, VT, Custom); - setOperationAction(ISD::VECTOR_SPLICE, VT, Custom); - setOperationAction(ISD::VSELECT, VT, Custom); - setOperationAction(ISD::XOR, VT, Custom); - setOperationAction(ISD::ZERO_EXTEND, VT, Custom); + setOperationAction(ISD::ABS, VT, Default); + setOperationAction(ISD::ADD, VT, Default); + setOperationAction(ISD::AND, VT, Default); + setOperationAction(ISD::ANY_EXTEND, VT, Default); + setOperationAction(ISD::BITCAST, VT, PreferNEON ? Legal : Default); + setOperationAction(ISD::BITREVERSE, VT, Default); + setOperationAction(ISD::BSWAP, VT, Default); + setOperationAction(ISD::BUILD_VECTOR, VT, Default); + setOperationAction(ISD::CONCAT_VECTORS, VT, Default); + setOperationAction(ISD::CTLZ, VT, Default); + setOperationAction(ISD::CTPOP, VT, Default); + setOperationAction(ISD::CTTZ, VT, Default); + setOperationAction(ISD::EXTRACT_SUBVECTOR, VT, Default); + setOperationAction(ISD::EXTRACT_VECTOR_ELT, VT, Default); + setOperationAction(ISD::FABS, VT, Default); + setOperationAction(ISD::FADD, VT, Default); + setOperationAction(ISD::FCEIL, VT, Default); + setOperationAction(ISD::FCOPYSIGN, VT, Default); + setOperationAction(ISD::FDIV, VT, Default); + setOperationAction(ISD::FFLOOR, VT, Default); + setOperationAction(ISD::FMA, VT, Default); + setOperationAction(ISD::FMAXIMUM, VT, Default); + setOperationAction(ISD::FMAXNUM, VT, Default); + setOperationAction(ISD::FMINIMUM, VT, Default); + setOperationAction(ISD::FMINNUM, VT, Default); + setOperationAction(ISD::FMUL, VT, Default); + setOperationAction(ISD::FNEARBYINT, VT, Default); + setOperationAction(ISD::FNEG, VT, Default); + setOperationAction(ISD::FP_EXTEND, VT, Default); + setOperationAction(ISD::FP_ROUND, VT, Default); + setOperationAction(ISD::FP_TO_SINT, VT, Default); + setOperationAction(ISD::FP_TO_UINT, VT, Default); + setOperationAction(ISD::FRINT, VT, Default); + setOperationAction(ISD::FROUND, VT, Default); + setOperationAction(ISD::FROUNDEVEN, VT, Default); + setOperationAction(ISD::FSQRT, VT, Default); + setOperationAction(ISD::FSUB, VT, Default); + setOperationAction(ISD::FTRUNC, VT, Default); + setOperationAction(ISD::INSERT_VECTOR_ELT, VT, Default); + setOperationAction(ISD::LOAD, VT, PreferNEON ? Legal : Default); + setOperationAction(ISD::MGATHER, VT, PreferSVE ? Default : Expand); + setOperationAction(ISD::MLOAD, VT, Default); + setOperationAction(ISD::MSCATTER, VT, PreferSVE ? Default : Expand); + setOperationAction(ISD::MSTORE, VT, Default); + setOperationAction(ISD::MUL, VT, Default); + setOperationAction(ISD::MULHS, VT, Default); + setOperationAction(ISD::MULHU, VT, Default); + setOperationAction(ISD::OR, VT, Default); + setOperationAction(ISD::SCALAR_TO_VECTOR, VT, PreferNEON ? Legal : Expand); + setOperationAction(ISD::SDIV, VT, Default); + setOperationAction(ISD::SELECT, VT, Default); + setOperationAction(ISD::SETCC, VT, Default); + setOperationAction(ISD::SHL, VT, Default); + setOperationAction(ISD::SIGN_EXTEND, VT, Default); + setOperationAction(ISD::SIGN_EXTEND_INREG, VT, Default); + setOperationAction(ISD::SINT_TO_FP, VT, Default); + setOperationAction(ISD::SMAX, VT, Default); + setOperationAction(ISD::SMIN, VT, Default); + setOperationAction(ISD::SPLAT_VECTOR, VT, Default); + setOperationAction(ISD::SRA, VT, Default); + setOperationAction(ISD::SRL, VT, Default); + setOperationAction(ISD::STORE, VT, PreferNEON ? Legal : Default); + setOperationAction(ISD::SUB, VT, Default); + setOperationAction(ISD::TRUNCATE, VT, Default); + setOperationAction(ISD::UDIV, VT, Default); + setOperationAction(ISD::UINT_TO_FP, VT, Default); + setOperationAction(ISD::UMAX, VT, Default); + setOperationAction(ISD::UMIN, VT, Default); + setOperationAction(ISD::VECREDUCE_ADD, VT, Default); + setOperationAction(ISD::VECREDUCE_AND, VT, Default); + setOperationAction(ISD::VECREDUCE_FADD, VT, Default); + setOperationAction(ISD::VECREDUCE_FMAX, VT, Default); + setOperationAction(ISD::VECREDUCE_FMIN, VT, Default); + setOperationAction(ISD::VECREDUCE_FMAXIMUM, VT, Default); + setOperationAction(ISD::VECREDUCE_FMINIMUM, VT, Default); + setOperationAction(ISD::VECREDUCE_OR, VT, Default); + setOperationAction(ISD::VECREDUCE_SEQ_FADD, VT, PreferSVE ? Default : Expand); + setOperationAction(ISD::VECREDUCE_SMAX, VT, Default); + setOperationAction(ISD::VECREDUCE_SMIN, VT, Default); + setOperationAction(ISD::VECREDUCE_UMAX, VT, Default); + setOperationAction(ISD::VECREDUCE_UMIN, VT, Default); + setOperationAction(ISD::VECREDUCE_XOR, VT, Default); + setOperationAction(ISD::VECTOR_SHUFFLE, VT, Default); + setOperationAction(ISD::VECTOR_SPLICE, VT, Default); + setOperationAction(ISD::VSELECT, VT, Default); + setOperationAction(ISD::XOR, VT, Default); + setOperationAction(ISD::ZERO_EXTEND, VT, Default); } void AArch64TargetLowering::addDRTypeForNEON(MVT VT) { @@ -17600,12 +17585,32 @@ static SDValue performMulCombine(SDNode *N, SelectionDAG &DAG, return false; }; + // Can the const C be decomposed into (2^M + 1) * 2^N + 1), eg: + // C = 11 is equal to (1+4)*2+1, we don't decompose it into (1+2)*4-1 as + // the (2^N - 1) can't be execused via a single instruction. + auto isPowPlusPlusOneConst = [](APInt C, APInt &M, APInt &N) { + APInt CVMinus1 = C - 1; + if (CVMinus1.isNegative()) + return false; + unsigned TrailingZeroes = CVMinus1.countr_zero(); + APInt SCVMinus1 = CVMinus1.ashr(TrailingZeroes) - 1; + if (SCVMinus1.isPowerOf2()) { + unsigned BitWidth = SCVMinus1.getBitWidth(); + M = APInt(BitWidth, SCVMinus1.logBase2()); + N = APInt(BitWidth, TrailingZeroes); + return true; + } + return false; + }; + if (ConstValue.isNonNegative()) { // (mul x, (2^N + 1) * 2^M) => (shl (add (shl x, N), x), M) // (mul x, 2^N - 1) => (sub (shl x, N), x) // (mul x, (2^(N-M) - 1) * 2^M) => (sub (shl x, N), (shl x, M)) // (mul x, (2^M + 1) * (2^N + 1)) // => MV = (add (shl x, M), x); (add (shl MV, N), MV) + // (mul x, (2^M + 1) * 2^N + 1)) + // => MV = add (shl x, M), x); add (shl MV, N), x) APInt SCVMinus1 = ShiftedConstValue - 1; APInt SCVPlus1 = ShiftedConstValue + 1; APInt CVPlus1 = ConstValue + 1; @@ -17619,18 +17624,29 @@ static SDValue performMulCombine(SDNode *N, SelectionDAG &DAG, } else if (SCVPlus1.isPowerOf2()) { ShiftAmt = SCVPlus1.logBase2() + TrailingZeroes; return Sub(Shl(N0, ShiftAmt), Shl(N0, TrailingZeroes)); - } else if (Subtarget->hasALULSLFast() && - isPowPlusPlusConst(ConstValue, CVM, CVN)) { + } + if (Subtarget->hasALULSLFast() && + isPowPlusPlusConst(ConstValue, CVM, CVN)) { APInt CVMMinus1 = CVM - 1; APInt CVNMinus1 = CVN - 1; unsigned ShiftM1 = CVMMinus1.logBase2(); unsigned ShiftN1 = CVNMinus1.logBase2(); - // LSLFast implicate that Shifts <= 3 places are fast - if (ShiftM1 <= 3 && ShiftN1 <= 3) { + // ALULSLFast implicate that Shifts <= 4 places are fast + if (ShiftM1 <= 4 && ShiftN1 <= 4) { SDValue MVal = Add(Shl(N0, ShiftM1), N0); return Add(Shl(MVal, ShiftN1), MVal); } } + if (Subtarget->hasALULSLFast() && + isPowPlusPlusOneConst(ConstValue, CVM, CVN)) { + unsigned ShiftM = CVM.getZExtValue(); + unsigned ShiftN = CVN.getZExtValue(); + // ALULSLFast implicate that Shifts <= 4 places are fast + if (ShiftM <= 4 && ShiftN <= 4) { + SDValue MVal = Add(Shl(N0, CVM.getZExtValue()), N0); + return Add(Shl(MVal, CVN.getZExtValue()), N0); + } + } } else { // (mul x, -(2^N - 1)) => (sub x, (shl x, N)) // (mul x, -(2^N + 1)) => - (add (shl x, N), x) @@ -18647,14 +18663,12 @@ static SDValue performConcatVectorsCombine(SDNode *N, if (DCI.isBeforeLegalizeOps()) return SDValue(); - // Optimise concat_vectors of two [us]avgceils or [us]avgfloors with a 128-bit - // destination size, combine into an avg of two contacts of the source - // vectors. eg: concat(uhadd(a,b), uhadd(c, d)) -> uhadd(concat(a, c), - // concat(b, d)) + // Optimise concat_vectors of two identical binops with a 128-bit destination + // size, combine into an binop of two contacts of the source vectors. eg: + // concat(uhadd(a,b), uhadd(c, d)) -> uhadd(concat(a, c), concat(b, d)) if (N->getNumOperands() == 2 && N0Opc == N1Opc && VT.is128BitVector() && - (N0Opc == ISD::AVGCEILU || N0Opc == ISD::AVGCEILS || - N0Opc == ISD::AVGFLOORU || N0Opc == ISD::AVGFLOORS) && - N0->hasOneUse() && N1->hasOneUse()) { + DAG.getTargetLoweringInfo().isBinOp(N0Opc) && N0->hasOneUse() && + N1->hasOneUse()) { SDValue N00 = N0->getOperand(0); SDValue N01 = N0->getOperand(1); SDValue N10 = N1->getOperand(0); diff --git a/llvm/lib/Target/AArch64/AArch64ISelLowering.h b/llvm/lib/Target/AArch64/AArch64ISelLowering.h index db6e8a00d2fb5e960f388ff191337ed46d4d1d4a..400368a5e1303d4e85cfa8a58b4b9a79b538eedb 100644 --- a/llvm/lib/Target/AArch64/AArch64ISelLowering.h +++ b/llvm/lib/Target/AArch64/AArch64ISelLowering.h @@ -1013,7 +1013,7 @@ private: bool isExtFreeImpl(const Instruction *Ext) const override; void addTypeForNEON(MVT VT); - void addTypeForFixedLengthSVE(MVT VT, bool StreamingSVE); + void addTypeForFixedLengthSVE(MVT VT); void addDRTypeForNEON(MVT VT); void addQRTypeForNEON(MVT VT); diff --git a/llvm/lib/Target/AArch64/AArch64InstrInfo.cpp b/llvm/lib/Target/AArch64/AArch64InstrInfo.cpp index 9518d573bccdd17f12e97d10e1632a9ff73e433c..55fecc4b4845fd864802f7028f428a9176eb351b 100644 --- a/llvm/lib/Target/AArch64/AArch64InstrInfo.cpp +++ b/llvm/lib/Target/AArch64/AArch64InstrInfo.cpp @@ -643,7 +643,8 @@ static unsigned canFoldIntoCSel(const MachineRegisterInfo &MRI, unsigned VReg, case AArch64::ADDSXri: case AArch64::ADDSWri: // if NZCV is used, do not fold. - if (DefMI->findRegisterDefOperandIdx(AArch64::NZCV, true) == -1) + if (DefMI->findRegisterDefOperandIdx(AArch64::NZCV, /*TRI=*/nullptr, + true) == -1) return 0; // fall-through to ADDXri and ADDWri. [[fallthrough]]; @@ -671,7 +672,8 @@ static unsigned canFoldIntoCSel(const MachineRegisterInfo &MRI, unsigned VReg, case AArch64::SUBSXrr: case AArch64::SUBSWrr: // if NZCV is used, do not fold. - if (DefMI->findRegisterDefOperandIdx(AArch64::NZCV, true) == -1) + if (DefMI->findRegisterDefOperandIdx(AArch64::NZCV, /*TRI=*/nullptr, + true) == -1) return 0; // fall-through to SUBXrr and SUBWrr. [[fallthrough]]; @@ -1275,7 +1277,8 @@ static unsigned convertToNonFlagSettingOpc(const MachineInstr &MI) { // Don't convert all compare instructions, because for some the zero register // encoding becomes the sp register. bool MIDefinesZeroReg = false; - if (MI.definesRegister(AArch64::WZR) || MI.definesRegister(AArch64::XZR)) + if (MI.definesRegister(AArch64::WZR, /*TRI=*/nullptr) || + MI.definesRegister(AArch64::XZR, /*TRI=*/nullptr)) MIDefinesZeroReg = true; switch (MI.getOpcode()) { @@ -1519,10 +1522,11 @@ bool AArch64InstrInfo::optimizeCompareInstr( assert(MRI); // Replace SUBSWrr with SUBWrr if NZCV is not used. - int DeadNZCVIdx = CmpInstr.findRegisterDefOperandIdx(AArch64::NZCV, true); + int DeadNZCVIdx = + CmpInstr.findRegisterDefOperandIdx(AArch64::NZCV, /*TRI=*/nullptr, true); if (DeadNZCVIdx != -1) { - if (CmpInstr.definesRegister(AArch64::WZR) || - CmpInstr.definesRegister(AArch64::XZR)) { + if (CmpInstr.definesRegister(AArch64::WZR, /*TRI=*/nullptr) || + CmpInstr.definesRegister(AArch64::XZR, /*TRI=*/nullptr)) { CmpInstr.eraseFromParent(); return true; } @@ -1623,7 +1627,7 @@ findCondCodeUseOperandIdxForBranchOrSelect(const MachineInstr &Instr) { return -1; case AArch64::Bcc: { - int Idx = Instr.findRegisterUseOperandIdx(AArch64::NZCV); + int Idx = Instr.findRegisterUseOperandIdx(AArch64::NZCV, /*TRI=*/nullptr); assert(Idx >= 2); return Idx - 2; } @@ -1638,7 +1642,7 @@ findCondCodeUseOperandIdxForBranchOrSelect(const MachineInstr &Instr) { case AArch64::CSNEGXr: case AArch64::FCSELSrrr: case AArch64::FCSELDrrr: { - int Idx = Instr.findRegisterUseOperandIdx(AArch64::NZCV); + int Idx = Instr.findRegisterUseOperandIdx(AArch64::NZCV, /*TRI=*/nullptr); assert(Idx >= 1); return Idx - 1; } @@ -1846,7 +1850,7 @@ static bool canCmpInstrBeRemoved(MachineInstr &MI, MachineInstr &CmpInstr, return false; // NZCV needs to be defined - if (MI.findRegisterDefOperandIdx(AArch64::NZCV, true) != -1) + if (MI.findRegisterDefOperandIdx(AArch64::NZCV, /*TRI=*/nullptr, true) != -1) return false; // CmpInstr is 'ADDS %vreg, 0' or 'SUBS %vreg, 0' or 'SUBS %vreg, 1' @@ -5913,7 +5917,7 @@ static bool canCombine(MachineBasicBlock &MBB, MachineOperand &MO, } if (isCombineInstrSettingFlag(CombineOpc) && - MI->findRegisterDefOperandIdx(AArch64::NZCV, true) == -1) + MI->findRegisterDefOperandIdx(AArch64::NZCV, /*TRI=*/nullptr, true) == -1) return false; return true; @@ -6051,7 +6055,8 @@ static bool getMaddPatterns(MachineInstr &Root, if (!isCombineInstrCandidate(Opc)) return false; if (isCombineInstrSettingFlag(Opc)) { - int Cmp_NZCV = Root.findRegisterDefOperandIdx(AArch64::NZCV, true); + int Cmp_NZCV = + Root.findRegisterDefOperandIdx(AArch64::NZCV, /*TRI=*/nullptr, true); // When NZCV is live bail out. if (Cmp_NZCV == -1) return false; @@ -6546,7 +6551,8 @@ static bool getMiscPatterns(MachineInstr &Root, } if (isCombineInstrSettingFlag(Opc) && - Root.findRegisterDefOperandIdx(AArch64::NZCV, true) == -1) + Root.findRegisterDefOperandIdx(AArch64::NZCV, /*TRI=*/nullptr, true) == + -1) return false; if (canCombine(MBB, Root.getOperand(2), AArch64::ADDWrr) || @@ -6918,19 +6924,26 @@ genSubAdd2SubSub(MachineFunction &MF, MachineRegisterInfo &MRI, assert((Opcode == AArch64::SUBWrr || Opcode == AArch64::SUBXrr) && "Unexpected instruction opcode."); + uint32_t Flags = Root.mergeFlagsWith(*AddMI); + Flags &= ~MachineInstr::NoSWrap; + Flags &= ~MachineInstr::NoUWrap; + MachineInstrBuilder MIB1 = BuildMI(MF, MIMetadata(Root), TII->get(Opcode), NewVR) .addReg(RegA, getKillRegState(RegAIsKill)) - .addReg(RegB, getKillRegState(RegBIsKill)); + .addReg(RegB, getKillRegState(RegBIsKill)) + .setMIFlags(Flags); MachineInstrBuilder MIB2 = BuildMI(MF, MIMetadata(Root), TII->get(Opcode), ResultReg) .addReg(NewVR, getKillRegState(true)) - .addReg(RegC, getKillRegState(RegCIsKill)); + .addReg(RegC, getKillRegState(RegCIsKill)) + .setMIFlags(Flags); InstrIdxForVirtReg.insert(std::make_pair(NewVR, 0)); InsInstrs.push_back(MIB1); InsInstrs.push_back(MIB2); DelInstrs.push_back(AddMI); + DelInstrs.push_back(&Root); } /// When getMachineCombinerPatterns() finds potential patterns, @@ -6960,13 +6973,13 @@ void AArch64InstrInfo::genAlternativeCodeSequence( // ==> (A - B) - C genSubAdd2SubSub(MF, MRI, TII, Root, InsInstrs, DelInstrs, 1, InstrIdxForVirtReg); - break; + return; case AArch64MachineCombinerPattern::SUBADD_OP2: // A - (B + C) // ==> (A - C) - B genSubAdd2SubSub(MF, MRI, TII, Root, InsInstrs, DelInstrs, 2, InstrIdxForVirtReg); - break; + return; case AArch64MachineCombinerPattern::MULADDW_OP1: case AArch64MachineCombinerPattern::MULADDX_OP1: // MUL I=A,B,0 @@ -8031,7 +8044,8 @@ bool AArch64InstrInfo::optimizeCondBranch(MachineInstr &MI) const { DefMI->getOperand(2).getReg() == AArch64::XZR)) return false; - if (DefMI->findRegisterDefOperandIdx(AArch64::NZCV, true) != -1) + if (DefMI->findRegisterDefOperandIdx(AArch64::NZCV, /*TRI=*/nullptr, + true) != -1) return false; AArch64CC::CondCode CC = (AArch64CC::CondCode)DefMI->getOperand(3).getImm(); @@ -9238,7 +9252,8 @@ AArch64InstrInfo::isCopyInstrImpl(const MachineInstr &MI) const { MI.getOperand(0).getSubReg() == 0) && (!MI.getOperand(0).getReg().isPhysical() || MI.findRegisterDefOperandIdx(MI.getOperand(0).getReg() - AArch64::W0 + - AArch64::X0) == -1)) + AArch64::X0, + /*TRI=*/nullptr) == -1)) return DestSourcePair{MI.getOperand(0), MI.getOperand(2)}; if (MI.getOpcode() == AArch64::ORRXrs && diff --git a/llvm/lib/Target/AArch64/AArch64InstrInfo.h b/llvm/lib/Target/AArch64/AArch64InstrInfo.h index 9a2914891675c543cc34f599096598100051c1ef..f434799c3982b4b0a4a95a6b89b9c86190544ef4 100644 --- a/llvm/lib/Target/AArch64/AArch64InstrInfo.h +++ b/llvm/lib/Target/AArch64/AArch64InstrInfo.h @@ -725,6 +725,7 @@ static inline unsigned getAUTOpcodeForKey(AArch64PACKey::ID K, bool Zero) { case DA: return Zero ? AArch64::AUTDZA : AArch64::AUTDA; case DB: return Zero ? AArch64::AUTDZB : AArch64::AUTDB; } + llvm_unreachable("Unhandled AArch64PACKey::ID enum"); } /// Return PAC opcode to be used for a ptrauth sign using the given key, or its @@ -737,6 +738,7 @@ static inline unsigned getPACOpcodeForKey(AArch64PACKey::ID K, bool Zero) { case DA: return Zero ? AArch64::PACDZA : AArch64::PACDA; case DB: return Zero ? AArch64::PACDZB : AArch64::PACDB; } + llvm_unreachable("Unhandled AArch64PACKey::ID enum"); } // struct TSFlags { diff --git a/llvm/lib/Target/AArch64/AArch64InstrInfo.td b/llvm/lib/Target/AArch64/AArch64InstrInfo.td index fb18d1c63ae80dd3a100166a7d9e77d12327a08e..17d96370c04a59545fd77e062d83b3a5a97b832b 100644 --- a/llvm/lib/Target/AArch64/AArch64InstrInfo.td +++ b/llvm/lib/Target/AArch64/AArch64InstrInfo.td @@ -230,6 +230,12 @@ def HasSVE2p1_or_HasSME2 def HasSVE2p1_or_HasSME2p1 : Predicate<"Subtarget->hasSVE2p1() || Subtarget->hasSME2p1()">, AssemblerPredicateWithAll<(any_of FeatureSME2p1, FeatureSVE2p1), "sme2p1 or sve2p1">; + +def HasSMEF16F16orSMEF8F16 + : Predicate<"Subtarget->hasSMEF16F16() || Subtarget->hasSMEF8F16()">, + AssemblerPredicateWithAll<(any_of FeatureSMEF16F16, FeatureSMEF8F16), + "sme-f16f16 or sme-f8f16">; + // A subset of NEON instructions are legal in Streaming SVE execution mode, // they should be enabled if either has been specified. def HasNEONorSME @@ -315,6 +321,8 @@ def UseNegativeImmediates def UseScalarIncVL : Predicate<"Subtarget->useScalarIncVL()">; +def NoUseScalarIncVL : Predicate<"!Subtarget->useScalarIncVL()">; + def UseSVEFPLD1R : Predicate<"!Subtarget->noSVEFPLD1R()">; def IsNeonAvailable : Predicate<"Subtarget->isNeonAvailable()">; diff --git a/llvm/lib/Target/AArch64/AArch64MacroFusion.cpp b/llvm/lib/Target/AArch64/AArch64MacroFusion.cpp index 05d60872bf51acac4b80e61e640f7805660d1df9..ff7a0d1faedf7ce6afc59282df24c8d9f51489ad 100644 --- a/llvm/lib/Target/AArch64/AArch64MacroFusion.cpp +++ b/llvm/lib/Target/AArch64/AArch64MacroFusion.cpp @@ -245,7 +245,7 @@ static bool isCCSelectPair(const MachineInstr *FirstMI, if (FirstMI == nullptr) return true; - if (FirstMI->definesRegister(AArch64::WZR)) + if (FirstMI->definesRegister(AArch64::WZR, /*TRI=*/nullptr)) switch (FirstMI->getOpcode()) { case AArch64::SUBSWrs: return !AArch64InstrInfo::hasShiftedReg(*FirstMI); @@ -263,7 +263,7 @@ static bool isCCSelectPair(const MachineInstr *FirstMI, if (FirstMI == nullptr) return true; - if (FirstMI->definesRegister(AArch64::XZR)) + if (FirstMI->definesRegister(AArch64::XZR, /*TRI=*/nullptr)) switch (FirstMI->getOpcode()) { case AArch64::SUBSXrs: return !AArch64InstrInfo::hasShiftedReg(*FirstMI); diff --git a/llvm/lib/Target/AArch64/AArch64PerfectShuffle.h b/llvm/lib/Target/AArch64/AArch64PerfectShuffle.h index 7abaead694d11488d0958ec49b37f355037c5e3c..a143243a8d3bb310175016a8c7e62622b05b7c9e 100644 --- a/llvm/lib/Target/AArch64/AArch64PerfectShuffle.h +++ b/llvm/lib/Target/AArch64/AArch64PerfectShuffle.h @@ -6620,11 +6620,28 @@ static unsigned getPerfectShuffleCost(llvm::ArrayRef M) { return (PFEntry >> 30) + 1; } -inline bool isZIPMask(ArrayRef M, EVT VT, unsigned &WhichResult) { +/// Return true for zip1 or zip2 masks of the form: +/// <0, 8, 1, 9, 2, 10, 3, 11> or +/// <4, 12, 5, 13, 6, 14, 7, 15> +inline bool isZIPMask(ArrayRef M, EVT VT, unsigned &WhichResultOut) { unsigned NumElts = VT.getVectorNumElements(); if (NumElts % 2 != 0) return false; - WhichResult = (M[0] == 0 ? 0 : 1); + // Check the first non-undef element for which half to use. + unsigned WhichResult = 2; + for (unsigned i = 0; i != NumElts / 2; i++) { + if (M[i * 2] >= 0) { + WhichResult = ((unsigned)M[i * 2] == i ? 0 : 1); + break; + } else if (M[i * 2 + 1] >= 0) { + WhichResult = ((unsigned)M[i * 2 + 1] == NumElts + i ? 0 : 1); + break; + } + } + if (WhichResult == 2) + return false; + + // Check all elements match. unsigned Idx = WhichResult * NumElts / 2; for (unsigned i = 0; i != NumElts; i += 2) { if ((M[i] >= 0 && (unsigned)M[i] != Idx) || @@ -6632,20 +6649,34 @@ inline bool isZIPMask(ArrayRef M, EVT VT, unsigned &WhichResult) { return false; Idx += 1; } - + WhichResultOut = WhichResult; return true; } -inline bool isUZPMask(ArrayRef M, EVT VT, unsigned &WhichResult) { +/// Return true for uzp1 or uzp2 masks of the form: +/// <0, 2, 4, 6, 8, 10, 12, 14> or +/// <1, 3, 5, 7, 9, 11, 13, 15> +inline bool isUZPMask(ArrayRef M, EVT VT, unsigned &WhichResultOut) { unsigned NumElts = VT.getVectorNumElements(); - WhichResult = (M[0] == 0 ? 0 : 1); + // Check the first non-undef element for which half to use. + unsigned WhichResult = 2; + for (unsigned i = 0; i != NumElts; i++) { + if (M[i] >= 0) { + WhichResult = ((unsigned)M[i] == i * 2 ? 0 : 1); + break; + } + } + if (WhichResult == 2) + return false; + + // Check all elements match. for (unsigned i = 0; i != NumElts; ++i) { if (M[i] < 0) continue; // ignore UNDEF indices if ((unsigned)M[i] != 2 * i + WhichResult) return false; } - + WhichResultOut = WhichResult; return true; } diff --git a/llvm/lib/Target/AArch64/AArch64Processors.td b/llvm/lib/Target/AArch64/AArch64Processors.td index c50a8200dd898de41647b2c3cdc11ecd3ee9aee1..8772e51bf0ab42fff24d55d8e6b080ad3385c321 100644 --- a/llvm/lib/Target/AArch64/AArch64Processors.td +++ b/llvm/lib/Target/AArch64/AArch64Processors.td @@ -447,6 +447,15 @@ def TuneNeoverseN2 : SubtargetFeature<"neoversen2", "ARMProcFamily", "NeoverseN2 FeatureEnableSelectOptimize, FeaturePredictableSelectIsExpensive]>; +def TuneNeoverseN3 : SubtargetFeature<"neoversen3", "ARMProcFamily", "NeoverseN3", + "Neoverse N3 ARM processors", [ + FeatureFuseAES, + FeaturePostRAScheduler, + FeatureALULSLFast, + FeatureFuseAdrpAdd, + FeatureEnableSelectOptimize, + FeaturePredictableSelectIsExpensive]>; + def TuneNeoverse512TVB : SubtargetFeature<"neoverse512tvb", "ARMProcFamily", "Neoverse512TVB", "Neoverse 512-TVB ARM processors", [ FeatureFuseAES, @@ -476,6 +485,24 @@ def TuneNeoverseV2 : SubtargetFeature<"neoversev2", "ARMProcFamily", "NeoverseV2 FeatureEnableSelectOptimize, FeaturePredictableSelectIsExpensive]>; +def TuneNeoverseV3 : SubtargetFeature<"neoversev3", "ARMProcFamily", "NeoverseV3", + "Neoverse V3 ARM processors", [ + FeatureFuseAES, + FeatureALULSLFast, + FeatureFuseAdrpAdd, + FeaturePostRAScheduler, + FeatureEnableSelectOptimize, + FeaturePredictableSelectIsExpensive]>; + +def TuneNeoverseV3AE : SubtargetFeature<"neoversev3AE", "ARMProcFamily", "NeoverseV3", + "Neoverse V3AE ARM processors", [ + FeatureFuseAES, + FeatureALULSLFast, + FeatureFuseAdrpAdd, + FeaturePostRAScheduler, + FeatureEnableSelectOptimize, + FeaturePredictableSelectIsExpensive]>; + def TuneSaphira : SubtargetFeature<"saphira", "ARMProcFamily", "Saphira", "Qualcomm Saphira processors", [ FeaturePostRAScheduler, @@ -715,6 +742,10 @@ def ProcessorFeatures { FeatureMatMulInt8, FeatureMTE, FeatureSVE2, FeatureSVE2BitPerm, FeatureTRBE, FeaturePerfMon]; + list NeoverseN3 = [HasV9_2aOps, FeatureETE, FeatureFP16FML, + FeatureFullFP16, FeatureMTE, FeaturePerfMon, + FeatureRandGen, FeatureSPE, FeatureSPE_EEF, + FeatureSVE2BitPerm]; list Neoverse512TVB = [HasV8_4aOps, FeatureBF16, FeatureCacheDeepPersist, FeatureCrypto, FeatureFPARMv8, FeatureFP16FML, FeatureFullFP16, FeatureMatMulInt8, FeatureNEON, @@ -729,6 +760,14 @@ def ProcessorFeatures { FeaturePerfMon, FeatureETE, FeatureMatMulInt8, FeatureNEON, FeatureSVE2BitPerm, FeatureFP16FML, FeatureMTE, FeatureRandGen]; + list NeoverseV3 = [HasV9_2aOps, FeatureETE, FeatureFP16FML, + FeatureFullFP16, FeatureLS64, FeatureMTE, + FeaturePerfMon, FeatureRandGen, FeatureSPE, + FeatureSPE_EEF, FeatureSVE2BitPerm, FeatureBRBE]; + list NeoverseV3AE = [HasV9_2aOps, FeatureETE, FeatureFP16FML, + FeatureFullFP16, FeatureLS64, FeatureMTE, + FeaturePerfMon, FeatureRandGen, FeatureSPE, + FeatureSPE_EEF, FeatureSVE2BitPerm, FeatureBRBE]; list Saphira = [HasV8_4aOps, FeatureCrypto, FeatureFPARMv8, FeatureNEON, FeatureSPE, FeaturePerfMon]; list ThunderX = [HasV8_0aOps, FeatureCRC, FeatureCrypto, @@ -831,12 +870,18 @@ def : ProcessorModel<"neoverse-n1", NeoverseN1Model, ProcessorFeatures.NeoverseN1, [TuneNeoverseN1]>; def : ProcessorModel<"neoverse-n2", NeoverseN2Model, ProcessorFeatures.NeoverseN2, [TuneNeoverseN2]>; +def : ProcessorModel<"neoverse-n3", NeoverseN2Model, + ProcessorFeatures.NeoverseN3, [TuneNeoverseN3]>; def : ProcessorModel<"neoverse-512tvb", NeoverseV1Model, ProcessorFeatures.Neoverse512TVB, [TuneNeoverse512TVB]>; def : ProcessorModel<"neoverse-v1", NeoverseV1Model, ProcessorFeatures.NeoverseV1, [TuneNeoverseV1]>; def : ProcessorModel<"neoverse-v2", NeoverseV2Model, ProcessorFeatures.NeoverseV2, [TuneNeoverseV2]>; +def : ProcessorModel<"neoverse-v3", NeoverseV2Model, + ProcessorFeatures.NeoverseV3, [TuneNeoverseV3]>; +def : ProcessorModel<"neoverse-v3ae", NeoverseV2Model, + ProcessorFeatures.NeoverseV3AE, [TuneNeoverseV3AE]>; def : ProcessorModel<"exynos-m3", ExynosM3Model, ProcessorFeatures.ExynosM3, [TuneExynosM3]>; def : ProcessorModel<"exynos-m4", ExynosM4Model, ProcessorFeatures.ExynosM4, diff --git a/llvm/lib/Target/AArch64/AArch64RedundantCopyElimination.cpp b/llvm/lib/Target/AArch64/AArch64RedundantCopyElimination.cpp index 1494312886a40de8e35f0a77cb1213dced49e5c7..69fc13883f6b834a6c8239e1ef0c589ec1d1ca76 100644 --- a/llvm/lib/Target/AArch64/AArch64RedundantCopyElimination.cpp +++ b/llvm/lib/Target/AArch64/AArch64RedundantCopyElimination.cpp @@ -265,7 +265,7 @@ bool AArch64RedundantCopyElimination::knownRegValInBlock( } // Bail if we see an instruction that defines NZCV that we don't handle. - if (PredI.definesRegister(AArch64::NZCV)) + if (PredI.definesRegister(AArch64::NZCV, /*TRI=*/nullptr)) return false; // Track clobbered and used registers. diff --git a/llvm/lib/Target/AArch64/AArch64SMEInstrInfo.td b/llvm/lib/Target/AArch64/AArch64SMEInstrInfo.td index 2db0fa253434501f487e16621a4609a5eff74471..574178c8d5244c1223d04da1c618ad934aa27009 100644 --- a/llvm/lib/Target/AArch64/AArch64SMEInstrInfo.td +++ b/llvm/lib/Target/AArch64/AArch64SMEInstrInfo.td @@ -792,12 +792,14 @@ defm LUTI4_S_2ZTZI : sme2p1_luti4_vector_vg2_index<"luti4">; defm LUTI4_S_4ZTZI : sme2p1_luti4_vector_vg4_index<"luti4">; } -let Predicates = [HasSME2p1, HasSMEF16F16] in { +let Predicates = [HasSMEF16F16orSMEF8F16] in { defm FADD_VG2_M2Z_H : sme2_multivec_accum_add_sub_vg2<"fadd", 0b0100, MatrixOp16, ZZ_h_mul_r, nxv8f16, null_frag>; defm FADD_VG4_M4Z_H : sme2_multivec_accum_add_sub_vg4<"fadd", 0b0100, MatrixOp16, ZZZZ_h_mul_r, nxv8f16, null_frag>; defm FSUB_VG2_M2Z_H : sme2_multivec_accum_add_sub_vg2<"fsub", 0b0101, MatrixOp16, ZZ_h_mul_r, nxv8f16, null_frag>; defm FSUB_VG4_M4Z_H : sme2_multivec_accum_add_sub_vg4<"fsub", 0b0101, MatrixOp16, ZZZZ_h_mul_r, nxv8f16, null_frag>; +} +let Predicates = [HasSMEF16F16] in { defm FMLA_VG2_M2ZZI_H : sme2p1_multi_vec_array_vg2_index_16b<"fmla", 0b00, 0b100, ZZ_h_mul_r, ZPR4b16>; defm FMLA_VG4_M4ZZI_H : sme2p1_multi_vec_array_vg4_index_16b<"fmla", 0b000, ZZZZ_h_mul_r, ZPR4b16>; defm FMLA_VG2_M2ZZ_H : sme2_dot_mla_add_sub_array_vg24_single<"fmla", 0b0011100, MatrixOp16, ZZ_h, ZPR4b16>; diff --git a/llvm/lib/Target/AArch64/AArch64SVEInstrInfo.td b/llvm/lib/Target/AArch64/AArch64SVEInstrInfo.td index 705fa523a8b8f235a6e33c976e38c069e6081aae..3331ba7f99a161ced244981bde6e67770d2cc9fb 100644 --- a/llvm/lib/Target/AArch64/AArch64SVEInstrInfo.td +++ b/llvm/lib/Target/AArch64/AArch64SVEInstrInfo.td @@ -2517,6 +2517,23 @@ let Predicates = [HasSVEorSME] in { def : Pat<(vscale (sve_cntd_imm_neg i32:$imm)), (SUBXrs XZR, (CNTD_XPiI 31, $imm), 0)>; } + // Add NoUseScalarIncVL to avoid affecting for patterns with UseScalarIncVL + let Predicates = [HasSVEorSME, NoUseScalarIncVL] in { + def : Pat<(add GPR64:$op, (vscale (sve_cnth_imm_neg i32:$imm))), + (SUBXrs GPR64:$op, (CNTH_XPiI 31, $imm), 0)>; + def : Pat<(add GPR64:$op, (vscale (sve_cntw_imm_neg i32:$imm))), + (SUBXrs GPR64:$op, (CNTW_XPiI 31, $imm), 0)>; + def : Pat<(add GPR64:$op, (vscale (sve_cntd_imm_neg i32:$imm))), + (SUBXrs GPR64:$op, (CNTD_XPiI 31, $imm), 0)>; + + def : Pat<(add GPR32:$op, (i32 (trunc (vscale (sve_cnth_imm_neg i32:$imm))))), + (SUBSWrr GPR32:$op, (EXTRACT_SUBREG (CNTH_XPiI 31, $imm), sub_32))>; + def : Pat<(add GPR32:$op, (i32 (trunc (vscale (sve_cntw_imm_neg i32:$imm))))), + (SUBSWrr GPR32:$op, (EXTRACT_SUBREG (CNTW_XPiI 31, $imm), sub_32))>; + def : Pat<(add GPR32:$op, (i32 (trunc (vscale (sve_cntd_imm_neg i32:$imm))))), + (SUBSWrr GPR32:$op, (EXTRACT_SUBREG (CNTD_XPiI 31, $imm), sub_32))>; + } + let AddedComplexity = 5 in { def : Pat<(nxv8i16 (add ZPR:$op, (nxv8i16 (splat_vector (i32 (trunc (vscale (sve_cnth_imm i32:$imm)))))))), (INCH_ZPiI ZPR:$op, 31, $imm)>; @@ -4102,7 +4119,7 @@ defm BFCLAMP_ZZZ : sve2p1_bfclamp<"bfclamp", AArch64fclamp>; // SME2.1 or SVE2.1 instructions //===----------------------------------------------------------------------===// let Predicates = [HasSVE2p1_or_HasSME2p1] in { -defm FADDQV : sve2p1_fp_reduction_q<0b000, "faddqv", int_aarch64_sve_addqv>; +defm FADDQV : sve2p1_fp_reduction_q<0b000, "faddqv", int_aarch64_sve_faddqv>; defm FMAXNMQV : sve2p1_fp_reduction_q<0b100, "fmaxnmqv", int_aarch64_sve_fmaxnmqv>; defm FMINNMQV : sve2p1_fp_reduction_q<0b101, "fminnmqv", int_aarch64_sve_fminnmqv>; defm FMAXQV : sve2p1_fp_reduction_q<0b110, "fmaxqv", int_aarch64_sve_fmaxqv>; diff --git a/llvm/lib/Target/AArch64/AArch64Subtarget.cpp b/llvm/lib/Target/AArch64/AArch64Subtarget.cpp index 9eb1ecbb031580343700647606cafd1981f8257e..7d34dd1c7768783fc9e1d031586b2e641c9cf64c 100644 --- a/llvm/lib/Target/AArch64/AArch64Subtarget.cpp +++ b/llvm/lib/Target/AArch64/AArch64Subtarget.cpp @@ -144,7 +144,6 @@ void AArch64Subtarget::initializeProperties(bool HasMinSize) { case CortexA78C: case CortexR82: case CortexX1: - case CortexX1C: PrefFunctionAlignment = Align(16); PrefLoopAlignment = Align(32); MaxBytesForLoopAlignment = 16; @@ -235,7 +234,9 @@ void AArch64Subtarget::initializeProperties(bool HasMinSize) { MaxBytesForLoopAlignment = 16; break; case NeoverseN2: + case NeoverseN3: case NeoverseV2: + case NeoverseV3: PrefFunctionAlignment = Align(16); PrefLoopAlignment = Align(32); MaxBytesForLoopAlignment = 16; diff --git a/llvm/lib/Target/AArch64/AArch64Subtarget.h b/llvm/lib/Target/AArch64/AArch64Subtarget.h index c5ebd4c6cc615ae02dc073da7caff2fbe3f84b5c..3f3eefc4f68077cbbb3856c3c15c1f2ee153f18f 100644 --- a/llvm/lib/Target/AArch64/AArch64Subtarget.h +++ b/llvm/lib/Target/AArch64/AArch64Subtarget.h @@ -39,61 +39,9 @@ class AArch64Subtarget final : public AArch64GenSubtargetInfo { public: enum ARMProcFamilyEnum : uint8_t { Others, - A64FX, - Ampere1, - Ampere1A, - Ampere1B, - AppleA7, - AppleA10, - AppleA11, - AppleA12, - AppleA13, - AppleA14, - AppleA15, - AppleA16, - AppleA17, - Carmel, - CortexA35, - CortexA53, - CortexA55, - CortexA510, - CortexA520, - CortexA57, - CortexA65, - CortexA72, - CortexA73, - CortexA75, - CortexA76, - CortexA77, - CortexA78, - CortexA78AE, - CortexA78C, - CortexA710, - CortexA715, - CortexA720, - CortexR82, - CortexX1, - CortexX1C, - CortexX2, - CortexX3, - CortexX4, - ExynosM3, - Falkor, - Kryo, - NeoverseE1, - NeoverseN1, - NeoverseN2, - Neoverse512TVB, - NeoverseV1, - NeoverseV2, - Saphira, - ThunderX2T99, - ThunderX, - ThunderXT81, - ThunderXT83, - ThunderXT88, - ThunderX3T110, - TSV110 +#define ARM_PROCESSOR_FAMILY(ENUM) ENUM, +#include "llvm/TargetParser/AArch64TargetParserDef.inc" +#undef ARM_PROCESSOR_FAMILY }; protected: diff --git a/llvm/lib/Target/AArch64/AArch64TargetTransformInfo.cpp b/llvm/lib/Target/AArch64/AArch64TargetTransformInfo.cpp index 700242b88346cbcba1e1b304cf8741a7f999eb7d..af3a94a0faece8a141f7f1f865a324841b1a5702 100644 --- a/llvm/lib/Target/AArch64/AArch64TargetTransformInfo.cpp +++ b/llvm/lib/Target/AArch64/AArch64TargetTransformInfo.cpp @@ -790,6 +790,27 @@ AArch64TTIImpl::getIntrinsicInstrCost(const IntrinsicCostAttributes &ICA, break; return TyL.first + ExtraCost; } + case Intrinsic::get_active_lane_mask: { + auto *RetTy = dyn_cast(ICA.getReturnType()); + if (RetTy) { + EVT RetVT = getTLI()->getValueType(DL, RetTy); + EVT OpVT = getTLI()->getValueType(DL, ICA.getArgTypes()[0]); + if (!getTLI()->shouldExpandGetActiveLaneMask(RetVT, OpVT) && + !getTLI()->isTypeLegal(RetVT)) { + // We don't have enough context at this point to determine if the mask + // is going to be kept live after the block, which will force the vXi1 + // type to be expanded to legal vectors of integers, e.g. v4i1->v4i32. + // For now, we just assume the vectorizer created this intrinsic and + // the result will be the input for a PHI. In this case the cost will + // be extremely high for fixed-width vectors. + // NOTE: getScalarizationOverhead returns a cost that's far too + // pessimistic for the actual generated codegen. In reality there are + // two instructions generated per lane. + return RetTy->getNumElements() * 2; + } + } + break; + } default: break; } diff --git a/llvm/lib/Target/AArch64/AArch64TargetTransformInfo.h b/llvm/lib/Target/AArch64/AArch64TargetTransformInfo.h index dba384481f6a349274dbf9b307463869f0236bda..678c132e6a80a1bee5144dc13fd4a16789a578a2 100644 --- a/llvm/lib/Target/AArch64/AArch64TargetTransformInfo.h +++ b/llvm/lib/Target/AArch64/AArch64TargetTransformInfo.h @@ -203,7 +203,7 @@ public: unsigned Opcode, Type *Ty, TTI::TargetCostKind CostKind, TTI::OperandValueInfo Op1Info = {TTI::OK_AnyValue, TTI::OP_None}, TTI::OperandValueInfo Op2Info = {TTI::OK_AnyValue, TTI::OP_None}, - ArrayRef Args = ArrayRef(), + ArrayRef Args = std::nullopt, const Instruction *CxtI = nullptr); InstructionCost getAddressComputationCost(Type *Ty, ScalarEvolution *SE, diff --git a/llvm/lib/Target/AArch64/GISel/AArch64LegalizerInfo.cpp b/llvm/lib/Target/AArch64/GISel/AArch64LegalizerInfo.cpp index 85dd0f2eb192d93863406ee77afe0389b0188f85..f42c415a9e44f354a982ca48d134abbb14ec5469 100644 --- a/llvm/lib/Target/AArch64/GISel/AArch64LegalizerInfo.cpp +++ b/llvm/lib/Target/AArch64/GISel/AArch64LegalizerInfo.cpp @@ -93,18 +93,12 @@ AArch64LegalizerInfo::AArch64LegalizerInfo(const AArch64Subtarget &ST) .legalFor(PackedVectorAllTypeList) .widenScalarToNextPow2(0) .clampScalar(0, s8, s64) - .fewerElementsIf( - [=](const LegalityQuery &Query) { - return Query.Types[0].isVector() && - (Query.Types[0].getElementType() != s64 || - Query.Types[0].getNumElements() != 2); - }, - [=](const LegalityQuery &Query) { - LLT EltTy = Query.Types[0].getElementType(); - if (EltTy == s64) - return std::make_pair(0, LLT::fixed_vector(2, 64)); - return std::make_pair(0, EltTy); - }); + .moreElementsToNextPow2(0) + .widenVectorEltsToVectorMinSize(0, 64) + .clampNumElements(0, v8s8, v16s8) + .clampNumElements(0, v4s16, v8s16) + .clampNumElements(0, v2s32, v4s32) + .clampNumElements(0, v2s64, v2s64); getActionDefinitionsBuilder(G_PHI) .legalFor({p0, s16, s32, s64}) diff --git a/llvm/lib/Target/AArch64/GISel/AArch64PostSelectOptimize.cpp b/llvm/lib/Target/AArch64/GISel/AArch64PostSelectOptimize.cpp index 94584e20f5ab3fb2e45631db22faaca43c16a33e..11866f2dd18649003cef2840188a4c05b28d3c45 100644 --- a/llvm/lib/Target/AArch64/GISel/AArch64PostSelectOptimize.cpp +++ b/llvm/lib/Target/AArch64/GISel/AArch64PostSelectOptimize.cpp @@ -199,10 +199,11 @@ bool AArch64PostSelectOptimize::optimizeNZCVDefs(MachineBasicBlock &MBB) { for (auto &II : instructionsWithoutDebug(MBB.rbegin(), MBB.rend())) { bool NZCVDead = LRU.available(AArch64::NZCV); - if (NZCVDead && II.definesRegister(AArch64::NZCV)) { + if (NZCVDead && II.definesRegister(AArch64::NZCV, /*TRI=*/nullptr)) { // The instruction defines NZCV, but NZCV is dead. unsigned NewOpc = getNonFlagSettingVariant(II.getOpcode()); - int DeadNZCVIdx = II.findRegisterDefOperandIdx(AArch64::NZCV); + int DeadNZCVIdx = + II.findRegisterDefOperandIdx(AArch64::NZCV, /*TRI=*/nullptr); if (DeadNZCVIdx != -1) { if (NewOpc) { // If there is an equivalent non-flag-setting op, we convert. diff --git a/llvm/lib/Target/AArch64/MCTargetDesc/AArch64ELFObjectWriter.cpp b/llvm/lib/Target/AArch64/MCTargetDesc/AArch64ELFObjectWriter.cpp index abbf20257edcc039dc4c511c57043432cdb1c4e4..b4c5cde5fd888d10c8c38dfe27e9120f8b5187df 100644 --- a/llvm/lib/Target/AArch64/MCTargetDesc/AArch64ELFObjectWriter.cpp +++ b/llvm/lib/Target/AArch64/MCTargetDesc/AArch64ELFObjectWriter.cpp @@ -146,8 +146,8 @@ unsigned AArch64ELFObjectWriter::getRelocType(MCContext &Ctx, "ILP32 8 byte PC relative data " "relocation not supported (LP64 eqv: PREL64)"); return ELF::R_AARCH64_NONE; - } else - return ELF::R_AARCH64_PREL64; + } + return ELF::R_AARCH64_PREL64; case AArch64::fixup_aarch64_pcrel_adr_imm21: if (SymLoc != AArch64MCExpr::VK_ABS) Ctx.reportError(Fixup.getLoc(), @@ -162,9 +162,8 @@ unsigned AArch64ELFObjectWriter::getRelocType(MCContext &Ctx, "invalid fixup for 32-bit pcrel ADRP instruction " "VK_ABS VK_NC"); return ELF::R_AARCH64_NONE; - } else { - return ELF::R_AARCH64_ADR_PREL_PG_HI21_NC; } + return ELF::R_AARCH64_ADR_PREL_PG_HI21_NC; } if (SymLoc == AArch64MCExpr::VK_GOT && !IsNC) return R_CLS(ADR_GOT_PAGE); @@ -286,14 +285,12 @@ unsigned AArch64ELFObjectWriter::getRelocType(MCContext &Ctx, if (SymLoc == AArch64MCExpr::VK_TPREL && IsNC) return R_CLS(TLSLE_LDST32_TPREL_LO12_NC); if (SymLoc == AArch64MCExpr::VK_GOT && IsNC) { - if (IsILP32) { + if (IsILP32) return ELF::R_AARCH64_P32_LD32_GOT_LO12_NC; - } else { - Ctx.reportError(Fixup.getLoc(), - "LP64 4 byte unchecked GOT load/store relocation " - "not supported (ILP32 eqv: LD32_GOT_LO12_NC"); - return ELF::R_AARCH64_NONE; - } + Ctx.reportError(Fixup.getLoc(), + "LP64 4 byte unchecked GOT load/store relocation " + "not supported (ILP32 eqv: LD32_GOT_LO12_NC"); + return ELF::R_AARCH64_NONE; } if (SymLoc == AArch64MCExpr::VK_GOT && !IsNC) { if (IsILP32) { @@ -309,25 +306,20 @@ unsigned AArch64ELFObjectWriter::getRelocType(MCContext &Ctx, return ELF::R_AARCH64_NONE; } if (SymLoc == AArch64MCExpr::VK_GOTTPREL && IsNC) { - if (IsILP32) { + if (IsILP32) return ELF::R_AARCH64_P32_TLSIE_LD32_GOTTPREL_LO12_NC; - } else { - Ctx.reportError(Fixup.getLoc(), - "LP64 32-bit load/store " - "relocation not supported (ILP32 eqv: " - "TLSIE_LD32_GOTTPREL_LO12_NC)"); - return ELF::R_AARCH64_NONE; - } + Ctx.reportError(Fixup.getLoc(), "LP64 32-bit load/store " + "relocation not supported (ILP32 eqv: " + "TLSIE_LD32_GOTTPREL_LO12_NC)"); + return ELF::R_AARCH64_NONE; } if (SymLoc == AArch64MCExpr::VK_TLSDESC && !IsNC) { - if (IsILP32) { + if (IsILP32) return ELF::R_AARCH64_P32_TLSDESC_LD32_LO12; - } else { - Ctx.reportError(Fixup.getLoc(), - "LP64 4 byte TLSDESC load/store relocation " - "not supported (ILP32 eqv: TLSDESC_LD64_LO12)"); - return ELF::R_AARCH64_NONE; - } + Ctx.reportError(Fixup.getLoc(), + "LP64 4 byte TLSDESC load/store relocation " + "not supported (ILP32 eqv: TLSDESC_LD64_LO12)"); + return ELF::R_AARCH64_NONE; } Ctx.reportError(Fixup.getLoc(), @@ -344,12 +336,11 @@ unsigned AArch64ELFObjectWriter::getRelocType(MCContext &Ctx, if (AddressLoc == AArch64MCExpr::VK_LO15) return ELF::R_AARCH64_LD64_GOTPAGE_LO15; return ELF::R_AARCH64_LD64_GOT_LO12_NC; - } else { - Ctx.reportError(Fixup.getLoc(), "ILP32 64-bit load/store " - "relocation not supported (LP64 eqv: " - "LD64_GOT_LO12_NC)"); - return ELF::R_AARCH64_NONE; } + Ctx.reportError(Fixup.getLoc(), "ILP32 64-bit load/store " + "relocation not supported (LP64 eqv: " + "LD64_GOT_LO12_NC)"); + return ELF::R_AARCH64_NONE; } if (SymLoc == AArch64MCExpr::VK_DTPREL && !IsNC) return R_CLS(TLSLD_LDST64_DTPREL_LO12); @@ -360,24 +351,20 @@ unsigned AArch64ELFObjectWriter::getRelocType(MCContext &Ctx, if (SymLoc == AArch64MCExpr::VK_TPREL && IsNC) return R_CLS(TLSLE_LDST64_TPREL_LO12_NC); if (SymLoc == AArch64MCExpr::VK_GOTTPREL && IsNC) { - if (!IsILP32) { + if (!IsILP32) return ELF::R_AARCH64_TLSIE_LD64_GOTTPREL_LO12_NC; - } else { - Ctx.reportError(Fixup.getLoc(), "ILP32 64-bit load/store " - "relocation not supported (LP64 eqv: " - "TLSIE_LD64_GOTTPREL_LO12_NC)"); - return ELF::R_AARCH64_NONE; - } + Ctx.reportError(Fixup.getLoc(), "ILP32 64-bit load/store " + "relocation not supported (LP64 eqv: " + "TLSIE_LD64_GOTTPREL_LO12_NC)"); + return ELF::R_AARCH64_NONE; } if (SymLoc == AArch64MCExpr::VK_TLSDESC) { - if (!IsILP32) { + if (!IsILP32) return ELF::R_AARCH64_TLSDESC_LD64_LO12; - } else { - Ctx.reportError(Fixup.getLoc(), "ILP32 64-bit load/store " - "relocation not supported (LP64 eqv: " - "TLSDESC_LD64_LO12)"); - return ELF::R_AARCH64_NONE; - } + Ctx.reportError(Fixup.getLoc(), "ILP32 64-bit load/store " + "relocation not supported (LP64 eqv: " + "TLSDESC_LD64_LO12)"); + return ELF::R_AARCH64_NONE; } Ctx.reportError(Fixup.getLoc(), "invalid fixup for 64-bit load/store instruction"); diff --git a/llvm/lib/Target/AArch64/MCTargetDesc/AArch64ELFStreamer.cpp b/llvm/lib/Target/AArch64/MCTargetDesc/AArch64ELFStreamer.cpp index ad21f2673a64128c0ac86bb21aa1ccb6ab6b77dc..f5bea3336cbf73dc9b1b7411033a4c17ec2a9f48 100644 --- a/llvm/lib/Target/AArch64/MCTargetDesc/AArch64ELFStreamer.cpp +++ b/llvm/lib/Target/AArch64/MCTargetDesc/AArch64ELFStreamer.cpp @@ -306,13 +306,12 @@ llvm::createAArch64AsmTargetStreamer(MCStreamer &S, formatted_raw_ostream &OS, return new AArch64TargetAsmStreamer(S, OS); } -MCELFStreamer *llvm::createAArch64ELFStreamer( - MCContext &Context, std::unique_ptr TAB, - std::unique_ptr OW, std::unique_ptr Emitter, - bool RelaxAll) { +MCELFStreamer * +llvm::createAArch64ELFStreamer(MCContext &Context, + std::unique_ptr TAB, + std::unique_ptr OW, + std::unique_ptr Emitter) { AArch64ELFStreamer *S = new AArch64ELFStreamer( Context, std::move(TAB), std::move(OW), std::move(Emitter)); - if (RelaxAll) - S->getAssembler().setRelaxAll(true); return S; } diff --git a/llvm/lib/Target/AArch64/MCTargetDesc/AArch64ELFStreamer.h b/llvm/lib/Target/AArch64/MCTargetDesc/AArch64ELFStreamer.h index 25c609ee1496b3a652c1b9f54e27fa2eb81b33dd..e6df79ba19d4cfdb92e0179f184fec935fa23a21 100644 --- a/llvm/lib/Target/AArch64/MCTargetDesc/AArch64ELFStreamer.h +++ b/llvm/lib/Target/AArch64/MCTargetDesc/AArch64ELFStreamer.h @@ -20,8 +20,7 @@ namespace llvm { MCELFStreamer *createAArch64ELFStreamer(MCContext &Context, std::unique_ptr TAB, std::unique_ptr OW, - std::unique_ptr Emitter, - bool RelaxAll); + std::unique_ptr Emitter); } #endif diff --git a/llvm/lib/Target/AArch64/MCTargetDesc/AArch64MCTargetDesc.cpp b/llvm/lib/Target/AArch64/MCTargetDesc/AArch64MCTargetDesc.cpp index 043f0a03b7975697caa44c2ff7d40c172a5cce27..0dd4a78f962d41c1396ead4d516ad4de1461cfca 100644 --- a/llvm/lib/Target/AArch64/MCTargetDesc/AArch64MCTargetDesc.cpp +++ b/llvm/lib/Target/AArch64/MCTargetDesc/AArch64MCTargetDesc.cpp @@ -378,30 +378,28 @@ static MCInstPrinter *createAArch64MCInstPrinter(const Triple &T, static MCStreamer *createELFStreamer(const Triple &T, MCContext &Ctx, std::unique_ptr &&TAB, std::unique_ptr &&OW, - std::unique_ptr &&Emitter, - bool RelaxAll) { + std::unique_ptr &&Emitter) { return createAArch64ELFStreamer(Ctx, std::move(TAB), std::move(OW), - std::move(Emitter), RelaxAll); + std::move(Emitter)); } static MCStreamer *createMachOStreamer(MCContext &Ctx, std::unique_ptr &&TAB, std::unique_ptr &&OW, std::unique_ptr &&Emitter, - bool RelaxAll, bool DWARFMustBeAtTheEnd) { return createMachOStreamer(Ctx, std::move(TAB), std::move(OW), - std::move(Emitter), RelaxAll, DWARFMustBeAtTheEnd, + std::move(Emitter), DWARFMustBeAtTheEnd, /*LabelSections*/ true); } static MCStreamer * createWinCOFFStreamer(MCContext &Ctx, std::unique_ptr &&TAB, std::unique_ptr &&OW, - std::unique_ptr &&Emitter, bool RelaxAll, + std::unique_ptr &&Emitter, bool IncrementalLinkerCompatible) { return createAArch64WinCOFFStreamer(Ctx, std::move(TAB), std::move(OW), - std::move(Emitter), RelaxAll, + std::move(Emitter), IncrementalLinkerCompatible); } diff --git a/llvm/lib/Target/AArch64/MCTargetDesc/AArch64WinCOFFStreamer.cpp b/llvm/lib/Target/AArch64/MCTargetDesc/AArch64WinCOFFStreamer.cpp index 438ac6cc47885ed035d465c70a4f782a30350fc5..c25cc2e99adcabe3e69ae45456b1679c588d6314 100644 --- a/llvm/lib/Target/AArch64/MCTargetDesc/AArch64WinCOFFStreamer.cpp +++ b/llvm/lib/Target/AArch64/MCTargetDesc/AArch64WinCOFFStreamer.cpp @@ -294,7 +294,7 @@ void AArch64TargetWinCOFFStreamer::emitARM64WinCFISaveAnyRegQPX(unsigned Reg, MCWinCOFFStreamer *llvm::createAArch64WinCOFFStreamer( MCContext &Context, std::unique_ptr MAB, std::unique_ptr OW, std::unique_ptr Emitter, - bool RelaxAll, bool IncrementalLinkerCompatible) { + bool IncrementalLinkerCompatible) { auto *S = new AArch64WinCOFFStreamer(Context, std::move(MAB), std::move(Emitter), std::move(OW)); S->getAssembler().setIncrementalLinkerCompatible(IncrementalLinkerCompatible); diff --git a/llvm/lib/Target/AArch64/MCTargetDesc/AArch64WinCOFFStreamer.h b/llvm/lib/Target/AArch64/MCTargetDesc/AArch64WinCOFFStreamer.h index 8c0656652eed2afc3b4600020df54c23c94ae8c5..a13b1a451be5fd854b186846f18eec6252065ffd 100644 --- a/llvm/lib/Target/AArch64/MCTargetDesc/AArch64WinCOFFStreamer.h +++ b/llvm/lib/Target/AArch64/MCTargetDesc/AArch64WinCOFFStreamer.h @@ -21,7 +21,7 @@ namespace llvm { MCWinCOFFStreamer *createAArch64WinCOFFStreamer( MCContext &Context, std::unique_ptr TAB, std::unique_ptr OW, std::unique_ptr Emitter, - bool RelaxAll, bool IncrementalLinkerCompatible); + bool IncrementalLinkerCompatible); } // end llvm namespace #endif diff --git a/llvm/lib/Target/AMDGPU/AMDGPU.td b/llvm/lib/Target/AMDGPU/AMDGPU.td index 5c2c6d4b13c66975ad0b05af485fc44f01c1c48b..8abe9920c02c2d35570d4e88a927c059d3816178 100644 --- a/llvm/lib/Target/AMDGPU/AMDGPU.td +++ b/llvm/lib/Target/AMDGPU/AMDGPU.td @@ -307,6 +307,12 @@ def FeatureMSAALoadDstSelBug : SubtargetFeature<"msaa-load-dst-sel-bug", "MSAA loads not honoring dst_sel bug" >; +def FeaturePrivEnabledTrap2NopBug : SubtargetFeature<"priv-enabled-trap2-nop-bug", + "HasPrivEnabledTrap2NopBug", + "true", + "Hardware that runs with PRIV=1 interpreting 's_trap 2' as a nop bug" +>; + class SubtargetFeatureLDSBankCount : SubtargetFeature < "ldsbankcount"#Value, "LDSBankCount", @@ -1487,13 +1493,16 @@ def FeatureISAVersion11_Generic: FeatureSet< [FeatureMSAALoadDstSelBug, FeatureVALUTransUseHazard, FeatureUserSGPRInit16Bug, + FeatureMADIntraFwdBug, + FeaturePrivEnabledTrap2NopBug, FeatureRequiresCOV6])>; def FeatureISAVersion11_0_Common : FeatureSet< !listconcat(FeatureISAVersion11_Common.Features, [FeatureMSAALoadDstSelBug, FeatureVALUTransUseHazard, - FeatureMADIntraFwdBug])>; + FeatureMADIntraFwdBug, + FeaturePrivEnabledTrap2NopBug])>; def FeatureISAVersion11_0_0 : FeatureSet< !listconcat(FeatureISAVersion11_0_Common.Features, diff --git a/llvm/lib/Target/AMDGPU/AMDGPUISelLowering.cpp b/llvm/lib/Target/AMDGPU/AMDGPUISelLowering.cpp index db69d50799e70b92932cfb1645d6aa20bb949167..7993b63121110ce0212d839c7fbc00e6d4eea772 100644 --- a/llvm/lib/Target/AMDGPU/AMDGPUISelLowering.cpp +++ b/llvm/lib/Target/AMDGPU/AMDGPUISelLowering.cpp @@ -148,6 +148,19 @@ AMDGPUTargetLowering::AMDGPUTargetLowering(const TargetMachine &TM, setOperationAction(ISD::LOAD, MVT::i128, Promote); AddPromotedToType(ISD::LOAD, MVT::i128, MVT::v4i32); + // TODO: Would be better to consume as directly legal + setOperationAction(ISD::ATOMIC_LOAD, MVT::f32, Promote); + AddPromotedToType(ISD::ATOMIC_LOAD, MVT::f32, MVT::i32); + + setOperationAction(ISD::ATOMIC_LOAD, MVT::f64, Promote); + AddPromotedToType(ISD::ATOMIC_LOAD, MVT::f64, MVT::i64); + + setOperationAction(ISD::ATOMIC_LOAD, MVT::f16, Promote); + AddPromotedToType(ISD::ATOMIC_LOAD, MVT::f16, MVT::i16); + + setOperationAction(ISD::ATOMIC_LOAD, MVT::bf16, Promote); + AddPromotedToType(ISD::ATOMIC_LOAD, MVT::bf16, MVT::i16); + // There are no 64-bit extloads. These should be done as a 32-bit extload and // an extension to 64-bit. for (MVT VT : MVT::integer_valuetypes()) @@ -5377,6 +5390,7 @@ const char* AMDGPUTargetLowering::getTargetNodeName(unsigned Opcode) const { NODE_NAME_CASE(RETURN_TO_EPILOG) NODE_NAME_CASE(ENDPGM) NODE_NAME_CASE(ENDPGM_TRAP) + NODE_NAME_CASE(SIMULATED_TRAP) NODE_NAME_CASE(DWORDADDR) NODE_NAME_CASE(FRACT) NODE_NAME_CASE(SETCC) diff --git a/llvm/lib/Target/AMDGPU/AMDGPUISelLowering.h b/llvm/lib/Target/AMDGPU/AMDGPUISelLowering.h index f10a357125e56229379971fd88f20acea69a71d9..269c414521dbcc3a6c677cd1e0718b1cdfbc4f3c 100644 --- a/llvm/lib/Target/AMDGPU/AMDGPUISelLowering.h +++ b/llvm/lib/Target/AMDGPU/AMDGPUISelLowering.h @@ -230,6 +230,12 @@ public: bool isCheapToSpeculateCtlz(Type *Ty) const override; bool isSDNodeAlwaysUniform(const SDNode *N) const override; + + // FIXME: This hook should not exist + AtomicExpansionKind shouldCastAtomicLoadInIR(LoadInst *LI) const override { + return AtomicExpansionKind::None; + } + static CCAssignFn *CCAssignFnForCall(CallingConv::ID CC, bool IsVarArg); static CCAssignFn *CCAssignFnForReturn(CallingConv::ID CC, bool IsVarArg); @@ -407,6 +413,9 @@ enum NodeType : unsigned { // s_endpgm, but we may want to insert it in the middle of the block. ENDPGM_TRAP, + // "s_trap 2" equivalent on hardware that does not support it. + SIMULATED_TRAP, + // Return to a shader part's epilog code. RETURN_TO_EPILOG, diff --git a/llvm/lib/Target/AMDGPU/AMDGPUInstrInfo.td b/llvm/lib/Target/AMDGPU/AMDGPUInstrInfo.td index 82f58ea38fd0a7221815b003795f6ed1af25b32b..702f6e67c552718e48705770d585c634a5846822 100644 --- a/llvm/lib/Target/AMDGPU/AMDGPUInstrInfo.td +++ b/llvm/lib/Target/AMDGPU/AMDGPUInstrInfo.td @@ -377,6 +377,8 @@ def AMDGPUendpgm : SDNode<"AMDGPUISD::ENDPGM", SDTNone, [SDNPHasChain, SDNPOptInGlue]>; def AMDGPUendpgm_trap : SDNode<"AMDGPUISD::ENDPGM_TRAP", SDTNone, [SDNPHasChain]>; +def AMDGPUsimulated_trap : SDNode<"AMDGPUISD::SIMULATED_TRAP", SDTNone, + [SDNPHasChain]>; def AMDGPUreturn_to_epilog : SDNode<"AMDGPUISD::RETURN_TO_EPILOG", SDTNone, [SDNPHasChain, SDNPOptInGlue, SDNPVariadic]>; diff --git a/llvm/lib/Target/AMDGPU/AMDGPULegalizerInfo.cpp b/llvm/lib/Target/AMDGPU/AMDGPULegalizerInfo.cpp index 780dfaae11ef3ed81a4f14ea61404dfb62ddeddc..6cd93abff1a42908af33ff80716669d0c463621f 100644 --- a/llvm/lib/Target/AMDGPU/AMDGPULegalizerInfo.cpp +++ b/llvm/lib/Target/AMDGPU/AMDGPULegalizerInfo.cpp @@ -4248,7 +4248,8 @@ bool AMDGPULegalizerInfo::loadInputValue( AMDGPU::isEntryFunctionCC(CC) && !MFI->hasWorkGroupIDZ() ? ~0u : 0xFFFFu); const ArgDescriptor WorkGroupIDZ = ArgDescriptor::createRegister(AMDGPU::TTMP7, 0xFFFF0000u); - if (ST.hasArchitectedSGPRs() && AMDGPU::isCompute(CC)) { + if (ST.hasArchitectedSGPRs() && + (AMDGPU::isCompute(CC) || CC == CallingConv::AMDGPU_Gfx)) { switch (ArgType) { case AMDGPUFunctionArgInfo::WORKGROUP_ID_X: Arg = &WorkGroupIDX; @@ -6724,8 +6725,18 @@ bool AMDGPULegalizerInfo::legalizeTrapHsaQueuePtr( return true; } -bool AMDGPULegalizerInfo::legalizeTrapHsa( - MachineInstr &MI, MachineRegisterInfo &MRI, MachineIRBuilder &B) const { +bool AMDGPULegalizerInfo::legalizeTrapHsa(MachineInstr &MI, + MachineRegisterInfo &MRI, + MachineIRBuilder &B) const { + // We need to simulate the 's_trap 2' instruction on targets that run in + // PRIV=1 (where it is treated as a nop). + if (ST.hasPrivEnabledTrap2NopBug()) { + ST.getInstrInfo()->insertSimulatedTrap(MRI, B.getMBB(), MI, + MI.getDebugLoc()); + MI.eraseFromParent(); + return true; + } + B.buildInstr(AMDGPU::S_TRAP) .addImm(static_cast(GCNSubtarget::TrapID::LLVMAMDHSATrap)); MI.eraseFromParent(); diff --git a/llvm/lib/Target/AMDGPU/AMDGPURegisterBankInfo.cpp b/llvm/lib/Target/AMDGPU/AMDGPURegisterBankInfo.cpp index aa4ec785bf02a3ef8f857a88a5b3b9052f291d0a..56345d14a331ca75063534cb8461482e4acb057f 100644 --- a/llvm/lib/Target/AMDGPU/AMDGPURegisterBankInfo.cpp +++ b/llvm/lib/Target/AMDGPU/AMDGPURegisterBankInfo.cpp @@ -2261,7 +2261,7 @@ void AMDGPURegisterBankInfo::applyMappingImpl( case AMDGPU::G_FCMP: if (!Subtarget.hasSALUFloatInsts()) break; - LLVM_FALLTHROUGH; + [[fallthrough]]; case AMDGPU::G_ICMP: case AMDGPU::G_UADDO: case AMDGPU::G_USUBO: diff --git a/llvm/lib/Target/AMDGPU/AMDGPUTargetTransformInfo.h b/llvm/lib/Target/AMDGPU/AMDGPUTargetTransformInfo.h index 0dab3a982779435225ab02d5b6dc84727789fbe5..b423df17302ca20e2c87ac1b74b05ee609ce1358 100644 --- a/llvm/lib/Target/AMDGPU/AMDGPUTargetTransformInfo.h +++ b/llvm/lib/Target/AMDGPU/AMDGPUTargetTransformInfo.h @@ -155,7 +155,7 @@ public: unsigned Opcode, Type *Ty, TTI::TargetCostKind CostKind, TTI::OperandValueInfo Op1Info = {TTI::OK_AnyValue, TTI::OP_None}, TTI::OperandValueInfo Op2Info = {TTI::OK_AnyValue, TTI::OP_None}, - ArrayRef Args = ArrayRef(), + ArrayRef Args = std::nullopt, const Instruction *CxtI = nullptr); InstructionCost getCFInstrCost(unsigned Opcode, TTI::TargetCostKind CostKind, diff --git a/llvm/lib/Target/AMDGPU/GCNHazardRecognizer.cpp b/llvm/lib/Target/AMDGPU/GCNHazardRecognizer.cpp index 75766b11ca82299827dbd5ef36c93b9898c86af4..f0c111eaf0600cd816bf3a3036724c15e14f7e77 100644 --- a/llvm/lib/Target/AMDGPU/GCNHazardRecognizer.cpp +++ b/llvm/lib/Target/AMDGPU/GCNHazardRecognizer.cpp @@ -241,7 +241,7 @@ GCNHazardRecognizer::getHazardType(SUnit *SU, int Stalls) { (ST.hasReadM0SendMsgHazard() && isSendMsgTraceDataOrGDS(TII, *MI)) || (ST.hasReadM0LdsDmaHazard() && isLdsDma(*MI)) || (ST.hasReadM0LdsDirectHazard() && - MI->readsRegister(AMDGPU::LDS_DIRECT))) && + MI->readsRegister(AMDGPU::LDS_DIRECT, /*TRI=*/nullptr))) && checkReadM0Hazards(MI) > 0) return HazardType; @@ -381,7 +381,8 @@ unsigned GCNHazardRecognizer::PreEmitNoopsCommon(MachineInstr *MI) { MI->getOpcode() == AMDGPU::DS_READ_ADDTID_B32)) || (ST.hasReadM0SendMsgHazard() && isSendMsgTraceDataOrGDS(TII, *MI)) || (ST.hasReadM0LdsDmaHazard() && isLdsDma(*MI)) || - (ST.hasReadM0LdsDirectHazard() && MI->readsRegister(AMDGPU::LDS_DIRECT))) + (ST.hasReadM0LdsDirectHazard() && + MI->readsRegister(AMDGPU::LDS_DIRECT, /*TRI=*/nullptr))) return std::max(WaitStates, checkReadM0Hazards(MI)); if (SIInstrInfo::isMAI(*MI)) @@ -1161,7 +1162,7 @@ bool GCNHazardRecognizer::fixVMEMtoScalarWriteHazards(MachineInstr *MI) { for (const MachineOperand &Def : MI->defs()) { const MachineOperand *Op = - I.findRegisterUseOperand(Def.getReg(), false, TRI); + I.findRegisterUseOperand(Def.getReg(), TRI, false); if (!Op) continue; return true; diff --git a/llvm/lib/Target/AMDGPU/GCNSubtarget.h b/llvm/lib/Target/AMDGPU/GCNSubtarget.h index 2ca5ae306b11bedff5b81ac78952e7b9d6522409..be337e0b2192f297064d565c96d9bb25c63858e3 100644 --- a/llvm/lib/Target/AMDGPU/GCNSubtarget.h +++ b/llvm/lib/Target/AMDGPU/GCNSubtarget.h @@ -224,6 +224,7 @@ protected: bool HasImageStoreD16Bug = false; bool HasImageGather4D16Bug = false; bool HasMSAALoadDstSelBug = false; + bool HasPrivEnabledTrap2NopBug = false; bool Has1_5xVGPRs = false; bool HasMADIntraFwdBug = false; bool HasVOPDInsts = false; @@ -1032,6 +1033,8 @@ public: bool hasMSAALoadDstSelBug() const { return HasMSAALoadDstSelBug; } + bool hasPrivEnabledTrap2NopBug() const { return HasPrivEnabledTrap2NopBug; } + bool hasNSAEncoding() const { return HasNSAEncoding; } bool hasNonNSAEncoding() const { return getGeneration() < GFX12; } diff --git a/llvm/lib/Target/AMDGPU/MCTargetDesc/AMDGPUELFStreamer.cpp b/llvm/lib/Target/AMDGPU/MCTargetDesc/AMDGPUELFStreamer.cpp index 1ce7012040daa40031b1ed91edca80e73b281bff..4e9a33227a5dcb530cf3c9fe42034d3dd25dc92c 100644 --- a/llvm/lib/Target/AMDGPU/MCTargetDesc/AMDGPUELFStreamer.cpp +++ b/llvm/lib/Target/AMDGPU/MCTargetDesc/AMDGPUELFStreamer.cpp @@ -28,10 +28,11 @@ public: } -MCELFStreamer *llvm::createAMDGPUELFStreamer( - const Triple &T, MCContext &Context, std::unique_ptr MAB, - std::unique_ptr OW, std::unique_ptr Emitter, - bool RelaxAll) { +MCELFStreamer * +llvm::createAMDGPUELFStreamer(const Triple &T, MCContext &Context, + std::unique_ptr MAB, + std::unique_ptr OW, + std::unique_ptr Emitter) { return new AMDGPUELFStreamer(T, Context, std::move(MAB), std::move(OW), std::move(Emitter)); } diff --git a/llvm/lib/Target/AMDGPU/MCTargetDesc/AMDGPUELFStreamer.h b/llvm/lib/Target/AMDGPU/MCTargetDesc/AMDGPUELFStreamer.h index e09e2dca1b47af76585c31480450f5cbdf98b1c0..f9ece5f22b0f7a794f19f662cf0814dd78e95660 100644 --- a/llvm/lib/Target/AMDGPU/MCTargetDesc/AMDGPUELFStreamer.h +++ b/llvm/lib/Target/AMDGPU/MCTargetDesc/AMDGPUELFStreamer.h @@ -26,8 +26,7 @@ class Triple; MCELFStreamer *createAMDGPUELFStreamer(const Triple &T, MCContext &Context, std::unique_ptr MAB, std::unique_ptr OW, - std::unique_ptr Emitter, - bool RelaxAll); + std::unique_ptr Emitter); } // namespace llvm. #endif diff --git a/llvm/lib/Target/AMDGPU/MCTargetDesc/AMDGPUMCTargetDesc.cpp b/llvm/lib/Target/AMDGPU/MCTargetDesc/AMDGPUMCTargetDesc.cpp index 4700a984770bfb1ed33fbb67159044ce796750c5..30dd384051b9401080c28389950a8093e9b0ec9f 100644 --- a/llvm/lib/Target/AMDGPU/MCTargetDesc/AMDGPUMCTargetDesc.cpp +++ b/llvm/lib/Target/AMDGPU/MCTargetDesc/AMDGPUMCTargetDesc.cpp @@ -112,10 +112,9 @@ static MCTargetStreamer *createAMDGPUNullTargetStreamer(MCStreamer &S) { static MCStreamer *createMCStreamer(const Triple &T, MCContext &Context, std::unique_ptr &&MAB, std::unique_ptr &&OW, - std::unique_ptr &&Emitter, - bool RelaxAll) { + std::unique_ptr &&Emitter) { return createAMDGPUELFStreamer(T, Context, std::move(MAB), std::move(OW), - std::move(Emitter), RelaxAll); + std::move(Emitter)); } namespace { diff --git a/llvm/lib/Target/AMDGPU/R600InstrInfo.cpp b/llvm/lib/Target/AMDGPU/R600InstrInfo.cpp index 7f874b245b8f4f4836e2f8c7668633fd061230b7..98e7359357891aaa8d56e27167679e7f95f66231 100644 --- a/llvm/lib/Target/AMDGPU/R600InstrInfo.cpp +++ b/llvm/lib/Target/AMDGPU/R600InstrInfo.cpp @@ -207,11 +207,11 @@ bool R600InstrInfo::mustBeLastInClause(unsigned Opcode) const { } bool R600InstrInfo::usesAddressRegister(MachineInstr &MI) const { - return MI.findRegisterUseOperandIdx(R600::AR_X, false, &RI) != -1; + return MI.findRegisterUseOperandIdx(R600::AR_X, &RI, false) != -1; } bool R600InstrInfo::definesAddressRegister(MachineInstr &MI) const { - return MI.findRegisterDefOperandIdx(R600::AR_X, false, false, &RI) != -1; + return MI.findRegisterDefOperandIdx(R600::AR_X, &RI, false, false) != -1; } bool R600InstrInfo::readsLDSSrcReg(const MachineInstr &MI) const { diff --git a/llvm/lib/Target/AMDGPU/SIFixSGPRCopies.cpp b/llvm/lib/Target/AMDGPU/SIFixSGPRCopies.cpp index 8b21c22b44971066d093a06c4c07df2633be4c66..a00ca625fc7390f7720fb66abc780b63a95024a2 100644 --- a/llvm/lib/Target/AMDGPU/SIFixSGPRCopies.cpp +++ b/llvm/lib/Target/AMDGPU/SIFixSGPRCopies.cpp @@ -947,8 +947,9 @@ void SIFixSGPRCopies::analyzeVGPRToSGPRCopy(MachineInstr* MI) { (Inst->isCopy() && Inst->getOperand(0).getReg() == AMDGPU::SCC)) { auto I = Inst->getIterator(); auto E = Inst->getParent()->end(); - while (++I != E && !I->findRegisterDefOperand(AMDGPU::SCC)) { - if (I->readsRegister(AMDGPU::SCC)) + while (++I != E && + !I->findRegisterDefOperand(AMDGPU::SCC, /*TRI=*/nullptr)) { + if (I->readsRegister(AMDGPU::SCC, /*TRI=*/nullptr)) Users.push_back(&*I); } } else if (Inst->getNumExplicitDefs() != 0) { diff --git a/llvm/lib/Target/AMDGPU/SIISelLowering.cpp b/llvm/lib/Target/AMDGPU/SIISelLowering.cpp index 17b6e0cb9c3b4547831855a48b017de4c1caa5a5..cb4efdc7cf657c6908110be7da7de2ecc21621fc 100644 --- a/llvm/lib/Target/AMDGPU/SIISelLowering.cpp +++ b/llvm/lib/Target/AMDGPU/SIISelLowering.cpp @@ -2124,7 +2124,8 @@ SDValue SITargetLowering::getPreloadedValue(SelectionDAG &DAG, AMDGPU::isEntryFunctionCC(CC) && !MFI.hasWorkGroupIDZ() ? ~0u : 0xFFFFu); const ArgDescriptor WorkGroupIDZ = ArgDescriptor::createRegister(AMDGPU::TTMP7, 0xFFFF0000u); - if (Subtarget->hasArchitectedSGPRs() && AMDGPU::isCompute(CC)) { + if (Subtarget->hasArchitectedSGPRs() && + (AMDGPU::isCompute(CC) || CC == CallingConv::AMDGPU_Gfx)) { switch (PVID) { case AMDGPUFunctionArgInfo::WORKGROUP_ID_X: Reg = &WorkGroupIDX; @@ -2798,7 +2799,9 @@ SDValue SITargetLowering::LowerFormalArguments( (void)UserSGPRInfo; if (!Subtarget->enableFlatScratch()) assert(!UserSGPRInfo.hasFlatScratchInit()); - if (CallConv != CallingConv::AMDGPU_CS || !Subtarget->hasArchitectedSGPRs()) + if ((CallConv != CallingConv::AMDGPU_CS && + CallConv != CallingConv::AMDGPU_Gfx) || + !Subtarget->hasArchitectedSGPRs()) assert(!Info->hasWorkGroupIDX() && !Info->hasWorkGroupIDY() && !Info->hasWorkGroupIDZ()); } @@ -5402,6 +5405,14 @@ MachineBasicBlock *SITargetLowering::EmitInstrWithCustomInserter( MI.eraseFromParent(); return SplitBB; } + case AMDGPU::SIMULATED_TRAP: { + assert(Subtarget->hasPrivEnabledTrap2NopBug()); + MachineRegisterInfo &MRI = BB->getParent()->getRegInfo(); + MachineBasicBlock *SplitBB = + TII->insertSimulatedTrap(MRI, *BB, MI, MI.getDebugLoc()); + MI.eraseFromParent(); + return SplitBB; + } default: if (TII->isImage(MI) || TII->isMUBUF(MI)) { if (!MI.mayStore()) @@ -6620,6 +6631,11 @@ SDValue SITargetLowering::lowerTrapHsa( SDLoc SL(Op); SDValue Chain = Op.getOperand(0); + // We need to simulate the 's_trap 2' instruction on targets that run in + // PRIV=1 (where it is treated as a nop). + if (Subtarget->hasPrivEnabledTrap2NopBug()) + return DAG.getNode(AMDGPUISD::SIMULATED_TRAP, SL, MVT::Other, Chain); + uint64_t TrapID = static_cast(GCNSubtarget::TrapID::LLVMAMDHSATrap); SDValue Ops[] = { Chain, diff --git a/llvm/lib/Target/AMDGPU/SIInsertWaitcnts.cpp b/llvm/lib/Target/AMDGPU/SIInsertWaitcnts.cpp index 36de5b89af02809433c48945e0a960cdec4b1cd8..91a1c40dd8247dfc87ea0a061939b80fbe3a0afa 100644 --- a/llvm/lib/Target/AMDGPU/SIInsertWaitcnts.cpp +++ b/llvm/lib/Target/AMDGPU/SIInsertWaitcnts.cpp @@ -2252,12 +2252,12 @@ bool SIInsertWaitcnts::insertWaitcntInBlock(MachineFunction &MF, // Don't examine operands unless we need to track vccz correctness. if (ST->hasReadVCCZBug() || !ST->partialVCCWritesUpdateVCCZ()) { - if (Inst.definesRegister(AMDGPU::VCC_LO) || - Inst.definesRegister(AMDGPU::VCC_HI)) { + if (Inst.definesRegister(AMDGPU::VCC_LO, /*TRI=*/nullptr) || + Inst.definesRegister(AMDGPU::VCC_HI, /*TRI=*/nullptr)) { // Up to gfx9, writes to vcc_lo and vcc_hi don't update vccz. if (!ST->partialVCCWritesUpdateVCCZ()) VCCZCorrect = false; - } else if (Inst.definesRegister(AMDGPU::VCC)) { + } else if (Inst.definesRegister(AMDGPU::VCC, /*TRI=*/nullptr)) { // There is a hardware bug on CI/SI where SMRD instruction may corrupt // vccz bit, so when we detect that an instruction may read from a // corrupt vccz bit, we need to: diff --git a/llvm/lib/Target/AMDGPU/SIInstrInfo.cpp b/llvm/lib/Target/AMDGPU/SIInstrInfo.cpp index f4b21b7dfac391b6716e9f5e059393d0b3b8b680..e20fe1b716b6474cf464267e96bd79f171ce4f66 100644 --- a/llvm/lib/Target/AMDGPU/SIInstrInfo.cpp +++ b/llvm/lib/Target/AMDGPU/SIInstrInfo.cpp @@ -164,7 +164,7 @@ static bool resultDependsOnExec(const MachineInstr &MI) { break; case AMDGPU::S_AND_B32: case AMDGPU::S_AND_B64: - if (!Use.readsRegister(AMDGPU::EXEC)) + if (!Use.readsRegister(AMDGPU::EXEC, /*TRI=*/nullptr)) return true; break; default: @@ -2026,6 +2026,57 @@ void SIInstrInfo::insertReturn(MachineBasicBlock &MBB) const { } } +MachineBasicBlock *SIInstrInfo::insertSimulatedTrap(MachineRegisterInfo &MRI, + MachineBasicBlock &MBB, + MachineInstr &MI, + const DebugLoc &DL) const { + MachineFunction *MF = MBB.getParent(); + MachineBasicBlock *SplitBB = MBB.splitAt(MI, /*UpdateLiveIns=*/false); + MachineBasicBlock *HaltLoop = MF->CreateMachineBasicBlock(); + MF->push_back(HaltLoop); + + constexpr unsigned DoorbellIDMask = 0x3ff; + constexpr unsigned ECQueueWaveAbort = 0x400; + + // Start with a `s_trap 2`, if we're in PRIV=1 and we need the workaround this + // will be a nop. + BuildMI(MBB, MI, DL, get(AMDGPU::S_TRAP)) + .addImm(static_cast(GCNSubtarget::TrapID::LLVMAMDHSATrap)); + Register DoorbellReg = MRI.createVirtualRegister(&AMDGPU::SReg_32RegClass); + BuildMI(MBB, MI, DL, get(AMDGPU::S_SENDMSG_RTN_B32), DoorbellReg) + .addImm(AMDGPU::SendMsg::ID_RTN_GET_DOORBELL); + BuildMI(MBB, MI, DL, get(AMDGPU::S_MOV_B32), AMDGPU::TTMP2) + .addUse(AMDGPU::M0); + Register DoorbellRegMasked = + MRI.createVirtualRegister(&AMDGPU::SReg_32RegClass); + BuildMI(MBB, MI, DL, get(AMDGPU::S_AND_B32), DoorbellRegMasked) + .addUse(DoorbellReg) + .addImm(DoorbellIDMask); + Register SetWaveAbortBit = + MRI.createVirtualRegister(&AMDGPU::SReg_32RegClass); + BuildMI(MBB, MI, DL, get(AMDGPU::S_OR_B32), SetWaveAbortBit) + .addUse(DoorbellRegMasked) + .addImm(ECQueueWaveAbort); + BuildMI(MBB, MI, DL, get(AMDGPU::S_MOV_B32), AMDGPU::M0) + .addUse(SetWaveAbortBit); + BuildMI(MBB, MI, DL, get(AMDGPU::S_SENDMSG)) + .addImm(AMDGPU::SendMsg::ID_INTERRUPT); + BuildMI(MBB, MI, DL, get(AMDGPU::S_MOV_B32), AMDGPU::M0) + .addUse(AMDGPU::TTMP2); + BuildMI(MBB, MI, DL, get(AMDGPU::S_BRANCH)).addMBB(HaltLoop); + + BuildMI(*HaltLoop, HaltLoop->end(), DL, get(AMDGPU::S_SETHALT)).addImm(5); + BuildMI(*HaltLoop, HaltLoop->end(), DL, get(AMDGPU::S_BRANCH)) + .addMBB(HaltLoop); + + if (SplitBB != &MBB) + MBB.removeSuccessor(SplitBB); + MBB.addSuccessor(HaltLoop); + HaltLoop->addSuccessor(HaltLoop); + + return SplitBB; +} + unsigned SIInstrInfo::getNumWaitStates(const MachineInstr &MI) { switch (MI.getOpcode()) { default: @@ -6689,7 +6740,7 @@ SIInstrInfo::legalizeOperands(MachineInstr &MI, // Also include following copies of the return value ++End; while (End != MBB.end() && End->isCopy() && End->getOperand(1).isReg() && - MI.definesRegister(End->getOperand(1).getReg())) + MI.definesRegister(End->getOperand(1).getReg(), /*TRI=*/nullptr)) ++End; CreatedBB = loadMBUFScalarOperandsFromVGPR(*this, MI, {Dest}, MDT, Start, End); @@ -7257,7 +7308,7 @@ void SIInstrInfo::moveToVALUImpl(SIInstrWorklist &Worklist, .add(Inst.getOperand(1)); } legalizeOperands(*NewInstr, MDT); - int SCCIdx = Inst.findRegisterDefOperandIdx(AMDGPU::SCC); + int SCCIdx = Inst.findRegisterDefOperandIdx(AMDGPU::SCC, /*TRI=*/nullptr); MachineOperand SCCOp = Inst.getOperand(SCCIdx); addSCCDefUsersToVALUWorklist(SCCOp, Inst, Worklist, CondReg); Inst.eraseFromParent(); @@ -7523,7 +7574,7 @@ void SIInstrInfo::lowerSelect(SIInstrWorklist &Worklist, MachineInstr &Inst, for (MachineInstr &CandI : make_range(std::next(MachineBasicBlock::reverse_iterator(Inst)), Inst.getParent()->rend())) { - if (CandI.findRegisterDefOperandIdx(AMDGPU::SCC, false, false, &RI) != + if (CandI.findRegisterDefOperandIdx(AMDGPU::SCC, &RI, false, false) != -1) { if (CandI.isCopy() && CandI.getOperand(0).getReg() == AMDGPU::SCC) { BuildMI(MBB, MII, DL, get(AMDGPU::COPY), NewCondReg) @@ -8338,7 +8389,7 @@ void SIInstrInfo::addSCCDefUsersToVALUWorklist(MachineOperand &Op, make_range(std::next(MachineBasicBlock::iterator(SCCDefInst)), SCCDefInst.getParent()->end())) { // Check if SCC is used first. - int SCCIdx = MI.findRegisterUseOperandIdx(AMDGPU::SCC, false, &RI); + int SCCIdx = MI.findRegisterUseOperandIdx(AMDGPU::SCC, &RI, false); if (SCCIdx != -1) { if (MI.isCopy()) { MachineRegisterInfo &MRI = MI.getParent()->getParent()->getRegInfo(); @@ -8355,7 +8406,7 @@ void SIInstrInfo::addSCCDefUsersToVALUWorklist(MachineOperand &Op, } } // Exit if we find another SCC def. - if (MI.findRegisterDefOperandIdx(AMDGPU::SCC, false, false, &RI) != -1) + if (MI.findRegisterDefOperandIdx(AMDGPU::SCC, &RI, false, false) != -1) break; } for (auto &Copy : CopyToDelete) @@ -9408,7 +9459,7 @@ MachineInstr *SIInstrInfo::createPHIDestinationCopy( auto Cur = MBB.begin(); if (Cur != MBB.end()) do { - if (!Cur->isPHI() && Cur->readsRegister(Dst)) + if (!Cur->isPHI() && Cur->readsRegister(Dst, /*TRI=*/nullptr)) return BuildMI(MBB, Cur, DL, get(TargetOpcode::COPY), Dst).addReg(Src); ++Cur; } while (Cur != MBB.end() && Cur != LastPHIIt); @@ -9424,7 +9475,7 @@ MachineInstr *SIInstrInfo::createPHISourceCopy( (InsPt->getOpcode() == AMDGPU::SI_IF || InsPt->getOpcode() == AMDGPU::SI_ELSE || InsPt->getOpcode() == AMDGPU::SI_IF_BREAK) && - InsPt->definesRegister(Src)) { + InsPt->definesRegister(Src, /*TRI=*/nullptr)) { InsPt++; return BuildMI(MBB, InsPt, DL, get(ST.isWave32() ? AMDGPU::S_MOV_B32_term @@ -9796,7 +9847,8 @@ bool SIInstrInfo::optimizeCompareInstr(MachineInstr &CmpInstr, Register SrcReg, return false; } - MachineOperand *SccDef = Def->findRegisterDefOperand(AMDGPU::SCC); + MachineOperand *SccDef = + Def->findRegisterDefOperand(AMDGPU::SCC, /*TRI=*/nullptr); SccDef->setIsDead(false); CmpInstr.eraseFromParent(); diff --git a/llvm/lib/Target/AMDGPU/SIInstrInfo.h b/llvm/lib/Target/AMDGPU/SIInstrInfo.h index 4c5978cdc6665c68c912589878bf2b4fbed320a5..b314b9b2fb5135580db385a8abf638aec2aecd38 100644 --- a/llvm/lib/Target/AMDGPU/SIInstrInfo.h +++ b/llvm/lib/Target/AMDGPU/SIInstrInfo.h @@ -1194,6 +1194,15 @@ public: unsigned Quantity) const override; void insertReturn(MachineBasicBlock &MBB) const; + + /// Build instructions that simulate the behavior of a `s_trap 2` instructions + /// for hardware (namely, gfx11) that runs in PRIV=1 mode. There, s_trap is + /// interpreted as a nop. + MachineBasicBlock *insertSimulatedTrap(MachineRegisterInfo &MRI, + MachineBasicBlock &MBB, + MachineInstr &MI, + const DebugLoc &DL) const; + /// Return the number of wait states that result from executing this /// instruction. static unsigned getNumWaitStates(const MachineInstr &MI); diff --git a/llvm/lib/Target/AMDGPU/SIInstructions.td b/llvm/lib/Target/AMDGPU/SIInstructions.td index d6d49889656bbc45a7658907785953a640041094..cca8d96f29c0fc96d90b7781a20eb321f2debc33 100644 --- a/llvm/lib/Target/AMDGPU/SIInstructions.td +++ b/llvm/lib/Target/AMDGPU/SIInstructions.td @@ -106,6 +106,12 @@ def ENDPGM_TRAP : SPseudoInstSI< let usesCustomInserter = 1; } +def SIMULATED_TRAP : SPseudoInstSI<(outs), (ins), [(AMDGPUsimulated_trap)], + "SIMULATED_TRAP"> { + let hasSideEffects = 1; + let usesCustomInserter = 1; +} + def ATOMIC_FENCE : SPseudoInstSI< (outs), (ins i32imm:$ordering, i32imm:$scope), [(atomic_fence (i32 timm:$ordering), (i32 timm:$scope))], diff --git a/llvm/lib/Target/AMDGPU/SIMachineFunctionInfo.cpp b/llvm/lib/Target/AMDGPU/SIMachineFunctionInfo.cpp index 12433dc83c4892e89c29eb9f90b25fbe03302ac2..bf4a501cc3159d34cbf25e89a692d22b1ba7d04e 100644 --- a/llvm/lib/Target/AMDGPU/SIMachineFunctionInfo.cpp +++ b/llvm/lib/Target/AMDGPU/SIMachineFunctionInfo.cpp @@ -110,7 +110,8 @@ SIMachineFunctionInfo::SIMachineFunctionInfo(const Function &F, } if (!AMDGPU::isGraphics(CC) || - (CC == CallingConv::AMDGPU_CS && ST.hasArchitectedSGPRs())) { + ((CC == CallingConv::AMDGPU_CS || CC == CallingConv::AMDGPU_CS) && + ST.hasArchitectedSGPRs())) { if (IsKernel || !F.hasFnAttribute("amdgpu-no-workgroup-id-x")) WorkGroupIDX = true; diff --git a/llvm/lib/Target/AMDGPU/SIOptimizeExecMaskingPreRA.cpp b/llvm/lib/Target/AMDGPU/SIOptimizeExecMaskingPreRA.cpp index d2a5eb89da129cbc90885c324ea2bbfa6157b089..c91d241f81abcc795c9d3ce1792067c75ce99734 100644 --- a/llvm/lib/Target/AMDGPU/SIOptimizeExecMaskingPreRA.cpp +++ b/llvm/lib/Target/AMDGPU/SIOptimizeExecMaskingPreRA.cpp @@ -456,7 +456,8 @@ bool SIOptimizeExecMaskingPreRA::runOnMachineFunction(MachineFunction &MF) { Register SavedExec = I->getOperand(0).getReg(); if (SavedExec.isVirtual() && MRI->hasOneNonDBGUse(SavedExec)) { MachineInstr *SingleExecUser = &*MRI->use_instr_nodbg_begin(SavedExec); - int Idx = SingleExecUser->findRegisterUseOperandIdx(SavedExec); + int Idx = SingleExecUser->findRegisterUseOperandIdx(SavedExec, + /*TRI=*/nullptr); assert(Idx != -1); if (SingleExecUser->getParent() == I->getParent() && !SingleExecUser->getOperand(Idx).isImplicit() && diff --git a/llvm/lib/Target/AMDGPU/SIPreEmitPeephole.cpp b/llvm/lib/Target/AMDGPU/SIPreEmitPeephole.cpp index 82da53d0c0ebdd4b07a6f63df382d4bd556dd5b2..875bccb208c846166f27636c0fe9feb1c109b42a 100644 --- a/llvm/lib/Target/AMDGPU/SIPreEmitPeephole.cpp +++ b/llvm/lib/Target/AMDGPU/SIPreEmitPeephole.cpp @@ -171,7 +171,7 @@ bool SIPreEmitPeephole::optimizeVccBranch(MachineInstr &MI) const { if (A->getOpcode() == AndN2) MaskValue = ~MaskValue; - if (!ReadsCond && A->registerDefIsDead(AMDGPU::SCC)) { + if (!ReadsCond && A->registerDefIsDead(AMDGPU::SCC, /*TRI=*/nullptr)) { if (!MI.killsRegister(CondReg, TRI)) { // Replace AND with MOV if (MaskValue == 0) { @@ -235,7 +235,7 @@ bool SIPreEmitPeephole::optimizeVccBranch(MachineInstr &MI) const { TII->get(IsVCCZ ? AMDGPU::S_CBRANCH_EXECZ : AMDGPU::S_CBRANCH_EXECNZ)); } - MI.removeOperand(MI.findRegisterUseOperandIdx(CondReg, false /*Kill*/, TRI)); + MI.removeOperand(MI.findRegisterUseOperandIdx(CondReg, TRI, false /*Kill*/)); MI.addImplicitDefUseOperands(*MBB.getParent()); return true; diff --git a/llvm/lib/Target/AMDGPU/SIRegisterInfo.cpp b/llvm/lib/Target/AMDGPU/SIRegisterInfo.cpp index acb54fd10b90dc9b29f0a0f14621e2eb7741126b..ddb5f719356855d42403e8f4a658ec05634b4eba 100644 --- a/llvm/lib/Target/AMDGPU/SIRegisterInfo.cpp +++ b/llvm/lib/Target/AMDGPU/SIRegisterInfo.cpp @@ -2366,8 +2366,8 @@ bool SIRegisterInfo::eliminateFrameIndex(MachineBasicBlock::iterator MI, return false; } - bool NeedSaveSCC = - RS->isRegUsed(AMDGPU::SCC) && !MI->definesRegister(AMDGPU::SCC); + bool NeedSaveSCC = RS->isRegUsed(AMDGPU::SCC) && + !MI->definesRegister(AMDGPU::SCC, /*TRI=*/nullptr); Register TmpSReg = UseSGPR ? TmpReg @@ -2409,7 +2409,8 @@ bool SIRegisterInfo::eliminateFrameIndex(MachineBasicBlock::iterator MI, if (TmpSReg == FrameReg) { // Undo frame register modification. - if (NeedSaveSCC && !MI->registerDefIsDead(AMDGPU::SCC)) { + if (NeedSaveSCC && + !MI->registerDefIsDead(AMDGPU::SCC, /*TRI=*/nullptr)) { MachineBasicBlock::iterator I = BuildMI(*MBB, std::next(MI), DL, TII->get(AMDGPU::S_ADDC_U32), TmpSReg) @@ -2439,8 +2440,8 @@ bool SIRegisterInfo::eliminateFrameIndex(MachineBasicBlock::iterator MI, // Convert to a swizzled stack address by scaling by the wave size. // In an entry function/kernel the offset is already swizzled. bool IsSALU = isSGPRClass(TII->getOpRegClass(*MI, FIOperandNum)); - bool LiveSCC = - RS->isRegUsed(AMDGPU::SCC) && !MI->definesRegister(AMDGPU::SCC); + bool LiveSCC = RS->isRegUsed(AMDGPU::SCC) && + !MI->definesRegister(AMDGPU::SCC, /*TRI=*/nullptr); const TargetRegisterClass *RC = IsSALU && !LiveSCC ? &AMDGPU::SReg_32RegClass : &AMDGPU::VGPR_32RegClass; diff --git a/llvm/lib/Target/AMDGPU/SIShrinkInstructions.cpp b/llvm/lib/Target/AMDGPU/SIShrinkInstructions.cpp index 3c6f6ddfd89d0d16ff222c4ce2919582ff6004b6..647fae904d393dabbb0f0b4a70d1ef86df531f57 100644 --- a/llvm/lib/Target/AMDGPU/SIShrinkInstructions.cpp +++ b/llvm/lib/Target/AMDGPU/SIShrinkInstructions.cpp @@ -1014,7 +1014,7 @@ bool SIShrinkInstructions::runOnMachineFunction(MachineFunction &MF) { // Copy deadness from the old explicit vcc def to the new implicit def. if (SDst && SDst->isDead()) - Inst32->findRegisterDefOperand(VCCReg)->setIsDead(); + Inst32->findRegisterDefOperand(VCCReg, /*TRI=*/nullptr)->setIsDead(); MI.eraseFromParent(); foldImmediates(*Inst32); diff --git a/llvm/lib/Target/AMDGPU/SIWholeQuadMode.cpp b/llvm/lib/Target/AMDGPU/SIWholeQuadMode.cpp index 5e6c34992930be8b22cfcabcc746c10e6bc72706..ea8109bbee9aed22d3ffc561b6d6afd4397840a9 100644 --- a/llvm/lib/Target/AMDGPU/SIWholeQuadMode.cpp +++ b/llvm/lib/Target/AMDGPU/SIWholeQuadMode.cpp @@ -1525,10 +1525,10 @@ void SIWholeQuadMode::lowerCopyInstrs() { MI->getOperand(0).setIsEarlyClobber(false); LIS->createAndComputeVirtRegInterval(Reg); } - int Index = MI->findRegisterUseOperandIdx(AMDGPU::EXEC); + int Index = MI->findRegisterUseOperandIdx(AMDGPU::EXEC, /*TRI=*/nullptr); while (Index >= 0) { MI->removeOperand(Index); - Index = MI->findRegisterUseOperandIdx(AMDGPU::EXEC); + Index = MI->findRegisterUseOperandIdx(AMDGPU::EXEC, /*TRI=*/nullptr); } MI->setDesc(TII->get(AMDGPU::COPY)); LLVM_DEBUG(dbgs() << " -> " << *MI); diff --git a/llvm/lib/Target/ARM/A15SDOptimizer.cpp b/llvm/lib/Target/ARM/A15SDOptimizer.cpp index 3543cefeb399de26728f91eaf433171ff5446176..be87707a297d25341665e279db94f38122494081 100644 --- a/llvm/lib/Target/ARM/A15SDOptimizer.cpp +++ b/llvm/lib/Target/ARM/A15SDOptimizer.cpp @@ -156,7 +156,7 @@ unsigned A15SDOptimizer::getPrefSPRLane(unsigned SReg) { MachineInstr *MI = MRI->getVRegDef(SReg); if (!MI) return ARM::ssub_0; - MachineOperand *MO = MI->findRegisterDefOperand(SReg); + MachineOperand *MO = MI->findRegisterDefOperand(SReg, /*TRI=*/nullptr); if (!MO) return ARM::ssub_0; assert(MO->isReg() && "Non-register operand found!"); @@ -192,7 +192,7 @@ void A15SDOptimizer::eraseInstrWithNoUses(MachineInstr *MI) { Register Reg = MO.getReg(); if (!Reg.isVirtual()) continue; - MachineOperand *Op = MI->findRegisterDefOperand(Reg); + MachineOperand *Op = MI->findRegisterDefOperand(Reg, /*TRI=*/nullptr); if (!Op) continue; diff --git a/llvm/lib/Target/ARM/ARMBaseInstrInfo.cpp b/llvm/lib/Target/ARM/ARMBaseInstrInfo.cpp index 5d0468948dfb6172afed64fd3626d9f6eb3795f5..8f873bee484acc7679304f365cc4e836c27753dd 100644 --- a/llvm/lib/Target/ARM/ARMBaseInstrInfo.cpp +++ b/llvm/lib/Target/ARM/ARMBaseInstrInfo.cpp @@ -326,7 +326,7 @@ ARMBaseInstrInfo::convertToThreeAddress(MachineInstr &MI, LiveVariables *LV, for (unsigned j = 0; j < 2; ++j) { // Look at the two new MI's in reverse order. MachineInstr *NewMI = NewMIs[j]; - if (!NewMI->readsRegister(Reg)) + if (!NewMI->readsRegister(Reg, /*TRI=*/nullptr)) continue; LV->addVirtualRegisterKilled(Reg, *NewMI); if (VI.removeKill(MI)) @@ -1732,7 +1732,7 @@ bool ARMBaseInstrInfo::expandPostRAPseudo(MachineInstr &MI) const { // Get rid of the old implicit-def of DstRegD. Leave it if it defines a Q-reg // or some other super-register. - int ImpDefIdx = MI.findRegisterDefOperandIdx(DstRegD); + int ImpDefIdx = MI.findRegisterDefOperandIdx(DstRegD, /*TRI=*/nullptr); if (ImpDefIdx != -1) MI.removeOperand(ImpDefIdx); @@ -2085,7 +2085,7 @@ bool ARMBaseInstrInfo::isSchedulingBoundary(const MachineInstr &MI, // Calls don't actually change the stack pointer, even if they have imp-defs. // No ARM calling conventions change the stack pointer. (X86 calling // conventions sometimes do). - if (!MI.isCall() && MI.definesRegister(ARM::SP)) + if (!MI.isCall() && MI.definesRegister(ARM::SP, /*TRI=*/nullptr)) return true; return false; @@ -4137,7 +4137,7 @@ static const MachineInstr *getBundledDefMI(const TargetRegisterInfo *TRI, int Idx = -1; while (II->isInsideBundle()) { - Idx = II->findRegisterDefOperandIdx(Reg, false, true, TRI); + Idx = II->findRegisterDefOperandIdx(Reg, TRI, false, true); if (Idx != -1) break; --II; @@ -4161,7 +4161,7 @@ static const MachineInstr *getBundledUseMI(const TargetRegisterInfo *TRI, // FIXME: This doesn't properly handle multiple uses. int Idx = -1; while (II != E && II->isInsideBundle()) { - Idx = II->findRegisterUseOperandIdx(Reg, false, TRI); + Idx = II->findRegisterUseOperandIdx(Reg, TRI, false); if (Idx != -1) break; if (II->getOpcode() != ARM::t2IT) @@ -5361,7 +5361,7 @@ unsigned ARMBaseInstrInfo::getPartialRegUpdateClearance( case ARM::VMOVv2i32: case ARM::VMOVv2f32: case ARM::VMOVv1i64: - UseOp = MI.findRegisterUseOperandIdx(Reg, false, TRI); + UseOp = MI.findRegisterUseOperandIdx(Reg, TRI, false); break; // Explicitly reads the dependency. @@ -6092,7 +6092,7 @@ ARMBaseInstrInfo::getOutliningCandidateInfo( bool ARMBaseInstrInfo::checkAndUpdateStackOffset(MachineInstr *MI, int64_t Fixup, bool Updt) const { - int SPIdx = MI->findRegisterUseOperandIdx(ARM::SP); + int SPIdx = MI->findRegisterUseOperandIdx(ARM::SP, /*TRI=*/nullptr); unsigned AddrMode = (MI->getDesc().TSFlags & ARMII::AddrModeMask); if (SPIdx < 0) // No SP operand diff --git a/llvm/lib/Target/ARM/ARMConstantIslandPass.cpp b/llvm/lib/Target/ARM/ARMConstantIslandPass.cpp index 7a3ba5870bc6dfd89b807220e39c956f2a08b142..9579053943f9f004d401e9137ddd0272ef8d4a92 100644 --- a/llvm/lib/Target/ARM/ARMConstantIslandPass.cpp +++ b/llvm/lib/Target/ARM/ARMConstantIslandPass.cpp @@ -1937,7 +1937,7 @@ bool ARMConstantIslands::optimizeThumb2Branches() { // If the conditional branch doesn't kill CPSR, then CPSR can be liveout // so this transformation is not safe. - if (!Br.MI->killsRegister(ARM::CPSR)) + if (!Br.MI->killsRegister(ARM::CPSR, /*TRI=*/nullptr)) return false; Register PredReg; diff --git a/llvm/lib/Target/ARM/ARMFrameLowering.cpp b/llvm/lib/Target/ARM/ARMFrameLowering.cpp index 9b54dd4e4e618d75255bf91d0429f0cf18d620da..a332f743f495b8a3357a630f6d06003ac9c59b43 100644 --- a/llvm/lib/Target/ARM/ARMFrameLowering.cpp +++ b/llvm/lib/Target/ARM/ARMFrameLowering.cpp @@ -1873,7 +1873,7 @@ skipAlignedDPRCS2Spills(MachineBasicBlock::iterator MI, case 1: case 2: case 4: - assert(MI->killsRegister(ARM::R4) && "Missed kill flag"); + assert(MI->killsRegister(ARM::R4, /*TRI=*/nullptr) && "Missed kill flag"); ++MI; } return MI; diff --git a/llvm/lib/Target/ARM/ARMISelLowering.cpp b/llvm/lib/Target/ARM/ARMISelLowering.cpp index 3907131be6d13128b30c926f09a767c4a247efb4..d0e9f61c0bd1228ee717cdd9fab23403e021e89f 100644 --- a/llvm/lib/Target/ARM/ARMISelLowering.cpp +++ b/llvm/lib/Target/ARM/ARMISelLowering.cpp @@ -11796,9 +11796,9 @@ static bool checkAndUpdateCPSRKill(MachineBasicBlock::iterator SelectItr, MachineBasicBlock::iterator miI(std::next(SelectItr)); for (MachineBasicBlock::iterator miE = BB->end(); miI != miE; ++miI) { const MachineInstr& mi = *miI; - if (mi.readsRegister(ARM::CPSR)) + if (mi.readsRegister(ARM::CPSR, /*TRI=*/nullptr)) return false; - if (mi.definesRegister(ARM::CPSR)) + if (mi.definesRegister(ARM::CPSR, /*TRI=*/nullptr)) break; // Should have kill-flag - update below. } @@ -12157,7 +12157,7 @@ ARMTargetLowering::EmitInstrWithCustomInserter(MachineInstr &MI, // Check whether CPSR is live past the tMOVCCr_pseudo. const TargetRegisterInfo *TRI = Subtarget->getRegisterInfo(); - if (!MI.killsRegister(ARM::CPSR) && + if (!MI.killsRegister(ARM::CPSR, /*TRI=*/nullptr) && !checkAndUpdateCPSRKill(MI, thisMBB, TRI)) { copy0MBB->addLiveIn(ARM::CPSR); sinkMBB->addLiveIn(ARM::CPSR); diff --git a/llvm/lib/Target/ARM/ARMLoadStoreOptimizer.cpp b/llvm/lib/Target/ARM/ARMLoadStoreOptimizer.cpp index 469340784284cb69e02dd5b1299a0633ce841b8c..4a5b672f862bec194f44dcc50a56f0e278f184c6 100644 --- a/llvm/lib/Target/ARM/ARMLoadStoreOptimizer.cpp +++ b/llvm/lib/Target/ARM/ARMLoadStoreOptimizer.cpp @@ -495,7 +495,7 @@ void ARMLoadStoreOpt::UpdateBaseRegUses(MachineBasicBlock &MBB, bool InsertSub = false; unsigned Opc = MBBI->getOpcode(); - if (MBBI->readsRegister(Base)) { + if (MBBI->readsRegister(Base, /*TRI=*/nullptr)) { int Offset; bool IsLoad = Opc == ARM::tLDRi || Opc == ARM::tLDRHi || Opc == ARM::tLDRBi; @@ -560,7 +560,8 @@ void ARMLoadStoreOpt::UpdateBaseRegUses(MachineBasicBlock &MBB, return; } - if (MBBI->killsRegister(Base) || MBBI->definesRegister(Base)) + if (MBBI->killsRegister(Base, /*TRI=*/nullptr) || + MBBI->definesRegister(Base, /*TRI=*/nullptr)) // Register got killed. Stop updating. return; } @@ -888,7 +889,7 @@ MachineInstr *ARMLoadStoreOpt::MergeOpsUpdate(const MergeCandidate &Cand) { if (is_contained(ImpDefs, DefReg)) continue; // We can ignore cases where the super-reg is read and written. - if (MI->readsRegister(DefReg)) + if (MI->readsRegister(DefReg, /*TRI=*/nullptr)) continue; ImpDefs.push_back(DefReg); } @@ -903,7 +904,7 @@ MachineInstr *ARMLoadStoreOpt::MergeOpsUpdate(const MergeCandidate &Cand) { MachineBasicBlock &MBB = *LatestMI->getParent(); unsigned Offset = getMemoryOpOffset(*First); Register Base = getLoadStoreBaseOp(*First).getReg(); - bool BaseKill = LatestMI->killsRegister(Base); + bool BaseKill = LatestMI->killsRegister(Base, /*TRI=*/nullptr); Register PredReg; ARMCC::CondCodes Pred = getInstrPredicate(*First, PredReg); DebugLoc DL = First->getDebugLoc(); @@ -2076,7 +2077,8 @@ bool ARMLoadStoreOpt::CombineMovBx(MachineBasicBlock &MBB) { MachineBasicBlock::iterator Prev = MBBI; --Prev; - if (Prev->getOpcode() != ARM::tMOVr || !Prev->definesRegister(ARM::LR)) + if (Prev->getOpcode() != ARM::tMOVr || + !Prev->definesRegister(ARM::LR, /*TRI=*/nullptr)) return false; for (auto Use : Prev->uses()) @@ -3176,7 +3178,7 @@ bool ARMPreAllocLoadStoreOpt::DistributeIncrements(Register Base) { if (PrePostInc || BaseAccess->getParent() != Increment->getParent()) return false; Register PredReg; - if (Increment->definesRegister(ARM::CPSR) || + if (Increment->definesRegister(ARM::CPSR, /*TRI=*/nullptr) || getInstrPredicate(*Increment, PredReg) != ARMCC::AL) return false; diff --git a/llvm/lib/Target/ARM/ARMLowOverheadLoops.cpp b/llvm/lib/Target/ARM/ARMLowOverheadLoops.cpp index ea5dd5427ce72015fa7bcc338eb8e528fa729264..91a36898aecba13a81133725b7297331d1bd5fbd 100644 --- a/llvm/lib/Target/ARM/ARMLowOverheadLoops.cpp +++ b/llvm/lib/Target/ARM/ARMLowOverheadLoops.cpp @@ -91,11 +91,11 @@ static bool isVectorPredicated(MachineInstr *MI) { } static bool isVectorPredicate(MachineInstr *MI) { - return MI->findRegisterDefOperandIdx(ARM::VPR) != -1; + return MI->findRegisterDefOperandIdx(ARM::VPR, /*TRI=*/nullptr) != -1; } static bool hasVPRUse(MachineInstr &MI) { - return MI.findRegisterUseOperandIdx(ARM::VPR) != -1; + return MI.findRegisterUseOperandIdx(ARM::VPR, /*TRI=*/nullptr) != -1; } static bool isDomainMVE(MachineInstr *MI) { @@ -564,7 +564,8 @@ static bool TryRemove(MachineInstr *MI, ReachingDefAnalysis &RDA, SmallPtrSet ModifiedITs; SmallPtrSet RemoveITs; for (auto *Dead : Killed) { - if (MachineOperand *MO = Dead->findRegisterUseOperand(ARM::ITSTATE)) { + if (MachineOperand *MO = + Dead->findRegisterUseOperand(ARM::ITSTATE, /*TRI=*/nullptr)) { MachineInstr *IT = RDA.getMIOperand(Dead, *MO); RemoveITs.insert(IT); auto &CurrentBlock = ITBlocks[IT]; diff --git a/llvm/lib/Target/ARM/ARMSubtarget.cpp b/llvm/lib/Target/ARM/ARMSubtarget.cpp index 04ba20a17187b44967ea2472e4f1c12941eadbc8..5e13d8fabe0485dbb7af8ebc9a5038f629ac9c70 100644 --- a/llvm/lib/Target/ARM/ARMSubtarget.cpp +++ b/llvm/lib/Target/ARM/ARMSubtarget.cpp @@ -293,13 +293,11 @@ void ARMSubtarget::initSubtargetFeatures(StringRef CPU, StringRef FS) { case CortexA78C: case CortexA710: case CortexR4: - case CortexR4F: case CortexR5: case CortexR7: case CortexM3: case CortexM7: case CortexR52: - case CortexM52: case CortexX1: case CortexX1C: break; @@ -314,8 +312,6 @@ void ARMSubtarget::initSubtargetFeatures(StringRef CPU, StringRef FS) { case Krait: PreISelOperandLatencyAdjustment = 1; break; - case NeoverseN1: - case NeoverseN2: case NeoverseV1: break; case Swift: diff --git a/llvm/lib/Target/ARM/ARMSubtarget.h b/llvm/lib/Target/ARM/ARMSubtarget.h index 497ae160fde281e6e1cc5f9d0a755c5e9e37b03a..00239ff94b7ba5501f462b1dd410c2687087bba4 100644 --- a/llvm/lib/Target/ARM/ARMSubtarget.h +++ b/llvm/lib/Target/ARM/ARMSubtarget.h @@ -49,45 +49,9 @@ class ARMSubtarget : public ARMGenSubtargetInfo { protected: enum ARMProcFamilyEnum { Others, - - CortexA12, - CortexA15, - CortexA17, - CortexA32, - CortexA35, - CortexA5, - CortexA53, - CortexA55, - CortexA57, - CortexA7, - CortexA72, - CortexA73, - CortexA75, - CortexA76, - CortexA77, - CortexA78, - CortexA78AE, - CortexA78C, - CortexA710, - CortexA8, - CortexA9, - CortexM3, - CortexM7, - CortexM52, - CortexR4, - CortexR4F, - CortexR5, - CortexR52, - CortexR7, - CortexX1, - CortexX1C, - Exynos, - Krait, - Kryo, - NeoverseN1, - NeoverseN2, - NeoverseV1, - Swift +#define ARM_PROCESSOR_FAMILY(ENUM) ENUM, +#include "llvm/TargetParser/ARMTargetParserDef.inc" +#undef ARM_PROCESSOR_FAMILY }; enum ARMProcClassEnum { None, @@ -97,43 +61,9 @@ protected: RClass }; enum ARMArchEnum { - ARMv4, - ARMv4t, - ARMv5, - ARMv5t, - ARMv5te, - ARMv5tej, - ARMv6, - ARMv6k, - ARMv6kz, - ARMv6m, - ARMv6sm, - ARMv6t2, - ARMv7a, - ARMv7em, - ARMv7m, - ARMv7r, - ARMv7ve, - ARMv81a, - ARMv82a, - ARMv83a, - ARMv84a, - ARMv85a, - ARMv86a, - ARMv87a, - ARMv88a, - ARMv89a, - ARMv8a, - ARMv8mBaseline, - ARMv8mMainline, - ARMv8r, - ARMv81mMainline, - ARMv9a, - ARMv91a, - ARMv92a, - ARMv93a, - ARMv94a, - ARMv95a, +#define ARM_ARCHITECTURE(ENUM) ENUM, +#include "llvm/TargetParser/ARMTargetParserDef.inc" +#undef ARM_ARCHITECTURE }; public: diff --git a/llvm/lib/Target/ARM/ARMTargetTransformInfo.h b/llvm/lib/Target/ARM/ARMTargetTransformInfo.h index 04b32194f806f651577b4283a6ff7771f0ec74a8..58eab45b9641f57e1af2423bb0c60c5bcbdbd895 100644 --- a/llvm/lib/Target/ARM/ARMTargetTransformInfo.h +++ b/llvm/lib/Target/ARM/ARMTargetTransformInfo.h @@ -256,7 +256,7 @@ public: unsigned Opcode, Type *Ty, TTI::TargetCostKind CostKind, TTI::OperandValueInfo Op1Info = {TTI::OK_AnyValue, TTI::OP_None}, TTI::OperandValueInfo Op2Info = {TTI::OK_AnyValue, TTI::OP_None}, - ArrayRef Args = ArrayRef(), + ArrayRef Args = std::nullopt, const Instruction *CxtI = nullptr); InstructionCost diff --git a/llvm/lib/Target/ARM/AsmParser/ARMAsmParser.cpp b/llvm/lib/Target/ARM/AsmParser/ARMAsmParser.cpp index 028db9d17e300adc393f9dbe695792f6ea4ecc94..e54314cc7d00afa76ee5744d4de6717174a1ebe4 100644 --- a/llvm/lib/Target/ARM/AsmParser/ARMAsmParser.cpp +++ b/llvm/lib/Target/ARM/AsmParser/ARMAsmParser.cpp @@ -11104,7 +11104,7 @@ ARMAsmParser::checkEarlyTargetMatchPredicate(MCInst &Inst, return Match_MnemonicFail; } } - LLVM_FALLTHROUGH; + [[fallthrough]]; default: return Match_Success; } diff --git a/llvm/lib/Target/ARM/MCTargetDesc/ARMELFStreamer.cpp b/llvm/lib/Target/ARM/MCTargetDesc/ARMELFStreamer.cpp index 1d80af590d16e00bf9a342ec2e397e21571dcf0e..afd7dccbeca9b37c3f0c0b2ee803bef2baacf6a4 100644 --- a/llvm/lib/Target/ARM/MCTargetDesc/ARMELFStreamer.cpp +++ b/llvm/lib/Target/ARM/MCTargetDesc/ARMELFStreamer.cpp @@ -1487,8 +1487,7 @@ MCELFStreamer *createARMELFStreamer(MCContext &Context, std::unique_ptr TAB, std::unique_ptr OW, std::unique_ptr Emitter, - bool RelaxAll, bool IsThumb, - bool IsAndroid) { + bool IsThumb, bool IsAndroid) { ARMELFStreamer *S = new ARMELFStreamer(Context, std::move(TAB), std::move(OW), std::move(Emitter), IsThumb, IsAndroid); @@ -1497,8 +1496,6 @@ MCELFStreamer *createARMELFStreamer(MCContext &Context, // the status quo for ARM and setting EF_ARM_EABI_VER5 as the default. S->getAssembler().setELFHeaderEFlags(ELF::EF_ARM_EABI_VER5); - if (RelaxAll) - S->getAssembler().setRelaxAll(true); return S; } diff --git a/llvm/lib/Target/ARM/MCTargetDesc/ARMMCTargetDesc.cpp b/llvm/lib/Target/ARM/MCTargetDesc/ARMMCTargetDesc.cpp index 8d9959a9457dbef84e651929ef2fb70b7172f871..20603b6cf1b0bb2f6b873618c1fa3d1afdb00eca 100644 --- a/llvm/lib/Target/ARM/MCTargetDesc/ARMMCTargetDesc.cpp +++ b/llvm/lib/Target/ARM/MCTargetDesc/ARMMCTargetDesc.cpp @@ -359,10 +359,9 @@ static MCAsmInfo *createARMMCAsmInfo(const MCRegisterInfo &MRI, static MCStreamer *createELFStreamer(const Triple &T, MCContext &Ctx, std::unique_ptr &&MAB, std::unique_ptr &&OW, - std::unique_ptr &&Emitter, - bool RelaxAll) { + std::unique_ptr &&Emitter) { return createARMELFStreamer( - Ctx, std::move(MAB), std::move(OW), std::move(Emitter), false, + Ctx, std::move(MAB), std::move(OW), std::move(Emitter), (T.getArch() == Triple::thumb || T.getArch() == Triple::thumbeb), T.isAndroid()); } @@ -370,10 +369,10 @@ static MCStreamer *createELFStreamer(const Triple &T, MCContext &Ctx, static MCStreamer * createARMMachOStreamer(MCContext &Ctx, std::unique_ptr &&MAB, std::unique_ptr &&OW, - std::unique_ptr &&Emitter, bool RelaxAll, + std::unique_ptr &&Emitter, bool DWARFMustBeAtTheEnd) { return createMachOStreamer(Ctx, std::move(MAB), std::move(OW), - std::move(Emitter), false, DWARFMustBeAtTheEnd); + std::move(Emitter), DWARFMustBeAtTheEnd); } static MCInstPrinter *createARMMCInstPrinter(const Triple &T, diff --git a/llvm/lib/Target/ARM/MCTargetDesc/ARMMCTargetDesc.h b/llvm/lib/Target/ARM/MCTargetDesc/ARMMCTargetDesc.h index 3066d9ba6783b2024ca254dfb6c9eac99cfe6b4c..a673d590419ecc1e65da2ae137730ecfbe3b190e 100644 --- a/llvm/lib/Target/ARM/MCTargetDesc/ARMMCTargetDesc.h +++ b/llvm/lib/Target/ARM/MCTargetDesc/ARMMCTargetDesc.h @@ -94,7 +94,6 @@ MCStreamer *createARMWinCOFFStreamer(MCContext &Context, std::unique_ptr &&MAB, std::unique_ptr &&OW, std::unique_ptr &&Emitter, - bool RelaxAll, bool IncrementalLinkerCompatible); /// Construct an ELF Mach-O object writer. diff --git a/llvm/lib/Target/ARM/MCTargetDesc/ARMWinCOFFStreamer.cpp b/llvm/lib/Target/ARM/MCTargetDesc/ARMWinCOFFStreamer.cpp index cdd7f6fb715a7045de525c396a76faef7db8fed6..0fcf6eb1a5abb59416771ee987ee7530ac457c0e 100644 --- a/llvm/lib/Target/ARM/MCTargetDesc/ARMWinCOFFStreamer.cpp +++ b/llvm/lib/Target/ARM/MCTargetDesc/ARMWinCOFFStreamer.cpp @@ -66,11 +66,12 @@ void ARMWinCOFFStreamer::finishImpl() { } } -MCStreamer *llvm::createARMWinCOFFStreamer( - MCContext &Context, std::unique_ptr &&MAB, - std::unique_ptr &&OW, - std::unique_ptr &&Emitter, bool RelaxAll, - bool IncrementalLinkerCompatible) { +MCStreamer * +llvm::createARMWinCOFFStreamer(MCContext &Context, + std::unique_ptr &&MAB, + std::unique_ptr &&OW, + std::unique_ptr &&Emitter, + bool IncrementalLinkerCompatible) { auto *S = new ARMWinCOFFStreamer(Context, std::move(MAB), std::move(Emitter), std::move(OW)); S->getAssembler().setIncrementalLinkerCompatible(IncrementalLinkerCompatible); diff --git a/llvm/lib/Target/ARM/MVETPAndVPTOptimisationsPass.cpp b/llvm/lib/Target/ARM/MVETPAndVPTOptimisationsPass.cpp index e8d2cba7ee556fc1087e683bbfa00b8187a3e5f7..c9bbc41ac13bacbb098e2c32c94eef664e5455fa 100644 --- a/llvm/lib/Target/ARM/MVETPAndVPTOptimisationsPass.cpp +++ b/llvm/lib/Target/ARM/MVETPAndVPTOptimisationsPass.cpp @@ -667,17 +667,18 @@ static bool MoveVPNOTBeforeFirstUser(MachineBasicBlock &MBB, MachineOperand *VPNOTOperandKiller = nullptr; for (; Iter != MBB.end(); ++Iter) { if (MachineOperand *MO = - Iter->findRegisterUseOperand(VPNOTOperand, /*isKill*/ true)) { + Iter->findRegisterUseOperand(VPNOTOperand, /*TRI=*/nullptr, + /*isKill*/ true)) { // If we find the operand that kills the VPNOTOperand's result, save it. VPNOTOperandKiller = MO; } - if (Iter->findRegisterUseOperandIdx(Reg) != -1) { + if (Iter->findRegisterUseOperandIdx(Reg, /*TRI=*/nullptr) != -1) { MustMove = true; continue; } - if (Iter->findRegisterUseOperandIdx(VPNOTResult) == -1) + if (Iter->findRegisterUseOperandIdx(VPNOTResult, /*TRI=*/nullptr) == -1) continue; HasUser = true; @@ -731,7 +732,7 @@ bool MVETPAndVPTOptimisations::ReduceOldVCCRValueUses(MachineBasicBlock &MBB) { // If we already have a VCCRValue, and this is a VPNOT on VCCRValue, we've // found what we were looking for. if (VCCRValue && Iter->getOpcode() == ARM::MVE_VPNOT && - Iter->findRegisterUseOperandIdx(VCCRValue) != -1) { + Iter->findRegisterUseOperandIdx(VCCRValue, /*TRI=*/nullptr) != -1) { // Move the VPNOT closer to its first user if needed, and ignore if it // has no users. if (!MoveVPNOTBeforeFirstUser(MBB, Iter, VCCRValue)) @@ -763,7 +764,8 @@ bool MVETPAndVPTOptimisations::ReduceOldVCCRValueUses(MachineBasicBlock &MBB) { for (; Iter != End; ++Iter) { bool IsInteresting = false; - if (MachineOperand *MO = Iter->findRegisterUseOperand(VCCRValue)) { + if (MachineOperand *MO = + Iter->findRegisterUseOperand(VCCRValue, /*TRI=*/nullptr)) { IsInteresting = true; // - If the instruction is a VPNOT, it can be removed, and we can just @@ -794,8 +796,8 @@ bool MVETPAndVPTOptimisations::ReduceOldVCCRValueUses(MachineBasicBlock &MBB) { } else { // If the instr uses OppositeVCCRValue, make it use LastVPNOTResult // instead as they contain the same value. - if (MachineOperand *MO = - Iter->findRegisterUseOperand(OppositeVCCRValue)) { + if (MachineOperand *MO = Iter->findRegisterUseOperand( + OppositeVCCRValue, /*TRI=*/nullptr)) { IsInteresting = true; // This is pointless if LastVPNOTResult == OppositeVCCRValue. @@ -855,8 +857,9 @@ bool MVETPAndVPTOptimisations::ReplaceVCMPsByVPNOTs(MachineBasicBlock &MBB) { for (MachineInstr &Instr : MBB.instrs()) { if (PrevVCMP) { - if (MachineOperand *MO = Instr.findRegisterUseOperand( - PrevVCMP->getOperand(0).getReg(), /*isKill*/ true)) { + if (MachineOperand *MO = + Instr.findRegisterUseOperand(PrevVCMP->getOperand(0).getReg(), + /*TRI=*/nullptr, /*isKill*/ true)) { // If we come accross the instr that kills PrevVCMP's result, record it // so we can remove the kill flag later if we need to. PrevVCMPResultKiller = MO; diff --git a/llvm/lib/Target/ARM/MVEVPTBlockPass.cpp b/llvm/lib/Target/ARM/MVEVPTBlockPass.cpp index d2b0bcf1250fe78b3b7aacc5c94f7939f370ee5b..197eca421e21d32336e0986ebdd35b53a030c161 100644 --- a/llvm/lib/Target/ARM/MVEVPTBlockPass.cpp +++ b/llvm/lib/Target/ARM/MVEVPTBlockPass.cpp @@ -131,7 +131,8 @@ static bool StepOverPredicatedInstrs(MachineBasicBlock::instr_iterator &Iter, static bool IsVPRDefinedOrKilledByBlock(MachineBasicBlock::iterator Iter, MachineBasicBlock::iterator End) { for (; Iter != End; ++Iter) - if (Iter->definesRegister(ARM::VPR) || Iter->killsRegister(ARM::VPR)) + if (Iter->definesRegister(ARM::VPR, /*TRI=*/nullptr) || + Iter->killsRegister(ARM::VPR, /*TRI=*/nullptr)) return true; return false; } diff --git a/llvm/lib/Target/ARM/Thumb2ITBlockPass.cpp b/llvm/lib/Target/ARM/Thumb2ITBlockPass.cpp index 2945b5eaae3e3fd1675d57b2a4a93376204a1141..147bf751945db1cecff1830d4b6f324ef0761154 100644 --- a/llvm/lib/Target/ARM/Thumb2ITBlockPass.cpp +++ b/llvm/lib/Target/ARM/Thumb2ITBlockPass.cpp @@ -269,7 +269,8 @@ bool Thumb2ITBlock::InsertITInstructions(MachineBasicBlock &MBB) { MIB.addImm(Mask); // Last instruction in IT block kills ITSTATE. - LastITMI->findRegisterUseOperand(ARM::ITSTATE)->setIsKill(); + LastITMI->findRegisterUseOperand(ARM::ITSTATE, /*TRI=*/nullptr) + ->setIsKill(); // Finalize the bundle. finalizeBundle(MBB, InsertPos.getInstrIterator(), diff --git a/llvm/lib/Target/ARM/Thumb2InstrInfo.cpp b/llvm/lib/Target/ARM/Thumb2InstrInfo.cpp index fc2834cb0b45c7d6812f7a3b9da2af9839f3ae3f..8ef5c3d9d6bad359d2ecb876557317fb09a6029e 100644 --- a/llvm/lib/Target/ARM/Thumb2InstrInfo.cpp +++ b/llvm/lib/Target/ARM/Thumb2InstrInfo.cpp @@ -571,7 +571,7 @@ bool llvm::rewriteT2FrameIndex(MachineInstr &MI, unsigned FrameRegIdx, Register PredReg; if (Offset == 0 && getInstrPredicate(MI, PredReg) == ARMCC::AL && - !MI.definesRegister(ARM::CPSR)) { + !MI.definesRegister(ARM::CPSR, /*TRI=*/nullptr)) { // Turn it into a move. MI.setDesc(TII.get(ARM::tMOVr)); MI.getOperand(FrameRegIdx).ChangeToRegister(FrameReg, false); diff --git a/llvm/lib/Target/ARM/Thumb2SizeReduction.cpp b/llvm/lib/Target/ARM/Thumb2SizeReduction.cpp index 286010e2ba232740be3f1e93da72e8da9ec53064..f572af98600738562bf8d028d9e3e78185fb17fd 100644 --- a/llvm/lib/Target/ARM/Thumb2SizeReduction.cpp +++ b/llvm/lib/Target/ARM/Thumb2SizeReduction.cpp @@ -1097,12 +1097,13 @@ bool Thumb2SizeReduce::ReduceMBB(MachineBasicBlock &MBB, // marker is only on the BUNDLE instruction. Process the BUNDLE // instruction as we finish with the bundled instruction to work around // the inconsistency. - if (BundleMI->killsRegister(ARM::CPSR)) + if (BundleMI->killsRegister(ARM::CPSR, /*TRI=*/nullptr)) LiveCPSR = false; - MachineOperand *MO = BundleMI->findRegisterDefOperand(ARM::CPSR); + MachineOperand *MO = + BundleMI->findRegisterDefOperand(ARM::CPSR, /*TRI=*/nullptr); if (MO && !MO->isDead()) LiveCPSR = true; - MO = BundleMI->findRegisterUseOperand(ARM::CPSR); + MO = BundleMI->findRegisterUseOperand(ARM::CPSR, /*TRI=*/nullptr); if (MO && !MO->isKill()) LiveCPSR = true; } diff --git a/llvm/lib/Target/AVR/MCTargetDesc/AVRMCTargetDesc.cpp b/llvm/lib/Target/AVR/MCTargetDesc/AVRMCTargetDesc.cpp index ba370261e284c5a57b2a20d53382b790b1855c73..119baff83dae461085ea390b97d0dcfcce698a69 100644 --- a/llvm/lib/Target/AVR/MCTargetDesc/AVRMCTargetDesc.cpp +++ b/llvm/lib/Target/AVR/MCTargetDesc/AVRMCTargetDesc.cpp @@ -72,10 +72,9 @@ static MCInstPrinter *createAVRMCInstPrinter(const Triple &T, static MCStreamer *createMCStreamer(const Triple &T, MCContext &Context, std::unique_ptr &&MAB, std::unique_ptr &&OW, - std::unique_ptr &&Emitter, - bool RelaxAll) { + std::unique_ptr &&Emitter) { return createELFStreamer(Context, std::move(MAB), std::move(OW), - std::move(Emitter), RelaxAll); + std::move(Emitter)); } static MCTargetStreamer * diff --git a/llvm/lib/Target/BPF/BPFTargetTransformInfo.h b/llvm/lib/Target/BPF/BPFTargetTransformInfo.h index 5aa9ec283406c218d282b70e87ef2aeaf41cf64c..0ecff32a7525f8be65a92cf61ba5b1ba4fd9d6b1 100644 --- a/llvm/lib/Target/BPF/BPFTargetTransformInfo.h +++ b/llvm/lib/Target/BPF/BPFTargetTransformInfo.h @@ -59,14 +59,14 @@ public: unsigned Opcode, Type *Ty, TTI::TargetCostKind CostKind, TTI::OperandValueInfo Op1Info = {TTI::OK_AnyValue, TTI::OP_None}, TTI::OperandValueInfo Op2Info = {TTI::OK_AnyValue, TTI::OP_None}, - ArrayRef Args = ArrayRef(), - const Instruction *CxtI = nullptr) { - int ISD = TLI->InstructionOpcodeToISD(Opcode); - if (ISD == ISD::ADD && CostKind == TTI::TCK_RecipThroughput) - return SCEVCheapExpansionBudget.getValue() + 1; - - return BaseT::getArithmeticInstrCost(Opcode, Ty, CostKind, Op1Info, - Op2Info); + ArrayRef Args = std::nullopt, + const Instruction *CxtI = nullptr) { + int ISD = TLI->InstructionOpcodeToISD(Opcode); + if (ISD == ISD::ADD && CostKind == TTI::TCK_RecipThroughput) + return SCEVCheapExpansionBudget.getValue() + 1; + + return BaseT::getArithmeticInstrCost(Opcode, Ty, CostKind, Op1Info, + Op2Info); } TTI::MemCmpExpansionOptions enableMemCmpExpansion(bool OptSize, diff --git a/llvm/lib/Target/BPF/MCTargetDesc/BPFMCTargetDesc.cpp b/llvm/lib/Target/BPF/MCTargetDesc/BPFMCTargetDesc.cpp index 44932383fb43e974e89e9beebe1a9825cb031fc9..caf84701b999f0501d1b7c55c52d6cafafe296d8 100644 --- a/llvm/lib/Target/BPF/MCTargetDesc/BPFMCTargetDesc.cpp +++ b/llvm/lib/Target/BPF/MCTargetDesc/BPFMCTargetDesc.cpp @@ -50,13 +50,13 @@ static MCSubtargetInfo *createBPFMCSubtargetInfo(const Triple &TT, return createBPFMCSubtargetInfoImpl(TT, CPU, /*TuneCPU*/ CPU, FS); } -static MCStreamer *createBPFMCStreamer(const Triple &T, MCContext &Ctx, - std::unique_ptr &&MAB, - std::unique_ptr &&OW, - std::unique_ptr &&Emitter, - bool RelaxAll) { - return createELFStreamer(Ctx, std::move(MAB), std::move(OW), std::move(Emitter), - RelaxAll); +static MCStreamer * +createBPFMCStreamer(const Triple &T, MCContext &Ctx, + std::unique_ptr &&MAB, + std::unique_ptr &&OW, + std::unique_ptr &&Emitter) { + return createELFStreamer(Ctx, std::move(MAB), std::move(OW), + std::move(Emitter)); } static MCInstPrinter *createBPFMCInstPrinter(const Triple &T, diff --git a/llvm/lib/Target/CSKY/MCTargetDesc/CSKYMCTargetDesc.cpp b/llvm/lib/Target/CSKY/MCTargetDesc/CSKYMCTargetDesc.cpp index 64f01cd1c9fa7c2c88b48c98d9b6c45b95016eac..c3403ade389c40194c839ad7e1e52ee240d7b861 100644 --- a/llvm/lib/Target/CSKY/MCTargetDesc/CSKYMCTargetDesc.cpp +++ b/llvm/lib/Target/CSKY/MCTargetDesc/CSKYMCTargetDesc.cpp @@ -88,13 +88,10 @@ createCSKYObjectTargetStreamer(MCStreamer &S, const MCSubtargetInfo &STI) { static MCStreamer *createELFStreamer(const Triple &T, MCContext &Ctx, std::unique_ptr &&MAB, std::unique_ptr &&OW, - std::unique_ptr &&Emitter, - bool RelaxAll) { + std::unique_ptr &&Emitter) { CSKYELFStreamer *S = new CSKYELFStreamer(Ctx, std::move(MAB), std::move(OW), std::move(Emitter)); - if (RelaxAll) - S->getAssembler().setRelaxAll(true); return S; } diff --git a/llvm/lib/Target/Hexagon/HexagonCopyToCombine.cpp b/llvm/lib/Target/Hexagon/HexagonCopyToCombine.cpp index 310993662b672fe0844a67ebc8edf09324fcb74d..99ac0c346d0c0d3f09dbf2e0e72303fe9021a502 100644 --- a/llvm/lib/Target/Hexagon/HexagonCopyToCombine.cpp +++ b/llvm/lib/Target/Hexagon/HexagonCopyToCombine.cpp @@ -283,7 +283,7 @@ bool HexagonCopyToCombine::isSafeToMoveTogether(MachineInstr &I1, // uses I2's use reg we need to modify that (first) instruction to now kill // this reg. unsigned KilledOperand = 0; - if (I2.killsRegister(I2UseReg)) + if (I2.killsRegister(I2UseReg, /*TRI=*/nullptr)) KilledOperand = I2UseReg; MachineInstr *KillingInstr = nullptr; @@ -360,11 +360,12 @@ bool HexagonCopyToCombine::isSafeToMoveTogether(MachineInstr &I1, if (isUnsafeToMoveAcross(MI, I1UseReg, I1DestReg, TRI) || // Check for an aliased register kill. Bail out if we see one. - (!MI.killsRegister(I1UseReg) && MI.killsRegister(I1UseReg, TRI))) + (!MI.killsRegister(I1UseReg, /*TRI=*/nullptr) && + MI.killsRegister(I1UseReg, TRI))) return false; // Check for an exact kill (registers match). - if (I1UseReg && MI.killsRegister(I1UseReg)) { + if (I1UseReg && MI.killsRegister(I1UseReg, /*TRI=*/nullptr)) { assert(!KillingInstr && "Should only see one killing instruction"); KilledOperand = I1UseReg; KillingInstr = &MI; diff --git a/llvm/lib/Target/Hexagon/HexagonExpandCondsets.cpp b/llvm/lib/Target/Hexagon/HexagonExpandCondsets.cpp index e1005296d637520777bae238196708e29c6f56f5..204f3b6b20c751348610e2374267f0bf811f9236 100644 --- a/llvm/lib/Target/Hexagon/HexagonExpandCondsets.cpp +++ b/llvm/lib/Target/Hexagon/HexagonExpandCondsets.cpp @@ -779,7 +779,8 @@ MachineInstr *HexagonExpandCondsets::getReachingDefForPred(RegisterRef RD, // Check if this instruction can be ignored, i.e. if it is predicated // on the complementary condition. if (PredValid && HII->isPredicated(*MI)) { - if (MI->readsRegister(PredR) && (Cond != HII->isPredicatedTrue(*MI))) + if (MI->readsRegister(PredR, /*TRI=*/nullptr) && + (Cond != HII->isPredicatedTrue(*MI))) continue; } @@ -937,7 +938,8 @@ void HexagonExpandCondsets::renameInRange(RegisterRef RO, RegisterRef RN, // on the opposite condition. if (!HII->isPredicated(MI)) continue; - if (!MI.readsRegister(PredR) || (Cond != HII->isPredicatedTrue(MI))) + if (!MI.readsRegister(PredR, /*TRI=*/nullptr) || + (Cond != HII->isPredicatedTrue(MI))) continue; for (auto &Op : MI.operands()) { @@ -1007,7 +1009,8 @@ bool HexagonExpandCondsets::predicate(MachineInstr &TfrI, bool Cond, // By default assume that the instruction executes on the same condition // as TfrI (Exec_Then), and also on the opposite one (Exec_Else). unsigned Exec = Exec_Then | Exec_Else; - if (PredValid && HII->isPredicated(MI) && MI.readsRegister(PredR)) + if (PredValid && HII->isPredicated(MI) && + MI.readsRegister(PredR, /*TRI=*/nullptr)) Exec = (Cond == HII->isPredicatedTrue(MI)) ? Exec_Then : Exec_Else; for (auto &Op : MI.operands()) { diff --git a/llvm/lib/Target/Hexagon/HexagonInstrInfo.cpp b/llvm/lib/Target/Hexagon/HexagonInstrInfo.cpp index b9bf26ba7cca1ec3447cd9d0ac4dfdadf288754d..e04f9c6faacd3e0f3a9a6b14a0ffa1b745b36089 100644 --- a/llvm/lib/Target/Hexagon/HexagonInstrInfo.cpp +++ b/llvm/lib/Target/Hexagon/HexagonInstrInfo.cpp @@ -3517,7 +3517,7 @@ unsigned HexagonInstrInfo::getCompoundOpcode(const MachineInstr &GA, (GB.getOpcode() != Hexagon::J2_jumptnew)) return -1u; Register DestReg = GA.getOperand(0).getReg(); - if (!GB.readsRegister(DestReg)) + if (!GB.readsRegister(DestReg, /*TRI=*/nullptr)) return -1u; if (DestReg != Hexagon::P0 && DestReg != Hexagon::P1) return -1u; @@ -4334,7 +4334,7 @@ std::optional HexagonInstrInfo::getOperandLatency( if (DefMO.isReg() && DefMO.getReg().isPhysical()) { if (DefMO.isImplicit()) { for (MCPhysReg SR : HRI.superregs(DefMO.getReg())) { - int Idx = DefMI.findRegisterDefOperandIdx(SR, false, false, &HRI); + int Idx = DefMI.findRegisterDefOperandIdx(SR, &HRI, false, false); if (Idx != -1) { DefIdx = Idx; break; @@ -4345,7 +4345,7 @@ std::optional HexagonInstrInfo::getOperandLatency( const MachineOperand &UseMO = UseMI.getOperand(UseIdx); if (UseMO.isImplicit()) { for (MCPhysReg SR : HRI.superregs(UseMO.getReg())) { - int Idx = UseMI.findRegisterUseOperandIdx(SR, false, &HRI); + int Idx = UseMI.findRegisterUseOperandIdx(SR, &HRI, false); if (Idx != -1) { UseIdx = Idx; break; diff --git a/llvm/lib/Target/Hexagon/HexagonTargetTransformInfo.h b/llvm/lib/Target/Hexagon/HexagonTargetTransformInfo.h index 9689f2f5bb865c21ba85a8245e4bfb884052e4c0..90c402876a57cde372270abbd72a5a5a4988517f 100644 --- a/llvm/lib/Target/Hexagon/HexagonTargetTransformInfo.h +++ b/llvm/lib/Target/Hexagon/HexagonTargetTransformInfo.h @@ -141,7 +141,7 @@ public: unsigned Opcode, Type *Ty, TTI::TargetCostKind CostKind, TTI::OperandValueInfo Op1Info = {TTI::OK_AnyValue, TTI::OP_None}, TTI::OperandValueInfo Op2Info = {TTI::OK_AnyValue, TTI::OP_None}, - ArrayRef Args = ArrayRef(), + ArrayRef Args = std::nullopt, const Instruction *CxtI = nullptr); InstructionCost getCastInstrCost(unsigned Opcode, Type *Dst, Type *Src, TTI::CastContextHint CCH, diff --git a/llvm/lib/Target/Hexagon/MCTargetDesc/HexagonMCTargetDesc.cpp b/llvm/lib/Target/Hexagon/MCTargetDesc/HexagonMCTargetDesc.cpp index dc8328a6705da8ea5a9701e00c0c3f128aa61b4e..0a948402fb896ae1d8351008bfdbe12e2d968f7a 100644 --- a/llvm/lib/Target/Hexagon/MCTargetDesc/HexagonMCTargetDesc.cpp +++ b/llvm/lib/Target/Hexagon/MCTargetDesc/HexagonMCTargetDesc.cpp @@ -385,8 +385,7 @@ createMCAsmTargetStreamer(MCStreamer &S, formatted_raw_ostream &OS, static MCStreamer *createMCStreamer(Triple const &T, MCContext &Context, std::unique_ptr &&MAB, std::unique_ptr &&OW, - std::unique_ptr &&Emitter, - bool RelaxAll) { + std::unique_ptr &&Emitter) { return createHexagonELFStreamer(T, Context, std::move(MAB), std::move(OW), std::move(Emitter)); } diff --git a/llvm/lib/Target/Lanai/LanaiTargetTransformInfo.h b/llvm/lib/Target/Lanai/LanaiTargetTransformInfo.h index bc612963b0ada26aacdee1d382b966ade8cb3abc..b064f4d5b1edf32ce8f641826166b7dfac9de3e0 100644 --- a/llvm/lib/Target/Lanai/LanaiTargetTransformInfo.h +++ b/llvm/lib/Target/Lanai/LanaiTargetTransformInfo.h @@ -94,7 +94,7 @@ public: unsigned Opcode, Type *Ty, TTI::TargetCostKind CostKind, TTI::OperandValueInfo Op1Info = {TTI::OK_AnyValue, TTI::OP_None}, TTI::OperandValueInfo Op2Info = {TTI::OK_AnyValue, TTI::OP_None}, - ArrayRef Args = ArrayRef(), + ArrayRef Args = std::nullopt, const Instruction *CxtI = nullptr) { int ISD = TLI->InstructionOpcodeToISD(Opcode); diff --git a/llvm/lib/Target/Lanai/MCTargetDesc/LanaiMCTargetDesc.cpp b/llvm/lib/Target/Lanai/MCTargetDesc/LanaiMCTargetDesc.cpp index 8f83c883e822e09297795ce50468f51e7ba669a1..4a381c033b384debd85aca8b01a5db386ce3b395 100644 --- a/llvm/lib/Target/Lanai/MCTargetDesc/LanaiMCTargetDesc.cpp +++ b/llvm/lib/Target/Lanai/MCTargetDesc/LanaiMCTargetDesc.cpp @@ -63,13 +63,12 @@ createLanaiMCSubtargetInfo(const Triple &TT, StringRef CPU, StringRef FS) { static MCStreamer *createMCStreamer(const Triple &T, MCContext &Context, std::unique_ptr &&MAB, std::unique_ptr &&OW, - std::unique_ptr &&Emitter, - bool RelaxAll) { + std::unique_ptr &&Emitter) { if (!T.isOSBinFormatELF()) llvm_unreachable("OS not supported"); return createELFStreamer(Context, std::move(MAB), std::move(OW), - std::move(Emitter), RelaxAll); + std::move(Emitter)); } static MCInstPrinter *createLanaiMCInstPrinter(const Triple & /*T*/, diff --git a/llvm/lib/Target/LoongArch/LoongArchSubtarget.h b/llvm/lib/Target/LoongArch/LoongArchSubtarget.h index cecb4a50aa7633c2d23ab27fa75b9b76853fa395..a6e40840517fa8a005f010b59ac3e2cc5e7b6bf7 100644 --- a/llvm/lib/Target/LoongArch/LoongArchSubtarget.h +++ b/llvm/lib/Target/LoongArch/LoongArchSubtarget.h @@ -31,21 +31,11 @@ class StringRef; class LoongArchSubtarget : public LoongArchGenSubtargetInfo { virtual void anchor(); - bool HasLA32 = false; - bool HasLA64 = false; - bool HasBasicF = false; - bool HasBasicD = false; - bool HasExtLSX = false; - bool HasExtLASX = false; - bool HasExtLVZ = false; - bool HasExtLBT = false; - bool HasLaGlobalWithPcrel = false; - bool HasLaGlobalWithAbs = false; - bool HasLaLocalWithAbs = false; - bool HasUAL = false; - bool HasLinkerRelax = false; - bool HasExpAutoVec = false; - bool HasFrecipe = false; + +#define GET_SUBTARGETINFO_MACRO(ATTRIBUTE, DEFAULT, GETTER) \ + bool ATTRIBUTE = DEFAULT; +#include "LoongArchGenSubtargetInfo.inc" + unsigned GRLen = 32; MVT GRLenVT = MVT::i32; LoongArchABI::ABI TargetABI = LoongArchABI::ABI_Unknown; @@ -92,20 +82,12 @@ public: const SelectionDAGTargetInfo *getSelectionDAGInfo() const override { return &TSInfo; } + +#define GET_SUBTARGETINFO_MACRO(ATTRIBUTE, DEFAULT, GETTER) \ + bool GETTER() const { return ATTRIBUTE; } +#include "LoongArchGenSubtargetInfo.inc" + bool is64Bit() const { return HasLA64; } - bool hasBasicF() const { return HasBasicF; } - bool hasBasicD() const { return HasBasicD; } - bool hasExtLSX() const { return HasExtLSX; } - bool hasExtLASX() const { return HasExtLASX; } - bool hasExtLVZ() const { return HasExtLVZ; } - bool hasExtLBT() const { return HasExtLBT; } - bool hasLaGlobalWithPcrel() const { return HasLaGlobalWithPcrel; } - bool hasLaGlobalWithAbs() const { return HasLaGlobalWithAbs; } - bool hasLaLocalWithAbs() const { return HasLaLocalWithAbs; } - bool hasUAL() const { return HasUAL; } - bool hasLinkerRelax() const { return HasLinkerRelax; } - bool hasExpAutoVec() const { return HasExpAutoVec; } - bool hasFrecipe() const { return HasFrecipe; } MVT getGRLenVT() const { return GRLenVT; } unsigned getGRLen() const { return GRLen; } LoongArchABI::ABI getTargetABI() const { return TargetABI; } diff --git a/llvm/lib/Target/LoongArch/MCTargetDesc/LoongArchELFStreamer.cpp b/llvm/lib/Target/LoongArch/MCTargetDesc/LoongArchELFStreamer.cpp index a6e15e09463d261fa5d612803d483faccb7b7118..9e56333e5fd9b569809779e4f2e27f7c79fe29eb 100644 --- a/llvm/lib/Target/LoongArch/MCTargetDesc/LoongArchELFStreamer.cpp +++ b/llvm/lib/Target/LoongArch/MCTargetDesc/LoongArchELFStreamer.cpp @@ -82,11 +82,9 @@ namespace llvm { MCELFStreamer *createLoongArchELFStreamer(MCContext &C, std::unique_ptr MAB, std::unique_ptr MOW, - std::unique_ptr MCE, - bool RelaxAll) { + std::unique_ptr MCE) { LoongArchELFStreamer *S = new LoongArchELFStreamer( C, std::move(MAB), std::move(MOW), std::move(MCE)); - S->getAssembler().setRelaxAll(RelaxAll); return S; } } // end namespace llvm diff --git a/llvm/lib/Target/LoongArch/MCTargetDesc/LoongArchELFStreamer.h b/llvm/lib/Target/LoongArch/MCTargetDesc/LoongArchELFStreamer.h index 220b54092c72a113f1ecb5918f9ea1cc7795fc08..e220729d8923e243e483fce118c5ec604fd79b58 100644 --- a/llvm/lib/Target/LoongArch/MCTargetDesc/LoongArchELFStreamer.h +++ b/llvm/lib/Target/LoongArch/MCTargetDesc/LoongArchELFStreamer.h @@ -25,7 +25,6 @@ public: MCELFStreamer *createLoongArchELFStreamer(MCContext &C, std::unique_ptr MAB, std::unique_ptr MOW, - std::unique_ptr MCE, - bool RelaxAll); + std::unique_ptr MCE); } // end namespace llvm #endif diff --git a/llvm/lib/Target/LoongArch/MCTargetDesc/LoongArchMCTargetDesc.cpp b/llvm/lib/Target/LoongArch/MCTargetDesc/LoongArchMCTargetDesc.cpp index a4e6a09863e6a68746e72453237365664e8b354c..e40981f5b5cd57a16970b976e44f6c4b3edbae74 100644 --- a/llvm/lib/Target/LoongArch/MCTargetDesc/LoongArchMCTargetDesc.cpp +++ b/llvm/lib/Target/LoongArch/MCTargetDesc/LoongArchMCTargetDesc.cpp @@ -193,10 +193,9 @@ namespace { MCStreamer *createLoongArchELFStreamer(const Triple &T, MCContext &Context, std::unique_ptr &&MAB, std::unique_ptr &&MOW, - std::unique_ptr &&MCE, - bool RelaxAll) { + std::unique_ptr &&MCE) { return createLoongArchELFStreamer(Context, std::move(MAB), std::move(MOW), - std::move(MCE), RelaxAll); + std::move(MCE)); } } // end namespace diff --git a/llvm/lib/Target/M68k/M68kExpandPseudo.cpp b/llvm/lib/Target/M68k/M68kExpandPseudo.cpp index 7fcc65beaa653b5e32a5394530b504a6583aeaa1..c7fdd7d7c35023f3c213b13802e34102ff0bc77c 100644 --- a/llvm/lib/Target/M68k/M68kExpandPseudo.cpp +++ b/llvm/lib/Target/M68k/M68kExpandPseudo.cpp @@ -80,6 +80,13 @@ bool M68kExpandPseudo::ExpandMI(MachineBasicBlock &MBB, default: return false; + case M68k::MOVI8di: + return TII->ExpandMOVI(MIB, MVT::i8); + case M68k::MOVI16ri: + return TII->ExpandMOVI(MIB, MVT::i16); + case M68k::MOVI32ri: + return TII->ExpandMOVI(MIB, MVT::i32); + case M68k::MOVXd16d8: return TII->ExpandMOVX_RR(MIB, MVT::i16, MVT::i8); case M68k::MOVXd32d8: diff --git a/llvm/lib/Target/M68k/M68kISelLowering.cpp b/llvm/lib/Target/M68k/M68kISelLowering.cpp index 786aa7bcb64ea0d4440ba425e277a3f54a8bfb1a..62e4b36b5c9a80291454971133f249fbfda30937 100644 --- a/llvm/lib/Target/M68k/M68kISelLowering.cpp +++ b/llvm/lib/Target/M68k/M68kISelLowering.cpp @@ -3075,9 +3075,9 @@ static bool checkAndUpdateCCRKill(MachineBasicBlock::iterator SelectItr, MachineBasicBlock::iterator miI(std::next(SelectItr)); for (MachineBasicBlock::iterator miE = BB->end(); miI != miE; ++miI) { const MachineInstr &mi = *miI; - if (mi.readsRegister(M68k::CCR)) + if (mi.readsRegister(M68k::CCR, /*TRI=*/nullptr)) return false; - if (mi.definesRegister(M68k::CCR)) + if (mi.definesRegister(M68k::CCR, /*TRI=*/nullptr)) break; // Should have kill-flag - update below. } @@ -3208,7 +3208,7 @@ M68kTargetLowering::EmitLoweredSelect(MachineInstr &MI, const TargetRegisterInfo *TRI = Subtarget.getRegisterInfo(); MachineInstr *LastCCRSUser = CascadedCMOV ? CascadedCMOV : LastCMOV; - if (!LastCCRSUser->killsRegister(M68k::CCR) && + if (!LastCCRSUser->killsRegister(M68k::CCR, /*TRI=*/nullptr) && !checkAndUpdateCCRKill(LastCCRSUser, MBB, TRI)) { Copy0MBB->addLiveIn(M68k::CCR); SinkMBB->addLiveIn(M68k::CCR); diff --git a/llvm/lib/Target/M68k/M68kInstrData.td b/llvm/lib/Target/M68k/M68kInstrData.td index fa7e7aa0ed4619216c88aac34cbf4e0245c934cb..dc777a933e2786be59def055da068eabb48dd8c1 100644 --- a/llvm/lib/Target/M68k/M68kInstrData.td +++ b/llvm/lib/Target/M68k/M68kInstrData.td @@ -19,7 +19,7 @@ /// /// Pseudo: /// -/// MOVSX [x] MOVZX [x] MOVX [x] +/// MOVI [x] MOVSX [x] MOVZX [x] MOVX [x] /// /// Map: /// @@ -165,11 +165,12 @@ foreach AM = MxMoveSupportedAMs in { } // foreach AM // R <- I +// No pattern, as all immediate -> register moves are matched to the MOVI pseudo class MxMove_RI("MxOp"#TYPE.Size#"AddrMode_i"), MxOpBundle DST = !cast("MxOp"#TYPE.Size#"AddrMode_"#DST_REG)> : MxMove; + [(null_frag)], ENC>; foreach REG = ["r", "a", "d"] in { foreach TYPE = !if(!eq(REG, "d"), [MxType8, MxType16, MxType32], [MxType16, MxType32]) in @@ -242,6 +243,24 @@ def : Pat<(store MxType32.BPat :$src, MxType32.BPat :$dst), def : Pat<(store MxType32.BPat :$src, MxType32.JPat :$dst), (MOV32ji MxType32.JOp :$dst, MxType32.IOp :$src)>; +//===----------------------------------------------------------------------===// +// MOVEQ +//===----------------------------------------------------------------------===// + +/// ------------+---------+---+----------------------- +/// F E D C | B A 9 | 8 | 7 6 5 4 3 2 1 0 +/// ------------+---------+---+----------------------- +/// 0 1 1 1 | REG | 0 | DATA +/// ------------+---------+---+----------------------- + +// No pattern, as all immediate -> register moves are matched to the MOVI pseudo +let Defs = [CCR] in +def MOVQ : MxInst<(outs MxDRD32:$dst), (ins Mxi8imm:$imm), + "moveq\t$imm, $dst", + [(null_frag)]> { + let Inst = (descend 0b0111, (operand "$dst", 3), 0b0, (operand "$imm", 8)); +} + //===----------------------------------------------------------------------===// // MOVEM // @@ -496,7 +515,23 @@ class MxPseudoMove_RR PAT = []> class MxPseudoMove_RM PAT = []> : MxPseudo<(outs DST.ROp:$dst), (ins SRCOpd:$src), PAT>; -} + + +// These Pseudos handle loading immediates to registers. +// They are expanded post-RA into either move or moveq instructions, +// depending on size, destination register class, and immediate value. +// This is done with pseudoinstructions in order to not constrain RA to +// data registers if moveq matches. +class MxPseudoMove_DI + : MxPseudo<(outs TYPE.ROp:$dst), (ins TYPE.IOp:$src), + [(set TYPE.ROp:$dst, imm:$src)]>; + +// i8 imm -> reg can always be converted to moveq, +// but we still emit a pseudo for consistency. +def MOVI8di : MxPseudoMove_DI; +def MOVI16ri : MxPseudoMove_DI; +def MOVI32ri : MxPseudoMove_DI; +} // let Defs = [CCR] /// This group of Pseudos is analogues to the real x86 extending moves, but /// since M68k does not have those we need to emulate. These instructions diff --git a/llvm/lib/Target/M68k/M68kInstrInfo.cpp b/llvm/lib/Target/M68k/M68kInstrInfo.cpp index d56fef9e9029af833cac2e6f951a52ec4e8fcdaf..338db45782c96124591b22151c188ae3a9383da6 100644 --- a/llvm/lib/Target/M68k/M68kInstrInfo.cpp +++ b/llvm/lib/Target/M68k/M68kInstrInfo.cpp @@ -346,6 +346,40 @@ void M68kInstrInfo::AddZExt(MachineBasicBlock &MBB, BuildMI(MBB, I, DL, get(And), Reg).addReg(Reg).addImm(Mask); } +// Convert MOVI to MOVQ if the target is a data register and the immediate +// fits in a sign-extended i8, otherwise emit a plain MOV. +bool M68kInstrInfo::ExpandMOVI(MachineInstrBuilder &MIB, MVT MVTSize) const { + Register Reg = MIB->getOperand(0).getReg(); + int64_t Imm = MIB->getOperand(1).getImm(); + bool IsAddressReg = false; + + const auto *DR32 = RI.getRegClass(M68k::DR32RegClassID); + const auto *AR32 = RI.getRegClass(M68k::AR32RegClassID); + const auto *AR16 = RI.getRegClass(M68k::AR16RegClassID); + + if (AR16->contains(Reg) || AR32->contains(Reg)) + IsAddressReg = true; + + LLVM_DEBUG(dbgs() << "Expand " << *MIB.getInstr() << " to "); + + if (MVTSize == MVT::i8 || (!IsAddressReg && Imm >= -128 && Imm <= 127)) { + LLVM_DEBUG(dbgs() << "MOVEQ\n"); + + // We need to assign to the full register to make IV happy + Register SReg = + MVTSize == MVT::i32 ? Reg : Register(RI.getMatchingMegaReg(Reg, DR32)); + assert(SReg && "No viable MEGA register available"); + + MIB->setDesc(get(M68k::MOVQ)); + MIB->getOperand(0).setReg(SReg); + } else { + LLVM_DEBUG(dbgs() << "MOVE\n"); + MIB->setDesc(get(MVTSize == MVT::i16 ? M68k::MOV16ri : M68k::MOV32ri)); + } + + return true; +} + bool M68kInstrInfo::ExpandMOVX_RR(MachineInstrBuilder &MIB, MVT MVTDst, MVT MVTSrc) const { unsigned Move = MVTDst == MVT::i16 ? M68k::MOV16rr : M68k::MOV32rr; diff --git a/llvm/lib/Target/M68k/M68kInstrInfo.h b/llvm/lib/Target/M68k/M68kInstrInfo.h index 577967f2fdfc97dc6b321f33bb9110c911c03447..d1e1e1cd99987ba274e78d4f84c82c239da53f9a 100644 --- a/llvm/lib/Target/M68k/M68kInstrInfo.h +++ b/llvm/lib/Target/M68k/M68kInstrInfo.h @@ -302,6 +302,9 @@ public: void AddZExt(MachineBasicBlock &MBB, MachineBasicBlock::iterator I, DebugLoc DL, unsigned Reg, MVT From, MVT To) const; + /// Move immediate to register + bool ExpandMOVI(MachineInstrBuilder &MIB, MVT MVTSize) const; + /// Move across register classes without extension bool ExpandMOVX_RR(MachineInstrBuilder &MIB, MVT MVTDst, MVT MVTSrc) const; diff --git a/llvm/lib/Target/Mips/MCTargetDesc/MipsELFStreamer.cpp b/llvm/lib/Target/Mips/MCTargetDesc/MipsELFStreamer.cpp index 9843b6144343e3b56f9d2ce605d335684e4ad2f1..e907e8d8a700222bfb953622f51a0c029408fa7d 100644 --- a/llvm/lib/Target/Mips/MCTargetDesc/MipsELFStreamer.cpp +++ b/llvm/lib/Target/Mips/MCTargetDesc/MipsELFStreamer.cpp @@ -112,10 +112,11 @@ void MipsELFStreamer::EmitMipsOptionRecords() { I->EmitMipsOptionRecord(); } -MCELFStreamer *llvm::createMipsELFStreamer( - MCContext &Context, std::unique_ptr MAB, - std::unique_ptr OW, std::unique_ptr Emitter, - bool RelaxAll) { +MCELFStreamer * +llvm::createMipsELFStreamer(MCContext &Context, + std::unique_ptr MAB, + std::unique_ptr OW, + std::unique_ptr Emitter) { return new MipsELFStreamer(Context, std::move(MAB), std::move(OW), std::move(Emitter)); } diff --git a/llvm/lib/Target/Mips/MCTargetDesc/MipsELFStreamer.h b/llvm/lib/Target/Mips/MCTargetDesc/MipsELFStreamer.h index ac70e40d4dfe96055d7f405eb56cc18ad22a21da..051806d2cfe8f556623a508e76ab3583e67133ea 100644 --- a/llvm/lib/Target/Mips/MCTargetDesc/MipsELFStreamer.h +++ b/llvm/lib/Target/Mips/MCTargetDesc/MipsELFStreamer.h @@ -75,8 +75,7 @@ public: MCELFStreamer *createMipsELFStreamer(MCContext &Context, std::unique_ptr MAB, std::unique_ptr OW, - std::unique_ptr Emitter, - bool RelaxAll); + std::unique_ptr Emitter); } // end namespace llvm #endif // LLVM_LIB_TARGET_MIPS_MCTARGETDESC_MIPSELFSTREAMER_H diff --git a/llvm/lib/Target/Mips/MCTargetDesc/MipsMCNaCl.h b/llvm/lib/Target/Mips/MCTargetDesc/MipsMCNaCl.h index a84ca8ccfb2d12b77c46e890dfd081bf1c56edb5..2722e34b3f624691c70c73915d7365360a8d862a 100644 --- a/llvm/lib/Target/Mips/MCTargetDesc/MipsMCNaCl.h +++ b/llvm/lib/Target/Mips/MCTargetDesc/MipsMCNaCl.h @@ -22,11 +22,10 @@ bool isBasePlusOffsetMemoryAccess(unsigned Opcode, unsigned *AddrIdx, bool baseRegNeedsLoadStoreMask(unsigned Reg); // This function creates an MCELFStreamer for Mips NaCl. -MCELFStreamer *createMipsNaClELFStreamer(MCContext &Context, - std::unique_ptr TAB, - std::unique_ptr OW, - std::unique_ptr Emitter, - bool RelaxAll); +MCELFStreamer * +createMipsNaClELFStreamer(MCContext &Context, std::unique_ptr TAB, + std::unique_ptr OW, + std::unique_ptr Emitter); } #endif diff --git a/llvm/lib/Target/Mips/MCTargetDesc/MipsMCTargetDesc.cpp b/llvm/lib/Target/Mips/MCTargetDesc/MipsMCTargetDesc.cpp index d38b89f9a1f25856f5a85185dd475ca9924a56c2..499cbd873e299a9aaab949455f371e6833cc3c41 100644 --- a/llvm/lib/Target/Mips/MCTargetDesc/MipsMCTargetDesc.cpp +++ b/llvm/lib/Target/Mips/MCTargetDesc/MipsMCTargetDesc.cpp @@ -104,15 +104,14 @@ static MCInstPrinter *createMipsMCInstPrinter(const Triple &T, static MCStreamer *createMCStreamer(const Triple &T, MCContext &Context, std::unique_ptr &&MAB, std::unique_ptr &&OW, - std::unique_ptr &&Emitter, - bool RelaxAll) { + std::unique_ptr &&Emitter) { MCStreamer *S; if (!T.isOSNaCl()) S = createMipsELFStreamer(Context, std::move(MAB), std::move(OW), - std::move(Emitter), RelaxAll); + std::move(Emitter)); else S = createMipsNaClELFStreamer(Context, std::move(MAB), std::move(OW), - std::move(Emitter), RelaxAll); + std::move(Emitter)); return S; } diff --git a/llvm/lib/Target/Mips/MCTargetDesc/MipsNaClELFStreamer.cpp b/llvm/lib/Target/Mips/MCTargetDesc/MipsNaClELFStreamer.cpp index 4ba0ae91e2f6537e859ece0bd9cb3134ef1c98ce..86194a9ebb61a29296a7097da2586cc444db8cd3 100644 --- a/llvm/lib/Target/Mips/MCTargetDesc/MipsNaClELFStreamer.cpp +++ b/llvm/lib/Target/Mips/MCTargetDesc/MipsNaClELFStreamer.cpp @@ -259,15 +259,12 @@ bool baseRegNeedsLoadStoreMask(unsigned Reg) { return Reg != Mips::SP && Reg != Mips::T8; } -MCELFStreamer *createMipsNaClELFStreamer(MCContext &Context, - std::unique_ptr TAB, - std::unique_ptr OW, - std::unique_ptr Emitter, - bool RelaxAll) { +MCELFStreamer * +createMipsNaClELFStreamer(MCContext &Context, std::unique_ptr TAB, + std::unique_ptr OW, + std::unique_ptr Emitter) { MipsNaClELFStreamer *S = new MipsNaClELFStreamer( Context, std::move(TAB), std::move(OW), std::move(Emitter)); - if (RelaxAll) - S->getAssembler().setRelaxAll(true); // Set bundle-alignment as required by the NaCl ABI for the target. S->emitBundleAlignMode(MIPS_NACL_BUNDLE_ALIGN); diff --git a/llvm/lib/Target/Mips/MipsDelaySlotFiller.cpp b/llvm/lib/Target/Mips/MipsDelaySlotFiller.cpp index cb98c04ff4e501c52936901cfd4413479426ae9e..b525606b1f8fd763202d1f31f5291d6d0de21fc8 100644 --- a/llvm/lib/Target/Mips/MipsDelaySlotFiller.cpp +++ b/llvm/lib/Target/Mips/MipsDelaySlotFiller.cpp @@ -365,7 +365,8 @@ void RegDefsUses::setCallerSaved(const MachineInstr &MI) { // Add RA/RA_64 to Defs to prevent users of RA/RA_64 from going into // the delay slot. The reason is that RA/RA_64 must not be changed // in the delay slot so that the callee can return to the caller. - if (MI.definesRegister(Mips::RA) || MI.definesRegister(Mips::RA_64)) { + if (MI.definesRegister(Mips::RA, /*TRI=*/nullptr) || + MI.definesRegister(Mips::RA_64, /*TRI=*/nullptr)) { Defs.set(Mips::RA); Defs.set(Mips::RA_64); } diff --git a/llvm/lib/Target/Mips/MipsExpandPseudo.cpp b/llvm/lib/Target/Mips/MipsExpandPseudo.cpp index d33852a04baf0d3e7c556fd2e8415e061b9598e6..199474fbd82d753d44500353057e13c42d0afb83 100644 --- a/llvm/lib/Target/Mips/MipsExpandPseudo.cpp +++ b/llvm/lib/Target/Mips/MipsExpandPseudo.cpp @@ -479,13 +479,13 @@ bool MipsExpandPseudo::expandAtomicBinOpSubword( BuildMI(loopMBB, DL, TII->get(Mips::SRAV), StoreVal) .addReg(OldVal) .addReg(ShiftAmnt); - if (STI->hasMips32r2() && !IsUnsigned) { - BuildMI(loopMBB, DL, TII->get(SEOp), StoreVal).addReg(StoreVal); - } else if (STI->hasMips32r2() && IsUnsigned) { + if (IsUnsigned) { const unsigned OpMask = SEOp == Mips::SEH ? 0xffff : 0xff; BuildMI(loopMBB, DL, TII->get(Mips::ANDi), StoreVal) .addReg(StoreVal) .addImm(OpMask); + } else if (STI->hasMips32r2()) { + BuildMI(loopMBB, DL, TII->get(SEOp), StoreVal).addReg(StoreVal); } else { const unsigned ShiftImm = SEOp == Mips::SEH ? 16 : 24; const unsigned SROp = IsUnsigned ? Mips::SRL : Mips::SRA; diff --git a/llvm/lib/Target/Mips/MipsInstrInfo.cpp b/llvm/lib/Target/Mips/MipsInstrInfo.cpp index 392cc15d7943afa66b870b484bb5f82340de6caf..f4fba5e53132df9f33bfd707d3742a260f6eb5bd 100644 --- a/llvm/lib/Target/Mips/MipsInstrInfo.cpp +++ b/llvm/lib/Target/Mips/MipsInstrInfo.cpp @@ -619,7 +619,7 @@ bool MipsInstrInfo::SafeInLoadDelaySlot(const MachineInstr &MIInSlot, return false; return !llvm::any_of(LoadMI.defs(), [&](const MachineOperand &Op) { - return Op.isReg() && MIInSlot.readsRegister(Op.getReg()); + return Op.isReg() && MIInSlot.readsRegister(Op.getReg(), /*TRI=*/nullptr); }); } @@ -699,7 +699,7 @@ MipsInstrInfo::genInstrWithNewOpc(unsigned NewOpc, bool BranchWithZeroOperand = false; if (I->isBranch() && !I->isPseudo()) { auto TRI = I->getParent()->getParent()->getSubtarget().getRegisterInfo(); - ZeroOperandPosition = I->findRegisterUseOperandIdx(Mips::ZERO, false, TRI); + ZeroOperandPosition = I->findRegisterUseOperandIdx(Mips::ZERO, TRI, false); BranchWithZeroOperand = ZeroOperandPosition != -1; } diff --git a/llvm/lib/Target/NVPTX/NVPTXISelDAGToDAG.cpp b/llvm/lib/Target/NVPTX/NVPTXISelDAGToDAG.cpp index a362709c98efd6645f9b3809c1d5c6e62330cf4f..595395bb1b4b43b6858bd40f43601fd85466225d 100644 --- a/llvm/lib/Target/NVPTX/NVPTXISelDAGToDAG.cpp +++ b/llvm/lib/Target/NVPTX/NVPTXISelDAGToDAG.cpp @@ -30,6 +30,10 @@ using namespace llvm; #define DEBUG_TYPE "nvptx-isel" #define PASS_NAME "NVPTX DAG->DAG Pattern Instruction Selection" +static cl::opt + EnableRsqrtOpt("nvptx-rsqrt-approx-opt", cl::init(true), cl::Hidden, + cl::desc("Enable reciprocal sqrt optimization")); + /// createNVPTXISelDag - This pass converts a legalized DAG into a /// NVPTX-specific DAG, ready for instruction scheduling. FunctionPass *llvm::createNVPTXISelDag(NVPTXTargetMachine &TM, @@ -74,6 +78,8 @@ bool NVPTXDAGToDAGISel::allowUnsafeFPMath() const { return TL->allowUnsafeFPMath(*MF); } +bool NVPTXDAGToDAGISel::doRsqrtOpt() const { return EnableRsqrtOpt; } + /// Select - Select instructions not customized! Used for /// expanded, promoted and normal instructions. void NVPTXDAGToDAGISel::Select(SDNode *N) { diff --git a/llvm/lib/Target/NVPTX/NVPTXISelDAGToDAG.h b/llvm/lib/Target/NVPTX/NVPTXISelDAGToDAG.h index 10822f87cef308283f3fe779a13121b24f3a20ac..7a7774744bc71def9272e2ee3465170df7abd1af 100644 --- a/llvm/lib/Target/NVPTX/NVPTXISelDAGToDAG.h +++ b/llvm/lib/Target/NVPTX/NVPTXISelDAGToDAG.h @@ -36,6 +36,7 @@ class LLVM_LIBRARY_VISIBILITY NVPTXDAGToDAGISel : public SelectionDAGISel { bool useF32FTZ() const; bool allowFMA() const; bool allowUnsafeFPMath() const; + bool doRsqrtOpt() const; public: static char ID; diff --git a/llvm/lib/Target/NVPTX/NVPTXInstrInfo.td b/llvm/lib/Target/NVPTX/NVPTXInstrInfo.td index 931292c7fd6042eb8a4194a2f9874ce2a09c52ea..897ee89323f083eb4cf26af228f644694cb7dfcd 100644 --- a/llvm/lib/Target/NVPTX/NVPTXInstrInfo.td +++ b/llvm/lib/Target/NVPTX/NVPTXInstrInfo.td @@ -142,6 +142,7 @@ def hasLDU : Predicate<"Subtarget->hasLDU()">; def doF32FTZ : Predicate<"useF32FTZ()">; def doNoF32FTZ : Predicate<"!useF32FTZ()">; +def doRsqrtOpt : Predicate<"doRsqrtOpt()">; def doMulWide : Predicate<"doMulWide">; diff --git a/llvm/lib/Target/NVPTX/NVPTXIntrinsics.td b/llvm/lib/Target/NVPTX/NVPTXIntrinsics.td index ec9170b4e41e5c6f8b37d326f7582f9ce46fd7a7..5f6e28283c5d250c642c7361b852d1148f4f64dc 100644 --- a/llvm/lib/Target/NVPTX/NVPTXIntrinsics.td +++ b/llvm/lib/Target/NVPTX/NVPTXIntrinsics.td @@ -1171,11 +1171,36 @@ def : Pat<(int_nvvm_sqrt_f Float32Regs:$a), def INT_NVVM_RSQRT_APPROX_FTZ_F : F_MATH_1<"rsqrt.approx.ftz.f32 \t$dst, $src0;", Float32Regs, Float32Regs, int_nvvm_rsqrt_approx_ftz_f>; +def INT_NVVM_RSQRT_APPROX_FTZ_D + : F_MATH_1<"rsqrt.approx.ftz.f64 \t$dst, $src0;", Float64Regs, Float64Regs, + int_nvvm_rsqrt_approx_ftz_d>; + def INT_NVVM_RSQRT_APPROX_F : F_MATH_1<"rsqrt.approx.f32 \t$dst, $src0;", Float32Regs, Float32Regs, int_nvvm_rsqrt_approx_f>; def INT_NVVM_RSQRT_APPROX_D : F_MATH_1<"rsqrt.approx.f64 \t$dst, $src0;", Float64Regs, Float64Regs, int_nvvm_rsqrt_approx_d>; +// 1.0f / sqrt_approx -> rsqrt_approx +def: Pat<(fdiv FloatConst1, (int_nvvm_sqrt_approx_f Float32Regs:$a)), + (INT_NVVM_RSQRT_APPROX_F Float32Regs:$a)>, + Requires<[doRsqrtOpt]>; +def: Pat<(fdiv FloatConst1, (int_nvvm_sqrt_approx_ftz_f Float32Regs:$a)), + (INT_NVVM_RSQRT_APPROX_FTZ_F Float32Regs:$a)>, + Requires<[doRsqrtOpt]>; +// same for int_nvvm_sqrt_f when non-precision sqrt is requested +def: Pat<(fdiv FloatConst1, (int_nvvm_sqrt_f Float32Regs:$a)), + (INT_NVVM_RSQRT_APPROX_F Float32Regs:$a)>, + Requires<[doRsqrtOpt, do_SQRTF32_APPROX, doNoF32FTZ]>; +def: Pat<(fdiv FloatConst1, (int_nvvm_sqrt_f Float32Regs:$a)), + (INT_NVVM_RSQRT_APPROX_FTZ_F Float32Regs:$a)>, + Requires<[doRsqrtOpt, do_SQRTF32_APPROX, doF32FTZ]>; + +def: Pat<(fdiv FloatConst1, (fsqrt Float32Regs:$a)), + (INT_NVVM_RSQRT_APPROX_F Float32Regs:$a)>, + Requires<[doRsqrtOpt, do_SQRTF32_APPROX, doNoF32FTZ]>; +def: Pat<(fdiv FloatConst1, (fsqrt Float32Regs:$a)), + (INT_NVVM_RSQRT_APPROX_FTZ_F Float32Regs:$a)>, + Requires<[doRsqrtOpt, do_SQRTF32_APPROX, doF32FTZ]>; // // Add // diff --git a/llvm/lib/Target/NVPTX/NVPTXTargetTransformInfo.h b/llvm/lib/Target/NVPTX/NVPTXTargetTransformInfo.h index 3ce2675560c4df0c5d865ebe8245492b2ba0ef21..5a4fbab97f952e021f26f5f9a52cf4497b5696df 100644 --- a/llvm/lib/Target/NVPTX/NVPTXTargetTransformInfo.h +++ b/llvm/lib/Target/NVPTX/NVPTXTargetTransformInfo.h @@ -98,7 +98,7 @@ public: unsigned Opcode, Type *Ty, TTI::TargetCostKind CostKind, TTI::OperandValueInfo Op1Info = {TTI::OK_AnyValue, TTI::OP_None}, TTI::OperandValueInfo Op2Info = {TTI::OK_AnyValue, TTI::OP_None}, - ArrayRef Args = ArrayRef(), + ArrayRef Args = std::nullopt, const Instruction *CxtI = nullptr); void getUnrollingPreferences(Loop *L, ScalarEvolution &SE, diff --git a/llvm/lib/Target/PowerPC/MCTargetDesc/PPCMCTargetDesc.cpp b/llvm/lib/Target/PowerPC/MCTargetDesc/PPCMCTargetDesc.cpp index b849b7be7b7be8c73e79d94a9424a8d4ad5a4734..241078b038735b65ddb5eb6195ce4da30f3ff248 100644 --- a/llvm/lib/Target/PowerPC/MCTargetDesc/PPCMCTargetDesc.cpp +++ b/llvm/lib/Target/PowerPC/MCTargetDesc/PPCMCTargetDesc.cpp @@ -203,15 +203,16 @@ static MCStreamer * createPPCELFStreamer(const Triple &T, MCContext &Context, std::unique_ptr &&MAB, std::unique_ptr &&OW, - std::unique_ptr &&Emitter, bool RelaxAll) { + std::unique_ptr &&Emitter) { return createPPCELFStreamer(Context, std::move(MAB), std::move(OW), std::move(Emitter)); } -static MCStreamer *createPPCXCOFFStreamer( - const Triple &T, MCContext &Context, std::unique_ptr &&MAB, - std::unique_ptr &&OW, - std::unique_ptr &&Emitter, bool RelaxAll) { +static MCStreamer * +createPPCXCOFFStreamer(const Triple &T, MCContext &Context, + std::unique_ptr &&MAB, + std::unique_ptr &&OW, + std::unique_ptr &&Emitter) { return createPPCXCOFFStreamer(Context, std::move(MAB), std::move(OW), std::move(Emitter)); } diff --git a/llvm/lib/Target/PowerPC/PPCAsmPrinter.cpp b/llvm/lib/Target/PowerPC/PPCAsmPrinter.cpp index 6e1002c45d81cb3d976bd3e2ba60a1dbecdbe03d..51b79dc2b04b4ec3d5876e1478e5521384743d73 100644 --- a/llvm/lib/Target/PowerPC/PPCAsmPrinter.cpp +++ b/llvm/lib/Target/PowerPC/PPCAsmPrinter.cpp @@ -27,7 +27,7 @@ #include "PPCTargetStreamer.h" #include "TargetInfo/PowerPCTargetInfo.h" #include "llvm/ADT/MapVector.h" -#include "llvm/ADT/SmallPtrSet.h" +#include "llvm/ADT/SetVector.h" #include "llvm/ADT/Statistic.h" #include "llvm/ADT/StringExtras.h" #include "llvm/ADT/StringRef.h" @@ -242,7 +242,7 @@ class PPCAIXAsmPrinter : public PPCAsmPrinter { private: /// Symbols lowered from ExternalSymbolSDNodes, we will need to emit extern /// linkage for them in AIX. - SmallPtrSet ExtSymSDNodeSymbols; + SmallSetVector ExtSymSDNodeSymbols; /// A format indicator and unique trailing identifier to form part of the /// sinit/sterm function names. diff --git a/llvm/lib/Target/PowerPC/PPCCTRLoops.cpp b/llvm/lib/Target/PowerPC/PPCCTRLoops.cpp index 5299c0c924b3c53f7eaec793bc25f0d6c3b924e1..491779124e8a77267b722a2d65f863defc252d15 100644 --- a/llvm/lib/Target/PowerPC/PPCCTRLoops.cpp +++ b/llvm/lib/Target/PowerPC/PPCCTRLoops.cpp @@ -123,10 +123,12 @@ bool PPCCTRLoops::isCTRClobber(MachineInstr *MI, bool CheckReads) const { // CTR defination inside the callee of a call instruction will not impact // the defination of MTCTRloop, so we can use definesRegister() for the // check, no need to check the regmask. - return MI->definesRegister(PPC::CTR) || MI->definesRegister(PPC::CTR8); + return MI->definesRegister(PPC::CTR, /*TRI=*/nullptr) || + MI->definesRegister(PPC::CTR8, /*TRI=*/nullptr); } - if (MI->modifiesRegister(PPC::CTR) || MI->modifiesRegister(PPC::CTR8)) + if (MI->modifiesRegister(PPC::CTR, /*TRI=*/nullptr) || + MI->modifiesRegister(PPC::CTR8, /*TRI=*/nullptr)) return true; if (MI->getDesc().isCall()) @@ -134,7 +136,8 @@ bool PPCCTRLoops::isCTRClobber(MachineInstr *MI, bool CheckReads) const { // We define the CTR in the loop preheader, so if there is any CTR reader in // the loop, we also can not use CTR loop form. - if (MI->readsRegister(PPC::CTR) || MI->readsRegister(PPC::CTR8)) + if (MI->readsRegister(PPC::CTR, /*TRI=*/nullptr) || + MI->readsRegister(PPC::CTR8, /*TRI=*/nullptr)) return true; return false; diff --git a/llvm/lib/Target/PowerPC/PPCInstr64Bit.td b/llvm/lib/Target/PowerPC/PPCInstr64Bit.td index a9359794a641c95ec99ad98038eb69f2e6825360..9af8ada7837614c1d311bc555ab5460a3f53e609 100644 --- a/llvm/lib/Target/PowerPC/PPCInstr64Bit.td +++ b/llvm/lib/Target/PowerPC/PPCInstr64Bit.td @@ -76,7 +76,7 @@ let Interpretation64Bit = 1, isCodeGenOnly = 1 in { let isTerminator = 1, isBarrier = 1, PPC970_Unit = 7, hasSideEffects = 0 in { let isReturn = 1, isPredicable = 1, Uses = [LR8, RM] in def BLR8 : XLForm_2_ext<19, 16, 20, 0, 0, (outs), (ins), "blr", IIC_BrB, - [(retglue)]>, Requires<[In64BitMode]>; + [(PPCretglue)]>, Requires<[In64BitMode]>; let isBranch = 1, isIndirectBranch = 1, Uses = [CTR8] in { let isPredicable = 1 in def BCTR8 : XLForm_2_ext<19, 528, 20, 0, 0, (outs), (ins), "bctr", IIC_BrB, diff --git a/llvm/lib/Target/PowerPC/PPCInstrInfo.cpp b/llvm/lib/Target/PowerPC/PPCInstrInfo.cpp index b32f178ca38e65f5a32df2f67be91f7beea94f28..9e56de732c587e8a568e533ac18702b6eb61b5a4 100644 --- a/llvm/lib/Target/PowerPC/PPCInstrInfo.cpp +++ b/llvm/lib/Target/PowerPC/PPCInstrInfo.cpp @@ -2125,7 +2125,8 @@ bool PPCInstrInfo::foldImmediate(MachineInstr &UseMI, MachineInstr &DefMI, static bool MBBDefinesCTR(MachineBasicBlock &MBB) { for (MachineInstr &MI : MBB) - if (MI.definesRegister(PPC::CTR) || MI.definesRegister(PPC::CTR8)) + if (MI.definesRegister(PPC::CTR, /*TRI=*/nullptr) || + MI.definesRegister(PPC::CTR8, /*TRI=*/nullptr)) return true; return false; } @@ -2731,19 +2732,19 @@ bool PPCInstrInfo::optimizeCompareInstr(MachineInstr &CmpInstr, Register SrcReg, MI->setDesc(NewDesc); for (MCPhysReg ImpDef : NewDesc.implicit_defs()) { - if (!MI->definesRegister(ImpDef)) { + if (!MI->definesRegister(ImpDef, /*TRI=*/nullptr)) { MI->addOperand(*MI->getParent()->getParent(), MachineOperand::CreateReg(ImpDef, true, true)); } } for (MCPhysReg ImpUse : NewDesc.implicit_uses()) { - if (!MI->readsRegister(ImpUse)) { + if (!MI->readsRegister(ImpUse, /*TRI=*/nullptr)) { MI->addOperand(*MI->getParent()->getParent(), MachineOperand::CreateReg(ImpUse, false, true)); } } } - assert(MI->definesRegister(PPC::CR0) && + assert(MI->definesRegister(PPC::CR0, /*TRI=*/nullptr) && "Record-form instruction does not define cr0?"); // Modify the condition code of operands in OperandsToUpdate. @@ -2793,7 +2794,7 @@ bool PPCInstrInfo::optimizeCmpPostRA(MachineInstr &CmpMI) const { bool SrcRegHasOtherUse = false; MachineInstr *SrcMI = getDefMIPostRA(SrcReg, CmpMI, SrcRegHasOtherUse); - if (!SrcMI || !SrcMI->definesRegister(SrcReg)) + if (!SrcMI || !SrcMI->definesRegister(SrcReg, /*TRI=*/nullptr)) return false; MachineOperand RegMO = CmpMI.getOperand(0); @@ -2806,7 +2807,7 @@ bool PPCInstrInfo::optimizeCmpPostRA(MachineInstr &CmpMI) const { bool IsCRRegKilled = false; if (!isRegElgibleForForwarding(RegMO, *SrcMI, CmpMI, false, IsCRRegKilled, SeenUseOfCRReg) || - SrcMI->definesRegister(CRReg) || SeenUseOfCRReg) + SrcMI->definesRegister(CRReg, /*TRI=*/nullptr) || SeenUseOfCRReg) return false; int SrcMIOpc = SrcMI->getOpcode(); @@ -2823,7 +2824,7 @@ bool PPCInstrInfo::optimizeCmpPostRA(MachineInstr &CmpMI) const { .addReg(CRReg, RegState::ImplicitDefine); SrcMI->clearRegisterDeads(CRReg); - assert(SrcMI->definesRegister(PPC::CR0) && + assert(SrcMI->definesRegister(PPC::CR0, /*TRI=*/nullptr) && "Record-form instruction does not define cr0?"); LLVM_DEBUG(dbgs() << "with: "); @@ -3293,7 +3294,7 @@ void PPCInstrInfo::replaceInstrOperandWithImm(MachineInstr &MI, // result its number of explicit operands may be changed, thus the begin of // implicit operand is changed. const TargetRegisterInfo *TRI = &getRegisterInfo(); - int UseOpIdx = MI.findRegisterUseOperandIdx(InUseReg, false, TRI); + int UseOpIdx = MI.findRegisterUseOperandIdx(InUseReg, TRI, false); if (UseOpIdx >= 0) { MachineOperand &MO = MI.getOperand(UseOpIdx); if (MO.isImplicit()) diff --git a/llvm/lib/Target/PowerPC/PPCInstrInfo.td b/llvm/lib/Target/PowerPC/PPCInstrInfo.td index 261b9a3d1dffe9a17a21eb5d1821005c7b167617..7929a781dbda84bc09828b679a46d7477e8809aa 100644 --- a/llvm/lib/Target/PowerPC/PPCInstrInfo.td +++ b/llvm/lib/Target/PowerPC/PPCInstrInfo.td @@ -336,7 +336,7 @@ def PPCbctrl_load_toc_rm : SDNode<"PPCISD::BCTRL_LOAD_TOC_RM", [SDNPHasChain, SDNPOptInGlue, SDNPOutGlue, SDNPVariadic]>; -def retglue : SDNode<"PPCISD::RET_GLUE", SDTNone, +def PPCretglue : SDNode<"PPCISD::RET_GLUE", SDTNone, [SDNPHasChain, SDNPOptInGlue, SDNPVariadic]>; def PPCtc_return : SDNode<"PPCISD::TC_RETURN", SDT_PPCTC_ret, @@ -1299,7 +1299,7 @@ def RESTORE_CRBIT : PPCEmitTimePseudo<(outs crbitrc:$cond), (ins memri:$F), let isTerminator = 1, isBarrier = 1, PPC970_Unit = 7, hasSideEffects = 0 in { let isPredicable = 1, isReturn = 1, Uses = [LR, RM] in def BLR : XLForm_2_ext<19, 16, 20, 0, 0, (outs), (ins), "blr", IIC_BrB, - [(retglue)]>, Requires<[In32BitMode]>; + [(PPCretglue)]>, Requires<[In32BitMode]>; let isBranch = 1, isIndirectBranch = 1, Uses = [CTR] in { let isPredicable = 1 in def BCTR : XLForm_2_ext<19, 528, 20, 0, 0, (outs), (ins), "bctr", IIC_BrB, diff --git a/llvm/lib/Target/PowerPC/PPCPreEmitPeephole.cpp b/llvm/lib/Target/PowerPC/PPCPreEmitPeephole.cpp index 6e3bf26a598a9a6d121f828abe4e95602d1c7ad3..a182be3ea712b4d823cedb276b40ecd070cdfbfa 100644 --- a/llvm/lib/Target/PowerPC/PPCPreEmitPeephole.cpp +++ b/llvm/lib/Target/PowerPC/PPCPreEmitPeephole.cpp @@ -158,7 +158,7 @@ static bool hasPCRelativeForm(MachineInstr &Use) { ++AfterBBI) { // Track the operand that kill Reg. We would unset the kill flag of // the operand if there is a following redundant load immediate. - int KillIdx = AfterBBI->findRegisterUseOperandIdx(Reg, true, TRI); + int KillIdx = AfterBBI->findRegisterUseOperandIdx(Reg, TRI, true); // We can't just clear implicit kills, so if we encounter one, stop // looking further. @@ -204,7 +204,7 @@ static bool hasPCRelativeForm(MachineInstr &Use) { DeadOrKillToUnset->setIsKill(false); } DeadOrKillToUnset = - AfterBBI->findRegisterDefOperand(Reg, true, true, TRI); + AfterBBI->findRegisterDefOperand(Reg, TRI, true, true); if (DeadOrKillToUnset) LLVM_DEBUG(dbgs() << " Dead flag of " << *DeadOrKillToUnset << " from " diff --git a/llvm/lib/Target/PowerPC/PPCRegisterInfo.cpp b/llvm/lib/Target/PowerPC/PPCRegisterInfo.cpp index 0f450a4bf9692bce736a91e00e651dacbae2b89d..7e4cd6c72aa87a45b72926c24330a56c499a6960 100644 --- a/llvm/lib/Target/PowerPC/PPCRegisterInfo.cpp +++ b/llvm/lib/Target/PowerPC/PPCRegisterInfo.cpp @@ -1013,8 +1013,8 @@ void PPCRegisterInfo::lowerCRRestore(MachineBasicBlock::iterator II, Register Reg = MF.getRegInfo().createVirtualRegister(LP64 ? G8RC : GPRC); Register DestReg = MI.getOperand(0).getReg(); - assert(MI.definesRegister(DestReg) && - "RESTORE_CR does not define its destination"); + assert(MI.definesRegister(DestReg, /*TRI=*/nullptr) && + "RESTORE_CR does not define its destination"); addFrameReference(BuildMI(MBB, II, dl, TII.get(LP64 ? PPC::LWZ8 : PPC::LWZ), Reg), FrameIndex); @@ -1175,8 +1175,8 @@ void PPCRegisterInfo::lowerCRBitRestore(MachineBasicBlock::iterator II, Register Reg = MF.getRegInfo().createVirtualRegister(LP64 ? G8RC : GPRC); Register DestReg = MI.getOperand(0).getReg(); - assert(MI.definesRegister(DestReg) && - "RESTORE_CRBIT does not define its destination"); + assert(MI.definesRegister(DestReg, /*TRI=*/nullptr) && + "RESTORE_CRBIT does not define its destination"); addFrameReference(BuildMI(MBB, II, dl, TII.get(LP64 ? PPC::LWZ8 : PPC::LWZ), Reg), FrameIndex); @@ -1363,7 +1363,7 @@ void PPCRegisterInfo::lowerACCRestore(MachineBasicBlock::iterator II, DebugLoc DL = MI.getDebugLoc(); Register DestReg = MI.getOperand(0).getReg(); - assert(MI.definesRegister(DestReg) && + assert(MI.definesRegister(DestReg, /*TRI=*/nullptr) && "RESTORE_ACC does not define its destination"); bool IsPrimed = PPC::ACCRCRegClass.contains(DestReg); @@ -1491,7 +1491,7 @@ void PPCRegisterInfo::lowerQuadwordRestore(MachineBasicBlock::iterator II, DebugLoc DL = MI.getDebugLoc(); Register DestReg = MI.getOperand(0).getReg(); - assert(MI.definesRegister(DestReg) && + assert(MI.definesRegister(DestReg, /*TRI=*/nullptr) && "RESTORE_QUADWORD does not define its destination"); Register Reg = PPC::X0 + (DestReg - PPC::G8p0) * 2; diff --git a/llvm/lib/Target/PowerPC/PPCTargetTransformInfo.h b/llvm/lib/Target/PowerPC/PPCTargetTransformInfo.h index 36006dd7df7396affc0d1b2c3cdc7154d4563b58..061f5da5daf53b86525f500e028b88142b5e7e6f 100644 --- a/llvm/lib/Target/PowerPC/PPCTargetTransformInfo.h +++ b/llvm/lib/Target/PowerPC/PPCTargetTransformInfo.h @@ -106,7 +106,7 @@ public: unsigned Opcode, Type *Ty, TTI::TargetCostKind CostKind, TTI::OperandValueInfo Op1Info = {TTI::OK_AnyValue, TTI::OP_None}, TTI::OperandValueInfo Op2Info = {TTI::OK_AnyValue, TTI::OP_None}, - ArrayRef Args = ArrayRef(), + ArrayRef Args = std::nullopt, const Instruction *CxtI = nullptr); InstructionCost getShuffleCost(TTI::ShuffleKind Kind, Type *Tp, ArrayRef Mask, diff --git a/llvm/lib/Target/RISCV/AsmParser/RISCVAsmParser.cpp b/llvm/lib/Target/RISCV/AsmParser/RISCVAsmParser.cpp index 3f4a73ad89bf8ace318b15c4db01a2892fc565d2..8ac79ddce595e0d36a41ba5fdf8ca455c8f2b47d 100644 --- a/llvm/lib/Target/RISCV/AsmParser/RISCVAsmParser.cpp +++ b/llvm/lib/Target/RISCV/AsmParser/RISCVAsmParser.cpp @@ -38,7 +38,7 @@ #include "llvm/Support/CommandLine.h" #include "llvm/Support/MathExtras.h" #include "llvm/Support/RISCVAttributes.h" -#include "llvm/Support/RISCVISAInfo.h" +#include "llvm/TargetParser/RISCVISAInfo.h" #include diff --git a/llvm/lib/Target/RISCV/MCA/RISCVCustomBehaviour.cpp b/llvm/lib/Target/RISCV/MCA/RISCVCustomBehaviour.cpp index 8d97c5ffd20a05ab543bddbbe19c8e52ffd27cc5..fb0dc482e6081302b8fceb22f8a475719e8f1182 100644 --- a/llvm/lib/Target/RISCV/MCA/RISCVCustomBehaviour.cpp +++ b/llvm/lib/Target/RISCV/MCA/RISCVCustomBehaviour.cpp @@ -20,26 +20,6 @@ #define DEBUG_TYPE "llvm-mca-riscv-custombehaviour" -// This brings in a table with primary key of -// base instruction opcode and lmul and maps -// to the opcode of the pseudo instruction. -namespace RISCVVInversePseudosTable { -using namespace llvm; -using namespace llvm::RISCV; - -struct PseudoInfo { - uint16_t Pseudo; - uint16_t BaseInstr; - uint8_t VLMul; - uint8_t SEW; -}; - -#define GET_RISCVVInversePseudosTable_IMPL -#define GET_RISCVVInversePseudosTable_DECL -#include "RISCVGenSearchableTables.inc" - -} // end namespace RISCVVInversePseudosTable - namespace llvm { namespace mca { diff --git a/llvm/lib/Target/RISCV/MCTargetDesc/RISCVBaseInfo.cpp b/llvm/lib/Target/RISCV/MCTargetDesc/RISCVBaseInfo.cpp index 67c9060b515772bfe6e8b357ece2d855a0f549f4..4c59474df883585506bb3a252a36fa5e353a8cfb 100644 --- a/llvm/lib/Target/RISCV/MCTargetDesc/RISCVBaseInfo.cpp +++ b/llvm/lib/Target/RISCV/MCTargetDesc/RISCVBaseInfo.cpp @@ -16,7 +16,6 @@ #include "llvm/MC/MCInst.h" #include "llvm/MC/MCRegisterInfo.h" #include "llvm/MC/MCSubtargetInfo.h" -#include "llvm/Support/RISCVISAInfo.h" #include "llvm/Support/raw_ostream.h" #include "llvm/TargetParser/TargetParser.h" #include "llvm/TargetParser/Triple.h" diff --git a/llvm/lib/Target/RISCV/MCTargetDesc/RISCVBaseInfo.h b/llvm/lib/Target/RISCV/MCTargetDesc/RISCVBaseInfo.h index aa641bc866aa5e91b9a7acf45913968c94c7309d..08f056f78979af4cd7afe5ea3c848fef50d7fd6b 100644 --- a/llvm/lib/Target/RISCV/MCTargetDesc/RISCVBaseInfo.h +++ b/llvm/lib/Target/RISCV/MCTargetDesc/RISCVBaseInfo.h @@ -19,7 +19,7 @@ #include "llvm/ADT/StringRef.h" #include "llvm/ADT/StringSwitch.h" #include "llvm/MC/MCInstrDesc.h" -#include "llvm/Support/RISCVISAInfo.h" +#include "llvm/TargetParser/RISCVISAInfo.h" #include "llvm/TargetParser/RISCVTargetParser.h" #include "llvm/TargetParser/SubtargetFeature.h" diff --git a/llvm/lib/Target/RISCV/MCTargetDesc/RISCVELFStreamer.cpp b/llvm/lib/Target/RISCV/MCTargetDesc/RISCVELFStreamer.cpp index cdf7c048a4bf1183e1e7cfde7131023959a62fee..ae7ce476fff2225d0b7fe7b22e83760389247163 100644 --- a/llvm/lib/Target/RISCV/MCTargetDesc/RISCVELFStreamer.cpp +++ b/llvm/lib/Target/RISCV/MCTargetDesc/RISCVELFStreamer.cpp @@ -197,11 +197,9 @@ namespace llvm { MCELFStreamer *createRISCVELFStreamer(MCContext &C, std::unique_ptr MAB, std::unique_ptr MOW, - std::unique_ptr MCE, - bool RelaxAll) { + std::unique_ptr MCE) { RISCVELFStreamer *S = new RISCVELFStreamer(C, std::move(MAB), std::move(MOW), std::move(MCE)); - S->getAssembler().setRelaxAll(RelaxAll); return S; } } // namespace llvm diff --git a/llvm/lib/Target/RISCV/MCTargetDesc/RISCVELFStreamer.h b/llvm/lib/Target/RISCV/MCTargetDesc/RISCVELFStreamer.h index e8f29cd8449ba0bf9bafe17f40c3f71a12ae451c..212d731889f1ae0dc265dc2bd77ab39507bf6b0a 100644 --- a/llvm/lib/Target/RISCV/MCTargetDesc/RISCVELFStreamer.h +++ b/llvm/lib/Target/RISCV/MCTargetDesc/RISCVELFStreamer.h @@ -75,7 +75,6 @@ public: MCELFStreamer *createRISCVELFStreamer(MCContext &C, std::unique_ptr MAB, std::unique_ptr MOW, - std::unique_ptr MCE, - bool RelaxAll); + std::unique_ptr MCE); } #endif diff --git a/llvm/lib/Target/RISCV/MCTargetDesc/RISCVMCTargetDesc.cpp b/llvm/lib/Target/RISCV/MCTargetDesc/RISCVMCTargetDesc.cpp index 79e56a7a6d03d7738ee501d1866cefb15924ede6..691a5892ae827b56ba18c2a9e142aca2eefcc022 100644 --- a/llvm/lib/Target/RISCV/MCTargetDesc/RISCVMCTargetDesc.cpp +++ b/llvm/lib/Target/RISCV/MCTargetDesc/RISCVMCTargetDesc.cpp @@ -43,6 +43,15 @@ #define GET_SUBTARGETINFO_MC_DESC #include "RISCVGenSubtargetInfo.inc" +namespace llvm::RISCVVInversePseudosTable { + +using namespace RISCV; + +#define GET_RISCVVInversePseudosTable_IMPL +#include "RISCVGenSearchableTables.inc" + +} // namespace llvm::RISCVVInversePseudosTable + using namespace llvm; static MCInstrInfo *createRISCVMCInstrInfo() { @@ -323,10 +332,9 @@ namespace { MCStreamer *createRISCVELFStreamer(const Triple &T, MCContext &Context, std::unique_ptr &&MAB, std::unique_ptr &&MOW, - std::unique_ptr &&MCE, - bool RelaxAll) { + std::unique_ptr &&MCE) { return createRISCVELFStreamer(Context, std::move(MAB), std::move(MOW), - std::move(MCE), RelaxAll); + std::move(MCE)); } } // end anonymous namespace diff --git a/llvm/lib/Target/RISCV/MCTargetDesc/RISCVMCTargetDesc.h b/llvm/lib/Target/RISCV/MCTargetDesc/RISCVMCTargetDesc.h index 3cfddb530cdf63035a8bd61cd28b9932d896850a..d4aa0fe99078e15ffd729b2c881ca277f6535a96 100644 --- a/llvm/lib/Target/RISCV/MCTargetDesc/RISCVMCTargetDesc.h +++ b/llvm/lib/Target/RISCV/MCTargetDesc/RISCVMCTargetDesc.h @@ -37,7 +37,21 @@ MCAsmBackend *createRISCVAsmBackend(const Target &T, const MCSubtargetInfo &STI, std::unique_ptr createRISCVELFObjectWriter(uint8_t OSABI, bool Is64Bit); -} + +namespace RISCVVInversePseudosTable { + +struct PseudoInfo { + uint16_t Pseudo; + uint16_t BaseInstr; + uint8_t VLMul; + uint8_t SEW; +}; + +#define GET_RISCVVInversePseudosTable_DECL +#include "RISCVGenSearchableTables.inc" + +} // namespace RISCVVInversePseudosTable +} // namespace llvm // Defines symbolic names for RISC-V registers. #define GET_REGINFO_ENUM diff --git a/llvm/lib/Target/RISCV/MCTargetDesc/RISCVTargetStreamer.cpp b/llvm/lib/Target/RISCV/MCTargetDesc/RISCVTargetStreamer.cpp index 4a4b1e13c2b9ec35a5dc81de24fc6e9c3cc425b5..0f92e9ed6a64d39f3d6920c81355da64c3305db4 100644 --- a/llvm/lib/Target/RISCV/MCTargetDesc/RISCVTargetStreamer.cpp +++ b/llvm/lib/Target/RISCV/MCTargetDesc/RISCVTargetStreamer.cpp @@ -16,7 +16,7 @@ #include "llvm/MC/MCSymbol.h" #include "llvm/Support/FormattedStream.h" #include "llvm/Support/RISCVAttributes.h" -#include "llvm/Support/RISCVISAInfo.h" +#include "llvm/TargetParser/RISCVISAInfo.h" using namespace llvm; diff --git a/llvm/lib/Target/RISCV/RISCV.h b/llvm/lib/Target/RISCV/RISCV.h index 7af543f018ccbd5ed10e9b19aa2c80cc58656bba..d405395dcf9ec4146db78ee6fc6bb19fd9ff0ae7 100644 --- a/llvm/lib/Target/RISCV/RISCV.h +++ b/llvm/lib/Target/RISCV/RISCV.h @@ -61,6 +61,9 @@ void initializeRISCVExpandAtomicPseudoPass(PassRegistry &); FunctionPass *createRISCVInsertVSETVLIPass(); void initializeRISCVInsertVSETVLIPass(PassRegistry &); +FunctionPass *createRISCVCoalesceVSETVLIPass(); +void initializeRISCVCoalesceVSETVLIPass(PassRegistry &); + FunctionPass *createRISCVPostRAExpandPseudoPass(); void initializeRISCVPostRAExpandPseudoPass(PassRegistry &); FunctionPass *createRISCVInsertReadWriteCSRPass(); diff --git a/llvm/lib/Target/RISCV/RISCVAsmPrinter.cpp b/llvm/lib/Target/RISCV/RISCVAsmPrinter.cpp index 779f179dff619ff81aa3f54e8013da4b76a01241..6eceaddc747d15ed9f116b095bf7c2ac955124a8 100644 --- a/llvm/lib/Target/RISCV/RISCVAsmPrinter.cpp +++ b/llvm/lib/Target/RISCV/RISCVAsmPrinter.cpp @@ -37,8 +37,8 @@ #include "llvm/MC/MCStreamer.h" #include "llvm/MC/MCSymbol.h" #include "llvm/MC/TargetRegistry.h" -#include "llvm/Support/RISCVISAInfo.h" #include "llvm/Support/raw_ostream.h" +#include "llvm/TargetParser/RISCVISAInfo.h" #include "llvm/Transforms/Instrumentation/HWAddressSanitizer.h" using namespace llvm; diff --git a/llvm/lib/Target/RISCV/RISCVFeatures.td b/llvm/lib/Target/RISCV/RISCVFeatures.td index b064191b838e5b5de9e53e82363d08a7aa1bb07d..c3dc4ea53697c041bb8d344cb677976a1c16e2f7 100644 --- a/llvm/lib/Target/RISCV/RISCVFeatures.td +++ b/llvm/lib/Target/RISCV/RISCVFeatures.td @@ -391,7 +391,7 @@ def HasStdExtZcb : Predicate<"Subtarget->hasStdExtZcb()">, def FeatureStdExtZcd : RISCVExtension<"zcd", 1, 0, "'Zcd' (Compressed Double-Precision Floating-Point Instructions)", - [FeatureStdExtZca]>; + [FeatureStdExtD, FeatureStdExtZca]>; def HasStdExtCOrZcd : Predicate<"Subtarget->hasStdExtCOrZcd()">, @@ -402,7 +402,7 @@ def HasStdExtCOrZcd def FeatureStdExtZcf : RISCVExtension<"zcf", 1, 0, "'Zcf' (Compressed Single-Precision Floating-Point Instructions)", - [FeatureStdExtZca]>; + [FeatureStdExtF, FeatureStdExtZca]>; def FeatureStdExtZcmp : RISCVExtension<"zcmp", 1, 0, @@ -423,8 +423,7 @@ def HasStdExtZcmt : Predicate<"Subtarget->hasStdExtZcmt()">, def FeatureStdExtZce : RISCVExtension<"zce", 1, 0, "'Zce' (Compressed extensions for microcontrollers)", - [FeatureStdExtZca, FeatureStdExtZcb, FeatureStdExtZcmp, - FeatureStdExtZcmt]>; + [FeatureStdExtZcb, FeatureStdExtZcmp, FeatureStdExtZcmt]>; def HasStdExtCOrZcfOrZce : Predicate<"Subtarget->hasStdExtC() || Subtarget->hasStdExtZcf() " @@ -1016,8 +1015,7 @@ def HasVendorXTHeadCmo : Predicate<"Subtarget->hasVendorXTHeadCmo()">, def FeatureVendorXTHeadFMemIdx : RISCVExtension<"xtheadfmemidx", 1, 0, - "'xtheadfmemidx' (T-Head FP Indexed Memory Operations)", - [FeatureStdExtF]>; + "'xtheadfmemidx' (T-Head FP Indexed Memory Operations)">; def HasVendorXTHeadFMemIdx : Predicate<"Subtarget->hasVendorXTHeadFMemIdx()">, AssemblerPredicate<(all_of FeatureVendorXTHeadFMemIdx), "'xtheadfmemidx' (T-Head FP Indexed Memory Operations)">; @@ -1089,7 +1087,7 @@ def HasVendorXSfvqmaccqoq def FeatureVendorXSfvfwmaccqqq : RISCVExtension<"xsfvfwmaccqqq", 1, 0, "'XSfvfwmaccqqq' (SiFive Matrix Multiply Accumulate Instruction and 4-by-4))", - [FeatureStdExtZve32f, FeatureStdExtZvfbfmin]>; + [FeatureStdExtZvfbfmin]>; def HasVendorXSfvfwmaccqqq : Predicate<"Subtarget->hasVendorXSfvfwmaccqqq()">, AssemblerPredicate<(all_of FeatureVendorXSfvfwmaccqqq), diff --git a/llvm/lib/Target/RISCV/RISCVISelDAGToDAG.cpp b/llvm/lib/Target/RISCV/RISCVISelDAGToDAG.cpp index f99dc0b857636884d5b909231ce3aadfe1a10a15..b0568297a470a751e999028fc7467fa9eb944ef0 100644 --- a/llvm/lib/Target/RISCV/RISCVISelDAGToDAG.cpp +++ b/llvm/lib/Target/RISCV/RISCVISelDAGToDAG.cpp @@ -43,7 +43,6 @@ namespace llvm::RISCV { #define GET_RISCVVSETable_IMPL #define GET_RISCVVLXTable_IMPL #define GET_RISCVVSXTable_IMPL -#define GET_RISCVMaskedPseudosTable_IMPL #include "RISCVGenSearchableTables.inc" } // namespace llvm::RISCV diff --git a/llvm/lib/Target/RISCV/RISCVISelDAGToDAG.h b/llvm/lib/Target/RISCV/RISCVISelDAGToDAG.h index 92f818b0dc48910acf14c63b4cbfdb69cfb56222..7d4aec2dfdc9841efd74857d179c8d51d5c116f2 100644 --- a/llvm/lib/Target/RISCV/RISCVISelDAGToDAG.h +++ b/llvm/lib/Target/RISCV/RISCVISelDAGToDAG.h @@ -261,13 +261,6 @@ struct VLX_VSXPseudo { uint16_t Pseudo; }; -struct RISCVMaskedPseudoInfo { - uint16_t MaskedPseudo; - uint16_t UnmaskedPseudo; - uint8_t MaskOpIdx; - uint8_t MaskAffectsResult : 1; -}; - #define GET_RISCVVSSEGTable_DECL #define GET_RISCVVLSEGTable_DECL #define GET_RISCVVLXSEGTable_DECL @@ -276,8 +269,6 @@ struct RISCVMaskedPseudoInfo { #define GET_RISCVVSETable_DECL #define GET_RISCVVLXTable_DECL #define GET_RISCVVSXTable_DECL -#define GET_RISCVMaskedPseudosTable_DECL -#include "RISCVGenSearchableTables.inc" } // namespace RISCV } // namespace llvm diff --git a/llvm/lib/Target/RISCV/RISCVISelLowering.cpp b/llvm/lib/Target/RISCV/RISCVISelLowering.cpp index 41483c49ae03cd4d04e3830f4ee21464b487eae1..539aa3525545039344d4db75d63d20cfd0c7cd3c 100644 --- a/llvm/lib/Target/RISCV/RISCVISelLowering.cpp +++ b/llvm/lib/Target/RISCV/RISCVISelLowering.cpp @@ -13416,12 +13416,33 @@ static SDValue expandMul(SDNode *N, SelectionDAG &DAG, return SDValue(); uint64_t MulAmt = CNode->getZExtValue(); - // 3/5/9 * 2^N -> shXadd (sll X, C), (sll X, C) - // Matched in tablegen, avoid perturbing patterns. - for (uint64_t Divisor : {3, 5, 9}) - if (MulAmt % Divisor == 0 && isPowerOf2_64(MulAmt / Divisor)) + // WARNING: The code below is knowingly incorrect with regards to undef semantics. + // We're adding additional uses of X here, and in principle, we should be freezing + // X before doing so. However, adding freeze here causes real regressions, and no + // other target properly freezes X in these cases either. + SDValue X = N->getOperand(0); + + for (uint64_t Divisor : {3, 5, 9}) { + if (MulAmt % Divisor != 0) + continue; + uint64_t MulAmt2 = MulAmt / Divisor; + // 3/5/9 * 2^N -> shXadd (sll X, C), (sll X, C) + // Matched in tablegen, avoid perturbing patterns. + if (isPowerOf2_64(MulAmt2)) return SDValue(); + // 3/5/9 * 3/5/9 -> shXadd (shYadd X, X), (shYadd X, X) + if (MulAmt2 == 3 || MulAmt2 == 5 || MulAmt2 == 9) { + SDLoc DL(N); + SDValue Mul359 = + DAG.getNode(RISCVISD::SHL_ADD, DL, VT, X, + DAG.getConstant(Log2_64(Divisor - 1), DL, VT), X); + return DAG.getNode(RISCVISD::SHL_ADD, DL, VT, Mul359, + DAG.getConstant(Log2_64(MulAmt2 - 1), DL, VT), + Mul359); + } + } + // If this is a power 2 + 2/4/8, we can use a shift followed by a single // shXadd. First check if this a sum of two power of 2s because that's // easy. Then count how many zeros are up to the first bit. @@ -13430,33 +13451,31 @@ static SDValue expandMul(SDNode *N, SelectionDAG &DAG, if (ScaleShift >= 1 && ScaleShift < 4) { unsigned ShiftAmt = Log2_64((MulAmt & (MulAmt - 1))); SDLoc DL(N); - SDValue X = DAG.getFreeze(N->getOperand(0)); SDValue Shift1 = DAG.getNode(ISD::SHL, DL, VT, X, DAG.getConstant(ShiftAmt, DL, VT)); - SDValue Shift2 = - DAG.getNode(ISD::SHL, DL, VT, X, DAG.getConstant(ScaleShift, DL, VT)); - return DAG.getNode(ISD::ADD, DL, VT, Shift1, Shift2); + return DAG.getNode(RISCVISD::SHL_ADD, DL, VT, X, + DAG.getConstant(ScaleShift, DL, VT), Shift1); } } // 2^(1,2,3) * 3,5,9 + 1 -> (shXadd (shYadd x, x), x) - // Matched in tablegen, avoid perturbing patterns. - switch (MulAmt) { - case 11: - case 13: - case 19: - case 21: - case 25: - case 27: - case 29: - case 37: - case 41: - case 45: - case 73: - case 91: - return SDValue(); - default: - break; + // This is the two instruction form, there are also three instruction + // variants we could implement. e.g. + // (2^(1,2,3) * 3,5,9 + 1) << C2 + // 2^(C1>3) * 3,5,9 +/- 1 + for (uint64_t Divisor : {3, 5, 9}) { + uint64_t C = MulAmt - 1; + if (C <= Divisor) + continue; + unsigned TZ = llvm::countr_zero(C); + if ((C >> TZ) == Divisor && (TZ == 1 || TZ == 2 || TZ == 3)) { + SDLoc DL(N); + SDValue Mul359 = + DAG.getNode(RISCVISD::SHL_ADD, DL, VT, X, + DAG.getConstant(Log2_64(Divisor - 1), DL, VT), X); + return DAG.getNode(RISCVISD::SHL_ADD, DL, VT, Mul359, + DAG.getConstant(TZ, DL, VT), X); + } } // 2^n + 2/4/8 + 1 -> (add (shl X, C1), (shXadd X, X)) @@ -13465,13 +13484,25 @@ static SDValue expandMul(SDNode *N, SelectionDAG &DAG, if (ScaleShift >= 1 && ScaleShift < 4) { unsigned ShiftAmt = Log2_64(((MulAmt - 1) & (MulAmt - 2))); SDLoc DL(N); - SDValue X = DAG.getFreeze(N->getOperand(0)); SDValue Shift1 = DAG.getNode(ISD::SHL, DL, VT, X, DAG.getConstant(ShiftAmt, DL, VT)); - SDValue Shift2 = - DAG.getNode(ISD::SHL, DL, VT, X, DAG.getConstant(ScaleShift, DL, VT)); return DAG.getNode(ISD::ADD, DL, VT, Shift1, - DAG.getNode(ISD::ADD, DL, VT, Shift2, X)); + DAG.getNode(RISCVISD::SHL_ADD, DL, VT, X, + DAG.getConstant(ScaleShift, DL, VT), X)); + } + } + + // 2^N - 3/5/9 --> (sub (shl X, C1), (shXadd X, x)) + for (uint64_t Offset : {3, 5, 9}) { + if (isPowerOf2_64(MulAmt + Offset)) { + SDLoc DL(N); + SDValue Shift1 = + DAG.getNode(ISD::SHL, DL, VT, X, + DAG.getConstant(Log2_64(MulAmt + Offset), DL, VT)); + SDValue Mul359 = DAG.getNode(RISCVISD::SHL_ADD, DL, VT, X, + DAG.getConstant(Log2_64(Offset - 1), DL, VT), + X); + return DAG.getNode(ISD::SUB, DL, VT, Shift1, Mul359); } } @@ -16817,7 +16848,7 @@ SDValue RISCVTargetLowering::PerformDAGCombine(SDNode *N, StrideC && StrideC->getZExtValue() == ElementSize) return DAG.getMaskedStore(Store->getChain(), DL, Value, Base, DAG.getUNDEF(XLenVT), Mask, - Store->getMemoryVT(), Store->getMemOperand(), + Value.getValueType(), Store->getMemOperand(), ISD::UNINDEXED, false); return SDValue(); } @@ -17758,6 +17789,18 @@ static MachineBasicBlock *emitSelectPseudo(MachineInstr &MI, return TailMBB; } +// Helper to find Masked Pseudo instruction from MC instruction, LMUL and SEW. +static const RISCV::RISCVMaskedPseudoInfo * +lookupMaskedIntrinsic(uint16_t MCOpcode, RISCVII::VLMUL LMul, unsigned SEW) { + const RISCVVInversePseudosTable::PseudoInfo *Inverse = + RISCVVInversePseudosTable::getBaseInfo(MCOpcode, LMul, SEW); + assert(Inverse && "Unexpected LMUL and SEW pair for instruction"); + const RISCV::RISCVMaskedPseudoInfo *Masked = + RISCV::lookupMaskedIntrinsicByUnmasked(Inverse->Pseudo); + assert(Masked && "Could not find masked instruction for LMUL and SEW pair"); + return Masked; +} + static MachineBasicBlock *emitVFROUND_NOEXCEPT_MASK(MachineInstr &MI, MachineBasicBlock *BB, unsigned CVTXOpc) { @@ -17795,80 +17838,9 @@ static MachineBasicBlock *emitVFROUND_NOEXCEPT_MASK(MachineInstr &MI, unsigned Log2SEW = MI.getOperand(RISCVII::getSEWOpNum(MI.getDesc())).getImm(); // There is no E8 variant for VFCVT_F_X. assert(Log2SEW >= 4); - // Since MI (VFROUND) isn't SEW specific, we cannot use a macro to make - // handling of different (LMUL, SEW) pairs easier because we need to pull the - // SEW immediate from MI, and that information is not avaliable during macro - // expansion. - unsigned CVTFOpc; - if (Log2SEW == 4) { - switch (LMul) { - case RISCVII::LMUL_1: - CVTFOpc = RISCV::PseudoVFCVT_F_X_V_M1_E16_MASK; - break; - case RISCVII::LMUL_2: - CVTFOpc = RISCV::PseudoVFCVT_F_X_V_M2_E16_MASK; - break; - case RISCVII::LMUL_4: - CVTFOpc = RISCV::PseudoVFCVT_F_X_V_M4_E16_MASK; - break; - case RISCVII::LMUL_8: - CVTFOpc = RISCV::PseudoVFCVT_F_X_V_M8_E16_MASK; - break; - case RISCVII::LMUL_F2: - CVTFOpc = RISCV::PseudoVFCVT_F_X_V_MF2_E16_MASK; - break; - case RISCVII::LMUL_F4: - CVTFOpc = RISCV::PseudoVFCVT_F_X_V_MF4_E16_MASK; - break; - case RISCVII::LMUL_F8: - case RISCVII::LMUL_RESERVED: - llvm_unreachable("Unexpected LMUL and SEW combination value for MI."); - } - } else if (Log2SEW == 5) { - switch (LMul) { - case RISCVII::LMUL_1: - CVTFOpc = RISCV::PseudoVFCVT_F_X_V_M1_E32_MASK; - break; - case RISCVII::LMUL_2: - CVTFOpc = RISCV::PseudoVFCVT_F_X_V_M2_E32_MASK; - break; - case RISCVII::LMUL_4: - CVTFOpc = RISCV::PseudoVFCVT_F_X_V_M4_E32_MASK; - break; - case RISCVII::LMUL_8: - CVTFOpc = RISCV::PseudoVFCVT_F_X_V_M8_E32_MASK; - break; - case RISCVII::LMUL_F2: - CVTFOpc = RISCV::PseudoVFCVT_F_X_V_MF2_E32_MASK; - break; - case RISCVII::LMUL_F4: - case RISCVII::LMUL_F8: - case RISCVII::LMUL_RESERVED: - llvm_unreachable("Unexpected LMUL and SEW combination value for MI."); - } - } else if (Log2SEW == 6) { - switch (LMul) { - case RISCVII::LMUL_1: - CVTFOpc = RISCV::PseudoVFCVT_F_X_V_M1_E64_MASK; - break; - case RISCVII::LMUL_2: - CVTFOpc = RISCV::PseudoVFCVT_F_X_V_M2_E64_MASK; - break; - case RISCVII::LMUL_4: - CVTFOpc = RISCV::PseudoVFCVT_F_X_V_M4_E64_MASK; - break; - case RISCVII::LMUL_8: - CVTFOpc = RISCV::PseudoVFCVT_F_X_V_M8_E64_MASK; - break; - case RISCVII::LMUL_F2: - case RISCVII::LMUL_F4: - case RISCVII::LMUL_F8: - case RISCVII::LMUL_RESERVED: - llvm_unreachable("Unexpected LMUL and SEW combination value for MI."); - } - } else { - llvm_unreachable("Unexpected LMUL and SEW combination value for MI."); - } + unsigned CVTFOpc = + lookupMaskedIntrinsic(RISCV::VFCVT_F_X_V, LMul, 1 << Log2SEW) + ->MaskedPseudo; BuildMI(*BB, MI, DL, TII.get(CVTFOpc)) .add(MI.getOperand(0)) @@ -18132,7 +18104,7 @@ void RISCVTargetLowering::AdjustInstrPostInstrSelection(MachineInstr &MI, if (MI.getOperand(Idx).getImm() != RISCVFPRndMode::DYN) return; // If the instruction already reads FRM, don't add another read. - if (MI.readsRegister(RISCV::FRM)) + if (MI.readsRegister(RISCV::FRM, /*TRI=*/nullptr)) return; MI.addOperand( MachineOperand::CreateReg(RISCV::FRM, /*isDef*/ false, /*isImp*/ true)); @@ -19669,6 +19641,7 @@ const char *RISCVTargetLowering::getTargetNodeName(unsigned Opcode) const { NODE_NAME_CASE(LLA) NODE_NAME_CASE(ADD_TPREL) NODE_NAME_CASE(MULHSU) + NODE_NAME_CASE(SHL_ADD) NODE_NAME_CASE(SLLW) NODE_NAME_CASE(SRAW) NODE_NAME_CASE(SRLW) diff --git a/llvm/lib/Target/RISCV/RISCVISelLowering.h b/llvm/lib/Target/RISCV/RISCVISelLowering.h index b10da3d40befb7a26b1e42883e7a6e717f5b83bf..ed14fd4539438a2c73bec797b81c2e4d597e4393 100644 --- a/llvm/lib/Target/RISCV/RISCVISelLowering.h +++ b/llvm/lib/Target/RISCV/RISCVISelLowering.h @@ -59,6 +59,12 @@ enum NodeType : unsigned { // Multiply high for signedxunsigned. MULHSU, + + // Represents (ADD (SHL a, b), c) with the arguments appearing in the order + // a, b, c. 'b' must be a constant. Maps to sh1add/sh2add/sh3add with zba + // or addsl with XTheadBa. + SHL_ADD, + // RV64I shifts, directly matching the semantics of the named RISC-V // instructions. SLLW, diff --git a/llvm/lib/Target/RISCV/RISCVInsertReadWriteCSR.cpp b/llvm/lib/Target/RISCV/RISCVInsertReadWriteCSR.cpp index aac0ecc1cfc9b8ebe89660cec52fdf680323b9d0..7b9e9fb988bc68e25cf6256e247c718adfcc0236 100644 --- a/llvm/lib/Target/RISCV/RISCVInsertReadWriteCSR.cpp +++ b/llvm/lib/Target/RISCV/RISCVInsertReadWriteCSR.cpp @@ -82,7 +82,8 @@ bool RISCVInsertReadWriteCSR::emitWriteRoundingModeOpt(MachineBasicBlock &MBB) { continue; } - if (MI.isCall() || MI.isInlineAsm() || MI.readsRegister(RISCV::FRM)) { + if (MI.isCall() || MI.isInlineAsm() || + MI.readsRegister(RISCV::FRM, /*TRI=*/nullptr)) { // Restore FRM before unknown operations. if (SavedFRM.isValid()) BuildMI(MBB, MI, MI.getDebugLoc(), TII->get(RISCV::WriteFRM)) @@ -92,7 +93,7 @@ bool RISCVInsertReadWriteCSR::emitWriteRoundingModeOpt(MachineBasicBlock &MBB) { continue; } - assert(!MI.modifiesRegister(RISCV::FRM) && + assert(!MI.modifiesRegister(RISCV::FRM, /*TRI=*/nullptr) && "Expected that MI could not modify FRM."); int FRMIdx = RISCVII::getFRMOpNum(MI.getDesc()); diff --git a/llvm/lib/Target/RISCV/RISCVInsertVSETVLI.cpp b/llvm/lib/Target/RISCV/RISCVInsertVSETVLI.cpp index 331253e39c0acb8a39042a62c6a0c896d21be6dd..c40b9031543fe2e5470a926a879d36e527001db9 100644 --- a/llvm/lib/Target/RISCV/RISCVInsertVSETVLI.cpp +++ b/llvm/lib/Target/RISCV/RISCVInsertVSETVLI.cpp @@ -27,16 +27,19 @@ #include "RISCV.h" #include "RISCVSubtarget.h" #include "llvm/ADT/Statistic.h" +#include "llvm/CodeGen/LiveDebugVariables.h" #include "llvm/CodeGen/LiveIntervals.h" +#include "llvm/CodeGen/LiveStacks.h" #include "llvm/CodeGen/MachineFunctionPass.h" #include using namespace llvm; #define DEBUG_TYPE "riscv-insert-vsetvli" #define RISCV_INSERT_VSETVLI_NAME "RISC-V Insert VSETVLI pass" +#define RISCV_COALESCE_VSETVLI_NAME "RISC-V Coalesce VSETVLI pass" STATISTIC(NumInsertedVSETVL, "Number of VSETVL inst inserted"); -STATISTIC(NumRemovedVSETVL, "Number of VSETVL inst removed"); +STATISTIC(NumCoalescedVSETVL, "Number of VSETVL inst coalesced"); static cl::opt DisableInsertVSETVLPHIOpt( "riscv-disable-insert-vsetvl-phi-opt", cl::init(false), cl::Hidden, @@ -190,6 +193,11 @@ static bool hasUndefinedMergeOp(const MachineInstr &MI, if (UseMO.getReg() == RISCV::NoRegister) return true; + if (UseMO.isUndef()) + return true; + if (UseMO.getReg().isPhysical()) + return false; + if (MachineInstr *UseMI = MRI.getVRegDef(UseMO.getReg())) { if (UseMI->isImplicitDef()) return true; @@ -254,6 +262,17 @@ struct DemandedFields { VLZeroness = true; } + // Make this the result of demanding both the fields in this and B. + void doUnion(const DemandedFields &B) { + VLAny |= B.VLAny; + VLZeroness |= B.VLZeroness; + SEW = std::max(SEW, B.SEW); + LMUL |= B.LMUL; + SEWLMULRatio |= B.SEWLMULRatio; + TailPolicy |= B.TailPolicy; + MaskPolicy |= B.MaskPolicy; + } + #if !defined(NDEBUG) || defined(LLVM_ENABLE_DUMP) /// Support for debugging, callable in GDB: V->dump() LLVM_DUMP_METHOD void dump() const { @@ -356,9 +375,11 @@ DemandedFields getDemanded(const MachineInstr &MI, // Most instructions don't use any of these subfeilds. DemandedFields Res; // Start conservative if registers are used - if (MI.isCall() || MI.isInlineAsm() || MI.readsRegister(RISCV::VL)) + if (MI.isCall() || MI.isInlineAsm() || + MI.readsRegister(RISCV::VL, /*TRI=*/nullptr)) Res.demandVL(); - if (MI.isCall() || MI.isInlineAsm() || MI.readsRegister(RISCV::VTYPE)) + if (MI.isCall() || MI.isInlineAsm() || + MI.readsRegister(RISCV::VTYPE, /*TRI=*/nullptr)) Res.demandVTYPE(); // Start conservative on the unlowered form too uint64_t TSFlags = MI.getDesc().TSFlags; @@ -442,6 +463,8 @@ class VSETVLIInfo { Uninitialized, AVLIsReg, AVLIsImm, + AVLIsVLMAX, + AVLIsIgnored, Unknown, } State = Uninitialized; @@ -468,7 +491,7 @@ public: bool isUnknown() const { return State == Unknown; } void setAVLReg(Register Reg) { - assert(Reg.isVirtual() || Reg == RISCV::X0 || Reg == RISCV::NoRegister); + assert(Reg.isVirtual()); AVLReg = Reg; State = AVLIsReg; } @@ -478,8 +501,14 @@ public: State = AVLIsImm; } + void setAVLVLMAX() { State = AVLIsVLMAX; } + + void setAVLIgnored() { State = AVLIsIgnored; } + bool hasAVLImm() const { return State == AVLIsImm; } bool hasAVLReg() const { return State == AVLIsReg; } + bool hasAVLVLMAX() const { return State == AVLIsVLMAX; } + bool hasAVLIgnored() const { return State == AVLIsIgnored; } Register getAVLReg() const { assert(hasAVLReg()); return AVLReg; @@ -495,6 +524,10 @@ public: setUnknown(); else if (Info.hasAVLReg()) setAVLReg(Info.getAVLReg()); + else if (Info.hasAVLVLMAX()) + setAVLVLMAX(); + else if (Info.hasAVLIgnored()) + setAVLIgnored(); else { assert(Info.hasAVLImm()); setAVLImm(Info.getAVLImm()); @@ -510,13 +543,14 @@ public: if (hasAVLImm()) return getAVLImm() > 0; if (hasAVLReg()) { - if (getAVLReg() == RISCV::X0) - return true; - if (MachineInstr *MI = MRI.getVRegDef(getAVLReg()); - MI && isNonZeroLoadImmediate(*MI)) - return true; - return false; + MachineInstr *MI = MRI.getUniqueVRegDef(getAVLReg()); + assert(MI); + return isNonZeroLoadImmediate(*MI); } + if (hasAVLVLMAX()) + return true; + if (hasAVLIgnored()) + return false; return false; } @@ -534,6 +568,12 @@ public: if (hasAVLImm() && Other.hasAVLImm()) return getAVLImm() == Other.getAVLImm(); + if (hasAVLVLMAX()) + return Other.hasAVLVLMAX() && hasSameVLMAX(Other); + + if (hasAVLIgnored()) + return Other.hasAVLIgnored(); + return false; } @@ -707,6 +747,10 @@ public: OS << "AVLReg=" << (unsigned)AVLReg; if (hasAVLImm()) OS << "AVLImm=" << (unsigned)AVLImm; + if (hasAVLVLMAX()) + OS << "AVLVLMAX"; + if (hasAVLIgnored()) + OS << "AVLIgnored"; OS << ", " << "VLMul=" << (unsigned)VLMul << ", " << "SEW=" << (unsigned)SEW << ", " @@ -778,11 +822,40 @@ private: VSETVLIInfo &Info) const; void computeIncomingVLVTYPE(const MachineBasicBlock &MBB); void emitVSETVLIs(MachineBasicBlock &MBB); - void doLocalPostpass(MachineBasicBlock &MBB); void doPRE(MachineBasicBlock &MBB); void insertReadVL(MachineBasicBlock &MBB); }; +class RISCVCoalesceVSETVLI : public MachineFunctionPass { +public: + static char ID; + const RISCVSubtarget *ST; + const TargetInstrInfo *TII; + MachineRegisterInfo *MRI; + LiveIntervals *LIS; + + RISCVCoalesceVSETVLI() : MachineFunctionPass(ID) {} + bool runOnMachineFunction(MachineFunction &MF) override; + + void getAnalysisUsage(AnalysisUsage &AU) const override { + AU.setPreservesCFG(); + + AU.addRequired(); + AU.addPreserved(); + AU.addRequired(); + AU.addPreserved(); + AU.addPreserved(); + AU.addPreserved(); + + MachineFunctionPass::getAnalysisUsage(AU); + } + + StringRef getPassName() const override { return RISCV_COALESCE_VSETVLI_NAME; } + +private: + bool coalesceVSETVLIs(MachineBasicBlock &MBB); +}; + } // end anonymous namespace char RISCVInsertVSETVLI::ID = 0; @@ -790,6 +863,11 @@ char RISCVInsertVSETVLI::ID = 0; INITIALIZE_PASS(RISCVInsertVSETVLI, DEBUG_TYPE, RISCV_INSERT_VSETVLI_NAME, false, false) +char RISCVCoalesceVSETVLI::ID = 0; + +INITIALIZE_PASS(RISCVCoalesceVSETVLI, "riscv-coalesce-vsetvli", + RISCV_COALESCE_VSETVLI_NAME, false, false) + // Return a VSETVLIInfo representing the changes made by this VSETVLI or // VSETIVLI instruction. static VSETVLIInfo getInfoForVSETVLI(const MachineInstr &MI) { @@ -802,7 +880,10 @@ static VSETVLIInfo getInfoForVSETVLI(const MachineInstr &MI) { Register AVLReg = MI.getOperand(1).getReg(); assert((AVLReg != RISCV::X0 || MI.getOperand(0).getReg() != RISCV::X0) && "Can't handle X0, X0 vsetvli yet"); - NewInfo.setAVLReg(AVLReg); + if (AVLReg == RISCV::X0) + NewInfo.setAVLVLMAX(); + else + NewInfo.setAVLReg(AVLReg); } NewInfo.setVTYPE(MI.getOperand(2).getImm()); @@ -869,7 +950,7 @@ static VSETVLIInfo computeInfoForInstr(const MachineInstr &MI, uint64_t TSFlags, if (ST.getRealMinVLen() == ST.getRealMaxVLen() && VLMAX <= 31) InstrInfo.setAVLImm(VLMAX); else - InstrInfo.setAVLReg(RISCV::X0); + InstrInfo.setAVLVLMAX(); } else InstrInfo.setAVLImm(Imm); @@ -878,7 +959,10 @@ static VSETVLIInfo computeInfoForInstr(const MachineInstr &MI, uint64_t TSFlags, } } else { assert(isScalarExtractInstr(MI)); - InstrInfo.setAVLReg(RISCV::NoRegister); + // TODO: If we are more clever about x0,x0 insertion then we should be able + // to deduce that the VL is ignored based off of DemandedFields, and remove + // the AVLIsIgnored state. Then we can just use an arbitrary immediate AVL. + InstrInfo.setAVLIgnored(); } #ifndef NDEBUG if (std::optional EEW = getEEWForLoadStore(MI)) { @@ -891,14 +975,14 @@ static VSETVLIInfo computeInfoForInstr(const MachineInstr &MI, uint64_t TSFlags, // AVL operand with the AVL of the defining vsetvli. We avoid general // register AVLs to avoid extending live ranges without being sure we can // kill the original source reg entirely. - if (InstrInfo.hasAVLReg() && InstrInfo.getAVLReg().isVirtual()) { - MachineInstr *DefMI = MRI->getVRegDef(InstrInfo.getAVLReg()); - if (DefMI && isVectorConfigInstr(*DefMI)) { + if (InstrInfo.hasAVLReg()) { + MachineInstr *DefMI = MRI->getUniqueVRegDef(InstrInfo.getAVLReg()); + assert(DefMI); + if (isVectorConfigInstr(*DefMI)) { VSETVLIInfo DefInstrInfo = getInfoForVSETVLI(*DefMI); if (DefInstrInfo.hasSameVLMAX(InstrInfo) && - (DefInstrInfo.hasAVLImm() || DefInstrInfo.getAVLReg() == RISCV::X0)) { + (DefInstrInfo.hasAVLImm() || DefInstrInfo.hasAVLVLMAX())) InstrInfo.setAVL(DefInstrInfo); - } } } @@ -932,19 +1016,18 @@ void RISCVInsertVSETVLI::insertVSETVLI(MachineBasicBlock &MBB, // If our AVL is a virtual register, it might be defined by a VSET(I)VLI. If // it has the same VLMAX we want and the last VL/VTYPE we observed is the // same, we can use the X0, X0 form. - if (Info.hasSameVLMAX(PrevInfo) && Info.hasAVLReg() && - Info.getAVLReg().isVirtual()) { - if (MachineInstr *DefMI = MRI->getVRegDef(Info.getAVLReg())) { - if (isVectorConfigInstr(*DefMI)) { - VSETVLIInfo DefInfo = getInfoForVSETVLI(*DefMI); - if (DefInfo.hasSameAVL(PrevInfo) && DefInfo.hasSameVLMAX(PrevInfo)) { - BuildMI(MBB, InsertPt, DL, TII->get(RISCV::PseudoVSETVLIX0)) - .addReg(RISCV::X0, RegState::Define | RegState::Dead) - .addReg(RISCV::X0, RegState::Kill) - .addImm(Info.encodeVTYPE()) - .addReg(RISCV::VL, RegState::Implicit); - return; - } + if (Info.hasSameVLMAX(PrevInfo) && Info.hasAVLReg()) { + MachineInstr *DefMI = MRI->getUniqueVRegDef(Info.getAVLReg()); + assert(DefMI); + if (isVectorConfigInstr(*DefMI)) { + VSETVLIInfo DefInfo = getInfoForVSETVLI(*DefMI); + if (DefInfo.hasSameAVL(PrevInfo) && DefInfo.hasSameVLMAX(PrevInfo)) { + BuildMI(MBB, InsertPt, DL, TII->get(RISCV::PseudoVSETVLIX0)) + .addReg(RISCV::X0, RegState::Define | RegState::Dead) + .addReg(RISCV::X0, RegState::Kill) + .addImm(Info.encodeVTYPE()) + .addReg(RISCV::VL, RegState::Implicit); + return; } } } @@ -958,8 +1041,7 @@ void RISCVInsertVSETVLI::insertVSETVLI(MachineBasicBlock &MBB, return; } - Register AVLReg = Info.getAVLReg(); - if (AVLReg == RISCV::NoRegister) { + if (Info.hasAVLIgnored()) { // We can only use x0, x0 if there's no chance of the vtype change causing // the previous vl to become invalid. if (PrevInfo.isValid() && !PrevInfo.isUnknown() && @@ -979,20 +1061,19 @@ void RISCVInsertVSETVLI::insertVSETVLI(MachineBasicBlock &MBB, return; } - if (AVLReg.isVirtual()) - MRI->constrainRegClass(AVLReg, &RISCV::GPRNoX0RegClass); - - // Use X0 as the DestReg unless AVLReg is X0. We also need to change the - // opcode if the AVLReg is X0 as they have different register classes for - // the AVL operand. - Register DestReg = RISCV::X0; - unsigned Opcode = RISCV::PseudoVSETVLI; - if (AVLReg == RISCV::X0) { - DestReg = MRI->createVirtualRegister(&RISCV::GPRRegClass); - Opcode = RISCV::PseudoVSETVLIX0; + if (Info.hasAVLVLMAX()) { + Register DestReg = MRI->createVirtualRegister(&RISCV::GPRRegClass); + BuildMI(MBB, InsertPt, DL, TII->get(RISCV::PseudoVSETVLIX0)) + .addReg(DestReg, RegState::Define | RegState::Dead) + .addReg(RISCV::X0, RegState::Kill) + .addImm(Info.encodeVTYPE()); + return; } - BuildMI(MBB, InsertPt, DL, TII->get(Opcode)) - .addReg(DestReg, RegState::Define | RegState::Dead) + + Register AVLReg = Info.getAVLReg(); + MRI->constrainRegClass(AVLReg, &RISCV::GPRNoX0RegClass); + BuildMI(MBB, InsertPt, DL, TII->get(RISCV::PseudoVSETVLI)) + .addReg(RISCV::X0, RegState::Define | RegState::Dead) .addReg(AVLReg) .addImm(Info.encodeVTYPE()); } @@ -1054,14 +1135,13 @@ bool RISCVInsertVSETVLI::needVSETVLI(const MachineInstr &MI, // it might be defined by a VSET(I)VLI. If it has the same VLMAX we need // and the last VL/VTYPE we observed is the same, we don't need a // VSETVLI here. - if (Require.hasAVLReg() && Require.getAVLReg().isVirtual() && - CurInfo.hasCompatibleVTYPE(Used, Require)) { - if (MachineInstr *DefMI = MRI->getVRegDef(Require.getAVLReg())) { - if (isVectorConfigInstr(*DefMI)) { - VSETVLIInfo DefInfo = getInfoForVSETVLI(*DefMI); - if (DefInfo.hasSameAVL(CurInfo) && DefInfo.hasSameVLMAX(CurInfo)) - return false; - } + if (Require.hasAVLReg() && CurInfo.hasCompatibleVTYPE(Used, Require)) { + MachineInstr *DefMI = MRI->getUniqueVRegDef(Require.getAVLReg()); + assert(DefMI); + if (isVectorConfigInstr(*DefMI)) { + VSETVLIInfo DefInfo = getInfoForVSETVLI(*DefMI); + if (DefInfo.hasSameAVL(CurInfo) && DefInfo.hasSameVLMAX(CurInfo)) + return false; } } @@ -1157,8 +1237,9 @@ void RISCVInsertVSETVLI::transferAfter(VSETVLIInfo &Info, // If this is something that updates VL/VTYPE that we don't know about, set // the state to unknown. - if (MI.isCall() || MI.isInlineAsm() || MI.modifiesRegister(RISCV::VL) || - MI.modifiesRegister(RISCV::VTYPE)) + if (MI.isCall() || MI.isInlineAsm() || + MI.modifiesRegister(RISCV::VL, /*TRI=*/nullptr) || + MI.modifiesRegister(RISCV::VTYPE, /*TRI=*/nullptr)) Info = VSETVLIInfo::getUnknown(); } @@ -1245,23 +1326,18 @@ bool RISCVInsertVSETVLI::needVSETVLIPHI(const VSETVLIInfo &Require, return true; Register AVLReg = Require.getAVLReg(); - if (!AVLReg.isVirtual()) - return true; // We need the AVL to be produce by a PHI node in this basic block. - MachineInstr *PHI = MRI->getVRegDef(AVLReg); - if (!PHI || PHI->getOpcode() != RISCV::PHI || PHI->getParent() != &MBB) + MachineInstr *PHI = MRI->getUniqueVRegDef(AVLReg); + assert(PHI); + if (PHI->getOpcode() != RISCV::PHI || PHI->getParent() != &MBB) return true; for (unsigned PHIOp = 1, NumOps = PHI->getNumOperands(); PHIOp != NumOps; PHIOp += 2) { Register InReg = PHI->getOperand(PHIOp).getReg(); MachineBasicBlock *PBB = PHI->getOperand(PHIOp + 1).getMBB(); - const BlockData &PBBInfo = BlockInfo[PBB->getNumber()]; - // If the exit from the predecessor has the VTYPE we are looking for - // we might be able to avoid a VSETVLI. - if (PBBInfo.Exit.isUnknown() || !PBBInfo.Exit.hasSameVTYPE(Require)) - return true; + const VSETVLIInfo &PBBExit = BlockInfo[PBB->getNumber()].Exit; // We need the PHI input to the be the output of a VSET(I)VLI. MachineInstr *DefMI = MRI->getVRegDef(InReg); @@ -1271,8 +1347,13 @@ bool RISCVInsertVSETVLI::needVSETVLIPHI(const VSETVLIInfo &Require, // We found a VSET(I)VLI make sure it matches the output of the // predecessor block. VSETVLIInfo DefInfo = getInfoForVSETVLI(*DefMI); - if (!DefInfo.hasSameAVL(PBBInfo.Exit) || - !DefInfo.hasSameVTYPE(PBBInfo.Exit)) + if (DefInfo != PBBExit) + return true; + + // Require has the same VL as PBBExit, so if the exit from the + // predecessor has the VTYPE we are looking for we might be able + // to avoid a VSETVLI. + if (PBBExit.isUnknown() || !PBBExit.hasSameVTYPE(Require)) return true; } @@ -1341,8 +1422,9 @@ void RISCVInsertVSETVLI::emitVSETVLIs(MachineBasicBlock &MBB) { /*isImp*/ true)); } - if (MI.isCall() || MI.isInlineAsm() || MI.modifiesRegister(RISCV::VL) || - MI.modifiesRegister(RISCV::VTYPE)) + if (MI.isCall() || MI.isInlineAsm() || + MI.modifiesRegister(RISCV::VL, /*TRI=*/nullptr) || + MI.modifiesRegister(RISCV::VTYPE, /*TRI=*/nullptr)) PrefixTransparent = false; transferAfter(CurInfo, MI); @@ -1417,10 +1499,9 @@ void RISCVInsertVSETVLI::doPRE(MachineBasicBlock &MBB) { // If the AVL value is a register (other than our VLMAX sentinel), // we need to prove the value is available at the point we're going // to insert the vsetvli at. - if (AvailableInfo.hasAVLReg() && RISCV::X0 != AvailableInfo.getAVLReg()) { - MachineInstr *AVLDefMI = MRI->getVRegDef(AvailableInfo.getAVLReg()); - if (!AVLDefMI) - return; + if (AvailableInfo.hasAVLReg()) { + MachineInstr *AVLDefMI = MRI->getUniqueVRegDef(AvailableInfo.getAVLReg()); + assert(AVLDefMI); // This is an inline dominance check which covers the case of // UnavailablePred being the preheader of a loop. if (AVLDefMI->getParent() != UnavailablePred) @@ -1430,6 +1511,11 @@ void RISCVInsertVSETVLI::doPRE(MachineBasicBlock &MBB) { return; } + // If the AVL isn't used in its predecessors then bail, since we have no AVL + // to insert a vsetvli with. + if (AvailableInfo.hasAVLIgnored()) + return; + // Model the effect of changing the input state of the block MBB to // AvailableInfo. We're looking for two issues here; one legality, // one profitability. @@ -1478,16 +1564,6 @@ void RISCVInsertVSETVLI::doPRE(MachineBasicBlock &MBB) { AvailableInfo, OldExit); } -static void doUnion(DemandedFields &A, DemandedFields B) { - A.VLAny |= B.VLAny; - A.VLZeroness |= B.VLZeroness; - A.SEW = std::max(A.SEW, B.SEW); - A.LMUL |= B.LMUL; - A.SEWLMULRatio |= B.SEWLMULRatio; - A.TailPolicy |= B.TailPolicy; - A.MaskPolicy |= B.MaskPolicy; -} - // Return true if we can mutate PrevMI to match MI without changing any the // fields which would be observed. static bool canMutatePriorConfig(const MachineInstr &PrevMI, @@ -1511,12 +1587,12 @@ static bool canMutatePriorConfig(const MachineInstr &PrevMI, auto &AVL = MI.getOperand(1); auto &PrevAVL = PrevMI.getOperand(1); - assert(MRI.isSSA()); // If the AVL is a register, we need to make sure MI's AVL dominates PrevMI. // For now just check that PrevMI uses the same virtual register. if (AVL.isReg() && AVL.getReg() != RISCV::X0 && - (!PrevAVL.isReg() || PrevAVL.getReg() != AVL.getReg())) + (!MRI.hasOneDef(AVL.getReg()) || !PrevAVL.isReg() || + PrevAVL.getReg() != AVL.getReg())) return false; } @@ -1526,7 +1602,7 @@ static bool canMutatePriorConfig(const MachineInstr &PrevMI, return areCompatibleVTYPEs(PriorVType, VType, Used); } -void RISCVInsertVSETVLI::doLocalPostpass(MachineBasicBlock &MBB) { +bool RISCVCoalesceVSETVLI::coalesceVSETVLIs(MachineBasicBlock &MBB) { MachineInstr *NextMI = nullptr; // We can have arbitrary code in successors, so VL and VTYPE // must be considered demanded. @@ -1537,9 +1613,10 @@ void RISCVInsertVSETVLI::doLocalPostpass(MachineBasicBlock &MBB) { for (MachineInstr &MI : make_range(MBB.rbegin(), MBB.rend())) { if (!isVectorConfigInstr(MI)) { - doUnion(Used, getDemanded(MI, MRI, ST)); - if (MI.isCall() || MI.isInlineAsm() || MI.modifiesRegister(RISCV::VL) || - MI.modifiesRegister(RISCV::VTYPE)) + Used.doUnion(getDemanded(MI, MRI, ST)); + if (MI.isCall() || MI.isInlineAsm() || + MI.modifiesRegister(RISCV::VL, /*TRI=*/nullptr) || + MI.modifiesRegister(RISCV::VTYPE, /*TRI=*/nullptr)) NextMI = nullptr; continue; } @@ -1558,8 +1635,28 @@ void RISCVInsertVSETVLI::doLocalPostpass(MachineBasicBlock &MBB) { if (canMutatePriorConfig(MI, *NextMI, Used, *MRI)) { if (!isVLPreservingConfig(*NextMI)) { - MI.getOperand(0).setReg(NextMI->getOperand(0).getReg()); + Register DefReg = NextMI->getOperand(0).getReg(); + + MI.getOperand(0).setReg(DefReg); MI.getOperand(0).setIsDead(false); + + // The def of DefReg moved to MI, so extend the LiveInterval up to + // it. + if (DefReg.isVirtual()) { + LiveInterval &DefLI = LIS->getInterval(DefReg); + SlotIndex MISlot = LIS->getInstructionIndex(MI).getRegSlot(); + VNInfo *DefVNI = DefLI.getVNInfoAt(DefLI.beginIndex()); + LiveInterval::Segment S(MISlot, DefLI.beginIndex(), DefVNI); + DefLI.addSegment(S); + DefVNI->def = MISlot; + // Mark DefLI as spillable if it was previously unspillable + DefLI.setWeight(0); + + // DefReg may have had no uses, in which case we need to shrink + // the LiveInterval up to MI. + LIS->shrinkToUses(&DefLI); + } + Register OldVLReg; if (MI.getOperand(1).isReg()) OldVLReg = MI.getOperand(1).getReg(); @@ -1567,11 +1664,21 @@ void RISCVInsertVSETVLI::doLocalPostpass(MachineBasicBlock &MBB) { MI.getOperand(1).ChangeToImmediate(NextMI->getOperand(1).getImm()); else MI.getOperand(1).ChangeToRegister(NextMI->getOperand(1).getReg(), false); - if (OldVLReg) { + + // Clear NextMI's AVL early so we're not counting it as a use. + if (NextMI->getOperand(1).isReg()) + NextMI->getOperand(1).setReg(RISCV::NoRegister); + + if (OldVLReg && OldVLReg.isVirtual()) { + // NextMI no longer uses OldVLReg so shrink its LiveInterval. + LIS->shrinkToUses(&LIS->getInterval(OldVLReg)); + MachineInstr *VLOpDef = MRI->getUniqueVRegDef(OldVLReg); if (VLOpDef && TII->isAddImmediate(*VLOpDef, OldVLReg) && - MRI->use_nodbg_empty(OldVLReg)) + MRI->use_nodbg_empty(OldVLReg)) { VLOpDef->eraseFromParent(); + LIS->removeInterval(OldVLReg); + } } MI.setDesc(NextMI->getDesc()); } @@ -1584,9 +1691,13 @@ void RISCVInsertVSETVLI::doLocalPostpass(MachineBasicBlock &MBB) { Used = getDemanded(MI, MRI, ST); } - NumRemovedVSETVL += ToDelete.size(); - for (auto *MI : ToDelete) + NumCoalescedVSETVL += ToDelete.size(); + for (auto *MI : ToDelete) { + LIS->RemoveMachineInstrFromMaps(*MI); MI->eraseFromParent(); + } + + return !ToDelete.empty(); } void RISCVInsertVSETVLI::insertReadVL(MachineBasicBlock &MBB) { @@ -1661,15 +1772,6 @@ bool RISCVInsertVSETVLI::runOnMachineFunction(MachineFunction &MF) { for (MachineBasicBlock &MBB : MF) emitVSETVLIs(MBB); - // Now that all vsetvlis are explicit, go through and do block local - // DSE and peephole based demanded fields based transforms. Note that - // this *must* be done outside the main dataflow so long as we allow - // any cross block analysis within the dataflow. We can't have both - // demanded fields based mutation and non-local analysis in the - // dataflow at the same time without introducing inconsistencies. - for (MachineBasicBlock &MBB : MF) - doLocalPostpass(MBB); - // Insert PseudoReadVL after VLEFF/VLSEGFF and replace it with the vl output // of VLEFF/VLSEGFF. for (MachineBasicBlock &MBB : MF) @@ -1683,3 +1785,29 @@ bool RISCVInsertVSETVLI::runOnMachineFunction(MachineFunction &MF) { FunctionPass *llvm::createRISCVInsertVSETVLIPass() { return new RISCVInsertVSETVLI(); } + +// Now that all vsetvlis are explicit, go through and do block local +// DSE and peephole based demanded fields based transforms. Note that +// this *must* be done outside the main dataflow so long as we allow +// any cross block analysis within the dataflow. We can't have both +// demanded fields based mutation and non-local analysis in the +// dataflow at the same time without introducing inconsistencies. +bool RISCVCoalesceVSETVLI::runOnMachineFunction(MachineFunction &MF) { + // Skip if the vector extension is not enabled. + ST = &MF.getSubtarget(); + if (!ST->hasVInstructions()) + return false; + TII = ST->getInstrInfo(); + MRI = &MF.getRegInfo(); + LIS = &getAnalysis(); + + bool Changed = false; + for (MachineBasicBlock &MBB : MF) + Changed |= coalesceVSETVLIs(MBB); + + return Changed; +} + +FunctionPass *llvm::createRISCVCoalesceVSETVLIPass() { + return new RISCVCoalesceVSETVLI(); +} diff --git a/llvm/lib/Target/RISCV/RISCVInsertWriteVXRM.cpp b/llvm/lib/Target/RISCV/RISCVInsertWriteVXRM.cpp index e487cc8b2e20c90fca5c945339171a99a06e6d0d..f72ba2d5c667b880f14e5f522c18b594943c35f7 100644 --- a/llvm/lib/Target/RISCV/RISCVInsertWriteVXRM.cpp +++ b/llvm/lib/Target/RISCV/RISCVInsertWriteVXRM.cpp @@ -225,7 +225,8 @@ bool RISCVInsertWriteVXRM::computeVXRMChanges(const MachineBasicBlock &MBB) { continue; } - if (MI.isCall() || MI.isInlineAsm() || MI.modifiesRegister(RISCV::VXRM)) { + if (MI.isCall() || MI.isInlineAsm() || + MI.modifiesRegister(RISCV::VXRM, /*TRI=*/nullptr)) { if (!BBInfo.VXRMUse.isValid()) BBInfo.VXRMUse.setUnknown(); @@ -386,7 +387,8 @@ void RISCVInsertWriteVXRM::emitWriteVXRM(MachineBasicBlock &MBB) { continue; } - if (MI.isCall() || MI.isInlineAsm() || MI.modifiesRegister(RISCV::VXRM)) + if (MI.isCall() || MI.isInlineAsm() || + MI.modifiesRegister(RISCV::VXRM, /*TRI=*/nullptr)) Info.setUnknown(); } diff --git a/llvm/lib/Target/RISCV/RISCVInstrInfo.cpp b/llvm/lib/Target/RISCV/RISCVInstrInfo.cpp index 8331fc0b8c30249f8cc2ab827b0d43bef6f5740e..3efd09aeae879d75df3cb838b41da20135c573c1 100644 --- a/llvm/lib/Target/RISCV/RISCVInstrInfo.cpp +++ b/llvm/lib/Target/RISCV/RISCVInstrInfo.cpp @@ -66,6 +66,13 @@ using namespace RISCV; } // namespace llvm::RISCVVPseudosTable +namespace llvm::RISCV { + +#define GET_RISCVMaskedPseudosTable_IMPL +#include "RISCVGenSearchableTables.inc" + +} // end namespace llvm::RISCV + RISCVInstrInfo::RISCVInstrInfo(RISCVSubtarget &STI) : RISCVGenInstrInfo(RISCV::ADJCALLSTACKDOWN, RISCV::ADJCALLSTACKUP), STI(STI) {} @@ -239,7 +246,7 @@ static bool isConvertibleToVMV_V_V(const RISCVSubtarget &STI, } else if (MBBI->getNumDefs()) { // Check all the instructions which will change VL. // For example, vleff has implicit def VL. - if (MBBI->modifiesRegister(RISCV::VL)) + if (MBBI->modifiesRegister(RISCV::VL, /*TRI=*/nullptr)) return false; // Only converting whole register copies to vmv.v.v when the defining @@ -1582,10 +1589,10 @@ void RISCVInstrInfo::finalizeInsInstrs( MachineFunction &MF = *Root.getMF(); for (auto *NewMI : InsInstrs) { - assert(static_cast(RISCV::getNamedOperandIdx( - NewMI->getOpcode(), RISCV::OpName::frm)) == - NewMI->getNumOperands() && - "Instruction has unexpected number of operands"); + // We'd already added the FRM operand. + if (static_cast(RISCV::getNamedOperandIdx( + NewMI->getOpcode(), RISCV::OpName::frm)) != NewMI->getNumOperands()) + continue; MachineInstrBuilder MIB(MF, NewMI); MIB.add(FRM); if (FRM.getImm() == RISCVFPRndMode::DYN) @@ -1626,8 +1633,230 @@ static bool isFMUL(unsigned Opc) { } } +bool RISCVInstrInfo::isVectorAssociativeAndCommutative(const MachineInstr &Inst, + bool Invert) const { +#define OPCODE_LMUL_CASE(OPC) \ + case RISCV::OPC##_M1: \ + case RISCV::OPC##_M2: \ + case RISCV::OPC##_M4: \ + case RISCV::OPC##_M8: \ + case RISCV::OPC##_MF2: \ + case RISCV::OPC##_MF4: \ + case RISCV::OPC##_MF8 + +#define OPCODE_LMUL_MASK_CASE(OPC) \ + case RISCV::OPC##_M1_MASK: \ + case RISCV::OPC##_M2_MASK: \ + case RISCV::OPC##_M4_MASK: \ + case RISCV::OPC##_M8_MASK: \ + case RISCV::OPC##_MF2_MASK: \ + case RISCV::OPC##_MF4_MASK: \ + case RISCV::OPC##_MF8_MASK + + unsigned Opcode = Inst.getOpcode(); + if (Invert) { + if (auto InvOpcode = getInverseOpcode(Opcode)) + Opcode = *InvOpcode; + else + return false; + } + + // clang-format off + switch (Opcode) { + default: + return false; + OPCODE_LMUL_CASE(PseudoVADD_VV): + OPCODE_LMUL_MASK_CASE(PseudoVADD_VV): + OPCODE_LMUL_CASE(PseudoVMUL_VV): + OPCODE_LMUL_MASK_CASE(PseudoVMUL_VV): + return true; + } + // clang-format on + +#undef OPCODE_LMUL_MASK_CASE +#undef OPCODE_LMUL_CASE +} + +bool RISCVInstrInfo::areRVVInstsReassociable(const MachineInstr &Root, + const MachineInstr &Prev) const { + if (!areOpcodesEqualOrInverse(Root.getOpcode(), Prev.getOpcode())) + return false; + + assert(Root.getMF() == Prev.getMF()); + const MachineRegisterInfo *MRI = &Root.getMF()->getRegInfo(); + const TargetRegisterInfo *TRI = MRI->getTargetRegisterInfo(); + + // Make sure vtype operands are also the same. + const MCInstrDesc &Desc = get(Root.getOpcode()); + const uint64_t TSFlags = Desc.TSFlags; + + auto checkImmOperand = [&](unsigned OpIdx) { + return Root.getOperand(OpIdx).getImm() == Prev.getOperand(OpIdx).getImm(); + }; + + auto checkRegOperand = [&](unsigned OpIdx) { + return Root.getOperand(OpIdx).getReg() == Prev.getOperand(OpIdx).getReg(); + }; + + // PassThru + // TODO: Potentially we can loosen the condition to consider Root to be + // associable with Prev if Root has NoReg as passthru. In which case we + // also need to loosen the condition on vector policies between these. + if (!checkRegOperand(1)) + return false; + + // SEW + if (RISCVII::hasSEWOp(TSFlags) && + !checkImmOperand(RISCVII::getSEWOpNum(Desc))) + return false; + + // Mask + if (RISCVII::usesMaskPolicy(TSFlags)) { + const MachineBasicBlock *MBB = Root.getParent(); + const MachineBasicBlock::const_reverse_iterator It1(&Root); + const MachineBasicBlock::const_reverse_iterator It2(&Prev); + Register MI1VReg; + + bool SeenMI2 = false; + for (auto End = MBB->rend(), It = It1; It != End; ++It) { + if (It == It2) { + SeenMI2 = true; + if (!MI1VReg.isValid()) + // There is no V0 def between Root and Prev; they're sharing the + // same V0. + break; + } + + if (It->modifiesRegister(RISCV::V0, TRI)) { + Register SrcReg = It->getOperand(1).getReg(); + // If it's not VReg it'll be more difficult to track its defs, so + // bailing out here just to be safe. + if (!SrcReg.isVirtual()) + return false; + + if (!MI1VReg.isValid()) { + // This is the V0 def for Root. + MI1VReg = SrcReg; + continue; + } + + // Some random mask updates. + if (!SeenMI2) + continue; + + // This is the V0 def for Prev; check if it's the same as that of + // Root. + if (MI1VReg != SrcReg) + return false; + else + break; + } + } + + // If we haven't encountered Prev, it's likely that this function was + // called in a wrong way (e.g. Root is before Prev). + assert(SeenMI2 && "Prev is expected to appear before Root"); + } + + // Tail / Mask policies + if (RISCVII::hasVecPolicyOp(TSFlags) && + !checkImmOperand(RISCVII::getVecPolicyOpNum(Desc))) + return false; + + // VL + if (RISCVII::hasVLOp(TSFlags)) { + unsigned OpIdx = RISCVII::getVLOpNum(Desc); + const MachineOperand &Op1 = Root.getOperand(OpIdx); + const MachineOperand &Op2 = Prev.getOperand(OpIdx); + if (Op1.getType() != Op2.getType()) + return false; + switch (Op1.getType()) { + case MachineOperand::MO_Register: + if (Op1.getReg() != Op2.getReg()) + return false; + break; + case MachineOperand::MO_Immediate: + if (Op1.getImm() != Op2.getImm()) + return false; + break; + default: + llvm_unreachable("Unrecognized VL operand type"); + } + } + + // Rounding modes + if (RISCVII::hasRoundModeOp(TSFlags) && + !checkImmOperand(RISCVII::getVLOpNum(Desc) - 1)) + return false; + + return true; +} + +// Most of our RVV pseudos have passthru operand, so the real operands +// start from index = 2. +bool RISCVInstrInfo::hasReassociableVectorSibling(const MachineInstr &Inst, + bool &Commuted) const { + const MachineBasicBlock *MBB = Inst.getParent(); + const MachineRegisterInfo &MRI = MBB->getParent()->getRegInfo(); + assert(RISCVII::isFirstDefTiedToFirstUse(get(Inst.getOpcode())) && + "Expect the present of passthrough operand."); + MachineInstr *MI1 = MRI.getUniqueVRegDef(Inst.getOperand(2).getReg()); + MachineInstr *MI2 = MRI.getUniqueVRegDef(Inst.getOperand(3).getReg()); + + // If only one operand has the same or inverse opcode and it's the second + // source operand, the operands must be commuted. + Commuted = !areRVVInstsReassociable(Inst, *MI1) && + areRVVInstsReassociable(Inst, *MI2); + if (Commuted) + std::swap(MI1, MI2); + + return areRVVInstsReassociable(Inst, *MI1) && + (isVectorAssociativeAndCommutative(*MI1) || + isVectorAssociativeAndCommutative(*MI1, /* Invert */ true)) && + hasReassociableOperands(*MI1, MBB) && + MRI.hasOneNonDBGUse(MI1->getOperand(0).getReg()); +} + +bool RISCVInstrInfo::hasReassociableOperands( + const MachineInstr &Inst, const MachineBasicBlock *MBB) const { + if (!isVectorAssociativeAndCommutative(Inst) && + !isVectorAssociativeAndCommutative(Inst, /*Invert=*/true)) + return TargetInstrInfo::hasReassociableOperands(Inst, MBB); + + const MachineOperand &Op1 = Inst.getOperand(2); + const MachineOperand &Op2 = Inst.getOperand(3); + const MachineRegisterInfo &MRI = MBB->getParent()->getRegInfo(); + + // We need virtual register definitions for the operands that we will + // reassociate. + MachineInstr *MI1 = nullptr; + MachineInstr *MI2 = nullptr; + if (Op1.isReg() && Op1.getReg().isVirtual()) + MI1 = MRI.getUniqueVRegDef(Op1.getReg()); + if (Op2.isReg() && Op2.getReg().isVirtual()) + MI2 = MRI.getUniqueVRegDef(Op2.getReg()); + + // And at least one operand must be defined in MBB. + return MI1 && MI2 && (MI1->getParent() == MBB || MI2->getParent() == MBB); +} + +void RISCVInstrInfo::getReassociateOperandIndices( + const MachineInstr &Root, unsigned Pattern, + std::array &OperandIndices) const { + TargetInstrInfo::getReassociateOperandIndices(Root, Pattern, OperandIndices); + if (RISCV::getRVVMCOpcode(Root.getOpcode())) { + // Skip the passthrough operand, so increment all indices by one. + for (unsigned I = 0; I < 5; ++I) + ++OperandIndices[I]; + } +} + bool RISCVInstrInfo::hasReassociableSibling(const MachineInstr &Inst, bool &Commuted) const { + if (isVectorAssociativeAndCommutative(Inst) || + isVectorAssociativeAndCommutative(Inst, /*Invert=*/true)) + return hasReassociableVectorSibling(Inst, Commuted); + if (!TargetInstrInfo::hasReassociableSibling(Inst, Commuted)) return false; @@ -1647,6 +1876,9 @@ bool RISCVInstrInfo::hasReassociableSibling(const MachineInstr &Inst, bool RISCVInstrInfo::isAssociativeAndCommutative(const MachineInstr &Inst, bool Invert) const { + if (isVectorAssociativeAndCommutative(Inst, Invert)) + return true; + unsigned Opc = Inst.getOpcode(); if (Invert) { auto InverseOpcode = getInverseOpcode(Opc); @@ -1699,6 +1931,38 @@ bool RISCVInstrInfo::isAssociativeAndCommutative(const MachineInstr &Inst, std::optional RISCVInstrInfo::getInverseOpcode(unsigned Opcode) const { +#define RVV_OPC_LMUL_CASE(OPC, INV) \ + case RISCV::OPC##_M1: \ + return RISCV::INV##_M1; \ + case RISCV::OPC##_M2: \ + return RISCV::INV##_M2; \ + case RISCV::OPC##_M4: \ + return RISCV::INV##_M4; \ + case RISCV::OPC##_M8: \ + return RISCV::INV##_M8; \ + case RISCV::OPC##_MF2: \ + return RISCV::INV##_MF2; \ + case RISCV::OPC##_MF4: \ + return RISCV::INV##_MF4; \ + case RISCV::OPC##_MF8: \ + return RISCV::INV##_MF8 + +#define RVV_OPC_LMUL_MASK_CASE(OPC, INV) \ + case RISCV::OPC##_M1_MASK: \ + return RISCV::INV##_M1_MASK; \ + case RISCV::OPC##_M2_MASK: \ + return RISCV::INV##_M2_MASK; \ + case RISCV::OPC##_M4_MASK: \ + return RISCV::INV##_M4_MASK; \ + case RISCV::OPC##_M8_MASK: \ + return RISCV::INV##_M8_MASK; \ + case RISCV::OPC##_MF2_MASK: \ + return RISCV::INV##_MF2_MASK; \ + case RISCV::OPC##_MF4_MASK: \ + return RISCV::INV##_MF4_MASK; \ + case RISCV::OPC##_MF8_MASK: \ + return RISCV::INV##_MF8_MASK + switch (Opcode) { default: return std::nullopt; @@ -1722,7 +1986,16 @@ RISCVInstrInfo::getInverseOpcode(unsigned Opcode) const { return RISCV::SUBW; case RISCV::SUBW: return RISCV::ADDW; + // clang-format off + RVV_OPC_LMUL_CASE(PseudoVADD_VV, PseudoVSUB_VV); + RVV_OPC_LMUL_MASK_CASE(PseudoVADD_VV, PseudoVSUB_VV); + RVV_OPC_LMUL_CASE(PseudoVSUB_VV, PseudoVADD_VV); + RVV_OPC_LMUL_MASK_CASE(PseudoVSUB_VV, PseudoVADD_VV); + // clang-format on } + +#undef RVV_OPC_LMUL_MASK_CASE +#undef RVV_OPC_LMUL_CASE } static bool canCombineFPFusedMultiply(const MachineInstr &Root, @@ -3145,6 +3418,16 @@ MachineInstr *RISCVInstrInfo::commuteInstructionImpl(MachineInstr &MI, return TargetInstrInfo::commuteInstructionImpl(MI, NewMI, OpIdx1, OpIdx2); } +#undef CASE_RVV_OPCODE_UNMASK_LMUL +#undef CASE_RVV_OPCODE_MASK_LMUL +#undef CASE_RVV_OPCODE_LMUL +#undef CASE_RVV_OPCODE_UNMASK_WIDEN +#undef CASE_RVV_OPCODE_UNMASK +#undef CASE_RVV_OPCODE_MASK_WIDEN +#undef CASE_RVV_OPCODE_MASK +#undef CASE_RVV_OPCODE_WIDEN +#undef CASE_RVV_OPCODE + #undef CASE_VMA_OPCODE_COMMON #undef CASE_VMA_OPCODE_LMULS_M1 #undef CASE_VMA_OPCODE_LMULS_MF2 @@ -3546,8 +3829,8 @@ RISCV::isRVVSpillForZvlsseg(unsigned Opcode) { } bool RISCV::isFaultFirstLoad(const MachineInstr &MI) { - return MI.getNumExplicitDefs() == 2 && MI.modifiesRegister(RISCV::VL) && - !MI.isInlineAsm(); + return MI.getNumExplicitDefs() == 2 && + MI.modifiesRegister(RISCV::VL, /*TRI=*/nullptr) && !MI.isInlineAsm(); } bool RISCV::hasEqualFRM(const MachineInstr &MI1, const MachineInstr &MI2) { diff --git a/llvm/lib/Target/RISCV/RISCVInstrInfo.h b/llvm/lib/Target/RISCV/RISCVInstrInfo.h index 70fe7da85be0e7495019fd7ca2532c2880080e4c..170f813eb10d7df5dfca79ac66bb8d0868f90cf7 100644 --- a/llvm/lib/Target/RISCV/RISCVInstrInfo.h +++ b/llvm/lib/Target/RISCV/RISCVInstrInfo.h @@ -266,6 +266,9 @@ public: SmallVectorImpl &DelInstrs, DenseMap &InstrIdxForVirtReg) const override; + bool hasReassociableOperands(const MachineInstr &Inst, + const MachineBasicBlock *MBB) const override; + bool hasReassociableSibling(const MachineInstr &Inst, bool &Commuted) const override; @@ -274,6 +277,10 @@ public: std::optional getInverseOpcode(unsigned Opcode) const override; + void getReassociateOperandIndices( + const MachineInstr &Root, unsigned Pattern, + std::array &OperandIndices) const override; + ArrayRef> getSerializableMachineMemOperandTargetFlags() const override; @@ -297,6 +304,13 @@ protected: private: unsigned getInstBundleLength(const MachineInstr &MI) const; + + bool isVectorAssociativeAndCommutative(const MachineInstr &MI, + bool Invert = false) const; + bool areRVVInstsReassociable(const MachineInstr &MI1, + const MachineInstr &MI2) const; + bool hasReassociableVectorSibling(const MachineInstr &Inst, + bool &Commuted) const; }; namespace RISCV { @@ -359,5 +373,17 @@ struct PseudoInfo { } // end namespace RISCVVPseudosTable +namespace RISCV { + +struct RISCVMaskedPseudoInfo { + uint16_t MaskedPseudo; + uint16_t UnmaskedPseudo; + uint8_t MaskOpIdx; + uint8_t MaskAffectsResult : 1; +}; +#define GET_RISCVMaskedPseudosTable_DECL +#include "RISCVGenSearchableTables.inc" +} // end namespace RISCV + } // end namespace llvm #endif diff --git a/llvm/lib/Target/RISCV/RISCVInstrInfo.td b/llvm/lib/Target/RISCV/RISCVInstrInfo.td index f9dadc6c0d4895a7b6631556d702368eb465b4a8..da4020758eb6e6dc2cccfa03c182f21f9bac7caf 100644 --- a/llvm/lib/Target/RISCV/RISCVInstrInfo.td +++ b/llvm/lib/Target/RISCV/RISCVInstrInfo.td @@ -1813,6 +1813,8 @@ def : Pat<(binop_allwusers (sext_inreg GPR:$rs1, i32), uimm5:$shamt), // Use binop_allwusers to recover immediates that may have been broken by // SimplifyDemandedBits. +def : Pat<(binop_allwusers GPR:$rs1, 0xffffffff), + (COPY GPR:$rs1)>; def : Pat<(binop_allwusers GPR:$rs1, u32simm12:$imm), (ANDI GPR:$rs1, u32simm12:$imm)>; diff --git a/llvm/lib/Target/RISCV/RISCVInstrInfoC.td b/llvm/lib/Target/RISCV/RISCVInstrInfoC.td index 18d38348f7214ff7e83361827aed15fd8b1641dc..f4e50d7aa45c5b5bcee5005b5e14d227805ad68f 100644 --- a/llvm/lib/Target/RISCV/RISCVInstrInfoC.td +++ b/llvm/lib/Target/RISCV/RISCVInstrInfoC.td @@ -841,7 +841,7 @@ def : InstAlias<".insn_cj $opcode, $funct3, $imm11", //===----------------------------------------------------------------------===// // Patterns are defined in the same order the compressed instructions appear -// on page 82 of the ISA manual. +// under the "RVC Instruction Set Listings" section of the ISA manual. // Quadrant 0 let Predicates = [HasStdExtCOrZca] in { diff --git a/llvm/lib/Target/RISCV/RISCVInstrInfoVPseudos.td b/llvm/lib/Target/RISCV/RISCVInstrInfoVPseudos.td index 435cd7f84c61228095d9c4558ad6c35b2d248756..e9715b40adc079a6968f02e5bb2d8f247168652d 100644 --- a/llvm/lib/Target/RISCV/RISCVInstrInfoVPseudos.td +++ b/llvm/lib/Target/RISCV/RISCVInstrInfoVPseudos.td @@ -3593,7 +3593,7 @@ multiclass VPseudoConversion { defvar suffix = !if(sew, "_" # MInfo.MX # "_E" # sew, "_" # MInfo.MX); - let VLMul = MInfo.value in { + let VLMul = MInfo.value, SEW=sew in { def suffix : VPseudoUnaryNoMask; def suffix # "_MASK" : VPseudoUnaryMask, @@ -3607,7 +3607,7 @@ multiclass VPseudoConversionRoundingMode { - let VLMul = MInfo.value in { + let VLMul = MInfo.value, SEW=sew in { defvar suffix = !if(sew, "_" # MInfo.MX # "_E" # sew, "_" # MInfo.MX); def suffix : VPseudoUnaryNoMaskRoundingMode; def suffix # "_MASK" : VPseudoUnaryMaskRoundingMode { - let VLMul = MInfo.value in { + let VLMul = MInfo.value, SEW=sew in { defvar suffix = !if(sew, "_" # MInfo.MX # "_E" # sew, "_" # MInfo.MX); def suffix : VPseudoUnaryNoMask_FRM; diff --git a/llvm/lib/Target/RISCV/RISCVInstrInfoXTHead.td b/llvm/lib/Target/RISCV/RISCVInstrInfoXTHead.td index 79ced3864363b9191df836b7c377fabb9112c826..b398c5e7fec2ec015718802d101f966d9426bc29 100644 --- a/llvm/lib/Target/RISCV/RISCVInstrInfoXTHead.td +++ b/llvm/lib/Target/RISCV/RISCVInstrInfoXTHead.td @@ -538,6 +538,8 @@ multiclass VPatTernaryVMAQA_VV_VX; +def : Pat<(XLenVT (riscv_shl_add GPR:$rs1, uimm2:$uimm2, GPR:$rs2)), + (TH_ADDSL GPR:$rs2, GPR:$rs1, uimm2:$uimm2)>; // Reuse complex patterns from StdExtZba def : Pat<(add_non_imm12 sh1add_op:$rs1, (XLenVT GPR:$rs2)), @@ -581,30 +583,6 @@ def : Pat<(mul (XLenVT GPR:$r), C9LeftShift:$i), (SLLI (XLenVT (TH_ADDSL GPR:$r, GPR:$r, 3)), (TrailingZeros C9LeftShift:$i))>; -def : Pat<(mul_const_oneuse GPR:$r, (XLenVT 11)), - (TH_ADDSL GPR:$r, (XLenVT (TH_ADDSL GPR:$r, GPR:$r, 2)), 1)>; -def : Pat<(mul_const_oneuse GPR:$r, (XLenVT 19)), - (TH_ADDSL GPR:$r, (XLenVT (TH_ADDSL GPR:$r, GPR:$r, 3)), 1)>; -def : Pat<(mul_const_oneuse GPR:$r, (XLenVT 13)), - (TH_ADDSL GPR:$r, (XLenVT (TH_ADDSL GPR:$r, GPR:$r, 1)), 2)>; -def : Pat<(mul_const_oneuse GPR:$r, (XLenVT 21)), - (TH_ADDSL GPR:$r, (XLenVT (TH_ADDSL GPR:$r, GPR:$r, 2)), 2)>; -def : Pat<(mul_const_oneuse GPR:$r, (XLenVT 37)), - (TH_ADDSL GPR:$r, (XLenVT (TH_ADDSL GPR:$r, GPR:$r, 3)), 2)>; -def : Pat<(mul_const_oneuse GPR:$r, (XLenVT 25)), - (TH_ADDSL (XLenVT (TH_ADDSL GPR:$r, GPR:$r, 2)), - (XLenVT (TH_ADDSL GPR:$r, GPR:$r, 2)), 2)>; -def : Pat<(mul_const_oneuse GPR:$r, (XLenVT 41)), - (TH_ADDSL GPR:$r, (XLenVT (TH_ADDSL GPR:$r, GPR:$r, 2)), 3)>; -def : Pat<(mul_const_oneuse GPR:$r, (XLenVT 73)), - (TH_ADDSL GPR:$r, (XLenVT (TH_ADDSL GPR:$r, GPR:$r, 3)), 3)>; -def : Pat<(mul_const_oneuse GPR:$r, (XLenVT 27)), - (TH_ADDSL (XLenVT (TH_ADDSL GPR:$r, GPR:$r, 3)), (XLenVT (TH_ADDSL GPR:$r, GPR:$r, 3)), 1)>; -def : Pat<(mul_const_oneuse GPR:$r, (XLenVT 45)), - (TH_ADDSL (XLenVT (TH_ADDSL GPR:$r, GPR:$r, 3)), (XLenVT (TH_ADDSL GPR:$r, GPR:$r, 3)), 2)>; -def : Pat<(mul_const_oneuse GPR:$r, (XLenVT 81)), - (TH_ADDSL (XLenVT (TH_ADDSL GPR:$r, GPR:$r, 3)), (XLenVT (TH_ADDSL GPR:$r, GPR:$r, 3)), 3)>; - def : Pat<(mul_const_oneuse GPR:$r, (XLenVT 200)), (SLLI (XLenVT (TH_ADDSL (XLenVT (TH_ADDSL GPR:$r, GPR:$r, 2)), (XLenVT (TH_ADDSL GPR:$r, GPR:$r, 2)), 2)), 3)>; diff --git a/llvm/lib/Target/RISCV/RISCVInstrInfoZb.td b/llvm/lib/Target/RISCV/RISCVInstrInfoZb.td index 434b071e628a0e4e164ee279817bea79e8384a8d..ffe2b7e27120847ee40c626984fd7a5eda46267b 100644 --- a/llvm/lib/Target/RISCV/RISCVInstrInfoZb.td +++ b/llvm/lib/Target/RISCV/RISCVInstrInfoZb.td @@ -26,18 +26,24 @@ // Operand and SDNode transformation definitions. //===----------------------------------------------------------------------===// -def riscv_clzw : SDNode<"RISCVISD::CLZW", SDT_RISCVIntUnaryOpW>; -def riscv_ctzw : SDNode<"RISCVISD::CTZW", SDT_RISCVIntUnaryOpW>; -def riscv_rolw : SDNode<"RISCVISD::ROLW", SDT_RISCVIntBinOpW>; -def riscv_rorw : SDNode<"RISCVISD::RORW", SDT_RISCVIntBinOpW>; -def riscv_brev8 : SDNode<"RISCVISD::BREV8", SDTIntUnaryOp>; -def riscv_orc_b : SDNode<"RISCVISD::ORC_B", SDTIntUnaryOp>; -def riscv_zip : SDNode<"RISCVISD::ZIP", SDTIntUnaryOp>; -def riscv_unzip : SDNode<"RISCVISD::UNZIP", SDTIntUnaryOp>; -def riscv_absw : SDNode<"RISCVISD::ABSW", SDTIntUnaryOp>; -def riscv_clmul : SDNode<"RISCVISD::CLMUL", SDTIntBinOp>; -def riscv_clmulh : SDNode<"RISCVISD::CLMULH", SDTIntBinOp>; -def riscv_clmulr : SDNode<"RISCVISD::CLMULR", SDTIntBinOp>; +def SDTIntShiftAddOp : SDTypeProfile<1, 3, [ // shl_add + SDTCisSameAs<0, 1>, SDTCisSameAs<0, 3>, SDTCisInt<0>, SDTCisInt<2>, + SDTCisInt<3> +]>; + +def riscv_shl_add : SDNode<"RISCVISD::SHL_ADD", SDTIntShiftAddOp>; +def riscv_clzw : SDNode<"RISCVISD::CLZW", SDT_RISCVIntUnaryOpW>; +def riscv_ctzw : SDNode<"RISCVISD::CTZW", SDT_RISCVIntUnaryOpW>; +def riscv_rolw : SDNode<"RISCVISD::ROLW", SDT_RISCVIntBinOpW>; +def riscv_rorw : SDNode<"RISCVISD::RORW", SDT_RISCVIntBinOpW>; +def riscv_brev8 : SDNode<"RISCVISD::BREV8", SDTIntUnaryOp>; +def riscv_orc_b : SDNode<"RISCVISD::ORC_B", SDTIntUnaryOp>; +def riscv_zip : SDNode<"RISCVISD::ZIP", SDTIntUnaryOp>; +def riscv_unzip : SDNode<"RISCVISD::UNZIP", SDTIntUnaryOp>; +def riscv_absw : SDNode<"RISCVISD::ABSW", SDTIntUnaryOp>; +def riscv_clmul : SDNode<"RISCVISD::CLMUL", SDTIntBinOp>; +def riscv_clmulh : SDNode<"RISCVISD::CLMULH", SDTIntBinOp>; +def riscv_clmulr : SDNode<"RISCVISD::CLMULR", SDTIntBinOp>; def UImmLog2XLenHalfAsmOperand : AsmOperandClass { let Name = "UImmLog2XLenHalf"; @@ -678,6 +684,8 @@ foreach i = {1,2,3} in { defvar shxadd = !cast("SH"#i#"ADD"); def : Pat<(XLenVT (add_like_non_imm12 (shl GPR:$rs1, (XLenVT i)), GPR:$rs2)), (shxadd GPR:$rs1, GPR:$rs2)>; + def : Pat<(XLenVT (riscv_shl_add GPR:$rs1, (XLenVT i), GPR:$rs2)), + (shxadd GPR:$rs1, GPR:$rs2)>; defvar pat = !cast("sh"#i#"add_op"); // More complex cases use a ComplexPattern. @@ -721,31 +729,6 @@ def : Pat<(mul (XLenVT GPR:$r), C9LeftShift:$i), (SLLI (XLenVT (SH3ADD GPR:$r, GPR:$r)), (TrailingZeros C9LeftShift:$i))>; -def : Pat<(mul_const_oneuse GPR:$r, (XLenVT 11)), - (SH1ADD (XLenVT (SH2ADD GPR:$r, GPR:$r)), GPR:$r)>; -def : Pat<(mul_const_oneuse GPR:$r, (XLenVT 19)), - (SH1ADD (XLenVT (SH3ADD GPR:$r, GPR:$r)), GPR:$r)>; -def : Pat<(mul_const_oneuse GPR:$r, (XLenVT 13)), - (SH2ADD (XLenVT (SH1ADD GPR:$r, GPR:$r)), GPR:$r)>; -def : Pat<(mul_const_oneuse GPR:$r, (XLenVT 21)), - (SH2ADD (XLenVT (SH2ADD GPR:$r, GPR:$r)), GPR:$r)>; -def : Pat<(mul_const_oneuse GPR:$r, (XLenVT 37)), - (SH2ADD (XLenVT (SH3ADD GPR:$r, GPR:$r)), GPR:$r)>; -def : Pat<(mul_const_oneuse GPR:$r, (XLenVT 25)), - (SH3ADD (XLenVT (SH1ADD GPR:$r, GPR:$r)), GPR:$r)>; -def : Pat<(mul_const_oneuse GPR:$r, (XLenVT 41)), - (SH3ADD (XLenVT (SH2ADD GPR:$r, GPR:$r)), GPR:$r)>; -def : Pat<(mul_const_oneuse GPR:$r, (XLenVT 73)), - (SH3ADD (XLenVT (SH3ADD GPR:$r, GPR:$r)), GPR:$r)>; -def : Pat<(mul_const_oneuse GPR:$r, (XLenVT 27)), - (SH1ADD (XLenVT (SH3ADD GPR:$r, GPR:$r)), - (XLenVT (SH3ADD GPR:$r, GPR:$r)))>; -def : Pat<(mul_const_oneuse GPR:$r, (XLenVT 45)), - (SH2ADD (XLenVT (SH3ADD GPR:$r, GPR:$r)), - (XLenVT (SH3ADD GPR:$r, GPR:$r)))>; -def : Pat<(mul_const_oneuse GPR:$r, (XLenVT 81)), - (SH3ADD (XLenVT (SH3ADD GPR:$r, GPR:$r)), - (XLenVT (SH3ADD GPR:$r, GPR:$r)))>; } // Predicates = [HasStdExtZba] let Predicates = [HasStdExtZba, IsRV64] in { @@ -764,6 +747,8 @@ foreach i = {1,2,3} in { defvar shxadd_uw = !cast("SH"#i#"ADD_UW"); def : Pat<(i64 (add_like_non_imm12 (shl (and GPR:$rs1, 0xFFFFFFFF), (i64 i)), (XLenVT GPR:$rs2))), (shxadd_uw GPR:$rs1, GPR:$rs2)>; + def : Pat<(i64 (riscv_shl_add (and GPR:$rs1, 0xFFFFFFFF), (i64 i), GPR:$rs2)), + (shxadd_uw GPR:$rs1, GPR:$rs2)>; } def : Pat<(i64 (add_like_non_imm12 (and (shl GPR:$rs1, (i64 1)), 0x1FFFFFFFF), (XLenVT GPR:$rs2))), @@ -881,6 +866,8 @@ foreach i = {1,2,3} in { defvar shxadd = !cast("SH"#i#"ADD"); def : Pat<(i32 (add_like_non_imm12 (shl GPR:$rs1, (i64 i)), GPR:$rs2)), (shxadd GPR:$rs1, GPR:$rs2)>; + def : Pat<(i32 (riscv_shl_add GPR:$rs1, (i32 i), GPR:$rs2)), + (shxadd GPR:$rs1, GPR:$rs2)>; } } diff --git a/llvm/lib/Target/RISCV/RISCVInstrInfoZvk.td b/llvm/lib/Target/RISCV/RISCVInstrInfoZvk.td index aac7dc444a2de3412b400b02b271546695e72af1..aaf9c019aedfe87e7fbc2ce10dacffa9859486bd 100644 --- a/llvm/lib/Target/RISCV/RISCVInstrInfoZvk.td +++ b/llvm/lib/Target/RISCV/RISCVInstrInfoZvk.td @@ -1,4 +1,4 @@ -//===-- RISCVInstrInfoZvk.td - RISC-V 'Zvk' instructions -------*- tablegen -*-===// +//===-- RISCVInstrInfoZvk.td - RISC-V 'Zvk' instructions ---*- tablegen -*-===// // // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. // See https://llvm.org/LICENSE.txt for license information. diff --git a/llvm/lib/Target/RISCV/RISCVOptWInstrs.cpp b/llvm/lib/Target/RISCV/RISCVOptWInstrs.cpp index ead91c5656be8b86898b16bf327908d54b8a14e0..788d8f9cfc853a0bac0ead9831641aeefefb1742 100644 --- a/llvm/lib/Target/RISCV/RISCVOptWInstrs.cpp +++ b/llvm/lib/Target/RISCV/RISCVOptWInstrs.cpp @@ -420,7 +420,7 @@ static bool isSignExtendedW(Register SrcReg, const RISCVSubtarget &ST, if (!MI) continue; - int OpNo = MI->findRegisterDefOperandIdx(Reg); + int OpNo = MI->findRegisterDefOperandIdx(Reg, /*TRI=*/nullptr); assert(OpNo != -1 && "Couldn't find register"); // If this is a sign extending operation we don't need to look any further. diff --git a/llvm/lib/Target/RISCV/RISCVTargetMachine.cpp b/llvm/lib/Target/RISCV/RISCVTargetMachine.cpp index ae1a6f179a49e31530f59ef567fe7f25e90743d2..0876f46728a10c836611f787d848301ac30603a8 100644 --- a/llvm/lib/Target/RISCV/RISCVTargetMachine.cpp +++ b/llvm/lib/Target/RISCV/RISCVTargetMachine.cpp @@ -91,11 +91,6 @@ static cl::opt cl::desc("Enable the loop data prefetch pass"), cl::init(true)); -static cl::opt - EnableSplitRegAlloc("riscv-split-regalloc", cl::Hidden, - cl::desc("Enable Split RegisterAlloc for RVV"), - cl::init(true)); - static cl::opt EnableMISchedLoadClustering( "riscv-misched-load-clustering", cl::Hidden, cl::desc("Enable load clustering in the machine scheduler"), @@ -121,6 +116,7 @@ extern "C" LLVM_EXTERNAL_VISIBILITY void LLVMInitializeRISCVTarget() { initializeRISCVExpandPseudoPass(*PR); initializeRISCVFoldMasksPass(*PR); initializeRISCVInsertVSETVLIPass(*PR); + initializeRISCVCoalesceVSETVLIPass(*PR); initializeRISCVInsertReadWriteCSRPass(*PR); initializeRISCVInsertWriteVXRMPass(*PR); initializeRISCVDAGToDAGISelPass(*PR); @@ -392,16 +388,15 @@ FunctionPass *RISCVPassConfig::createRVVRegAllocPass(bool Optimized) { } bool RISCVPassConfig::addRegAssignAndRewriteFast() { - if (EnableSplitRegAlloc) - addPass(createRVVRegAllocPass(false)); + addPass(createRVVRegAllocPass(false)); + addPass(createRISCVCoalesceVSETVLIPass()); return TargetPassConfig::addRegAssignAndRewriteFast(); } bool RISCVPassConfig::addRegAssignAndRewriteOptimized() { - if (EnableSplitRegAlloc) { - addPass(createRVVRegAllocPass(true)); - addPass(createVirtRegRewriter(false)); - } + addPass(createRVVRegAllocPass(true)); + addPass(createVirtRegRewriter(false)); + addPass(createRISCVCoalesceVSETVLIPass()); return TargetPassConfig::addRegAssignAndRewriteOptimized(); } diff --git a/llvm/lib/Target/RISCV/RISCVTargetTransformInfo.h b/llvm/lib/Target/RISCV/RISCVTargetTransformInfo.h index 2f9281ab89244729a9b91f3778082f7e4eaad84c..a4d1390875095855d427ef71b9b3bbbfa0062b01 100644 --- a/llvm/lib/Target/RISCV/RISCVTargetTransformInfo.h +++ b/llvm/lib/Target/RISCV/RISCVTargetTransformInfo.h @@ -210,7 +210,7 @@ public: unsigned Opcode, Type *Ty, TTI::TargetCostKind CostKind, TTI::OperandValueInfo Op1Info = {TTI::OK_AnyValue, TTI::OP_None}, TTI::OperandValueInfo Op2Info = {TTI::OK_AnyValue, TTI::OP_None}, - ArrayRef Args = ArrayRef(), + ArrayRef Args = std::nullopt, const Instruction *CxtI = nullptr); bool isElementTypeLegalForScalableVector(Type *Ty) const { diff --git a/llvm/lib/Target/SPIRV/MCTargetDesc/SPIRVMCTargetDesc.cpp b/llvm/lib/Target/SPIRV/MCTargetDesc/SPIRVMCTargetDesc.cpp index 78dfbf4ec9327a24d75c630b1f881769469a2d60..74ebaa9d0c0047ed6a652737ae85289af941e57f 100644 --- a/llvm/lib/Target/SPIRV/MCTargetDesc/SPIRVMCTargetDesc.cpp +++ b/llvm/lib/Target/SPIRV/MCTargetDesc/SPIRVMCTargetDesc.cpp @@ -53,9 +53,9 @@ static MCStreamer * createSPIRVMCStreamer(const Triple &T, MCContext &Ctx, std::unique_ptr &&MAB, std::unique_ptr &&OW, - std::unique_ptr &&Emitter, bool RelaxAll) { + std::unique_ptr &&Emitter) { return createSPIRVStreamer(Ctx, std::move(MAB), std::move(OW), - std::move(Emitter), RelaxAll); + std::move(Emitter)); } static MCTargetStreamer *createTargetAsmStreamer(MCStreamer &S, diff --git a/llvm/lib/Target/SPIRV/SPIRVBuiltins.cpp b/llvm/lib/Target/SPIRV/SPIRVBuiltins.cpp index 4b07d7e61fa1130b754dcd7ed2b05ff36734f337..7439d0fefa980038243dea637b16bf6071f7afa8 100644 --- a/llvm/lib/Target/SPIRV/SPIRVBuiltins.cpp +++ b/llvm/lib/Target/SPIRV/SPIRVBuiltins.cpp @@ -189,6 +189,10 @@ lookupBuiltin(StringRef DemangledCall, std::string BuiltinName = DemangledCall.substr(0, DemangledCall.find('(')).str(); + // Account for possible "__spirv_ocl_" prefix in SPIR-V friendly LLVM IR + if (BuiltinName.rfind("__spirv_ocl_", 0) == 0) + BuiltinName = BuiltinName.substr(12); + // Check if the extracted name contains type information between angle // brackets. If so, the builtin is an instantiated template - needs to have // the information after angle brackets and return type removed. @@ -2008,6 +2012,13 @@ static bool generateAsyncCopy(const SPIRV::IncomingCall *Call, const SPIRV::DemangledBuiltin *Builtin = Call->Builtin; unsigned Opcode = SPIRV::lookupNativeBuiltin(Builtin->Name, Builtin->Set)->Opcode; + + bool IsSet = Opcode == SPIRV::OpGroupAsyncCopy; + Register TypeReg = GR->getSPIRVTypeID(Call->ReturnType); + if (Call->isSpirvOp()) + return buildOpFromWrapper(MIRBuilder, Opcode, Call, + IsSet ? TypeReg : Register(0)); + auto Scope = buildConstantIntReg(SPIRV::Scope::Workgroup, MIRBuilder, GR); switch (Opcode) { @@ -2306,7 +2317,7 @@ Type *parseBuiltinCallArgumentBaseType(const StringRef DemangledCall, // parseBuiltinCallArgumentBaseType(...) as this function only retrieves the // base types. if (TypeStr.ends_with("*")) - TypeStr = TypeStr.slice(0, TypeStr.find_first_of(" ")); + TypeStr = TypeStr.slice(0, TypeStr.find_first_of(" *")); return parseBuiltinTypeNameToTargetExtType("opencl." + TypeStr.str() + "_t", Ctx); diff --git a/llvm/lib/Target/SPIRV/SPIRVBuiltins.td b/llvm/lib/Target/SPIRV/SPIRVBuiltins.td index 660000fb548d79205ef0f2fb8c07580c8b8ebc32..564028547821eceba90192840e7c0a3b871e826a 100644 --- a/llvm/lib/Target/SPIRV/SPIRVBuiltins.td +++ b/llvm/lib/Target/SPIRV/SPIRVBuiltins.td @@ -585,9 +585,9 @@ defm : DemangledNativeBuiltin<"__spirv_SpecConstantComposite", OpenCL_std, SpecC // Async Copy and Prefetch builtin records: defm : DemangledNativeBuiltin<"async_work_group_copy", OpenCL_std, AsyncCopy, 4, 4, OpGroupAsyncCopy>; -defm : DemangledNativeBuiltin<"__spirv_GroupAsyncCopy", OpenCL_std, AsyncCopy, 4, 4, OpGroupAsyncCopy>; +defm : DemangledNativeBuiltin<"__spirv_GroupAsyncCopy", OpenCL_std, AsyncCopy, 6, 6, OpGroupAsyncCopy>; defm : DemangledNativeBuiltin<"wait_group_events", OpenCL_std, AsyncCopy, 2, 2, OpGroupWaitEvents>; -defm : DemangledNativeBuiltin<"__spirv_GroupWaitEvents", OpenCL_std, AsyncCopy, 2, 2, OpGroupWaitEvents>; +defm : DemangledNativeBuiltin<"__spirv_GroupWaitEvents", OpenCL_std, AsyncCopy, 3, 3, OpGroupWaitEvents>; // Load and store builtin records: defm : DemangledNativeBuiltin<"__spirv_Load", OpenCL_std, LoadStore, 1, 3, OpLoad>; diff --git a/llvm/lib/Target/SPIRV/SPIRVEmitIntrinsics.cpp b/llvm/lib/Target/SPIRV/SPIRVEmitIntrinsics.cpp index 472bc8638c9af1d1ba83bb9c9b057d34b638a3e1..0d539b1ed9a8893cc8f491243812049d3f9fdb24 100644 --- a/llvm/lib/Target/SPIRV/SPIRVEmitIntrinsics.cpp +++ b/llvm/lib/Target/SPIRV/SPIRVEmitIntrinsics.cpp @@ -98,6 +98,8 @@ class SPIRVEmitIntrinsics return B.CreateIntrinsic(IntrID, {Types}, Args); } + void buildAssignPtr(IRBuilder<> &B, Type *ElemTy, Value *Arg); + void replaceMemInstrUses(Instruction *Old, Instruction *New, IRBuilder<> &B); void processInstrAfterVisit(Instruction *I, IRBuilder<> &B); void insertAssignPtrTypeIntrs(Instruction *I, IRBuilder<> &B); @@ -111,6 +113,7 @@ class SPIRVEmitIntrinsics void insertPtrCastOrAssignTypeInstr(Instruction *I, IRBuilder<> &B); void processGlobalValue(GlobalVariable &GV, IRBuilder<> &B); void processParamTypes(Function *F, IRBuilder<> &B); + void processParamTypesByFunHeader(Function *F, IRBuilder<> &B); Type *deduceFunParamElementType(Function *F, unsigned OpIdx); Type *deduceFunParamElementType(Function *F, unsigned OpIdx, std::unordered_set &FVisited); @@ -194,6 +197,17 @@ static inline void reportFatalOnTokenType(const Instruction *I) { false); } +void SPIRVEmitIntrinsics::buildAssignPtr(IRBuilder<> &B, Type *ElemTy, + Value *Arg) { + CallInst *AssignPtrTyCI = + buildIntrWithMD(Intrinsic::spv_assign_ptr_type, {Arg->getType()}, + Constant::getNullValue(ElemTy), Arg, + {B.getInt32(getPointerAddressSpace(Arg->getType()))}, B); + GR->addDeducedElementType(AssignPtrTyCI, ElemTy); + GR->addDeducedElementType(Arg, ElemTy); + AssignPtrTypeInstr[Arg] = AssignPtrTyCI; +} + // Set element pointer type to the given value of ValueTy and tries to // specify this type further (recursively) by Operand value, if needed. Type *SPIRVEmitIntrinsics::deduceElementTypeByValueDeep( @@ -232,6 +246,19 @@ Type *SPIRVEmitIntrinsics::deduceElementTypeByUsersDeep( return nullptr; } +// Implements what we know in advance about intrinsics and builtin calls +// TODO: consider feasibility of this particular case to be generalized by +// encoding knowledge about intrinsics and builtin calls by corresponding +// specification rules +static Type *getPointeeTypeByCallInst(StringRef DemangledName, + Function *CalledF, unsigned OpIdx) { + if ((DemangledName.starts_with("__spirv_ocl_printf(") || + DemangledName.starts_with("printf(")) && + OpIdx == 0) + return IntegerType::getInt8Ty(CalledF->getContext()); + return nullptr; +} + // Deduce and return a successfully deduced Type of the Instruction, // or nullptr otherwise. Type *SPIRVEmitIntrinsics::deduceElementTypeHelper(Value *I) { @@ -795,6 +822,8 @@ void SPIRVEmitIntrinsics::insertPtrCastOrAssignTypeInstr(Instruction *I, return; // collect information about formal parameter types + std::string DemangledName = + getOclOrSpirvBuiltinDemangledName(CI->getCalledFunction()->getName()); Function *CalledF = CI->getCalledFunction(); SmallVector CalledArgTys; bool HaveTypes = false; @@ -811,10 +840,15 @@ void SPIRVEmitIntrinsics::insertPtrCastOrAssignTypeInstr(Instruction *I, if (!ElemTy && hasPointeeTypeAttr(CalledArg)) ElemTy = getPointeeTypeByAttr(CalledArg); if (!ElemTy) { - for (User *U : CalledArg->users()) { - if (Instruction *Inst = dyn_cast(U)) { - if ((ElemTy = deduceElementTypeHelper(Inst)) != nullptr) - break; + ElemTy = getPointeeTypeByCallInst(DemangledName, CalledF, OpIdx); + if (ElemTy) { + GR->addDeducedElementType(CalledArg, ElemTy); + } else { + for (User *U : CalledArg->users()) { + if (Instruction *Inst = dyn_cast(U)) { + if ((ElemTy = deduceElementTypeHelper(Inst)) != nullptr) + break; + } } } } @@ -823,8 +857,6 @@ void SPIRVEmitIntrinsics::insertPtrCastOrAssignTypeInstr(Instruction *I, } } - std::string DemangledName = - getOclOrSpirvBuiltinDemangledName(CI->getCalledFunction()->getName()); if (DemangledName.empty() && !HaveTypes) return; @@ -835,8 +867,14 @@ void SPIRVEmitIntrinsics::insertPtrCastOrAssignTypeInstr(Instruction *I, continue; // Constants (nulls/undefs) are handled in insertAssignPtrTypeIntrs() - if (!isa(ArgOperand) && !isa(ArgOperand)) - continue; + if (!isa(ArgOperand) && !isa(ArgOperand)) { + // However, we may have assumptions about the formal argument's type and + // may have a need to insert a ptr cast for the actual parameter of this + // call. + Argument *CalledArg = CalledF->getArg(OpIdx); + if (!GR->findDeducedElementType(CalledArg)) + continue; + } Type *ExpectedType = OpIdx < CalledArgTys.size() ? CalledArgTys[OpIdx] : nullptr; @@ -1102,9 +1140,13 @@ void SPIRVEmitIntrinsics::processInstrAfterVisit(Instruction *I, (II->paramHasAttr(OpNo, Attribute::ImmArg)))) continue; B.SetInsertPoint(I); - auto *NewOp = - buildIntrWithMD(Intrinsic::spv_track_constant, - {Op->getType(), Op->getType()}, Op, Op, {}, B); + Value *OpTyVal = Op; + if (Op->getType()->isTargetExtTy()) + OpTyVal = Constant::getNullValue( + IntegerType::get(I->getContext(), GR->getPointerSize())); + auto *NewOp = buildIntrWithMD(Intrinsic::spv_track_constant, + {Op->getType(), OpTyVal->getType()}, Op, + OpTyVal, {}, B); I->setOperand(OpNo, NewOp); } } @@ -1179,28 +1221,29 @@ Type *SPIRVEmitIntrinsics::deduceFunParamElementType( return nullptr; } -void SPIRVEmitIntrinsics::processParamTypes(Function *F, IRBuilder<> &B) { +void SPIRVEmitIntrinsics::processParamTypesByFunHeader(Function *F, + IRBuilder<> &B) { B.SetInsertPointPastAllocas(F); for (unsigned OpIdx = 0; OpIdx < F->arg_size(); ++OpIdx) { Argument *Arg = F->getArg(OpIdx); if (!isUntypedPointerTy(Arg->getType())) continue; + Type *ElemTy = GR->findDeducedElementType(Arg); + if (!ElemTy && hasPointeeTypeAttr(Arg) && + (ElemTy = getPointeeTypeByAttr(Arg)) != nullptr) + buildAssignPtr(B, ElemTy, Arg); + } +} +void SPIRVEmitIntrinsics::processParamTypes(Function *F, IRBuilder<> &B) { + B.SetInsertPointPastAllocas(F); + for (unsigned OpIdx = 0; OpIdx < F->arg_size(); ++OpIdx) { + Argument *Arg = F->getArg(OpIdx); + if (!isUntypedPointerTy(Arg->getType())) + continue; Type *ElemTy = GR->findDeducedElementType(Arg); - if (!ElemTy) { - if (hasPointeeTypeAttr(Arg) && - (ElemTy = getPointeeTypeByAttr(Arg)) != nullptr) { - GR->addDeducedElementType(Arg, ElemTy); - } else if ((ElemTy = deduceFunParamElementType(F, OpIdx)) != nullptr) { - CallInst *AssignPtrTyCI = buildIntrWithMD( - Intrinsic::spv_assign_ptr_type, {Arg->getType()}, - Constant::getNullValue(ElemTy), Arg, - {B.getInt32(getPointerAddressSpace(Arg->getType()))}, B); - GR->addDeducedElementType(AssignPtrTyCI, ElemTy); - GR->addDeducedElementType(Arg, ElemTy); - AssignPtrTypeInstr[Arg] = AssignPtrTyCI; - } - } + if (!ElemTy && (ElemTy = deduceFunParamElementType(F, OpIdx)) != nullptr) + buildAssignPtr(B, ElemTy, Arg); } } @@ -1217,6 +1260,8 @@ bool SPIRVEmitIntrinsics::runOnFunction(Function &Func) { AggrConstTypes.clear(); AggrStores.clear(); + processParamTypesByFunHeader(F, B); + // StoreInst's operand type can be changed during the next transformations, // so we need to store it in the set. Also store already transformed types. for (auto &I : instructions(Func)) { diff --git a/llvm/lib/Target/SPIRV/SPIRVISelLowering.cpp b/llvm/lib/Target/SPIRV/SPIRVISelLowering.cpp index b8296c3f6eeaeeaa264eace08e0fe38c767dc7bf..96b4a570a26b1d9e5bde8c3683bd3db53e3ef2ef 100644 --- a/llvm/lib/Target/SPIRV/SPIRVISelLowering.cpp +++ b/llvm/lib/Target/SPIRV/SPIRVISelLowering.cpp @@ -314,6 +314,16 @@ void SPIRVTargetLowering::finalizeLowering(MachineFunction &MF) const { SPIRV::OpTypeBool)) MI.setDesc(STI.getInstrInfo()->get(SPIRV::OpLogicalNotEqual)); break; + case SPIRV::OpConstantI: { + SPIRVType *Type = GR.getSPIRVTypeForVReg(MI.getOperand(1).getReg()); + if (Type->getOpcode() != SPIRV::OpTypeInt && MI.getOperand(2).isImm() && + MI.getOperand(2).getImm() == 0) { + // Validate the null constant of a target extension type + MI.setDesc(STI.getInstrInfo()->get(SPIRV::OpConstantNull)); + for (unsigned i = MI.getNumOperands() - 1; i > 1; --i) + MI.removeOperand(i); + } + } break; } } } diff --git a/llvm/lib/Target/SPIRV/SPIRVInstructionSelector.cpp b/llvm/lib/Target/SPIRV/SPIRVInstructionSelector.cpp index 21a69fc3ad9b447751c9bf716727e03ea17f849c..9994a966c82c31d59fbd12dfe3a0f1a61e0517f4 100644 --- a/llvm/lib/Target/SPIRV/SPIRVInstructionSelector.cpp +++ b/llvm/lib/Target/SPIRV/SPIRVInstructionSelector.cpp @@ -646,6 +646,37 @@ bool SPIRVInstructionSelector::selectUnOp(Register ResVReg, const SPIRVType *ResType, MachineInstr &I, unsigned Opcode) const { + if (STI.isOpenCLEnv() && I.getOperand(1).isReg()) { + Register SrcReg = I.getOperand(1).getReg(); + bool IsGV = false; + for (MachineRegisterInfo::def_instr_iterator DefIt = + MRI->def_instr_begin(SrcReg); + DefIt != MRI->def_instr_end(); DefIt = std::next(DefIt)) { + if ((*DefIt).getOpcode() == TargetOpcode::G_GLOBAL_VALUE) { + IsGV = true; + break; + } + } + if (IsGV) { + uint32_t SpecOpcode = 0; + switch (Opcode) { + case SPIRV::OpConvertPtrToU: + SpecOpcode = static_cast(SPIRV::Opcode::ConvertPtrToU); + break; + case SPIRV::OpConvertUToPtr: + SpecOpcode = static_cast(SPIRV::Opcode::ConvertUToPtr); + break; + } + if (SpecOpcode) + return BuildMI(*I.getParent(), I, I.getDebugLoc(), + TII.get(SPIRV::OpSpecConstantOp)) + .addDef(ResVReg) + .addUse(GR.getSPIRVTypeID(ResType)) + .addImm(SpecOpcode) + .addUse(SrcReg) + .constrainAllUses(TII, TRI, RBI); + } + } return selectUnOpWithSrc(ResVReg, ResType, I, I.getOperand(1).getReg(), Opcode); } @@ -1587,8 +1618,18 @@ bool SPIRVInstructionSelector::selectIToF(Register ResVReg, bool SPIRVInstructionSelector::selectExt(Register ResVReg, const SPIRVType *ResType, MachineInstr &I, bool IsSigned) const { - if (GR.isScalarOrVectorOfType(I.getOperand(1).getReg(), SPIRV::OpTypeBool)) + Register SrcReg = I.getOperand(1).getReg(); + if (GR.isScalarOrVectorOfType(SrcReg, SPIRV::OpTypeBool)) return selectSelect(ResVReg, ResType, I, IsSigned); + + SPIRVType *SrcType = GR.getSPIRVTypeForVReg(SrcReg); + if (SrcType == ResType) + return BuildMI(*I.getParent(), I, I.getDebugLoc(), + TII.get(TargetOpcode::COPY)) + .addDef(ResVReg) + .addUse(SrcReg) + .constrainAllUses(TII, TRI, RBI); + unsigned Opcode = IsSigned ? SPIRV::OpSConvert : SPIRV::OpUConvert; return selectUnOp(ResVReg, ResType, I, Opcode); } @@ -1622,11 +1663,16 @@ bool SPIRVInstructionSelector::selectIntToBool(Register IntReg, bool SPIRVInstructionSelector::selectTrunc(Register ResVReg, const SPIRVType *ResType, MachineInstr &I) const { - if (GR.isScalarOrVectorOfType(ResVReg, SPIRV::OpTypeBool)) { - Register IntReg = I.getOperand(1).getReg(); - const SPIRVType *ArgType = GR.getSPIRVTypeForVReg(IntReg); + Register IntReg = I.getOperand(1).getReg(); + const SPIRVType *ArgType = GR.getSPIRVTypeForVReg(IntReg); + if (GR.isScalarOrVectorOfType(ResVReg, SPIRV::OpTypeBool)) return selectIntToBool(IntReg, ResVReg, I, ArgType, ResType); - } + if (ArgType == ResType) + return BuildMI(*I.getParent(), I, I.getDebugLoc(), + TII.get(TargetOpcode::COPY)) + .addDef(ResVReg) + .addUse(IntReg) + .constrainAllUses(TII, TRI, RBI); bool IsSigned = GR.isScalarOrVectorSigned(ResType); unsigned Opcode = IsSigned ? SPIRV::OpSConvert : SPIRV::OpUConvert; return selectUnOp(ResVReg, ResType, I, Opcode); diff --git a/llvm/lib/Target/SPIRV/SPIRVPreLegalizer.cpp b/llvm/lib/Target/SPIRV/SPIRVPreLegalizer.cpp index d16f6d5bf67ef420ea50d95957be5e0567525ae7..84508fb5fe09eb18a793b00b4fc00b6ed3536801 100644 --- a/llvm/lib/Target/SPIRV/SPIRVPreLegalizer.cpp +++ b/llvm/lib/Target/SPIRV/SPIRVPreLegalizer.cpp @@ -38,7 +38,9 @@ public: }; } // namespace -static void addConstantsToTrack(MachineFunction &MF, SPIRVGlobalRegistry *GR) { +static void +addConstantsToTrack(MachineFunction &MF, SPIRVGlobalRegistry *GR, + DenseMap &TargetExtConstTypes) { MachineRegisterInfo &MRI = MF.getRegInfo(); DenseMap RegsAlreadyAddedToDT; SmallVector ToErase, ToEraseComposites; @@ -47,6 +49,7 @@ static void addConstantsToTrack(MachineFunction &MF, SPIRVGlobalRegistry *GR) { if (!isSpvIntrinsic(MI, Intrinsic::spv_track_constant)) continue; ToErase.push_back(&MI); + Register SrcReg = MI.getOperand(2).getReg(); auto *Const = cast(cast( MI.getOperand(3).getMetadata()->getOperand(0)) @@ -54,14 +57,14 @@ static void addConstantsToTrack(MachineFunction &MF, SPIRVGlobalRegistry *GR) { if (auto *GV = dyn_cast(Const)) { Register Reg = GR->find(GV, &MF); if (!Reg.isValid()) - GR->add(GV, &MF, MI.getOperand(2).getReg()); + GR->add(GV, &MF, SrcReg); else RegsAlreadyAddedToDT[&MI] = Reg; } else { Register Reg = GR->find(Const, &MF); if (!Reg.isValid()) { if (auto *ConstVec = dyn_cast(Const)) { - auto *BuildVec = MRI.getVRegDef(MI.getOperand(2).getReg()); + auto *BuildVec = MRI.getVRegDef(SrcReg); assert(BuildVec && BuildVec->getOpcode() == TargetOpcode::G_BUILD_VECTOR); for (unsigned i = 0; i < ConstVec->getNumElements(); ++i) { @@ -75,7 +78,13 @@ static void addConstantsToTrack(MachineFunction &MF, SPIRVGlobalRegistry *GR) { BuildVec->getOperand(1 + i).setReg(ElemReg); } } - GR->add(Const, &MF, MI.getOperand(2).getReg()); + GR->add(Const, &MF, SrcReg); + if (Const->getType()->isTargetExtTy()) { + // remember association so that we can restore it when assign types + MachineInstr *SrcMI = MRI.getVRegDef(SrcReg); + if (SrcMI && SrcMI->getOpcode() == TargetOpcode::G_CONSTANT) + TargetExtConstTypes[SrcMI] = Const->getType(); + } } else { RegsAlreadyAddedToDT[&MI] = Reg; // This MI is unused and will be removed. If the MI uses @@ -224,6 +233,10 @@ static SPIRVType *propagateSPIRVType(MachineInstr *MI, SPIRVGlobalRegistry *GR, } break; } + case TargetOpcode::G_PTRTOINT: + SpirvTy = GR->getOrCreateSPIRVIntegerType( + MRI.getType(Reg).getScalarSizeInBits(), MIB); + break; case TargetOpcode::G_TRUNC: case TargetOpcode::G_ADDRSPACE_CAST: case TargetOpcode::G_PTR_ADD: @@ -252,6 +265,7 @@ createNewIdReg(SPIRVType *SpvType, Register SrcReg, MachineRegisterInfo &MRI, if (!SpvType) SpvType = GR.getSPIRVTypeForVReg(SrcReg); assert(SpvType && "VReg is expected to have SPIRV type"); + LLT SrcLLT = MRI.getType(SrcReg); LLT NewT = LLT::scalar(32); bool IsFloat = SpvType->getOpcode() == SPIRV::OpTypeFloat; bool IsVectorFloat = @@ -261,10 +275,10 @@ createNewIdReg(SPIRVType *SpvType, Register SrcReg, MachineRegisterInfo &MRI, IsFloat |= IsVectorFloat; auto GetIdOp = IsFloat ? SPIRV::GET_fID : SPIRV::GET_ID; auto DstClass = IsFloat ? &SPIRV::fIDRegClass : &SPIRV::IDRegClass; - if (MRI.getType(SrcReg).isPointer()) { + if (SrcLLT.isPointer()) { unsigned PtrSz = GR.getPointerSize(); NewT = LLT::pointer(0, PtrSz); - bool IsVec = MRI.getType(SrcReg).isVector(); + bool IsVec = SrcLLT.isVector(); if (IsVec) NewT = LLT::fixed_vector(2, NewT); if (PtrSz == 64) { @@ -284,7 +298,7 @@ createNewIdReg(SPIRVType *SpvType, Register SrcReg, MachineRegisterInfo &MRI, DstClass = &SPIRV::pID32RegClass; } } - } else if (MRI.getType(SrcReg).isVector()) { + } else if (SrcLLT.isVector()) { NewT = LLT::fixed_vector(2, NewT); if (IsFloat) { GetIdOp = SPIRV::GET_vfID; @@ -359,8 +373,10 @@ void processInstr(MachineInstr &MI, MachineIRBuilder &MIB, } } // namespace llvm -static void generateAssignInstrs(MachineFunction &MF, SPIRVGlobalRegistry *GR, - MachineIRBuilder MIB) { +static void +generateAssignInstrs(MachineFunction &MF, SPIRVGlobalRegistry *GR, + MachineIRBuilder MIB, + DenseMap &TargetExtConstTypes) { // Get access to information about available extensions const SPIRVSubtarget *ST = static_cast(&MIB.getMF().getSubtarget()); @@ -417,11 +433,14 @@ static void generateAssignInstrs(MachineFunction &MF, SPIRVGlobalRegistry *GR, continue; } Type *Ty = nullptr; - if (MI.getOpcode() == TargetOpcode::G_CONSTANT) - Ty = MI.getOperand(1).getCImm()->getType(); - else if (MI.getOpcode() == TargetOpcode::G_FCONSTANT) + if (MI.getOpcode() == TargetOpcode::G_CONSTANT) { + auto TargetExtIt = TargetExtConstTypes.find(&MI); + Ty = TargetExtIt == TargetExtConstTypes.end() + ? MI.getOperand(1).getCImm()->getType() + : TargetExtIt->second; + } else if (MI.getOpcode() == TargetOpcode::G_FCONSTANT) { Ty = MI.getOperand(1).getFPImm()->getType(); - else { + } else { assert(MI.getOpcode() == TargetOpcode::G_BUILD_VECTOR); Type *ElemTy = nullptr; MachineInstr *ElemMI = MRI.getVRegDef(MI.getOperand(1).getReg()); @@ -440,6 +459,7 @@ static void generateAssignInstrs(MachineFunction &MF, SPIRVGlobalRegistry *GR, insertAssignInstr(Reg, Ty, nullptr, GR, MIB, MRI); } else if (MI.getOpcode() == TargetOpcode::G_TRUNC || MI.getOpcode() == TargetOpcode::G_ZEXT || + MI.getOpcode() == TargetOpcode::G_PTRTOINT || MI.getOpcode() == TargetOpcode::G_GLOBAL_VALUE || MI.getOpcode() == TargetOpcode::COPY || MI.getOpcode() == TargetOpcode::G_ADDRSPACE_CAST) { @@ -483,7 +503,8 @@ static void processInstrsWithTypeFolding(MachineFunction &MF, continue; Register DstReg = MI.getOperand(0).getReg(); bool IsDstPtr = MRI.getType(DstReg).isPointer(); - if (IsDstPtr || MRI.getType(DstReg).isVector()) + bool isDstVec = MRI.getType(DstReg).isVector(); + if (IsDstPtr || isDstVec) MRI.setRegClass(DstReg, &SPIRV::IDRegClass); // Don't need to reset type of register holding constant and used in // G_ADDRSPACE_CAST, since it breaks legalizer. @@ -609,10 +630,12 @@ bool SPIRVPreLegalizer::runOnMachineFunction(MachineFunction &MF) { SPIRVGlobalRegistry *GR = ST.getSPIRVGlobalRegistry(); GR->setCurrentFunc(MF); MachineIRBuilder MIB(MF); - addConstantsToTrack(MF, GR); + // a registry of target extension constants + DenseMap TargetExtConstTypes; + addConstantsToTrack(MF, GR, TargetExtConstTypes); foldConstantsIntoIntrinsics(MF); insertBitcasts(MF, GR, MIB); - generateAssignInstrs(MF, GR, MIB); + generateAssignInstrs(MF, GR, MIB, TargetExtConstTypes); processSwitches(MF, GR, MIB); processInstrsWithTypeFolding(MF, GR, MIB); removeImplicitFallthroughs(MF, MIB); diff --git a/llvm/lib/Target/SPIRV/SPIRVSymbolicOperands.td b/llvm/lib/Target/SPIRV/SPIRVSymbolicOperands.td index ff102e318469f4e5cb1b52e1e90330e6980dce4f..31e19ad8630cdd6658a441d54881354d294ba520 100644 --- a/llvm/lib/Target/SPIRV/SPIRVSymbolicOperands.td +++ b/llvm/lib/Target/SPIRV/SPIRVSymbolicOperands.td @@ -1612,3 +1612,5 @@ multiclass OpcodeOperand value> { defm InBoundsPtrAccessChain : OpcodeOperand<70>; defm PtrCastToGeneric : OpcodeOperand<121>; defm Bitcast : OpcodeOperand<124>; +defm ConvertPtrToU : OpcodeOperand<117>; +defm ConvertUToPtr : OpcodeOperand<120>; diff --git a/llvm/lib/Target/SystemZ/SystemZElimCompare.cpp b/llvm/lib/Target/SystemZ/SystemZElimCompare.cpp index e58f50e471fc0ece73007f873d37a118e0f2624b..99067e3ef18732fcffb615481966147c7c5023d5 100644 --- a/llvm/lib/Target/SystemZ/SystemZElimCompare.cpp +++ b/llvm/lib/Target/SystemZ/SystemZElimCompare.cpp @@ -633,7 +633,7 @@ bool SystemZElimCompare::fuseCompareOperations( RegMask = MBBI->getOperand(3).getRegMask(); // Clear out all current operands. - int CCUse = MBBI->findRegisterUseOperandIdx(SystemZ::CC, false, TRI); + int CCUse = MBBI->findRegisterUseOperandIdx(SystemZ::CC, TRI, false); assert(CCUse >= 0 && "BRC/BCR must use CC"); Branch->removeOperand(CCUse); // Remove regmask (sibcall). @@ -707,11 +707,11 @@ bool SystemZElimCompare::processBlock(MachineBasicBlock &MBB) { continue; } - if (MI.definesRegister(SystemZ::CC)) { + if (MI.definesRegister(SystemZ::CC, /*TRI=*/nullptr)) { CCUsers.clear(); CompleteCCUsers = true; } - if (MI.readsRegister(SystemZ::CC) && CompleteCCUsers) + if (MI.readsRegister(SystemZ::CC, /*TRI=*/nullptr) && CompleteCCUsers) CCUsers.push_back(&MI); } return Changed; diff --git a/llvm/lib/Target/SystemZ/SystemZISelLowering.cpp b/llvm/lib/Target/SystemZ/SystemZISelLowering.cpp index 48956b571dc3b39f50dfd81b48967ae75ea42c48..2da4431cf077eb438ccb1a3fbb7fa20558efda6c 100644 --- a/llvm/lib/Target/SystemZ/SystemZISelLowering.cpp +++ b/llvm/lib/Target/SystemZ/SystemZISelLowering.cpp @@ -8092,9 +8092,9 @@ static bool checkCCKill(MachineInstr &MI, MachineBasicBlock *MBB) { MachineBasicBlock::iterator miI(std::next(MachineBasicBlock::iterator(MI))); for (MachineBasicBlock::iterator miE = MBB->end(); miI != miE; ++miI) { const MachineInstr& mi = *miI; - if (mi.readsRegister(SystemZ::CC)) + if (mi.readsRegister(SystemZ::CC, /*TRI=*/nullptr)) return false; - if (mi.definesRegister(SystemZ::CC)) + if (mi.definesRegister(SystemZ::CC, /*TRI=*/nullptr)) break; // Should have kill-flag - update below. } @@ -8233,7 +8233,8 @@ SystemZTargetLowering::emitSelect(MachineInstr &MI, } break; } - if (NextMI.definesRegister(SystemZ::CC) || NextMI.usesCustomInsertionHook()) + if (NextMI.definesRegister(SystemZ::CC, /*TRI=*/nullptr) || + NextMI.usesCustomInsertionHook()) break; bool User = false; for (auto *SelMI : Selects) @@ -8251,8 +8252,8 @@ SystemZTargetLowering::emitSelect(MachineInstr &MI, } MachineInstr *LastMI = Selects.back(); - bool CCKilled = - (LastMI->killsRegister(SystemZ::CC) || checkCCKill(*LastMI, MBB)); + bool CCKilled = (LastMI->killsRegister(SystemZ::CC, /*TRI=*/nullptr) || + checkCCKill(*LastMI, MBB)); MachineBasicBlock *StartMBB = MBB; MachineBasicBlock *JoinMBB = SystemZ::splitBlockAfter(LastMI, MBB); MachineBasicBlock *FalseMBB = SystemZ::emitBlockAfter(StartMBB); @@ -8352,7 +8353,8 @@ MachineBasicBlock *SystemZTargetLowering::emitCondStore(MachineInstr &MI, // Unless CC was killed in the CondStore instruction, mark it as // live-in to both FalseMBB and JoinMBB. - if (!MI.killsRegister(SystemZ::CC) && !checkCCKill(MI, JoinMBB)) { + if (!MI.killsRegister(SystemZ::CC, /*TRI=*/nullptr) && + !checkCCKill(MI, JoinMBB)) { FalseMBB->addLiveIn(SystemZ::CC); JoinMBB->addLiveIn(SystemZ::CC); } @@ -8755,7 +8757,7 @@ SystemZTargetLowering::emitAtomicCmpSwapW(MachineInstr &MI, // If the CC def wasn't dead in the ATOMIC_CMP_SWAPW, mark CC as live-in // to the block after the loop. At this point, CC may have been defined // either by the CR in LoopMBB or by the CS in SetMBB. - if (!MI.registerDefIsDead(SystemZ::CC)) + if (!MI.registerDefIsDead(SystemZ::CC, /*TRI=*/nullptr)) DoneMBB->addLiveIn(SystemZ::CC); MI.eraseFromParent(); @@ -9629,7 +9631,7 @@ SDValue SystemZTargetLowering::lowerVECREDUCE_ADD(SDValue Op, case 8: case 16: Op = DAG.getNode(SystemZISD::VSUM, DL, MVT::v4i32, Op, Zero); - LLVM_FALLTHROUGH; + [[fallthrough]]; case 32: case 64: Op = DAG.getNode(SystemZISD::VSUM, DL, MVT::i128, Op, diff --git a/llvm/lib/Target/SystemZ/SystemZInstrInfo.cpp b/llvm/lib/Target/SystemZ/SystemZInstrInfo.cpp index 950548abcfa92c62200adbcb7dce2134453a8f97..6b75c30943b40ae24e949d7cf61ee1c284de48d5 100644 --- a/llvm/lib/Target/SystemZ/SystemZInstrInfo.cpp +++ b/llvm/lib/Target/SystemZ/SystemZInstrInfo.cpp @@ -938,8 +938,9 @@ static LogicOp interpretAndImmediate(unsigned Opcode) { } static void transferDeadCC(MachineInstr *OldMI, MachineInstr *NewMI) { - if (OldMI->registerDefIsDead(SystemZ::CC)) { - MachineOperand *CCDef = NewMI->findRegisterDefOperand(SystemZ::CC); + if (OldMI->registerDefIsDead(SystemZ::CC, /*TRI=*/nullptr)) { + MachineOperand *CCDef = + NewMI->findRegisterDefOperand(SystemZ::CC, /*TRI=*/nullptr); if (CCDef != nullptr) CCDef->setIsDead(true); } @@ -1034,7 +1035,8 @@ MachineInstr *SystemZInstrInfo::foldMemoryOperandImpl( .addFrameIndex(FrameIndex) .addImm(0) .addImm(MI.getOperand(2).getImm()); - BuiltMI->findRegisterDefOperand(SystemZ::CC)->setIsDead(true); + BuiltMI->findRegisterDefOperand(SystemZ::CC, /*TRI=*/nullptr) + ->setIsDead(true); CCLiveRange->createDeadDef(MISlot, LIS->getVNInfoAllocator()); return BuiltMI; } @@ -1195,7 +1197,7 @@ MachineInstr *SystemZInstrInfo::foldMemoryOperandImpl( unsigned NumOps = MI.getNumExplicitOperands(); int MemOpcode = SystemZ::getMemOpcode(Opcode); if (MemOpcode == -1 || - (CCLiveAtMI && !MI.definesRegister(SystemZ::CC) && + (CCLiveAtMI && !MI.definesRegister(SystemZ::CC, /*TRI=*/nullptr) && get(MemOpcode).hasImplicitDefOfPhysReg(SystemZ::CC))) return nullptr; @@ -1303,9 +1305,9 @@ MachineInstr *SystemZInstrInfo::foldMemoryOperandImpl( MIB.addImm(CCValid); MIB.addImm(NeedsCommute ? CCMask ^ CCValid : CCMask); } - if (MIB->definesRegister(SystemZ::CC) && - (!MI.definesRegister(SystemZ::CC) || - MI.registerDefIsDead(SystemZ::CC))) { + if (MIB->definesRegister(SystemZ::CC, /*TRI=*/nullptr) && + (!MI.definesRegister(SystemZ::CC, /*TRI=*/nullptr) || + MI.registerDefIsDead(SystemZ::CC, /*TRI=*/nullptr))) { MIB->addRegisterDead(SystemZ::CC, TRI); if (CCLiveRange) CCLiveRange->createDeadDef(MISlot, LIS->getVNInfoAllocator()); @@ -1861,14 +1863,14 @@ prepareCompareSwapOperands(MachineBasicBlock::iterator const MBBI) const { bool CCLive = true; SmallVector CCUsers; for (MachineInstr &MI : llvm::make_range(std::next(MBBI), MBB->end())) { - if (MI.readsRegister(SystemZ::CC)) { + if (MI.readsRegister(SystemZ::CC, /*TRI=*/nullptr)) { unsigned Flags = MI.getDesc().TSFlags; if ((Flags & SystemZII::CCMaskFirst) || (Flags & SystemZII::CCMaskLast)) CCUsers.push_back(&MI); else return false; } - if (MI.definesRegister(SystemZ::CC)) { + if (MI.definesRegister(SystemZ::CC, /*TRI=*/nullptr)) { CCLive = false; break; } diff --git a/llvm/lib/Target/SystemZ/SystemZTargetTransformInfo.h b/llvm/lib/Target/SystemZ/SystemZTargetTransformInfo.h index 696d887c1d5db8001cca83e22a685db619220129..3cf4a69ac2818643936cd90fad902bdb23fd9a5a 100644 --- a/llvm/lib/Target/SystemZ/SystemZTargetTransformInfo.h +++ b/llvm/lib/Target/SystemZ/SystemZTargetTransformInfo.h @@ -89,7 +89,7 @@ public: unsigned Opcode, Type *Ty, TTI::TargetCostKind CostKind, TTI::OperandValueInfo Op1Info = {TTI::OK_AnyValue, TTI::OP_None}, TTI::OperandValueInfo Op2Info = {TTI::OK_AnyValue, TTI::OP_None}, - ArrayRef Args = ArrayRef(), + ArrayRef Args = std::nullopt, const Instruction *CxtI = nullptr); InstructionCost getShuffleCost(TTI::ShuffleKind Kind, VectorType *Tp, ArrayRef Mask, diff --git a/llvm/lib/Target/WebAssembly/MCTargetDesc/WebAssemblyMCTypeUtilities.cpp b/llvm/lib/Target/WebAssembly/MCTargetDesc/WebAssemblyMCTypeUtilities.cpp index b7b5b2a97c59e20b6848cc08fe6ba3349a73ca26..8ea02bd2ad1ff04e3c3b97287aff0da1c9eee310 100644 --- a/llvm/lib/Target/WebAssembly/MCTargetDesc/WebAssemblyMCTypeUtilities.cpp +++ b/llvm/lib/Target/WebAssembly/MCTargetDesc/WebAssemblyMCTypeUtilities.cpp @@ -18,24 +18,16 @@ using namespace llvm; std::optional WebAssembly::parseType(StringRef Type) { - // FIXME: can't use StringSwitch because wasm::ValType doesn't have a - // "invalid" value. - if (Type == "i32") - return wasm::ValType::I32; - if (Type == "i64") - return wasm::ValType::I64; - if (Type == "f32") - return wasm::ValType::F32; - if (Type == "f64") - return wasm::ValType::F64; - if (Type == "v128" || Type == "i8x16" || Type == "i16x8" || Type == "i32x4" || - Type == "i64x2" || Type == "f32x4" || Type == "f64x2") - return wasm::ValType::V128; - if (Type == "funcref") - return wasm::ValType::FUNCREF; - if (Type == "externref") - return wasm::ValType::EXTERNREF; - return std::nullopt; + return llvm::StringSwitch>{Type} + .Case("i32", wasm::ValType::I32) + .Case("i64", wasm::ValType::I64) + .Case("f32", wasm::ValType::F32) + .Case("f64", wasm::ValType::F64) + .Cases("v128", "i8x16", "i16x8", "i32x4", "i64x2", "f32x4", "f64x2", + wasm::ValType::V128) + .Case("funcref", wasm::ValType::FUNCREF) + .Case("externref", wasm::ValType::EXTERNREF) + .Default(std::nullopt); } WebAssembly::BlockType WebAssembly::parseBlockType(StringRef Type) { diff --git a/llvm/lib/Target/WebAssembly/WebAssemblyDebugValueManager.cpp b/llvm/lib/Target/WebAssembly/WebAssemblyDebugValueManager.cpp index a2a054127d5f65a139bee50d065c0a458a44fb2d..da3717499689da9452a56486829e67a760d8f534 100644 --- a/llvm/lib/Target/WebAssembly/WebAssemblyDebugValueManager.cpp +++ b/llvm/lib/Target/WebAssembly/WebAssemblyDebugValueManager.cpp @@ -37,7 +37,7 @@ WebAssemblyDebugValueManager::WebAssemblyDebugValueManager(MachineInstr *Def) ME = Def->getParent()->end(); MI != ME; ++MI) { // If another definition appears, stop - if (MI->definesRegister(CurrentReg)) + if (MI->definesRegister(CurrentReg, /*TRI=*/nullptr)) break; if (MI->isDebugValue() && MI->hasDebugOperandForReg(CurrentReg)) DbgValues.push_back(&*MI); diff --git a/llvm/lib/Target/WebAssembly/WebAssemblyRegStackify.cpp b/llvm/lib/Target/WebAssembly/WebAssemblyRegStackify.cpp index 3046f9476f91c34acf81a5ef57e08eb9e249d01b..ef174e1716ef1e1e149fc4bca601fe21eaec115e 100644 --- a/llvm/lib/Target/WebAssembly/WebAssemblyRegStackify.cpp +++ b/llvm/lib/Target/WebAssembly/WebAssemblyRegStackify.cpp @@ -80,13 +80,13 @@ FunctionPass *llvm::createWebAssemblyRegStackify() { // the expression stack. static void imposeStackOrdering(MachineInstr *MI) { // Write the opaque VALUE_STACK register. - if (!MI->definesRegister(WebAssembly::VALUE_STACK)) + if (!MI->definesRegister(WebAssembly::VALUE_STACK, /*TRI=*/nullptr)) MI->addOperand(MachineOperand::CreateReg(WebAssembly::VALUE_STACK, /*isDef=*/true, /*isImp=*/true)); // Also read the opaque VALUE_STACK register. - if (!MI->readsRegister(WebAssembly::VALUE_STACK)) + if (!MI->readsRegister(WebAssembly::VALUE_STACK, /*TRI=*/nullptr)) MI->addOperand(MachineOperand::CreateReg(WebAssembly::VALUE_STACK, /*isDef=*/false, /*isImp=*/true)); @@ -371,8 +371,8 @@ static bool isSafeToMove(const MachineOperand *Def, const MachineOperand *Use, Register Reg = MO.getReg(); // If the register is dead here and at Insert, ignore it. - if (MO.isDead() && Insert->definesRegister(Reg) && - !Insert->readsRegister(Reg)) + if (MO.isDead() && Insert->definesRegister(Reg, /*TRI=*/nullptr) && + !Insert->readsRegister(Reg, /*TRI=*/nullptr)) continue; if (Reg.isPhysical()) { @@ -864,7 +864,8 @@ bool WebAssemblyRegStackify::runOnMachineFunction(MachineFunction &MF) { if (WebAssembly::isArgument(DefI->getOpcode())) continue; - MachineOperand *Def = DefI->findRegisterDefOperand(Reg); + MachineOperand *Def = + DefI->findRegisterDefOperand(Reg, /*TRI=*/nullptr); assert(Def != nullptr); // Decide which strategy to take. Prefer to move a single-use value diff --git a/llvm/lib/Target/WebAssembly/WebAssemblyTargetTransformInfo.h b/llvm/lib/Target/WebAssembly/WebAssemblyTargetTransformInfo.h index a803fe5c1bbecc153a442e2388d1b477ed54f775..801f905d377ed921b8bd0a8ed4e89b3ea8f3d363 100644 --- a/llvm/lib/Target/WebAssembly/WebAssemblyTargetTransformInfo.h +++ b/llvm/lib/Target/WebAssembly/WebAssemblyTargetTransformInfo.h @@ -63,7 +63,7 @@ public: unsigned Opcode, Type *Ty, TTI::TargetCostKind CostKind, TTI::OperandValueInfo Op1Info = {TTI::OK_AnyValue, TTI::OP_None}, TTI::OperandValueInfo Op2Info = {TTI::OK_AnyValue, TTI::OP_None}, - ArrayRef Args = ArrayRef(), + ArrayRef Args = std::nullopt, const Instruction *CxtI = nullptr); using BaseT::getVectorInstrCost; InstructionCost getVectorInstrCost(unsigned Opcode, Type *Val, diff --git a/llvm/lib/Target/X86/MCTargetDesc/X86MCTargetDesc.h b/llvm/lib/Target/X86/MCTargetDesc/X86MCTargetDesc.h index 437a7bd6ff6c4cfe94962948b348c7a89429a1ce..18ecca34943f6b0d9220c475e31d9e69a3ab43c3 100644 --- a/llvm/lib/Target/X86/MCTargetDesc/X86MCTargetDesc.h +++ b/llvm/lib/Target/X86/MCTargetDesc/X86MCTargetDesc.h @@ -121,7 +121,6 @@ MCStreamer *createX86WinCOFFStreamer(MCContext &C, std::unique_ptr &&AB, std::unique_ptr &&OW, std::unique_ptr &&CE, - bool RelaxAll, bool IncrementalLinkerCompatible); /// Construct an X86 Mach-O object writer. diff --git a/llvm/lib/Target/X86/MCTargetDesc/X86WinCOFFStreamer.cpp b/llvm/lib/Target/X86/MCTargetDesc/X86WinCOFFStreamer.cpp index 36945d1f67468f96e2c6e1f8000e16112ba31f01..dac8bc1fb1be357491a909648725f38f04163ad6 100644 --- a/llvm/lib/Target/X86/MCTargetDesc/X86WinCOFFStreamer.cpp +++ b/llvm/lib/Target/X86/MCTargetDesc/X86WinCOFFStreamer.cpp @@ -70,11 +70,9 @@ MCStreamer *llvm::createX86WinCOFFStreamer(MCContext &C, std::unique_ptr &&AB, std::unique_ptr &&OW, std::unique_ptr &&CE, - bool RelaxAll, bool IncrementalLinkerCompatible) { X86WinCOFFStreamer *S = new X86WinCOFFStreamer(C, std::move(AB), std::move(CE), std::move(OW)); - S->getAssembler().setRelaxAll(RelaxAll); S->getAssembler().setIncrementalLinkerCompatible(IncrementalLinkerCompatible); return S; } diff --git a/llvm/lib/Target/X86/X86CmovConversion.cpp b/llvm/lib/Target/X86/X86CmovConversion.cpp index 8dc3b91f08e2920858c412419e5ea418e79f7866..297acf07115a9bf11313c68b07cc7102289be655 100644 --- a/llvm/lib/Target/X86/X86CmovConversion.cpp +++ b/llvm/lib/Target/X86/X86CmovConversion.cpp @@ -355,7 +355,7 @@ bool X86CmovConverterPass::collectCmovCandidates( FoundNonCMOVInst = true; // Check if this instruction define EFLAGS, to determine end of processed // range, as there would be no more instructions using current EFLAGS def. - if (I.definesRegister(X86::EFLAGS)) { + if (I.definesRegister(X86::EFLAGS, /*TRI=*/nullptr)) { // Check if current processed CMOV-group should not be skipped and add // it as a CMOV-group-candidate. if (!SkipGroup) @@ -582,7 +582,7 @@ bool X86CmovConverterPass::checkForProfitableCmovCandidates( } static bool checkEFLAGSLive(MachineInstr *MI) { - if (MI->killsRegister(X86::EFLAGS)) + if (MI->killsRegister(X86::EFLAGS, /*TRI=*/nullptr)) return false; // The EFLAGS operand of MI might be missing a kill marker. @@ -592,9 +592,9 @@ static bool checkEFLAGSLive(MachineInstr *MI) { // Scan forward through BB for a use/def of EFLAGS. for (auto I = std::next(ItrMI), E = BB->end(); I != E; ++I) { - if (I->readsRegister(X86::EFLAGS)) + if (I->readsRegister(X86::EFLAGS, /*TRI=*/nullptr)) return true; - if (I->definesRegister(X86::EFLAGS)) + if (I->definesRegister(X86::EFLAGS, /*TRI=*/nullptr)) return false; } diff --git a/llvm/lib/Target/X86/X86FixupSetCC.cpp b/llvm/lib/Target/X86/X86FixupSetCC.cpp index 269f8ce6bd7a421302530eea33a9241624bd456a..5c7105988070c37fa237f36dea1a1a4bade79837 100644 --- a/llvm/lib/Target/X86/X86FixupSetCC.cpp +++ b/llvm/lib/Target/X86/X86FixupSetCC.cpp @@ -69,7 +69,7 @@ bool X86FixupSetCCPass::runOnMachineFunction(MachineFunction &MF) { MachineInstr *FlagsDefMI = nullptr; for (auto &MI : MBB) { // Remember the most recent preceding eflags defining instruction. - if (MI.definesRegister(X86::EFLAGS)) + if (MI.definesRegister(X86::EFLAGS, /*TRI=*/nullptr)) FlagsDefMI = &MI; // Find a setcc that is used by a zext. @@ -94,7 +94,7 @@ bool X86FixupSetCCPass::runOnMachineFunction(MachineFunction &MF) { // it, itself, by definition, clobbers eflags. But it may happen that // FlagsDefMI also *uses* eflags, in which case the transformation is // invalid. - if (FlagsDefMI->readsRegister(X86::EFLAGS)) + if (FlagsDefMI->readsRegister(X86::EFLAGS, /*TRI=*/nullptr)) continue; // On 32-bit, we need to be careful to force an ABCD register. diff --git a/llvm/lib/Target/X86/X86FlagsCopyLowering.cpp b/llvm/lib/Target/X86/X86FlagsCopyLowering.cpp index d96613d7bb7efcfb599859ea65f199588cb7d5e5..78355d3550833ef1ed23733eb3ff15e66521c1ae 100644 --- a/llvm/lib/Target/X86/X86FlagsCopyLowering.cpp +++ b/llvm/lib/Target/X86/X86FlagsCopyLowering.cpp @@ -442,7 +442,8 @@ bool X86FlagsCopyLoweringPass::runOnMachineFunction(MachineFunction &MF) { llvm::reverse(llvm::make_range(Begin, End)), [&](MachineInstr &MI) { // Flag any instruction (other than the copy we are // currently rewriting) that defs EFLAGS. - return &MI != CopyI && MI.findRegisterDefOperand(X86::EFLAGS); + return &MI != CopyI && + MI.findRegisterDefOperand(X86::EFLAGS, /*TRI=*/nullptr); }); }; auto HasEFLAGSClobberPath = [&](MachineBasicBlock *BeginMBB, @@ -500,7 +501,7 @@ bool X86FlagsCopyLoweringPass::runOnMachineFunction(MachineFunction &MF) { auto DefIt = llvm::find_if( llvm::reverse(llvm::make_range(TestMBB->instr_begin(), TestPos)), [&](MachineInstr &MI) { - return MI.findRegisterDefOperand(X86::EFLAGS); + return MI.findRegisterDefOperand(X86::EFLAGS, /*TRI=*/nullptr); }); if (DefIt.base() != TestMBB->instr_begin()) { dbgs() << " Using EFLAGS defined by: "; @@ -562,9 +563,10 @@ bool X86FlagsCopyLoweringPass::runOnMachineFunction(MachineFunction &MF) { break; } - MachineOperand *FlagUse = MI.findRegisterUseOperand(X86::EFLAGS); + MachineOperand *FlagUse = + MI.findRegisterUseOperand(X86::EFLAGS, /*TRI=*/nullptr); if (!FlagUse) { - if (MI.findRegisterDefOperand(X86::EFLAGS)) { + if (MI.findRegisterDefOperand(X86::EFLAGS, /*TRI=*/nullptr)) { // If EFLAGS are defined, it's as-if they were killed. We can stop // scanning here. // @@ -615,7 +617,7 @@ bool X86FlagsCopyLoweringPass::runOnMachineFunction(MachineFunction &MF) { rewriteCopy(MI, *FlagUse, CopyDefI); } else { // We assume all other instructions that use flags also def them. - assert(MI.findRegisterDefOperand(X86::EFLAGS) && + assert(MI.findRegisterDefOperand(X86::EFLAGS, /*TRI=*/nullptr) && "Expected a def of EFLAGS for this instruction!"); // NB!!! Several arithmetic instructions only *partially* update @@ -734,7 +736,7 @@ CondRegArray X86FlagsCopyLoweringPass::collectCondsInRegs( // Stop scanning when we see the first definition of the EFLAGS as prior to // this we would potentially capture the wrong flag state. - if (MI.findRegisterDefOperand(X86::EFLAGS)) + if (MI.findRegisterDefOperand(X86::EFLAGS, /*TRI=*/nullptr)) break; } return CondRegs; @@ -914,7 +916,7 @@ void X86FlagsCopyLoweringPass::rewriteCondJmp( // Rewrite the jump to use the !ZF flag from the test, and kill its use of // flags afterward. JmpI.getOperand(1).setImm(Inverted ? X86::COND_E : X86::COND_NE); - JmpI.findRegisterUseOperand(X86::EFLAGS)->setIsKill(true); + JmpI.findRegisterUseOperand(X86::EFLAGS, /*TRI=*/nullptr)->setIsKill(true); LLVM_DEBUG(dbgs() << " fixed jCC: "; JmpI.dump()); } diff --git a/llvm/lib/Target/X86/X86FloatingPoint.cpp b/llvm/lib/Target/X86/X86FloatingPoint.cpp index 260879ffaa4f120aac8824e88cb77542163618f9..02c3ca9839fc2d81aacbebe4d7e5fda51fd5a896 100644 --- a/llvm/lib/Target/X86/X86FloatingPoint.cpp +++ b/llvm/lib/Target/X86/X86FloatingPoint.cpp @@ -829,7 +829,8 @@ static const TableEntry PopTable[] = { }; static bool doesInstructionSetFPSW(MachineInstr &MI) { - if (const MachineOperand *MO = MI.findRegisterDefOperand(X86::FPSW)) + if (const MachineOperand *MO = + MI.findRegisterDefOperand(X86::FPSW, /*TRI=*/nullptr)) if (!MO->isDead()) return true; return false; @@ -872,7 +873,7 @@ void FPS::popStackAfter(MachineBasicBlock::iterator &I) { if (doesInstructionSetFPSW(MI)) { MachineBasicBlock &MBB = *MI.getParent(); MachineBasicBlock::iterator Next = getNextFPInstruction(I); - if (Next != MBB.end() && Next->readsRegister(X86::FPSW)) + if (Next != MBB.end() && Next->readsRegister(X86::FPSW, /*TRI=*/nullptr)) I = Next; } I = BuildMI(*MBB, ++I, dl, TII->get(X86::ST_FPrr)).addReg(X86::ST0); @@ -1082,9 +1083,10 @@ void FPS::handleReturn(MachineBasicBlock::iterator &I) { // FP Register uses must be kills unless there are two uses of the same // register, in which case only one will be a kill. assert(Op.isUse() && - (Op.isKill() || // Marked kill. - getFPReg(Op) == FirstFPRegOp || // Second instance. - MI.killsRegister(Op.getReg())) && // Later use is marked kill. + (Op.isKill() || // Marked kill. + getFPReg(Op) == FirstFPRegOp || // Second instance. + MI.killsRegister(Op.getReg(), + /*TRI=*/nullptr)) && // Later use is marked kill. "Ret only defs operands, and values aren't live beyond it"); if (FirstFPRegOp == ~0U) @@ -1181,7 +1183,7 @@ void FPS::handleOneArgFP(MachineBasicBlock::iterator &I) { // Is this the last use of the source register? unsigned Reg = getFPReg(MI.getOperand(NumOps - 1)); - bool KillsSrc = MI.killsRegister(X86::FP0 + Reg); + bool KillsSrc = MI.killsRegister(X86::FP0 + Reg, /*TRI=*/nullptr); // FISTP64m is strange because there isn't a non-popping versions. // If we have one _and_ we don't want to pop the operand, duplicate the value @@ -1244,7 +1246,7 @@ void FPS::handleOneArgFPRW(MachineBasicBlock::iterator &I) { // Is this the last use of the source register? unsigned Reg = getFPReg(MI.getOperand(1)); - bool KillsSrc = MI.killsRegister(X86::FP0 + Reg); + bool KillsSrc = MI.killsRegister(X86::FP0 + Reg, /*TRI=*/nullptr); if (KillsSrc) { // If this is the last use of the source register, just make sure it's on @@ -1355,8 +1357,8 @@ void FPS::handleTwoArgFP(MachineBasicBlock::iterator &I) { unsigned Dest = getFPReg(MI.getOperand(0)); unsigned Op0 = getFPReg(MI.getOperand(NumOperands - 2)); unsigned Op1 = getFPReg(MI.getOperand(NumOperands - 1)); - bool KillsOp0 = MI.killsRegister(X86::FP0 + Op0); - bool KillsOp1 = MI.killsRegister(X86::FP0 + Op1); + bool KillsOp0 = MI.killsRegister(X86::FP0 + Op0, /*TRI=*/nullptr); + bool KillsOp1 = MI.killsRegister(X86::FP0 + Op1, /*TRI=*/nullptr); const DebugLoc &dl = MI.getDebugLoc(); unsigned TOS = getStackEntry(0); @@ -1453,8 +1455,8 @@ void FPS::handleCompareFP(MachineBasicBlock::iterator &I) { assert(NumOperands == 2 && "Illegal FUCOM* instruction!"); unsigned Op0 = getFPReg(MI.getOperand(NumOperands - 2)); unsigned Op1 = getFPReg(MI.getOperand(NumOperands - 1)); - bool KillsOp0 = MI.killsRegister(X86::FP0 + Op0); - bool KillsOp1 = MI.killsRegister(X86::FP0 + Op1); + bool KillsOp0 = MI.killsRegister(X86::FP0 + Op0, /*TRI=*/nullptr); + bool KillsOp1 = MI.killsRegister(X86::FP0 + Op1, /*TRI=*/nullptr); // Make sure the first operand is on the top of stack, the other one can be // anywhere. @@ -1480,7 +1482,7 @@ void FPS::handleCondMovFP(MachineBasicBlock::iterator &I) { unsigned Op0 = getFPReg(MI.getOperand(0)); unsigned Op1 = getFPReg(MI.getOperand(2)); - bool KillsOp1 = MI.killsRegister(X86::FP0 + Op1); + bool KillsOp1 = MI.killsRegister(X86::FP0 + Op1, /*TRI=*/nullptr); // The first operand *must* be on the top of the stack. moveToTop(Op0, I); @@ -1524,7 +1526,7 @@ void FPS::handleSpecialFP(MachineBasicBlock::iterator &Inst) { // We handle three kinds of copies: FP <- FP, FP <- ST, and ST <- FP. const MachineOperand &MO1 = MI.getOperand(1); const MachineOperand &MO0 = MI.getOperand(0); - bool KillsSrc = MI.killsRegister(MO1.getReg()); + bool KillsSrc = MI.killsRegister(MO1.getReg(), /*TRI=*/nullptr); // FP <- FP copy. unsigned DstFP = getFPReg(MO0); diff --git a/llvm/lib/Target/X86/X86ISelLowering.cpp b/llvm/lib/Target/X86/X86ISelLowering.cpp index a4df05e1bd03ca1a331d17491393d02768842fa4..f0cec6224e84e404fd5931ddd07c0c7925706996 100644 --- a/llvm/lib/Target/X86/X86ISelLowering.cpp +++ b/llvm/lib/Target/X86/X86ISelLowering.cpp @@ -20459,8 +20459,7 @@ static SDValue matchTruncateWithPACK(unsigned &PackOpcode, EVT DstVT, // the truncation then we can use PACKSS by converting the srl to a sra. // SimplifyDemandedBits often relaxes sra to srl so we need to reverse it. if (In.getOpcode() == ISD::SRL && In->hasOneUse()) - if (const APInt *ShAmt = DAG.getValidShiftAmountConstant( - In, APInt::getAllOnes(SrcVT.getVectorNumElements()))) { + if (const APInt *ShAmt = DAG.getValidShiftAmountConstant(In)) { if (*ShAmt == MinSignBits) { PackOpcode = X86ISD::PACKSS; return DAG.getNode(ISD::SRA, DL, SrcVT, In->ops()); @@ -27897,7 +27896,7 @@ static SDValue LowerVectorCTLZInRegLUT(SDValue Op, const SDLoc &DL, SDValue InRegLUT = DAG.getBuildVector(CurrVT, DL, LUTVec); // Begin by bitcasting the input to byte vector, then split those bytes - // into lo/hi nibbles and use the PSHUFB LUT to perform CLTZ on each of them. + // into lo/hi nibbles and use the PSHUFB LUT to perform CTLZ on each of them. // If the hi input nibble is zero then we add both results together, otherwise // we just take the hi result (by masking the lo result to zero before the // add). @@ -34228,10 +34227,10 @@ static bool isEFLAGSLiveAfter(MachineBasicBlock::iterator Itr, MachineBasicBlock *BB) { // Scan forward through BB for a use/def of EFLAGS. for (const MachineInstr &mi : llvm::make_range(std::next(Itr), BB->end())) { - if (mi.readsRegister(X86::EFLAGS)) + if (mi.readsRegister(X86::EFLAGS, /*TRI=*/nullptr)) return true; // If we found a def, we can stop searching. - if (mi.definesRegister(X86::EFLAGS)) + if (mi.definesRegister(X86::EFLAGS, /*TRI=*/nullptr)) return false; } @@ -34817,7 +34816,7 @@ X86TargetLowering::EmitLoweredCascadedSelect(MachineInstr &FirstCMOV, // If the EFLAGS register isn't dead in the terminator, then claim that it's // live into the sink and copy blocks. const TargetRegisterInfo *TRI = Subtarget.getRegisterInfo(); - if (!SecondCascadedCMOV.killsRegister(X86::EFLAGS) && + if (!SecondCascadedCMOV.killsRegister(X86::EFLAGS, /*TRI=*/nullptr) && !checkAndUpdateEFLAGSKill(SecondCascadedCMOV, ThisMBB, TRI)) { SecondInsertedMBB->addLiveIn(X86::EFLAGS); SinkMBB->addLiveIn(X86::EFLAGS); @@ -34973,7 +34972,7 @@ X86TargetLowering::EmitLoweredSelect(MachineInstr &MI, // If the EFLAGS register isn't dead in the terminator, then claim that it's // live into the sink and copy blocks. const TargetRegisterInfo *TRI = Subtarget.getRegisterInfo(); - if (!LastCMOV->killsRegister(X86::EFLAGS) && + if (!LastCMOV->killsRegister(X86::EFLAGS, /*TRI=*/nullptr) && !checkAndUpdateEFLAGSKill(LastCMOV, ThisMBB, TRI)) { FalseMBB->addLiveIn(X86::EFLAGS); SinkMBB->addLiveIn(X86::EFLAGS); @@ -36552,10 +36551,11 @@ X86TargetLowering::EmitInstrWithCustomInserter(MachineInstr &MI, // four operand definitions that are E[ABCD] registers. We skip them and // then insert the LEA. MachineBasicBlock::reverse_iterator RMBBI(MI.getReverseIterator()); - while (RMBBI != BB->rend() && (RMBBI->definesRegister(X86::EAX) || - RMBBI->definesRegister(X86::EBX) || - RMBBI->definesRegister(X86::ECX) || - RMBBI->definesRegister(X86::EDX))) { + while (RMBBI != BB->rend() && + (RMBBI->definesRegister(X86::EAX, /*TRI=*/nullptr) || + RMBBI->definesRegister(X86::EBX, /*TRI=*/nullptr) || + RMBBI->definesRegister(X86::ECX, /*TRI=*/nullptr) || + RMBBI->definesRegister(X86::EDX, /*TRI=*/nullptr))) { ++RMBBI; } MachineBasicBlock::iterator MBBI(RMBBI); diff --git a/llvm/lib/Target/X86/X86InstrInfo.cpp b/llvm/lib/Target/X86/X86InstrInfo.cpp index 510b08f9901a22f623d7bcd9beda8f52c363c57d..3d80c43b571f9cc61c91edca26903fc06468c907 100644 --- a/llvm/lib/Target/X86/X86InstrInfo.cpp +++ b/llvm/lib/Target/X86/X86InstrInfo.cpp @@ -1168,7 +1168,7 @@ bool X86InstrInfo::classifyLEAReg(MachineInstr &MI, const MachineOperand &Src, RC = Opc != X86::LEA32r ? &X86::GR64_NOSPRegClass : &X86::GR32_NOSPRegClass; } Register SrcReg = Src.getReg(); - isKill = MI.killsRegister(SrcReg); + isKill = MI.killsRegister(SrcReg, /*TRI=*/nullptr); // For both LEA64 and LEA32 the register already has essentially the right // type (32-bit or 64-bit) we may just need to forbid SP. @@ -3727,7 +3727,7 @@ bool X86InstrInfo::analyzeBranchImpl( // In practice we should never have an undef eflags operand, if we do // abort here as we are not prepared to preserve the flag. - if (I->findRegisterUseOperand(X86::EFLAGS)->isUndef()) + if (I->findRegisterUseOperand(X86::EFLAGS, /*TRI=*/nullptr)->isUndef()) return true; // Working from the bottom, handle the first conditional branch. @@ -5472,7 +5472,8 @@ bool X86InstrInfo::optimizeCompareInstr(MachineInstr &CmpInstr, Register SrcReg, } // Make sure Sub instruction defines EFLAGS and mark the def live. - MachineOperand *FlagDef = Sub->findRegisterDefOperand(X86::EFLAGS); + MachineOperand *FlagDef = + Sub->findRegisterDefOperand(X86::EFLAGS, /*TRI=*/nullptr); assert(FlagDef && "Unable to locate a def EFLAGS operand"); FlagDef->setIsDead(false); @@ -5629,7 +5630,7 @@ bool X86InstrInfo::foldImmediateImpl(MachineInstr &UseMI, MachineInstr *DefMI, return false; } - if (UseMI.findRegisterUseOperand(Reg)->getSubReg()) + if (UseMI.findRegisterUseOperand(Reg, /*TRI=*/nullptr)->getSubReg()) return false; // Immediate has larger code size than register. So avoid folding the // immediate if it has more than 1 use and we are optimizing for size. @@ -5676,7 +5677,8 @@ bool X86InstrInfo::foldImmediateImpl(MachineInstr &UseMI, MachineInstr *DefMI, if (!MakeChange) return true; UseMI.setDesc(get(X86::MOV32r0)); - UseMI.removeOperand(UseMI.findRegisterUseOperandIdx(Reg)); + UseMI.removeOperand( + UseMI.findRegisterUseOperandIdx(Reg, /*TRI=*/nullptr)); UseMI.addOperand(MachineOperand::CreateReg(X86::EFLAGS, /*isDef=*/true, /*isImp=*/true, /*isKill=*/false, @@ -5698,18 +5700,18 @@ bool X86InstrInfo::foldImmediateImpl(MachineInstr &UseMI, MachineInstr *DefMI, NewOpc == X86::SBB64ri32 || NewOpc == X86::SBB32ri || NewOpc == X86::SUB64ri32_ND || NewOpc == X86::SUB32ri_ND || NewOpc == X86::SBB64ri32_ND || NewOpc == X86::SBB32ri_ND) && - UseMI.findRegisterUseOperandIdx(Reg) != 2) + UseMI.findRegisterUseOperandIdx(Reg, /*TRI=*/nullptr) != 2) return false; // For CMP instructions the immediate can only be at index 1. if (((NewOpc == X86::CMP64ri32 || NewOpc == X86::CMP32ri) || (NewOpc == X86::CCMP64ri32 || NewOpc == X86::CCMP32ri)) && - UseMI.findRegisterUseOperandIdx(Reg) != 1) + UseMI.findRegisterUseOperandIdx(Reg, /*TRI=*/nullptr) != 1) return false; using namespace X86; if (isSHL(Opc) || isSHR(Opc) || isSAR(Opc) || isROL(Opc) || isROR(Opc) || isRCL(Opc) || isRCR(Opc)) { - unsigned RegIdx = UseMI.findRegisterUseOperandIdx(Reg); + unsigned RegIdx = UseMI.findRegisterUseOperandIdx(Reg, /*TRI=*/nullptr); if (RegIdx < 2) return false; if (!isInt<8>(ImmVal)) @@ -5733,13 +5735,15 @@ bool X86InstrInfo::foldImmediateImpl(MachineInstr &UseMI, MachineInstr *DefMI, if (!Modified) { // Modify the instruction. if (ImmVal == 0 && canConvert2Copy(NewOpc) && - UseMI.registerDefIsDead(X86::EFLAGS)) { + UseMI.registerDefIsDead(X86::EFLAGS, /*TRI=*/nullptr)) { // %100 = add %101, 0 // ==> // %100 = COPY %101 UseMI.setDesc(get(TargetOpcode::COPY)); - UseMI.removeOperand(UseMI.findRegisterUseOperandIdx(Reg)); - UseMI.removeOperand(UseMI.findRegisterDefOperandIdx(X86::EFLAGS)); + UseMI.removeOperand( + UseMI.findRegisterUseOperandIdx(Reg, /*TRI=*/nullptr)); + UseMI.removeOperand( + UseMI.findRegisterDefOperandIdx(X86::EFLAGS, /*TRI=*/nullptr)); UseMI.untieRegOperand(0); UseMI.clearFlag(MachineInstr::MIFlag::NoSWrap); UseMI.clearFlag(MachineInstr::MIFlag::NoUWrap); @@ -9538,7 +9542,8 @@ bool X86InstrInfo::hasReassociableOperands(const MachineInstr &Inst, // not change anything because rearranging the operands could affect other // instructions that depend on the exact status flags (zero, sign, etc.) // that are set by using these particular operands with this operation. - const MachineOperand *FlagDef = Inst.findRegisterDefOperand(X86::EFLAGS); + const MachineOperand *FlagDef = + Inst.findRegisterDefOperand(X86::EFLAGS, /*TRI=*/nullptr); assert((Inst.getNumDefs() == 1 || FlagDef) && "Implicit def isn't flags?"); if (FlagDef && !FlagDef->isDead()) return false; @@ -10060,8 +10065,10 @@ void X86InstrInfo::setSpecialOperandAttr(MachineInstr &OldMI1, MachineInstr &NewMI1, MachineInstr &NewMI2) const { // Integer instructions may define an implicit EFLAGS dest register operand. - MachineOperand *OldFlagDef1 = OldMI1.findRegisterDefOperand(X86::EFLAGS); - MachineOperand *OldFlagDef2 = OldMI2.findRegisterDefOperand(X86::EFLAGS); + MachineOperand *OldFlagDef1 = + OldMI1.findRegisterDefOperand(X86::EFLAGS, /*TRI=*/nullptr); + MachineOperand *OldFlagDef2 = + OldMI2.findRegisterDefOperand(X86::EFLAGS, /*TRI=*/nullptr); assert(!OldFlagDef1 == !OldFlagDef2 && "Unexpected instruction type for reassociation"); @@ -10072,8 +10079,10 @@ void X86InstrInfo::setSpecialOperandAttr(MachineInstr &OldMI1, assert(OldFlagDef1->isDead() && OldFlagDef2->isDead() && "Must have dead EFLAGS operand in reassociable instruction"); - MachineOperand *NewFlagDef1 = NewMI1.findRegisterDefOperand(X86::EFLAGS); - MachineOperand *NewFlagDef2 = NewMI2.findRegisterDefOperand(X86::EFLAGS); + MachineOperand *NewFlagDef1 = + NewMI1.findRegisterDefOperand(X86::EFLAGS, /*TRI=*/nullptr); + MachineOperand *NewFlagDef2 = + NewMI2.findRegisterDefOperand(X86::EFLAGS, /*TRI=*/nullptr); assert(NewFlagDef1 && NewFlagDef2 && "Unexpected operand in reassociable instruction"); diff --git a/llvm/lib/Target/X86/X86MCInstLower.cpp b/llvm/lib/Target/X86/X86MCInstLower.cpp index e6510be6b9afd03c37b805529f3d5d76a68b9aed..1d699b42dc673676e9060c6d1e0072c82322e1b4 100644 --- a/llvm/lib/Target/X86/X86MCInstLower.cpp +++ b/llvm/lib/Target/X86/X86MCInstLower.cpp @@ -506,7 +506,8 @@ void X86MCInstLower::Lower(const MachineInstr *MI, MCInst &OutMI) const { // recognize as TZCNT, which has better performance than BSF. // BSF and TZCNT have different interpretations on ZF bit. So make sure // it won't be used later. - const MachineOperand *FlagDef = MI->findRegisterDefOperand(X86::EFLAGS); + const MachineOperand *FlagDef = + MI->findRegisterDefOperand(X86::EFLAGS, /*TRI=*/nullptr); if (!MF.getFunction().hasOptSize() && FlagDef && FlagDef->isDead()) OutMI.setFlags(X86::IP_HAS_REPEAT); break; diff --git a/llvm/lib/Target/X86/X86PfmCounters.td b/llvm/lib/Target/X86/X86PfmCounters.td index d87a559aa353b1a9fcbd85602d01e49cb7fccb85..2b1dac411c992707f7108d6c1e18e49e72bc4438 100644 --- a/llvm/lib/Target/X86/X86PfmCounters.td +++ b/llvm/lib/Target/X86/X86PfmCounters.td @@ -204,6 +204,22 @@ def : PfmCountersBinding<"icelake-server", IceLakePfmCounters>; def : PfmCountersBinding<"rocketlake", IceLakePfmCounters>; def : PfmCountersBinding<"tigerlake", IceLakePfmCounters>; +def AlderLakePfmCounters : ProcPfmCounters { + let CycleCounter = UnhaltedCoreCyclesPfmCounter; + let UopsCounter = UopsIssuedPfmCounter; + let IssueCounters = [ + PfmIssueCounter<"ADLPPort00", "uops_dispatched_port:port_0">, + PfmIssueCounter<"ADLPPort01", "uops_dispatched_port:port_1">, + PfmIssueCounter<"ADLPPort02_03_10", "uops_dispatched_port:port_2_3_10">, + PfmIssueCounter<"ADLPPort04_09", "uops_dispatched_port:port_4_9">, + PfmIssueCounter<"ADLPPort05_11", "uops_dispatched_port:port_5_11">, + PfmIssueCounter<"ADLPPort06", "uops_dispatched_port:port_6">, + PfmIssueCounter<"ADLPPort07_08", "uops_dispatched_port:port_7_8"> + ]; + let ValidationCounters = DefaultIntelPfmValidationCounters; +} +def : PfmCountersBinding<"alderlake", AlderLakePfmCounters>; + // AMD X86 Counters. defvar DefaultAMDPfmValidationCounters = [ PfmValidationCounter, diff --git a/llvm/lib/Target/X86/X86SchedAlderlakeP.td b/llvm/lib/Target/X86/X86SchedAlderlakeP.td index 6f9d2cf7ffdf47a6520efe3e0e31786113bb3835..7756cd57cf7f848362de24c14c3d3c0f24e1b232 100644 --- a/llvm/lib/Target/X86/X86SchedAlderlakeP.td +++ b/llvm/lib/Target/X86/X86SchedAlderlakeP.td @@ -60,6 +60,8 @@ def ADLPPort01_05_10 : ProcResGroup<[ADLPPort01, ADLPPort05, ADLPPort10]>; def ADLPPort02_03 : ProcResGroup<[ADLPPort02, ADLPPort03]>; def ADLPPort02_03_07 : ProcResGroup<[ADLPPort02, ADLPPort03, ADLPPort07]>; def ADLPPort02_03_11 : ProcResGroup<[ADLPPort02, ADLPPort03, ADLPPort11]>; +def ADLPPort02_03_10 : ProcResGroup<[ADLPPort02, ADLPPort03, ADLPPort10]>; +def ADLPPort05_11 : ProcResGroup<[ADLPPort05, ADLPPort11]>; def ADLPPort07_08 : ProcResGroup<[ADLPPort07, ADLPPort08]>; // EU has 112 reservation stations. @@ -79,6 +81,10 @@ def ADLPPort02_03_07_08_11 : ProcResGroup<[ADLPPort02, ADLPPort03, ADLPPort07, let BufferSize = 72; } +def ADLPPortAny : ProcResGroup<[ADLPPort00, ADLPPort01, ADLPPort02, ADLPPort03, + ADLPPort04, ADLPPort05, ADLPPort06, ADLPPort07, + ADLPPort08, ADLPPort09, ADLPPort10, ADLPPort11]>; + // Integer loads are 5 cycles, so ReadAfterLd registers needn't be available // until 5 cycles after the memory operand. def : ReadAdvance; diff --git a/llvm/lib/Target/X86/X86SpeculativeLoadHardening.cpp b/llvm/lib/Target/X86/X86SpeculativeLoadHardening.cpp index 69a54e7667b55377677d9e17e7f6aea32c044d42..489c8f4925243209215fe293f7eeb19b2965f2cf 100644 --- a/llvm/lib/Target/X86/X86SpeculativeLoadHardening.cpp +++ b/llvm/lib/Target/X86/X86SpeculativeLoadHardening.cpp @@ -483,7 +483,7 @@ bool X86SpeculativeLoadHardeningPass::runOnMachineFunction( PredStateSubReg); ++NumInstsInserted; MachineOperand *ZeroEFLAGSDefOp = - ZeroI->findRegisterDefOperand(X86::EFLAGS); + ZeroI->findRegisterDefOperand(X86::EFLAGS, /*TRI=*/nullptr); assert(ZeroEFLAGSDefOp && ZeroEFLAGSDefOp->isImplicit() && "Must have an implicit def of EFLAGS!"); ZeroEFLAGSDefOp->setIsDead(true); @@ -762,7 +762,8 @@ X86SpeculativeLoadHardeningPass::tracePredStateThroughCFG( // If this is the last cmov and the EFLAGS weren't originally // live-in, mark them as killed. if (!LiveEFLAGS && Cond == Conds.back()) - CMovI->findRegisterUseOperand(X86::EFLAGS)->setIsKill(true); + CMovI->findRegisterUseOperand(X86::EFLAGS, /*TRI=*/nullptr) + ->setIsKill(true); ++NumInstsInserted; LLVM_DEBUG(dbgs() << " Inserting cmov: "; CMovI->dump(); @@ -1185,7 +1186,8 @@ X86SpeculativeLoadHardeningPass::tracePredStateThroughIndirectBranches( .addReg(PS->InitialReg) .addReg(PS->PoisonReg) .addImm(X86::COND_NE); - CMovI->findRegisterUseOperand(X86::EFLAGS)->setIsKill(true); + CMovI->findRegisterUseOperand(X86::EFLAGS, /*TRI=*/nullptr) + ->setIsKill(true); ++NumInstsInserted; LLVM_DEBUG(dbgs() << " Inserting cmov: "; CMovI->dump(); dbgs() << "\n"); CMovs.push_back(&*CMovI); @@ -1202,7 +1204,8 @@ X86SpeculativeLoadHardeningPass::tracePredStateThroughIndirectBranches( // Returns true if the MI has EFLAGS as a register def operand and it's live, // otherwise it returns false static bool isEFLAGSDefLive(const MachineInstr &MI) { - if (const MachineOperand *DefOp = MI.findRegisterDefOperand(X86::EFLAGS)) { + if (const MachineOperand *DefOp = + MI.findRegisterDefOperand(X86::EFLAGS, /*TRI=*/nullptr)) { return !DefOp->isDead(); } return false; @@ -1213,7 +1216,8 @@ static bool isEFLAGSLive(MachineBasicBlock &MBB, MachineBasicBlock::iterator I, // Check if EFLAGS are alive by seeing if there is a def of them or they // live-in, and then seeing if that def is in turn used. for (MachineInstr &MI : llvm::reverse(llvm::make_range(MBB.begin(), I))) { - if (MachineOperand *DefOp = MI.findRegisterDefOperand(X86::EFLAGS)) { + if (MachineOperand *DefOp = + MI.findRegisterDefOperand(X86::EFLAGS, /*TRI=*/nullptr)) { // If the def is dead, then EFLAGS is not live. if (DefOp->isDead()) return false; @@ -2182,7 +2186,7 @@ void X86SpeculativeLoadHardeningPass::tracePredStateThroughCall( .addReg(NewStateReg, RegState::Kill) .addReg(PS->PoisonReg) .addImm(X86::COND_NE); - CMovI->findRegisterUseOperand(X86::EFLAGS)->setIsKill(true); + CMovI->findRegisterUseOperand(X86::EFLAGS, /*TRI=*/nullptr)->setIsKill(true); ++NumInstsInserted; LLVM_DEBUG(dbgs() << " Inserting cmov: "; CMovI->dump(); dbgs() << "\n"); diff --git a/llvm/lib/Target/X86/X86TargetTransformInfo.h b/llvm/lib/Target/X86/X86TargetTransformInfo.h index 8ef9b4f86ffd7c25050536719527a2d7956ccb9b..b50193074573987478ffa16fc2d8abec13defc09 100644 --- a/llvm/lib/Target/X86/X86TargetTransformInfo.h +++ b/llvm/lib/Target/X86/X86TargetTransformInfo.h @@ -139,7 +139,7 @@ public: unsigned Opcode, Type *Ty, TTI::TargetCostKind CostKind, TTI::OperandValueInfo Op1Info = {TTI::OK_AnyValue, TTI::OP_None}, TTI::OperandValueInfo Op2Info = {TTI::OK_AnyValue, TTI::OP_None}, - ArrayRef Args = ArrayRef(), + ArrayRef Args = std::nullopt, const Instruction *CxtI = nullptr); InstructionCost getAltInstrCost(VectorType *VecTy, unsigned Opcode0, unsigned Opcode1, diff --git a/llvm/lib/Target/Xtensa/AsmParser/XtensaAsmParser.cpp b/llvm/lib/Target/Xtensa/AsmParser/XtensaAsmParser.cpp index 1fa00af2111e0c26901d1cacf924fafff67344e5..eaf0466302994ebc7f9e3424e734d2a73a5bb09a 100644 --- a/llvm/lib/Target/Xtensa/AsmParser/XtensaAsmParser.cpp +++ b/llvm/lib/Target/Xtensa/AsmParser/XtensaAsmParser.cpp @@ -8,7 +8,9 @@ // //===----------------------------------------------------------------------===// +#include "MCTargetDesc/XtensaMCExpr.h" #include "MCTargetDesc/XtensaMCTargetDesc.h" +#include "MCTargetDesc/XtensaTargetStreamer.h" #include "TargetInfo/XtensaTargetInfo.h" #include "llvm/ADT/STLExtras.h" #include "llvm/ADT/StringSwitch.h" @@ -22,6 +24,7 @@ #include "llvm/MC/MCRegisterInfo.h" #include "llvm/MC/MCStreamer.h" #include "llvm/MC/MCSubtargetInfo.h" +#include "llvm/MC/MCSymbol.h" #include "llvm/MC/TargetRegistry.h" #include "llvm/Support/Casting.h" @@ -35,6 +38,12 @@ class XtensaAsmParser : public MCTargetAsmParser { SMLoc getLoc() const { return getParser().getTok().getLoc(); } + XtensaTargetStreamer &getTargetStreamer() { + MCTargetStreamer &TS = *getParser().getStreamer().getTargetStreamer(); + return static_cast(TS); + } + + ParseStatus parseDirective(AsmToken DirectiveID) override; bool parseRegister(MCRegister &Reg, SMLoc &StartLoc, SMLoc &EndLoc) override; bool ParseInstruction(ParseInstructionInfo &Info, StringRef Name, SMLoc NameLoc, OperandVector &Operands) override; @@ -45,6 +54,9 @@ class XtensaAsmParser : public MCTargetAsmParser { unsigned validateTargetOperandClass(MCParsedAsmOperand &Op, unsigned Kind) override; + bool processInstruction(MCInst &Inst, SMLoc IDLoc, MCStreamer &Out, + const MCSubtargetInfo *STI); + // Auto-generated instruction matching functions #define GET_ASSEMBLER_HEADER #include "XtensaGenAsmMatcher.inc" @@ -62,6 +74,7 @@ class XtensaAsmParser : public MCTargetAsmParser { return ParseStatus::NoMatch; } ParseStatus parsePCRelTarget(OperandVector &Operands); + bool parseLiteralDirective(SMLoc L); public: enum XtensaMatchResultTy { @@ -148,7 +161,8 @@ public: bool isImm12() const { return isImm(-2048, 2047); } - bool isImm12m() const { return isImm(-2048, 2047); } + // Convert MOVI to literal load, when immediate is not in range (-2048, 2047) + bool isImm12m() const { return Kind == Immediate; } bool isOffset4m32() const { return isImm(0, 60) && @@ -348,6 +362,69 @@ static SMLoc RefineErrorLoc(const SMLoc Loc, const OperandVector &Operands, return Loc; } +bool XtensaAsmParser::processInstruction(MCInst &Inst, SMLoc IDLoc, + MCStreamer &Out, + const MCSubtargetInfo *STI) { + Inst.setLoc(IDLoc); + const unsigned Opcode = Inst.getOpcode(); + switch (Opcode) { + case Xtensa::L32R: { + const MCSymbolRefExpr *OpExpr = + static_cast(Inst.getOperand(1).getExpr()); + XtensaMCExpr::VariantKind Kind = XtensaMCExpr::VK_Xtensa_None; + const MCExpr *NewOpExpr = XtensaMCExpr::create(OpExpr, Kind, getContext()); + Inst.getOperand(1).setExpr(NewOpExpr); + break; + } + case Xtensa::MOVI: { + XtensaTargetStreamer &TS = this->getTargetStreamer(); + + // Expand MOVI operand + if (!Inst.getOperand(1).isExpr()) { + uint64_t ImmOp64 = Inst.getOperand(1).getImm(); + int32_t Imm = ImmOp64; + if (!isInt<12>(Imm)) { + XtensaTargetStreamer &TS = this->getTargetStreamer(); + MCInst TmpInst; + TmpInst.setLoc(IDLoc); + TmpInst.setOpcode(Xtensa::L32R); + const MCExpr *Value = MCConstantExpr::create(ImmOp64, getContext()); + MCSymbol *Sym = getContext().createTempSymbol(); + const MCExpr *Expr = MCSymbolRefExpr::create( + Sym, MCSymbolRefExpr::VK_None, getContext()); + const MCExpr *OpExpr = XtensaMCExpr::create( + Expr, XtensaMCExpr::VK_Xtensa_None, getContext()); + TmpInst.addOperand(Inst.getOperand(0)); + MCOperand Op1 = MCOperand::createExpr(OpExpr); + TmpInst.addOperand(Op1); + TS.emitLiteral(Sym, Value, true, IDLoc); + Inst = TmpInst; + } + } else { + MCInst TmpInst; + TmpInst.setLoc(IDLoc); + TmpInst.setOpcode(Xtensa::L32R); + const MCExpr *Value = Inst.getOperand(1).getExpr(); + MCSymbol *Sym = getContext().createTempSymbol(); + const MCExpr *Expr = + MCSymbolRefExpr::create(Sym, MCSymbolRefExpr::VK_None, getContext()); + const MCExpr *OpExpr = XtensaMCExpr::create( + Expr, XtensaMCExpr::VK_Xtensa_None, getContext()); + TmpInst.addOperand(Inst.getOperand(0)); + MCOperand Op1 = MCOperand::createExpr(OpExpr); + TmpInst.addOperand(Op1); + Inst = TmpInst; + TS.emitLiteral(Sym, Value, true, IDLoc); + } + break; + } + default: + break; + } + + return true; +} + bool XtensaAsmParser::MatchAndEmitInstruction(SMLoc IDLoc, unsigned &Opcode, OperandVector &Operands, MCStreamer &Out, @@ -361,6 +438,7 @@ bool XtensaAsmParser::MatchAndEmitInstruction(SMLoc IDLoc, unsigned &Opcode, default: break; case Match_Success: + processInstruction(Inst, IDLoc, Out, STI); Inst.setLoc(IDLoc); Out.emitInstruction(Inst, getSTI()); return false; @@ -686,6 +764,57 @@ bool XtensaAsmParser::ParseInstruction(ParseInstructionInfo &Info, return false; } +bool XtensaAsmParser::parseLiteralDirective(SMLoc L) { + MCAsmParser &Parser = getParser(); + const MCExpr *Value; + SMLoc LiteralLoc = getLexer().getLoc(); + XtensaTargetStreamer &TS = this->getTargetStreamer(); + + if (Parser.parseExpression(Value)) + return true; + + const MCSymbolRefExpr *SE = dyn_cast(Value); + + if (!SE) + return Error(LiteralLoc, "literal label must be a symbol"); + + if (Parser.parseComma()) + return true; + + SMLoc OpcodeLoc = getLexer().getLoc(); + if (parseOptionalToken(AsmToken::EndOfStatement)) + return Error(OpcodeLoc, "expected value"); + + if (Parser.parseExpression(Value)) + return true; + + if (parseEOL()) + return true; + + MCSymbol *Sym = getContext().getOrCreateSymbol(SE->getSymbol().getName()); + + TS.emitLiteral(Sym, Value, true, LiteralLoc); + + return false; +} + +ParseStatus XtensaAsmParser::parseDirective(AsmToken DirectiveID) { + StringRef IDVal = DirectiveID.getString(); + SMLoc Loc = getLexer().getLoc(); + + if (IDVal == ".literal_position") { + XtensaTargetStreamer &TS = this->getTargetStreamer(); + TS.emitLiteralPosition(); + return parseEOL(); + } + + if (IDVal == ".literal") { + return parseLiteralDirective(Loc); + } + + return ParseStatus::NoMatch; +} + // Force static initialization. extern "C" LLVM_EXTERNAL_VISIBILITY void LLVMInitializeXtensaAsmParser() { RegisterMCAsmParser X(getTheXtensaTarget()); diff --git a/llvm/lib/Target/Xtensa/CMakeLists.txt b/llvm/lib/Target/Xtensa/CMakeLists.txt index 2064511e75b82e59eafbd8f67e7ee99c4662aeae..726efadc87c0b2555d5c3f2f1f54d66b7c185676 100644 --- a/llvm/lib/Target/Xtensa/CMakeLists.txt +++ b/llvm/lib/Target/Xtensa/CMakeLists.txt @@ -4,6 +4,7 @@ set(LLVM_TARGET_DEFINITIONS Xtensa.td) tablegen(LLVM XtensaGenAsmMatcher.inc -gen-asm-matcher) tablegen(LLVM XtensaGenAsmWriter.inc -gen-asm-writer) +tablegen(LLVM XtensaGenCallingConv.inc -gen-callingconv) tablegen(LLVM XtensaGenDAGISel.inc -gen-dag-isel) tablegen(LLVM XtensaGenDisassemblerTables.inc -gen-disassembler) tablegen(LLVM XtensaGenInstrInfo.inc -gen-instr-info) @@ -15,6 +16,7 @@ add_public_tablegen_target(XtensaCommonTableGen) add_llvm_target(XtensaCodeGen XtensaAsmPrinter.cpp + XtensaConstantPoolValue.cpp XtensaFrameLowering.cpp XtensaInstrInfo.cpp XtensaISelDAGToDAG.cpp @@ -22,6 +24,7 @@ add_llvm_target(XtensaCodeGen XtensaRegisterInfo.cpp XtensaSubtarget.cpp XtensaTargetMachine.cpp + XtensaUtils.cpp LINK_COMPONENTS AsmPrinter diff --git a/llvm/lib/Target/Xtensa/MCTargetDesc/CMakeLists.txt b/llvm/lib/Target/Xtensa/MCTargetDesc/CMakeLists.txt index 6841b44f9d569cdb10bc806b35dee22728920881..dc12863394c7ad0cf25437319d2d65c43d55ebae 100644 --- a/llvm/lib/Target/Xtensa/MCTargetDesc/CMakeLists.txt +++ b/llvm/lib/Target/Xtensa/MCTargetDesc/CMakeLists.txt @@ -6,6 +6,7 @@ add_llvm_component_library(LLVMXtensaDesc XtensaMCCodeEmitter.cpp XtensaMCExpr.cpp XtensaMCTargetDesc.cpp + XtensaTargetStreamer.cpp LINK_COMPONENTS MC diff --git a/llvm/lib/Target/Xtensa/MCTargetDesc/XtensaMCTargetDesc.cpp b/llvm/lib/Target/Xtensa/MCTargetDesc/XtensaMCTargetDesc.cpp index 48674d15bdfbe27b56c01625fe4ea3ee8bbe2258..87ef66ba742b6d5500df0dc70e651c7263ea96c4 100644 --- a/llvm/lib/Target/Xtensa/MCTargetDesc/XtensaMCTargetDesc.cpp +++ b/llvm/lib/Target/Xtensa/MCTargetDesc/XtensaMCTargetDesc.cpp @@ -8,9 +8,10 @@ // //===----------------------------------------------------------------------===// #include "XtensaMCTargetDesc.h" +#include "TargetInfo/XtensaTargetInfo.h" #include "XtensaInstPrinter.h" #include "XtensaMCAsmInfo.h" -#include "TargetInfo/XtensaTargetInfo.h" +#include "XtensaTargetStreamer.h" #include "llvm/ADT/STLExtras.h" #include "llvm/MC/MCAsmInfo.h" #include "llvm/MC/MCInstrInfo.h" @@ -63,16 +64,29 @@ createXtensaMCSubtargetInfo(const Triple &TT, StringRef CPU, StringRef FS) { return createXtensaMCSubtargetInfoImpl(TT, CPU, CPU, FS); } +static MCTargetStreamer * +createXtensaAsmTargetStreamer(MCStreamer &S, formatted_raw_ostream &OS, + MCInstPrinter *InstPrint, bool isVerboseAsm) { + return new XtensaTargetAsmStreamer(S, OS); +} + +static MCTargetStreamer * +createXtensaObjectTargetStreamer(MCStreamer &S, const MCSubtargetInfo &STI) { + return new XtensaTargetELFStreamer(S); +} + extern "C" LLVM_EXTERNAL_VISIBILITY void LLVMInitializeXtensaTargetMC() { // Register the MCAsmInfo. - TargetRegistry::RegisterMCAsmInfo(getTheXtensaTarget(), createXtensaMCAsmInfo); + TargetRegistry::RegisterMCAsmInfo(getTheXtensaTarget(), + createXtensaMCAsmInfo); // Register the MCCodeEmitter. TargetRegistry::RegisterMCCodeEmitter(getTheXtensaTarget(), createXtensaMCCodeEmitter); // Register the MCInstrInfo. - TargetRegistry::RegisterMCInstrInfo(getTheXtensaTarget(), createXtensaMCInstrInfo); + TargetRegistry::RegisterMCInstrInfo(getTheXtensaTarget(), + createXtensaMCInstrInfo); // Register the MCInstPrinter. TargetRegistry::RegisterMCInstPrinter(getTheXtensaTarget(), @@ -89,4 +103,12 @@ extern "C" LLVM_EXTERNAL_VISIBILITY void LLVMInitializeXtensaTargetMC() { // Register the MCAsmBackend. TargetRegistry::RegisterMCAsmBackend(getTheXtensaTarget(), createXtensaMCAsmBackend); + + // Register the asm target streamer. + TargetRegistry::RegisterAsmTargetStreamer(getTheXtensaTarget(), + createXtensaAsmTargetStreamer); + + // Register the ELF target streamer. + TargetRegistry::RegisterObjectTargetStreamer( + getTheXtensaTarget(), createXtensaObjectTargetStreamer); } diff --git a/llvm/lib/Target/Xtensa/MCTargetDesc/XtensaTargetStreamer.cpp b/llvm/lib/Target/Xtensa/MCTargetDesc/XtensaTargetStreamer.cpp new file mode 100644 index 0000000000000000000000000000000000000000..0ea70cff4d404495fc367b7b46d1796e9d96be1e --- /dev/null +++ b/llvm/lib/Target/Xtensa/MCTargetDesc/XtensaTargetStreamer.cpp @@ -0,0 +1,119 @@ +//===-- XtensaTargetStreamer.cpp - Xtensa Target Streamer Methods ---------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// +// +// This file provides Xtensa specific target streamer methods. +// +//===----------------------------------------------------------------------===// + +#include "XtensaTargetStreamer.h" +#include "XtensaInstPrinter.h" +#include "llvm/BinaryFormat/ELF.h" +#include "llvm/MC/MCAssembler.h" +#include "llvm/MC/MCContext.h" +#include "llvm/MC/MCObjectFileInfo.h" +#include "llvm/MC/MCSectionELF.h" +#include "llvm/Support/Casting.h" +#include "llvm/Support/FormattedStream.h" + +using namespace llvm; + +static std::string getLiteralSectionName(StringRef CSectionName) { + std::size_t Pos = CSectionName.find(".text"); + std::string SectionName; + if (Pos != std::string::npos) { + SectionName = CSectionName.substr(0, Pos); + + if (Pos > 0) + SectionName += ".text"; + + CSectionName = CSectionName.drop_front(Pos); + CSectionName.consume_front(".text"); + + SectionName += ".literal"; + SectionName += CSectionName; + } else { + SectionName = CSectionName; + SectionName += ".literal"; + } + return SectionName; +} + +XtensaTargetStreamer::XtensaTargetStreamer(MCStreamer &S) + : MCTargetStreamer(S) {} + +XtensaTargetAsmStreamer::XtensaTargetAsmStreamer(MCStreamer &S, + formatted_raw_ostream &OS) + : XtensaTargetStreamer(S), OS(OS) {} + +void XtensaTargetAsmStreamer::emitLiteral(MCSymbol *LblSym, const MCExpr *Value, + bool SwitchLiteralSection, SMLoc L) { + SmallString<60> Str; + raw_svector_ostream LiteralStr(Str); + + LiteralStr << "\t.literal " << LblSym->getName() << ", "; + + if (auto CE = dyn_cast(Value)) { + LiteralStr << CE->getValue() << "\n"; + } else if (auto SRE = dyn_cast(Value)) { + const MCSymbol &Sym = SRE->getSymbol(); + LiteralStr << Sym.getName() << "\n"; + } else { + llvm_unreachable("unexpected constant pool entry type"); + } + + OS << LiteralStr.str(); +} + +void XtensaTargetAsmStreamer::emitLiteralPosition() { + OS << "\t.literal_position\n"; +} + +void XtensaTargetAsmStreamer::startLiteralSection(MCSection *BaseSection) { + emitLiteralPosition(); +} + +XtensaTargetELFStreamer::XtensaTargetELFStreamer(MCStreamer &S) + : XtensaTargetStreamer(S) {} + +void XtensaTargetELFStreamer::emitLiteral(MCSymbol *LblSym, const MCExpr *Value, + bool SwitchLiteralSection, SMLoc L) { + MCStreamer &OutStreamer = getStreamer(); + if (SwitchLiteralSection) { + MCContext &Context = OutStreamer.getContext(); + auto *CS = static_cast(OutStreamer.getCurrentSectionOnly()); + std::string SectionName = getLiteralSectionName(CS->getName()); + + MCSection *ConstSection = Context.getELFSection( + SectionName, ELF::SHT_PROGBITS, ELF::SHF_EXECINSTR | ELF::SHF_ALLOC); + + OutStreamer.pushSection(); + OutStreamer.switchSection(ConstSection); + } + + OutStreamer.emitLabel(LblSym, L); + OutStreamer.emitValue(Value, 4, L); + + if (SwitchLiteralSection) { + OutStreamer.popSection(); + } +} + +void XtensaTargetELFStreamer::startLiteralSection(MCSection *BaseSection) { + MCContext &Context = getStreamer().getContext(); + + std::string SectionName = getLiteralSectionName(BaseSection->getName()); + + MCSection *ConstSection = Context.getELFSection( + SectionName, ELF::SHT_PROGBITS, ELF::SHF_EXECINSTR | ELF::SHF_ALLOC); + + ConstSection->setAlignment(Align(4)); +} + +MCELFStreamer &XtensaTargetELFStreamer::getStreamer() { + return static_cast(Streamer); +} diff --git a/llvm/lib/Target/Xtensa/MCTargetDesc/XtensaTargetStreamer.h b/llvm/lib/Target/Xtensa/MCTargetDesc/XtensaTargetStreamer.h new file mode 100644 index 0000000000000000000000000000000000000000..817940e880b3c42056f938bb3a8a6709e5568d24 --- /dev/null +++ b/llvm/lib/Target/Xtensa/MCTargetDesc/XtensaTargetStreamer.h @@ -0,0 +1,58 @@ +//===-- XtensaTargetStreamer.h - Xtensa Target Streamer --------*- C++ -*--===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#ifndef LLVM_LIB_TARGET_XTENSA_XTENSATARGETSTREAMER_H +#define LLVM_LIB_TARGET_XTENSA_XTENSATARGETSTREAMER_H + +#include "llvm/MC/MCELFStreamer.h" +#include "llvm/MC/MCStreamer.h" +#include "llvm/Support/SMLoc.h" + +namespace llvm { +class formatted_raw_ostream; + +class XtensaTargetStreamer : public MCTargetStreamer { +public: + XtensaTargetStreamer(MCStreamer &S); + + // Emit literal label and literal Value to the literal section. If literal + // section is not switched yet (SwitchLiteralSection is true) then switch to + // literal section. + virtual void emitLiteral(MCSymbol *LblSym, const MCExpr *Value, + bool SwitchLiteralSection, SMLoc L = SMLoc()) = 0; + + virtual void emitLiteralPosition() = 0; + + // Switch to the literal section. The BaseSection name is used to construct + // literal section name. + virtual void startLiteralSection(MCSection *BaseSection) = 0; +}; + +class XtensaTargetAsmStreamer : public XtensaTargetStreamer { + formatted_raw_ostream &OS; + +public: + XtensaTargetAsmStreamer(MCStreamer &S, formatted_raw_ostream &OS); + void emitLiteral(MCSymbol *LblSym, const MCExpr *Value, + bool SwitchLiteralSection, SMLoc L) override; + void emitLiteralPosition() override; + void startLiteralSection(MCSection *Section) override; +}; + +class XtensaTargetELFStreamer : public XtensaTargetStreamer { +public: + XtensaTargetELFStreamer(MCStreamer &S); + MCELFStreamer &getStreamer(); + void emitLiteral(MCSymbol *LblSym, const MCExpr *Value, + bool SwitchLiteralSection, SMLoc L) override; + void emitLiteralPosition() override {} + void startLiteralSection(MCSection *Section) override; +}; +} // end namespace llvm + +#endif // LLVM_LIB_TARGET_XTENSA_XTENSATARGETSTREAMER_H diff --git a/llvm/lib/Target/Xtensa/Xtensa.td b/llvm/lib/Target/Xtensa/Xtensa.td index b953540be94de0b0089fa6c00a2e7a46e9056f5d..460a15e808b3a405d5dca9decbc2d4b5d14c23f3 100644 --- a/llvm/lib/Target/Xtensa/Xtensa.td +++ b/llvm/lib/Target/Xtensa/Xtensa.td @@ -35,6 +35,12 @@ def : Proc<"generic", []>; include "XtensaRegisterInfo.td" +//===----------------------------------------------------------------------===// +// Calling Convention Description +//===----------------------------------------------------------------------===// + +include "XtensaCallingConv.td" + //===----------------------------------------------------------------------===// // Instruction Descriptions //===----------------------------------------------------------------------===// diff --git a/llvm/lib/Target/Xtensa/XtensaAsmPrinter.cpp b/llvm/lib/Target/Xtensa/XtensaAsmPrinter.cpp index 87dbf2eb5166cda831a2f7fd7a282b0a92a4718e..e222919b28dc986c27abb001d56c60a2345e0f4a 100644 --- a/llvm/lib/Target/Xtensa/XtensaAsmPrinter.cpp +++ b/llvm/lib/Target/Xtensa/XtensaAsmPrinter.cpp @@ -12,8 +12,13 @@ //===----------------------------------------------------------------------===// #include "XtensaAsmPrinter.h" +#include "MCTargetDesc/XtensaMCExpr.h" +#include "MCTargetDesc/XtensaTargetStreamer.h" #include "TargetInfo/XtensaTargetInfo.h" +#include "XtensaConstantPoolValue.h" +#include "llvm/ADT/StringExtras.h" #include "llvm/BinaryFormat/ELF.h" +#include "llvm/CodeGen/MachineConstantPool.h" #include "llvm/CodeGen/MachineModuleInfoImpls.h" #include "llvm/CodeGen/TargetLoweringObjectFileImpl.h" #include "llvm/MC/MCExpr.h" @@ -25,12 +30,152 @@ using namespace llvm; +static MCSymbolRefExpr::VariantKind +getModifierVariantKind(XtensaCP::XtensaCPModifier Modifier) { + switch (Modifier) { + case XtensaCP::no_modifier: + return MCSymbolRefExpr::VK_None; + case XtensaCP::TPOFF: + return MCSymbolRefExpr::VK_TPOFF; + } + report_fatal_error("Invalid XtensaCPModifier!"); +} + void XtensaAsmPrinter::emitInstruction(const MachineInstr *MI) { MCInst LoweredMI; lowerToMCInst(MI, LoweredMI); EmitToStreamer(*OutStreamer, LoweredMI); } +void XtensaAsmPrinter::emitMachineConstantPoolValue( + MachineConstantPoolValue *MCPV) { + XtensaConstantPoolValue *ACPV = static_cast(MCPV); + MCSymbol *MCSym; + + assert(ACPV->isExtSymbol() && "unrecognized constant pool value"); + + XtensaConstantPoolSymbol *XtensaSym = cast(ACPV); + const char *Sym = XtensaSym->getSymbol(); + std::string SymName(Sym); + + if (XtensaSym->isPrivateLinkage()) + SymName = ".L" + SymName; + + MCSym = GetExternalSymbolSymbol(StringRef(SymName)); + MCSymbol *LblSym = GetCPISymbol(ACPV->getLabelId()); + auto *TS = + static_cast(OutStreamer->getTargetStreamer()); + MCSymbolRefExpr::VariantKind VK = getModifierVariantKind(ACPV->getModifier()); + + if (ACPV->getModifier() != XtensaCP::no_modifier) { + std::string SymName(MCSym->getName()); + StringRef Modifier = ACPV->getModifierText(); + SymName += Modifier; + MCSym = GetExternalSymbolSymbol(StringRef(SymName)); + } + + const MCExpr *Expr = MCSymbolRefExpr::create(MCSym, VK, OutContext); + TS->emitLiteral(LblSym, Expr, false); +} + +void XtensaAsmPrinter::emitMachineConstantPoolEntry( + const MachineConstantPoolEntry &CPE, int i) { + if (CPE.isMachineConstantPoolEntry()) { + XtensaConstantPoolValue *ACPV = + static_cast(CPE.Val.MachineCPVal); + ACPV->setLabelId(i); + emitMachineConstantPoolValue(CPE.Val.MachineCPVal); + } else { + MCSymbol *LblSym = GetCPISymbol(i); + auto *TS = + static_cast(OutStreamer->getTargetStreamer()); + const Constant *C = CPE.Val.ConstVal; + const MCExpr *Value = nullptr; + + Type *Ty = C->getType(); + if (const auto *CFP = dyn_cast(C)) { + Value = MCConstantExpr::create( + CFP->getValueAPF().bitcastToAPInt().getSExtValue(), OutContext); + } else if (const auto *CI = dyn_cast(C)) { + Value = MCConstantExpr::create(CI->getValue().getSExtValue(), OutContext); + } else if (isa(Ty)) { + Value = lowerConstant(C); + } else { + llvm_unreachable("unexpected constant pool entry type"); + } + + TS->emitLiteral(LblSym, Value, false); + } +} + +// EmitConstantPool - Print to the current output stream assembly +// representations of the constants in the constant pool MCP. This is +// used to print out constants which have been "spilled to memory" by +// the code generator. +void XtensaAsmPrinter::emitConstantPool() { + const Function &F = MF->getFunction(); + const MachineConstantPool *MCP = MF->getConstantPool(); + const std::vector &CP = MCP->getConstants(); + if (CP.empty()) + return; + + OutStreamer->pushSection(); + + auto *TS = + static_cast(OutStreamer->getTargetStreamer()); + MCSection *CS = getObjFileLowering().SectionForGlobal(&F, TM); + TS->startLiteralSection(CS); + + int CPIdx = 0; + for (const MachineConstantPoolEntry &CPE : CP) { + emitMachineConstantPoolEntry(CPE, CPIdx++); + } + + OutStreamer->popSection(); +} + +MCSymbol * +XtensaAsmPrinter::GetConstantPoolIndexSymbol(const MachineOperand &MO) const { + // Create a symbol for the name. + return GetCPISymbol(MO.getIndex()); +} + +MCOperand +XtensaAsmPrinter::LowerSymbolOperand(const MachineOperand &MO, + MachineOperand::MachineOperandType MOTy, + unsigned Offset) const { + const MCSymbol *Symbol; + XtensaMCExpr::VariantKind Kind = XtensaMCExpr::VK_Xtensa_None; + + switch (MOTy) { + case MachineOperand::MO_GlobalAddress: + Symbol = getSymbol(MO.getGlobal()); + Offset += MO.getOffset(); + break; + case MachineOperand::MO_ConstantPoolIndex: + Symbol = GetConstantPoolIndexSymbol(MO); + Offset += MO.getOffset(); + break; + default: + report_fatal_error(""); + } + + const MCExpr *ME = + MCSymbolRefExpr::create(Symbol, MCSymbolRefExpr::VK_None, OutContext); + ME = XtensaMCExpr::create(ME, Kind, OutContext); + + if (Offset) { + // Assume offset is never negative. + assert(Offset > 0); + + const MCConstantExpr *OffsetExpr = + MCConstantExpr::create(Offset, OutContext); + ME = MCBinaryExpr::createAdd(ME, OffsetExpr, OutContext); + } + + return MCOperand::createExpr(ME); +} + MCOperand XtensaAsmPrinter::lowerOperand(const MachineOperand &MO, unsigned Offset) const { MachineOperand::MachineOperandType MOTy = MO.getType(); @@ -45,6 +190,9 @@ MCOperand XtensaAsmPrinter::lowerOperand(const MachineOperand &MO, return MCOperand::createImm(MO.getImm() + Offset); case MachineOperand::MO_RegisterMask: break; + case MachineOperand::MO_GlobalAddress: + case MachineOperand::MO_ConstantPoolIndex: + return LowerSymbolOperand(MO, MOTy, Offset); default: report_fatal_error("unknown operand type"); } diff --git a/llvm/lib/Target/Xtensa/XtensaAsmPrinter.h b/llvm/lib/Target/Xtensa/XtensaAsmPrinter.h index dec2a1ee4954f96297ebb33f3cbe3cba6cc31ffd..f3fec19724aab66a1ac11ea3e7f5ba2b98aadb88 100644 --- a/llvm/lib/Target/Xtensa/XtensaAsmPrinter.h +++ b/llvm/lib/Target/Xtensa/XtensaAsmPrinter.h @@ -15,6 +15,7 @@ #include "XtensaTargetMachine.h" #include "llvm/CodeGen/AsmPrinter.h" +#include "llvm/CodeGen/MachineConstantPool.h" #include "llvm/Support/Compiler.h" namespace llvm { @@ -35,6 +36,18 @@ public: StringRef getPassName() const override { return "Xtensa Assembly Printer"; } void emitInstruction(const MachineInstr *MI) override; + void emitConstantPool() override; + + void emitMachineConstantPoolEntry(const MachineConstantPoolEntry &CPE, int i); + + void emitMachineConstantPoolValue(MachineConstantPoolValue *MCPV) override; + + MCSymbol *GetConstantPoolIndexSymbol(const MachineOperand &MO) const; + + MCOperand LowerSymbolOperand(const MachineOperand &MO, + MachineOperand::MachineOperandType MOTy, + unsigned Offset) const; + // Lower MachineInstr MI to MCInst OutMI. void lowerToMCInst(const MachineInstr *MI, MCInst &OutMI) const; diff --git a/llvm/lib/Target/Xtensa/XtensaCallingConv.td b/llvm/lib/Target/Xtensa/XtensaCallingConv.td new file mode 100644 index 0000000000000000000000000000000000000000..a348b4c890b22af40ae335ecb90e0a55ccbe3572 --- /dev/null +++ b/llvm/lib/Target/Xtensa/XtensaCallingConv.td @@ -0,0 +1,24 @@ +//===- XtensaCallingConv.td - Xtensa Calling Conventions -*- tablegen ---*-===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// +// This describes the calling conventions for the Xtensa ABI. +//===----------------------------------------------------------------------===// + +//===----------------------------------------------------------------------===// +// Xtensa return value calling convention +//===----------------------------------------------------------------------===// +def RetCC_Xtensa : CallingConv<[ + // First two return values go in a2, a3, a4, a5 + CCIfType<[i32], CCAssignToReg<[A2, A3, A4, A5]>>, + CCIfType<[i64], CCAssignToRegWithShadow<[A2, A4], [A3, A5]>> +]>; + +//===----------------------------------------------------------------------===// +// Callee-saved register lists. +//===----------------------------------------------------------------------===// + +def CSR_Xtensa : CalleeSavedRegs<(add A0, A12, A13, A14, A15)>; diff --git a/llvm/lib/Target/Xtensa/XtensaConstantPoolValue.cpp b/llvm/lib/Target/Xtensa/XtensaConstantPoolValue.cpp new file mode 100644 index 0000000000000000000000000000000000000000..4e53aa5736c72ce11724fc2f94f0e6652cdf5b10 --- /dev/null +++ b/llvm/lib/Target/Xtensa/XtensaConstantPoolValue.cpp @@ -0,0 +1,207 @@ +//===- XtensaConstantPoolValue.cpp - Xtensa constantpool value ------------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// +// +// This file implements the Xtensa specific constantpool value class. +// +//===----------------------------------------------------------------------===// + +#include "XtensaConstantPoolValue.h" +#include "llvm/ADT/FoldingSet.h" +#include "llvm/CodeGen/MachineBasicBlock.h" +#include "llvm/IR/Constant.h" +#include "llvm/IR/Constants.h" +#include "llvm/IR/GlobalValue.h" +#include "llvm/IR/Type.h" +#include "llvm/Support/raw_ostream.h" +#include +using namespace llvm; + +XtensaConstantPoolValue::XtensaConstantPoolValue( + Type *Ty, unsigned ID, XtensaCP::XtensaCPKind Kind, + XtensaCP::XtensaCPModifier modifier) + : MachineConstantPoolValue(Ty), LabelId(ID), Kind(Kind), + Modifier(modifier) {} + +XtensaConstantPoolValue::XtensaConstantPoolValue( + LLVMContext &C, unsigned ID, XtensaCP::XtensaCPKind Kind, + XtensaCP::XtensaCPModifier Modifier) + : MachineConstantPoolValue((Type *)Type::getInt32Ty(C)), LabelId(ID), + Kind(Kind), Modifier(Modifier) {} + +XtensaConstantPoolValue::~XtensaConstantPoolValue() {} + +StringRef XtensaConstantPoolValue::getModifierText() const { + switch (Modifier) { + case XtensaCP::no_modifier: + return ""; + case XtensaCP::TPOFF: + return "@TPOFF"; + } + report_fatal_error("Unknown modifier!"); +} + +int XtensaConstantPoolValue::getExistingMachineCPValue(MachineConstantPool *CP, + Align Alignment) { + report_fatal_error("Shouldn't be calling this directly!"); +} + +void XtensaConstantPoolValue::addSelectionDAGCSEId(FoldingSetNodeID &ID) { + ID.AddInteger(LabelId); +} + +bool XtensaConstantPoolValue::hasSameValue(XtensaConstantPoolValue *ACPV) { + if (ACPV->Kind == Kind) { + if (ACPV->LabelId == LabelId) + return true; + } + return false; +} + +#if !defined(NDEBUG) || defined(LLVM_ENABLE_DUMP) +void XtensaConstantPoolValue::dump() const { errs() << " " << *this; } +#endif + +void XtensaConstantPoolValue::print(raw_ostream &O) const {} + +//===----------------------------------------------------------------------===// +// XtensaConstantPoolConstant +//===----------------------------------------------------------------------===// + +XtensaConstantPoolConstant::XtensaConstantPoolConstant( + const Constant *C, unsigned ID, XtensaCP::XtensaCPKind Kind) + : XtensaConstantPoolValue(C->getType(), ID, Kind), CVal(C) {} + +XtensaConstantPoolConstant * +XtensaConstantPoolConstant::Create(const Constant *C, unsigned ID, + XtensaCP::XtensaCPKind Kind) { + return new XtensaConstantPoolConstant(C, ID, Kind); +} + +const BlockAddress *XtensaConstantPoolConstant::getBlockAddress() const { + return dyn_cast_or_null(CVal); +} + +int XtensaConstantPoolConstant::getExistingMachineCPValue( + MachineConstantPool *CP, Align Alignment) { + return getExistingMachineCPValueImpl(CP, + Alignment); +} + +bool XtensaConstantPoolConstant::hasSameValue(XtensaConstantPoolValue *ACPV) { + const XtensaConstantPoolConstant *ACPC = + dyn_cast(ACPV); + return ACPC && ACPC->CVal == CVal && + XtensaConstantPoolValue::hasSameValue(ACPV); +} + +void XtensaConstantPoolConstant::addSelectionDAGCSEId(FoldingSetNodeID &ID) { + ID.AddPointer(CVal); + XtensaConstantPoolValue::addSelectionDAGCSEId(ID); +} + +void XtensaConstantPoolConstant::print(raw_ostream &O) const { + O << CVal->getName(); + XtensaConstantPoolValue::print(O); +} + +XtensaConstantPoolSymbol::XtensaConstantPoolSymbol( + LLVMContext &C, const char *Str, unsigned ID, bool PrivLinkage, + XtensaCP::XtensaCPModifier Modifier) + : XtensaConstantPoolValue(C, ID, XtensaCP::CPExtSymbol, Modifier), S(Str), + PrivateLinkage(PrivLinkage) {} + +XtensaConstantPoolSymbol * +XtensaConstantPoolSymbol::Create(LLVMContext &C, const char *Str, unsigned ID, + bool PrivLinkage, + XtensaCP::XtensaCPModifier Modifier) + +{ + return new XtensaConstantPoolSymbol(C, Str, ID, PrivLinkage, Modifier); +} + +int XtensaConstantPoolSymbol::getExistingMachineCPValue(MachineConstantPool *CP, + Align Alignment) { + return getExistingMachineCPValueImpl(CP, Alignment); +} + +bool XtensaConstantPoolSymbol::hasSameValue(XtensaConstantPoolValue *ACPV) { + const XtensaConstantPoolSymbol *ACPS = + dyn_cast(ACPV); + return ACPS && ACPS->S == S && XtensaConstantPoolValue::hasSameValue(ACPV); +} + +void XtensaConstantPoolSymbol::addSelectionDAGCSEId(FoldingSetNodeID &ID) { + ID.AddString(S); + XtensaConstantPoolValue::addSelectionDAGCSEId(ID); +} + +void XtensaConstantPoolSymbol::print(raw_ostream &O) const { + O << S; + XtensaConstantPoolValue::print(O); +} + +XtensaConstantPoolMBB::XtensaConstantPoolMBB(LLVMContext &C, + const MachineBasicBlock *M, + unsigned Id) + : XtensaConstantPoolValue(C, 0, XtensaCP::CPMachineBasicBlock), MBB(M) {} + +XtensaConstantPoolMBB *XtensaConstantPoolMBB::Create(LLVMContext &C, + const MachineBasicBlock *M, + unsigned Idx) { + return new XtensaConstantPoolMBB(C, M, Idx); +} + +int XtensaConstantPoolMBB::getExistingMachineCPValue(MachineConstantPool *CP, + Align Alignment) { + return getExistingMachineCPValueImpl(CP, Alignment); +} + +bool XtensaConstantPoolMBB::hasSameValue(XtensaConstantPoolValue *ACPV) { + const XtensaConstantPoolMBB *ACPMBB = dyn_cast(ACPV); + return ACPMBB && ACPMBB->MBB == MBB && + XtensaConstantPoolValue::hasSameValue(ACPV); +} + +void XtensaConstantPoolMBB::addSelectionDAGCSEId(FoldingSetNodeID &ID) { + ID.AddPointer(MBB); + XtensaConstantPoolValue::addSelectionDAGCSEId(ID); +} + +void XtensaConstantPoolMBB::print(raw_ostream &O) const { + O << "BB#" << MBB->getNumber(); + XtensaConstantPoolValue::print(O); +} + +XtensaConstantPoolJumpTable::XtensaConstantPoolJumpTable(LLVMContext &C, + unsigned Index) + : XtensaConstantPoolValue(C, 0, XtensaCP::CPJumpTable), Idx(Index) {} + +XtensaConstantPoolJumpTable *XtensaConstantPoolJumpTable::Create(LLVMContext &C, + unsigned Idx) { + return new XtensaConstantPoolJumpTable(C, Idx); +} + +int XtensaConstantPoolJumpTable::getExistingMachineCPValue( + MachineConstantPool *CP, Align Alignment) { + return getExistingMachineCPValueImpl(CP, + Alignment); +} + +bool XtensaConstantPoolJumpTable::hasSameValue(XtensaConstantPoolValue *ACPV) { + const XtensaConstantPoolJumpTable *ACPJT = + dyn_cast(ACPV); + return ACPJT && ACPJT->Idx == Idx && + XtensaConstantPoolValue::hasSameValue(ACPV); +} + +void XtensaConstantPoolJumpTable::addSelectionDAGCSEId(FoldingSetNodeID &ID) {} + +void XtensaConstantPoolJumpTable::print(raw_ostream &O) const { + O << "JT" << Idx; + XtensaConstantPoolValue::print(O); +} diff --git a/llvm/lib/Target/Xtensa/XtensaConstantPoolValue.h b/llvm/lib/Target/Xtensa/XtensaConstantPoolValue.h new file mode 100644 index 0000000000000000000000000000000000000000..5580de48447468b511b0b6511639fda7cca0e021 --- /dev/null +++ b/llvm/lib/Target/Xtensa/XtensaConstantPoolValue.h @@ -0,0 +1,263 @@ +//===- XtensaConstantPoolValue.h - Xtensa constantpool value ----*- C++ -*-===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// +// +// This file implements the Xtensa specific constantpool value class. +// +//===----------------------------------------------------------------------===// + +#ifndef LLVM_LIB_TARGET_XTENSA_XTENSACONSTANTPOOLVALUE_H +#define LLVM_LIB_TARGET_XTENSA_XTENSACONSTANTPOOLVALUE_H + +#include "llvm/CodeGen/MachineConstantPool.h" +#include "llvm/Support/Casting.h" +#include "llvm/Support/ErrorHandling.h" +#include +#include +#include + +namespace llvm { + +class BlockAddress; +class Constant; +class GlobalValue; +class LLVMContext; +class MachineBasicBlock; + +namespace XtensaCP { +enum XtensaCPKind { + CPExtSymbol, + CPBlockAddress, + CPMachineBasicBlock, + CPJumpTable +}; + +enum XtensaCPModifier { + no_modifier, // None + TPOFF // Thread Pointer Offset +}; +} // namespace XtensaCP + +/// XtensaConstantPoolValue - Xtensa specific constantpool value. This is used +/// to represent PC-relative displacement between the address of the load +/// instruction and the constant being loaded. +class XtensaConstantPoolValue : public MachineConstantPoolValue { + unsigned LabelId; // Label id of the load. + XtensaCP::XtensaCPKind Kind; // Kind of constant. + XtensaCP::XtensaCPModifier Modifier; // Symbol name modifier + //(for example Global Variable name) + +protected: + XtensaConstantPoolValue( + Type *Ty, unsigned ID, XtensaCP::XtensaCPKind Kind, + XtensaCP::XtensaCPModifier Modifier = XtensaCP::no_modifier); + + XtensaConstantPoolValue( + LLVMContext &C, unsigned id, XtensaCP::XtensaCPKind Kind, + XtensaCP::XtensaCPModifier Modifier = XtensaCP::no_modifier); + + template + int getExistingMachineCPValueImpl(MachineConstantPool *CP, Align Alignment) { + const std::vector &Constants = CP->getConstants(); + for (unsigned i = 0, e = Constants.size(); i != e; ++i) { + if (Constants[i].isMachineConstantPoolEntry() && + (Constants[i].getAlign() >= Alignment)) { + auto *CPV = static_cast( + Constants[i].Val.MachineCPVal); + if (Derived *APC = dyn_cast(CPV)) + if (cast(this)->equals(APC)) + return i; + } + } + + return -1; + } + +public: + ~XtensaConstantPoolValue() override; + + XtensaCP::XtensaCPModifier getModifier() const { return Modifier; } + bool hasModifier() const { return Modifier != XtensaCP::no_modifier; } + StringRef getModifierText() const; + + unsigned getLabelId() const { return LabelId; } + void setLabelId(unsigned ID) { LabelId = ID; } + + bool isExtSymbol() const { return Kind == XtensaCP::CPExtSymbol; } + bool isBlockAddress() const { return Kind == XtensaCP::CPBlockAddress; } + bool isMachineBasicBlock() const { + return Kind == XtensaCP::CPMachineBasicBlock; + } + bool isJumpTable() const { return Kind == XtensaCP::CPJumpTable; } + + int getExistingMachineCPValue(MachineConstantPool *CP, + Align Alignment) override; + + void addSelectionDAGCSEId(FoldingSetNodeID &ID) override; + + /// hasSameValue - Return true if this Xtensa constpool value can share the + /// same constantpool entry as another Xtensa constpool value. + virtual bool hasSameValue(XtensaConstantPoolValue *ACPV); + + bool equals(const XtensaConstantPoolValue *A) const { + return this->LabelId == A->LabelId && this->Modifier == A->Modifier; + } + + void print(raw_ostream &O) const override; + +#if !defined(NDEBUG) || defined(LLVM_ENABLE_DUMP) + void dump() const; +#endif +}; + +inline raw_ostream &operator<<(raw_ostream &O, + const XtensaConstantPoolValue &V) { + V.print(O); + return O; +} + +/// XtensaConstantPoolConstant - Xtensa-specific constant pool values for +/// Constants (for example BlockAddresses). +class XtensaConstantPoolConstant : public XtensaConstantPoolValue { + const Constant *CVal; // Constant being loaded. + + XtensaConstantPoolConstant(const Constant *C, unsigned ID, + XtensaCP::XtensaCPKind Kind); + +public: + static XtensaConstantPoolConstant *Create(const Constant *C, unsigned ID, + XtensaCP::XtensaCPKind Kind); + + const BlockAddress *getBlockAddress() const; + + int getExistingMachineCPValue(MachineConstantPool *CP, + Align Alignment) override; + + /// hasSameValue - Return true if this Xtensa constpool value can share the + /// same constantpool entry as another Xtensa constpool value. + bool hasSameValue(XtensaConstantPoolValue *ACPV) override; + + void addSelectionDAGCSEId(FoldingSetNodeID &ID) override; + + void print(raw_ostream &O) const override; + static bool classof(const XtensaConstantPoolValue *APV) { + return APV->isBlockAddress(); + } + + bool equals(const XtensaConstantPoolConstant *A) const { + return CVal == A->CVal && XtensaConstantPoolValue::equals(A); + } +}; + +/// XtensaConstantPoolSymbol - Xtensa-specific constantpool values for external +/// symbols. +class XtensaConstantPoolSymbol : public XtensaConstantPoolValue { + const std::string S; // ExtSymbol being loaded. + bool PrivateLinkage; + + XtensaConstantPoolSymbol( + LLVMContext &C, const char *S, unsigned Id, bool PrivLinkage, + XtensaCP::XtensaCPModifier Modifier = XtensaCP::no_modifier); + +public: + static XtensaConstantPoolSymbol * + Create(LLVMContext &C, const char *S, unsigned ID, bool PrivLinkage, + XtensaCP::XtensaCPModifier Modifier = XtensaCP::no_modifier); + + const char *getSymbol() const { return S.c_str(); } + + int getExistingMachineCPValue(MachineConstantPool *CP, + Align Alignment) override; + + void addSelectionDAGCSEId(FoldingSetNodeID &ID) override; + + /// hasSameValue - Return true if this Xtensa constpool value can share the + /// same constantpool entry as another Xtensa constpool value. + bool hasSameValue(XtensaConstantPoolValue *ACPV) override; + + bool isPrivateLinkage() { return PrivateLinkage; } + + void print(raw_ostream &O) const override; + + static bool classof(const XtensaConstantPoolValue *ACPV) { + return ACPV->isExtSymbol(); + } + + bool equals(const XtensaConstantPoolSymbol *A) const { + return S == A->S && XtensaConstantPoolValue::equals(A); + } +}; + +/// XtensaConstantPoolMBB - Xtensa-specific constantpool value of a machine +/// basic block. +class XtensaConstantPoolMBB : public XtensaConstantPoolValue { + const MachineBasicBlock *MBB; // Machine basic block. + + XtensaConstantPoolMBB(LLVMContext &C, const MachineBasicBlock *M, + unsigned ID); + +public: + static XtensaConstantPoolMBB *Create(LLVMContext &C, + const MachineBasicBlock *M, unsigned ID); + + const MachineBasicBlock *getMBB() const { return MBB; } + + int getExistingMachineCPValue(MachineConstantPool *CP, + Align Alignment) override; + + void addSelectionDAGCSEId(FoldingSetNodeID &ID) override; + + /// hasSameValue - Return true if this Xtensa constpool value can share the + /// same constantpool entry as another Xtensa constpool value. + bool hasSameValue(XtensaConstantPoolValue *ACPV) override; + + void print(raw_ostream &O) const override; + + static bool classof(const XtensaConstantPoolValue *ACPV) { + return ACPV->isMachineBasicBlock(); + } + + bool equals(const XtensaConstantPoolMBB *A) const { + return MBB == A->MBB && XtensaConstantPoolValue::equals(A); + } +}; + +/// XtensaConstantPoolJumpTable - Xtensa-specific constantpool values for Jump +/// Table symbols. +class XtensaConstantPoolJumpTable : public XtensaConstantPoolValue { + unsigned Idx; // Jump Table Index. + + XtensaConstantPoolJumpTable(LLVMContext &C, unsigned Idx); + +public: + static XtensaConstantPoolJumpTable *Create(LLVMContext &C, unsigned Idx); + + unsigned getIndex() const { return Idx; } + + int getExistingMachineCPValue(MachineConstantPool *CP, + Align Alignment) override; + + void addSelectionDAGCSEId(FoldingSetNodeID &ID) override; + + /// hasSameValue - Return true if this Xtensa constpool value can share the + /// same constantpool entry as another Xtensa constpool value. + bool hasSameValue(XtensaConstantPoolValue *ACPV) override; + + void print(raw_ostream &O) const override; + + static bool classof(const XtensaConstantPoolValue *ACPV) { + return ACPV->isJumpTable(); + } + + bool equals(const XtensaConstantPoolJumpTable *A) const { + return Idx == A->Idx && XtensaConstantPoolValue::equals(A); + } +}; + +} // namespace llvm + +#endif /* LLVM_LIB_TARGET_XTENSA_XTENSACONSTANTPOOLVALUE_H */ diff --git a/llvm/lib/Target/Xtensa/XtensaFrameLowering.cpp b/llvm/lib/Target/Xtensa/XtensaFrameLowering.cpp index 2092a2d947f8665db5f2f9d5d04439edee83a4b3..ab37c09bf8bfe06051dc85a9fba50e4b889670dc 100644 --- a/llvm/lib/Target/Xtensa/XtensaFrameLowering.cpp +++ b/llvm/lib/Target/Xtensa/XtensaFrameLowering.cpp @@ -37,3 +37,23 @@ void XtensaFrameLowering::emitPrologue(MachineFunction &MF, void XtensaFrameLowering::emitEpilogue(MachineFunction &MF, MachineBasicBlock &MBB) const {} + +// Eliminate ADJCALLSTACKDOWN, ADJCALLSTACKUP pseudo instructions +MachineBasicBlock::iterator XtensaFrameLowering::eliminateCallFramePseudoInstr( + MachineFunction &MF, MachineBasicBlock &MBB, + MachineBasicBlock::iterator I) const { + const XtensaInstrInfo &TII = + *static_cast(MF.getSubtarget().getInstrInfo()); + + if (!hasReservedCallFrame(MF)) { + int64_t Amount = I->getOperand(0).getImm(); + + if (I->getOpcode() == Xtensa::ADJCALLSTACKDOWN) + Amount = -Amount; + + unsigned SP = Xtensa::SP; + TII.adjustStackPtr(SP, Amount, MBB, I); + } + + return MBB.erase(I); +} diff --git a/llvm/lib/Target/Xtensa/XtensaFrameLowering.h b/llvm/lib/Target/Xtensa/XtensaFrameLowering.h index 19e52310a99d9126a31270f49aa10791b5c64458..2da88ab14073ab85cf97fa1e30937274ee78c015 100644 --- a/llvm/lib/Target/Xtensa/XtensaFrameLowering.h +++ b/llvm/lib/Target/Xtensa/XtensaFrameLowering.h @@ -25,6 +25,10 @@ public: /// the function. void emitPrologue(MachineFunction &, MachineBasicBlock &) const override; void emitEpilogue(MachineFunction &MF, MachineBasicBlock &MBB) const override; + + MachineBasicBlock::iterator + eliminateCallFramePseudoInstr(MachineFunction &MF, MachineBasicBlock &MBB, + MachineBasicBlock::iterator I) const override; }; } // namespace llvm diff --git a/llvm/lib/Target/Xtensa/XtensaISelDAGToDAG.cpp b/llvm/lib/Target/Xtensa/XtensaISelDAGToDAG.cpp index 30073727545228be6ab52916e3ea238ad174b43f..5ebedefafc165e38d5a86cb47330d5c34d7a7fbc 100644 --- a/llvm/lib/Target/Xtensa/XtensaISelDAGToDAG.cpp +++ b/llvm/lib/Target/Xtensa/XtensaISelDAGToDAG.cpp @@ -12,9 +12,11 @@ #include "Xtensa.h" #include "XtensaTargetMachine.h" +#include "XtensaUtils.h" #include "llvm/CodeGen/MachineFunction.h" #include "llvm/CodeGen/MachineRegisterInfo.h" #include "llvm/CodeGen/SelectionDAGISel.h" +#include "llvm/IR/DiagnosticInfo.h" #include "llvm/Support/Debug.h" #include "llvm/Support/raw_ostream.h" @@ -37,9 +39,57 @@ public: void Select(SDNode *Node) override; + // For load/store instructions generate (base+offset) pair from + // memory address. The offset must be a multiple of scale argument. bool selectMemRegAddr(SDValue Addr, SDValue &Base, SDValue &Offset, int Scale) { - report_fatal_error("MemReg address is not implemented yet"); + EVT ValTy = Addr.getValueType(); + + // if Address is FI, get the TargetFrameIndex. + if (FrameIndexSDNode *FIN = dyn_cast(Addr)) { + Base = CurDAG->getTargetFrameIndex(FIN->getIndex(), ValTy); + Offset = CurDAG->getTargetConstant(0, SDLoc(Addr), ValTy); + + return true; + } + + if (TM.isPositionIndependent()) { + DiagnosticInfoUnsupported Diag(CurDAG->getMachineFunction().getFunction(), + "PIC relocations are not supported ", + Addr.getDebugLoc()); + CurDAG->getContext()->diagnose(Diag); + } + + if ((Addr.getOpcode() == ISD::TargetExternalSymbol || + Addr.getOpcode() == ISD::TargetGlobalAddress)) + return false; + + // Addresses of the form FI+const + bool Valid = false; + if (CurDAG->isBaseWithConstantOffset(Addr)) { + ConstantSDNode *CN = dyn_cast(Addr.getOperand(1)); + int64_t OffsetVal = CN->getSExtValue(); + + Valid = isValidAddrOffset(Scale, OffsetVal); + + if (Valid) { + // If the first operand is a FI, get the TargetFI Node + if (FrameIndexSDNode *FIN = + dyn_cast(Addr.getOperand(0))) + Base = CurDAG->getTargetFrameIndex(FIN->getIndex(), ValTy); + else + Base = Addr.getOperand(0); + + Offset = + CurDAG->getTargetConstant(CN->getZExtValue(), SDLoc(Addr), ValTy); + return true; + } + } + + // Last case + Base = Addr; + Offset = CurDAG->getTargetConstant(0, SDLoc(Addr), Addr.getValueType()); + return true; } bool selectMemRegAddrISH1(SDValue Addr, SDValue &Base, SDValue &Offset) { diff --git a/llvm/lib/Target/Xtensa/XtensaISelLowering.cpp b/llvm/lib/Target/Xtensa/XtensaISelLowering.cpp index 276fab838d17c0d982b89226d3eb74f2dfe82873..64b996b6a42e559e0bbb7319f7399267baf966e7 100644 --- a/llvm/lib/Target/Xtensa/XtensaISelLowering.cpp +++ b/llvm/lib/Target/Xtensa/XtensaISelLowering.cpp @@ -12,6 +12,7 @@ //===----------------------------------------------------------------------===// #include "XtensaISelLowering.h" +#include "XtensaConstantPoolValue.h" #include "XtensaSubtarget.h" #include "XtensaTargetMachine.h" #include "llvm/CodeGen/CallingConvLower.h" @@ -22,15 +23,26 @@ #include "llvm/CodeGen/TargetLoweringObjectFileImpl.h" #include "llvm/Support/Debug.h" #include "llvm/Support/ErrorHandling.h" +#include "llvm/Support/MathExtras.h" #include "llvm/Support/raw_ostream.h" +#include using namespace llvm; #define DEBUG_TYPE "xtensa-lower" +// Return true if we must use long (in fact, indirect) function call. +// It's simplified version, production implimentation must +// resolve a functions in ROM (usually glibc functions) +static bool isLongCall(const char *str) { + // Currently always use long calls + return true; +} + XtensaTargetLowering::XtensaTargetLowering(const TargetMachine &TM, const XtensaSubtarget &STI) : TargetLowering(TM), Subtarget(STI) { + MVT PtrVT = MVT::i32; // Set up the register classes. addRegisterClass(MVT::i32, &Xtensa::ARRegClass); @@ -41,18 +53,507 @@ XtensaTargetLowering::XtensaTargetLowering(const TargetMachine &TM, setMinFunctionAlignment(Align(4)); + setOperationAction(ISD::Constant, MVT::i32, Custom); + setOperationAction(ISD::Constant, MVT::i64, Expand); + + setBooleanContents(ZeroOrOneBooleanContent); + + setOperationAction(ISD::SIGN_EXTEND_INREG, MVT::i1, Expand); + setOperationAction(ISD::SIGN_EXTEND_INREG, MVT::i8, Expand); + setOperationAction(ISD::SIGN_EXTEND_INREG, MVT::i16, Expand); + + setOperationAction(ISD::BITCAST, MVT::i32, Expand); + setOperationAction(ISD::BITCAST, MVT::f32, Expand); + setOperationAction(ISD::UINT_TO_FP, MVT::i32, Expand); + setOperationAction(ISD::SINT_TO_FP, MVT::i32, Expand); + setOperationAction(ISD::FP_TO_UINT, MVT::i32, Expand); + setOperationAction(ISD::FP_TO_SINT, MVT::i32, Expand); + + // No sign extend instructions for i1 + for (MVT VT : MVT::integer_valuetypes()) { + setLoadExtAction(ISD::SEXTLOAD, VT, MVT::i1, Promote); + setLoadExtAction(ISD::ZEXTLOAD, VT, MVT::i1, Promote); + setLoadExtAction(ISD::EXTLOAD, VT, MVT::i1, Promote); + } + + setOperationAction(ISD::ConstantPool, PtrVT, Custom); + // Compute derived properties from the register classes computeRegisterProperties(STI.getRegisterInfo()); } +//===----------------------------------------------------------------------===// +// Calling conventions +//===----------------------------------------------------------------------===// + +#include "XtensaGenCallingConv.inc" + +static bool CC_Xtensa_Custom(unsigned ValNo, MVT ValVT, MVT LocVT, + CCValAssign::LocInfo LocInfo, + ISD::ArgFlagsTy ArgFlags, CCState &State) { + static const MCPhysReg IntRegs[] = {Xtensa::A2, Xtensa::A3, Xtensa::A4, + Xtensa::A5, Xtensa::A6, Xtensa::A7}; + + if (ArgFlags.isByVal()) { + Align ByValAlign = ArgFlags.getNonZeroByValAlign(); + unsigned ByValSize = ArgFlags.getByValSize(); + if (ByValSize < 4) { + ByValSize = 4; + } + if (ByValAlign < Align(4)) { + ByValAlign = Align(4); + } + unsigned Offset = State.AllocateStack(ByValSize, ByValAlign); + State.addLoc(CCValAssign::getMem(ValNo, ValVT, Offset, LocVT, LocInfo)); + // Mark all unused registers as allocated to avoid misuse + // of such registers. + while (State.AllocateReg(IntRegs)) + ; + return false; + } + + // Promote i8 and i16 + if (LocVT == MVT::i8 || LocVT == MVT::i16) { + LocVT = MVT::i32; + if (ArgFlags.isSExt()) + LocInfo = CCValAssign::SExt; + else if (ArgFlags.isZExt()) + LocInfo = CCValAssign::ZExt; + else + LocInfo = CCValAssign::AExt; + } + + unsigned Register; + + Align OrigAlign = ArgFlags.getNonZeroOrigAlign(); + bool needs64BitAlign = (ValVT == MVT::i32 && OrigAlign == Align(8)); + bool needs128BitAlign = (ValVT == MVT::i32 && OrigAlign == Align(16)); + + if (ValVT == MVT::i32) { + Register = State.AllocateReg(IntRegs); + // If this is the first part of an i64 arg, + // the allocated register must be either A2, A4 or A6. + if (needs64BitAlign && (Register == Xtensa::A3 || Register == Xtensa::A5 || + Register == Xtensa::A7)) + Register = State.AllocateReg(IntRegs); + // arguments with 16byte alignment must be passed in the first register or + // passed via stack + if (needs128BitAlign && (Register != Xtensa::A2)) + while ((Register = State.AllocateReg(IntRegs))) + ; + LocVT = MVT::i32; + } else if (ValVT == MVT::f64) { + // Allocate int register and shadow next int register. + Register = State.AllocateReg(IntRegs); + if (Register == Xtensa::A3 || Register == Xtensa::A5 || + Register == Xtensa::A7) + Register = State.AllocateReg(IntRegs); + State.AllocateReg(IntRegs); + LocVT = MVT::i32; + } else { + report_fatal_error("Cannot handle this ValVT."); + } + + if (!Register) { + unsigned Offset = State.AllocateStack(ValVT.getStoreSize(), OrigAlign); + State.addLoc(CCValAssign::getMem(ValNo, ValVT, Offset, LocVT, LocInfo)); + } else { + State.addLoc(CCValAssign::getReg(ValNo, ValVT, Register, LocVT, LocInfo)); + } + + return false; +} + +CCAssignFn *XtensaTargetLowering::CCAssignFnForCall(CallingConv::ID CC, + bool IsVarArg) const { + return CC_Xtensa_Custom; +} + +SDValue XtensaTargetLowering::LowerFormalArguments( + SDValue Chain, CallingConv::ID CallConv, bool IsVarArg, + const SmallVectorImpl &Ins, const SDLoc &DL, + SelectionDAG &DAG, SmallVectorImpl &InVals) const { + MachineFunction &MF = DAG.getMachineFunction(); + MachineFrameInfo &MFI = MF.getFrameInfo(); + + // Used with vargs to acumulate store chains. + std::vector OutChains; + + if (IsVarArg) + report_fatal_error("Var arg not supported by FormalArguments Lowering"); + + // Assign locations to all of the incoming arguments. + SmallVector ArgLocs; + CCState CCInfo(CallConv, IsVarArg, DAG.getMachineFunction(), ArgLocs, + *DAG.getContext()); + + CCInfo.AnalyzeFormalArguments(Ins, CCAssignFnForCall(CallConv, IsVarArg)); + + for (unsigned i = 0, e = ArgLocs.size(); i != e; ++i) { + CCValAssign &VA = ArgLocs[i]; + // Arguments stored on registers + if (VA.isRegLoc()) { + EVT RegVT = VA.getLocVT(); + const TargetRegisterClass *RC; + + if (RegVT == MVT::i32) + RC = &Xtensa::ARRegClass; + else + report_fatal_error("RegVT not supported by FormalArguments Lowering"); + + // Transform the arguments stored on + // physical registers into virtual ones + unsigned Register = MF.addLiveIn(VA.getLocReg(), RC); + SDValue ArgValue = DAG.getCopyFromReg(Chain, DL, Register, RegVT); + + // If this is an 8 or 16-bit value, it has been passed promoted + // to 32 bits. Insert an assert[sz]ext to capture this, then + // truncate to the right size. + if (VA.getLocInfo() != CCValAssign::Full) { + unsigned Opcode = 0; + if (VA.getLocInfo() == CCValAssign::SExt) + Opcode = ISD::AssertSext; + else if (VA.getLocInfo() == CCValAssign::ZExt) + Opcode = ISD::AssertZext; + if (Opcode) + ArgValue = DAG.getNode(Opcode, DL, RegVT, ArgValue, + DAG.getValueType(VA.getValVT())); + ArgValue = DAG.getNode((VA.getValVT() == MVT::f32) ? ISD::BITCAST + : ISD::TRUNCATE, + DL, VA.getValVT(), ArgValue); + } + + InVals.push_back(ArgValue); + + } else { + assert(VA.isMemLoc()); + + EVT ValVT = VA.getValVT(); + + // The stack pointer offset is relative to the caller stack frame. + int FI = MFI.CreateFixedObject(ValVT.getStoreSize(), VA.getLocMemOffset(), + true); + + if (Ins[VA.getValNo()].Flags.isByVal()) { + // Assume that in this case load operation is created + SDValue FIN = DAG.getFrameIndex(FI, MVT::i32); + InVals.push_back(FIN); + } else { + // Create load nodes to retrieve arguments from the stack + SDValue FIN = + DAG.getFrameIndex(FI, getFrameIndexTy(DAG.getDataLayout())); + InVals.push_back(DAG.getLoad( + ValVT, DL, Chain, FIN, + MachinePointerInfo::getFixedStack(DAG.getMachineFunction(), FI))); + } + } + } + + // All stores are grouped in one node to allow the matching between + // the size of Ins and InVals. This only happens when on varg functions + if (!OutChains.empty()) { + OutChains.push_back(Chain); + Chain = DAG.getNode(ISD::TokenFactor, DL, MVT::Other, OutChains); + } + + return Chain; +} + +SDValue +XtensaTargetLowering::LowerCall(CallLoweringInfo &CLI, + SmallVectorImpl &InVals) const { + SelectionDAG &DAG = CLI.DAG; + SDLoc &DL = CLI.DL; + SmallVector &Outs = CLI.Outs; + SmallVector &OutVals = CLI.OutVals; + SmallVector &Ins = CLI.Ins; + SDValue Chain = CLI.Chain; + SDValue Callee = CLI.Callee; + bool &IsTailCall = CLI.IsTailCall; + CallingConv::ID CallConv = CLI.CallConv; + bool IsVarArg = CLI.IsVarArg; + + MachineFunction &MF = DAG.getMachineFunction(); + EVT PtrVT = getPointerTy(DAG.getDataLayout()); + const TargetFrameLowering *TFL = Subtarget.getFrameLowering(); + + // TODO: Support tail call optimization. + IsTailCall = false; + + // Analyze the operands of the call, assigning locations to each operand. + SmallVector ArgLocs; + CCState CCInfo(CallConv, IsVarArg, MF, ArgLocs, *DAG.getContext()); + + CCAssignFn *CC = CCAssignFnForCall(CallConv, IsVarArg); + + CCInfo.AnalyzeCallOperands(Outs, CC); + + // Get a count of how many bytes are to be pushed on the stack. + unsigned NumBytes = CCInfo.getStackSize(); + + Align StackAlignment = TFL->getStackAlign(); + unsigned NextStackOffset = alignTo(NumBytes, StackAlignment); + + Chain = DAG.getCALLSEQ_START(Chain, NextStackOffset, 0, DL); + + // Copy argument values to their designated locations. + std::deque> RegsToPass; + SmallVector MemOpChains; + SDValue StackPtr; + for (unsigned I = 0, E = ArgLocs.size(); I != E; ++I) { + CCValAssign &VA = ArgLocs[I]; + SDValue ArgValue = OutVals[I]; + ISD::ArgFlagsTy Flags = Outs[I].Flags; + + if (VA.isRegLoc()) + // Queue up the argument copies and emit them at the end. + RegsToPass.push_back(std::make_pair(VA.getLocReg(), ArgValue)); + else if (Flags.isByVal()) { + assert(VA.isMemLoc()); + assert(Flags.getByValSize() && + "ByVal args of size 0 should have been ignored by front-end."); + assert(!IsTailCall && + "Do not tail-call optimize if there is a byval argument."); + + if (!StackPtr.getNode()) + StackPtr = DAG.getCopyFromReg(Chain, DL, Xtensa::SP, PtrVT); + unsigned Offset = VA.getLocMemOffset(); + SDValue Address = DAG.getNode(ISD::ADD, DL, PtrVT, StackPtr, + DAG.getIntPtrConstant(Offset, DL)); + SDValue SizeNode = DAG.getConstant(Flags.getByValSize(), DL, MVT::i32); + SDValue Memcpy = DAG.getMemcpy( + Chain, DL, Address, ArgValue, SizeNode, Flags.getNonZeroByValAlign(), + /*isVolatile=*/false, /*AlwaysInline=*/false, + /*isTailCall=*/false, MachinePointerInfo(), MachinePointerInfo()); + MemOpChains.push_back(Memcpy); + } else { + assert(VA.isMemLoc() && "Argument not register or memory"); + + // Work out the address of the stack slot. Unpromoted ints and + // floats are passed as right-justified 8-byte values. + if (!StackPtr.getNode()) + StackPtr = DAG.getCopyFromReg(Chain, DL, Xtensa::SP, PtrVT); + unsigned Offset = VA.getLocMemOffset(); + SDValue Address = DAG.getNode(ISD::ADD, DL, PtrVT, StackPtr, + DAG.getIntPtrConstant(Offset, DL)); + + // Emit the store. + MemOpChains.push_back( + DAG.getStore(Chain, DL, ArgValue, Address, MachinePointerInfo())); + } + } + + // Join the stores, which are independent of one another. + if (!MemOpChains.empty()) + Chain = DAG.getNode(ISD::TokenFactor, DL, MVT::Other, MemOpChains); + + // Build a sequence of copy-to-reg nodes, chained and glued together. + SDValue Glue; + for (unsigned I = 0, E = RegsToPass.size(); I != E; ++I) { + unsigned Reg = RegsToPass[I].first; + Chain = DAG.getCopyToReg(Chain, DL, Reg, RegsToPass[I].second, Glue); + Glue = Chain.getValue(1); + } + std::string name; + unsigned char TF = 0; + + // Accept direct calls by converting symbolic call addresses to the + // associated Target* opcodes. + if (ExternalSymbolSDNode *E = dyn_cast(Callee)) { + name = E->getSymbol(); + TF = E->getTargetFlags(); + if (isPositionIndependent()) { + report_fatal_error("PIC relocations is not supported"); + } else + Callee = DAG.getTargetExternalSymbol(E->getSymbol(), PtrVT, TF); + } else if (GlobalAddressSDNode *G = dyn_cast(Callee)) { + const GlobalValue *GV = G->getGlobal(); + name = GV->getName().str(); + } + + if ((!name.empty()) && isLongCall(name.c_str())) { + // Create a constant pool entry for the callee address + XtensaCP::XtensaCPModifier Modifier = XtensaCP::no_modifier; + + XtensaConstantPoolValue *CPV = XtensaConstantPoolSymbol::Create( + *DAG.getContext(), name.c_str(), 0 /* XtensaCLabelIndex */, false, + Modifier); + + // Get the address of the callee into a register + SDValue CPAddr = DAG.getTargetConstantPool(CPV, PtrVT, Align(4), 0, TF); + SDValue CPWrap = getAddrPCRel(CPAddr, DAG); + Callee = CPWrap; + } + + // The first call operand is the chain and the second is the target address. + SmallVector Ops; + Ops.push_back(Chain); + Ops.push_back(Callee); + + // Add a register mask operand representing the call-preserved registers. + const TargetRegisterInfo *TRI = Subtarget.getRegisterInfo(); + const uint32_t *Mask = TRI->getCallPreservedMask(MF, CallConv); + assert(Mask && "Missing call preserved mask for calling convention"); + Ops.push_back(DAG.getRegisterMask(Mask)); + + // Add argument registers to the end of the list so that they are + // known live into the call. + for (unsigned I = 0, E = RegsToPass.size(); I != E; ++I) { + unsigned Reg = RegsToPass[I].first; + Ops.push_back(DAG.getRegister(Reg, RegsToPass[I].second.getValueType())); + } + + // Glue the call to the argument copies, if any. + if (Glue.getNode()) + Ops.push_back(Glue); + + SDVTList NodeTys = DAG.getVTList(MVT::Other, MVT::Glue); + Chain = DAG.getNode(XtensaISD::CALL, DL, NodeTys, Ops); + Glue = Chain.getValue(1); + + // Mark the end of the call, which is glued to the call itself. + Chain = DAG.getCALLSEQ_END(Chain, DAG.getConstant(NumBytes, DL, PtrVT, true), + DAG.getConstant(0, DL, PtrVT, true), Glue, DL); + Glue = Chain.getValue(1); + + // Assign locations to each value returned by this call. + SmallVector RetLocs; + CCState RetCCInfo(CallConv, IsVarArg, MF, RetLocs, *DAG.getContext()); + RetCCInfo.AnalyzeCallResult(Ins, RetCC_Xtensa); + + // Copy all of the result registers out of their specified physreg. + for (unsigned I = 0, E = RetLocs.size(); I != E; ++I) { + CCValAssign &VA = RetLocs[I]; + + // Copy the value out, gluing the copy to the end of the call sequence. + unsigned Reg = VA.getLocReg(); + SDValue RetValue = DAG.getCopyFromReg(Chain, DL, Reg, VA.getLocVT(), Glue); + Chain = RetValue.getValue(1); + Glue = RetValue.getValue(2); + + InVals.push_back(RetValue); + } + return Chain; +} + +bool XtensaTargetLowering::CanLowerReturn( + CallingConv::ID CallConv, MachineFunction &MF, bool IsVarArg, + const SmallVectorImpl &Outs, LLVMContext &Context) const { + SmallVector RVLocs; + CCState CCInfo(CallConv, IsVarArg, MF, RVLocs, Context); + return CCInfo.CheckReturn(Outs, RetCC_Xtensa); +} + +SDValue +XtensaTargetLowering::LowerReturn(SDValue Chain, CallingConv::ID CallConv, + bool IsVarArg, + const SmallVectorImpl &Outs, + const SmallVectorImpl &OutVals, + const SDLoc &DL, SelectionDAG &DAG) const { + if (IsVarArg) + report_fatal_error("VarArg not supported"); + + MachineFunction &MF = DAG.getMachineFunction(); + + // Assign locations to each returned value. + SmallVector RetLocs; + CCState RetCCInfo(CallConv, IsVarArg, MF, RetLocs, *DAG.getContext()); + RetCCInfo.AnalyzeReturn(Outs, RetCC_Xtensa); + + SDValue Glue; + // Quick exit for void returns + if (RetLocs.empty()) + return DAG.getNode(XtensaISD::RET, DL, MVT::Other, Chain); + + // Copy the result values into the output registers. + SmallVector RetOps; + RetOps.push_back(Chain); + for (unsigned I = 0, E = RetLocs.size(); I != E; ++I) { + CCValAssign &VA = RetLocs[I]; + SDValue RetValue = OutVals[I]; + + // Make the return register live on exit. + assert(VA.isRegLoc() && "Can only return in registers!"); + + // Chain and glue the copies together. + unsigned Register = VA.getLocReg(); + Chain = DAG.getCopyToReg(Chain, DL, Register, RetValue, Glue); + Glue = Chain.getValue(1); + RetOps.push_back(DAG.getRegister(Register, VA.getLocVT())); + } + + // Update chain and glue. + RetOps[0] = Chain; + if (Glue.getNode()) + RetOps.push_back(Glue); + + return DAG.getNode(XtensaISD::RET, DL, MVT::Other, RetOps); +} + +SDValue XtensaTargetLowering::LowerImmediate(SDValue Op, + SelectionDAG &DAG) const { + const ConstantSDNode *CN = cast(Op); + SDLoc DL(CN); + APInt APVal = CN->getAPIntValue(); + int64_t Value = APVal.getSExtValue(); + if (Op.getValueType() == MVT::i32) { + // Check if use node maybe lowered to the MOVI instruction + if (Value > -2048 && Value <= 2047) + return Op; + // Check if use node maybe lowered to the ADDMI instruction + SDNode &OpNode = *Op.getNode(); + if ((OpNode.hasOneUse() && OpNode.use_begin()->getOpcode() == ISD::ADD) && + isShiftedInt<16, 8>(Value)) + return Op; + Type *Ty = Type::getInt32Ty(*DAG.getContext()); + Constant *CV = ConstantInt::get(Ty, Value); + SDValue CP = DAG.getConstantPool(CV, MVT::i32); + return CP; + } + return Op; +} + +SDValue XtensaTargetLowering::getAddrPCRel(SDValue Op, + SelectionDAG &DAG) const { + SDLoc DL(Op); + EVT Ty = Op.getValueType(); + return DAG.getNode(XtensaISD::PCREL_WRAPPER, DL, Ty, Op); +} + +SDValue XtensaTargetLowering::LowerConstantPool(ConstantPoolSDNode *CP, + SelectionDAG &DAG) const { + EVT PtrVT = getPointerTy(DAG.getDataLayout()); + SDValue Result; + if (!CP->isMachineConstantPoolEntry()) { + Result = DAG.getTargetConstantPool(CP->getConstVal(), PtrVT, CP->getAlign(), + CP->getOffset()); + } else { + report_fatal_error("This constantpool type is not supported yet"); + } + + return getAddrPCRel(Result, DAG); +} + SDValue XtensaTargetLowering::LowerOperation(SDValue Op, SelectionDAG &DAG) const { switch (Op.getOpcode()) { + case ISD::Constant: + return LowerImmediate(Op, DAG); + case ISD::ConstantPool: + return LowerConstantPool(cast(Op), DAG); default: report_fatal_error("Unexpected node to lower"); } } const char *XtensaTargetLowering::getTargetNodeName(unsigned Opcode) const { + switch (Opcode) { + case XtensaISD::CALL: + return "XtensaISD::CALL"; + case XtensaISD::PCREL_WRAPPER: + return "XtensaISD::PCREL_WRAPPER"; + case XtensaISD::RET: + return "XtensaISD::RET"; + } return nullptr; } diff --git a/llvm/lib/Target/Xtensa/XtensaISelLowering.h b/llvm/lib/Target/Xtensa/XtensaISelLowering.h index 8b03712efc9bb5a6c5ab37544dab5e98bf520858..077559e2d6129864f75c3e2db1e28a6e086d76fd 100644 --- a/llvm/lib/Target/Xtensa/XtensaISelLowering.h +++ b/llvm/lib/Target/Xtensa/XtensaISelLowering.h @@ -19,6 +19,23 @@ #include "llvm/CodeGen/TargetLowering.h" namespace llvm { + +namespace XtensaISD { +enum { + FIRST_NUMBER = ISD::BUILTIN_OP_END, + + // Calls a function. Operand 0 is the chain operand and operand 1 + // is the target address. The arguments start at operand 2. + // There is an optional glue operand at the end. + CALL, + + // Wraps a TargetGlobalAddress that should be loaded using PC-relative + // accesses. Operand 0 is the address. + PCREL_WRAPPER, + RET +}; +} + class XtensaSubtarget; class XtensaTargetLowering : public TargetLowering { @@ -30,10 +47,37 @@ public: SDValue LowerOperation(SDValue Op, SelectionDAG &DAG) const override; + SDValue LowerFormalArguments(SDValue Chain, CallingConv::ID CallConv, + bool isVarArg, + const SmallVectorImpl &Ins, + const SDLoc &DL, SelectionDAG &DAG, + SmallVectorImpl &InVals) const override; + + SDValue LowerCall(CallLoweringInfo &CLI, + SmallVectorImpl &InVals) const override; + + bool CanLowerReturn(CallingConv::ID CallConv, MachineFunction &MF, + bool isVarArg, + const SmallVectorImpl &Outs, + LLVMContext &Context) const override; + + SDValue LowerReturn(SDValue Chain, CallingConv::ID CallConv, bool IsVarArg, + const SmallVectorImpl &Outs, + const SmallVectorImpl &OutVals, const SDLoc &DL, + SelectionDAG &DAG) const override; + const XtensaSubtarget &getSubtarget() const { return Subtarget; } private: const XtensaSubtarget &Subtarget; + + SDValue LowerImmediate(SDValue Op, SelectionDAG &DAG) const; + + SDValue LowerConstantPool(ConstantPoolSDNode *CP, SelectionDAG &DAG) const; + + SDValue getAddrPCRel(SDValue Op, SelectionDAG &DAG) const; + + CCAssignFn *CCAssignFnForCall(CallingConv::ID CC, bool IsVarArg) const; }; } // end namespace llvm diff --git a/llvm/lib/Target/Xtensa/XtensaInstrInfo.cpp b/llvm/lib/Target/Xtensa/XtensaInstrInfo.cpp index 41b794d64fdb1f157ae9fb02efd70bc5a595f4f7..26d8727ce1d3bce4523e772f88ee3bebcd0f1d38 100644 --- a/llvm/lib/Target/Xtensa/XtensaInstrInfo.cpp +++ b/llvm/lib/Target/Xtensa/XtensaInstrInfo.cpp @@ -15,6 +15,7 @@ #include "XtensaInstrInfo.h" #include "XtensaTargetMachine.h" #include "llvm/CodeGen/MachineConstantPool.h" +#include "llvm/CodeGen/MachineFrameInfo.h" #include "llvm/CodeGen/MachineInstrBuilder.h" #include "llvm/CodeGen/MachineRegisterInfo.h" @@ -23,5 +24,139 @@ using namespace llvm; +static const MachineInstrBuilder & +addFrameReference(const MachineInstrBuilder &MIB, int FI) { + MachineInstr *MI = MIB; + MachineFunction &MF = *MI->getParent()->getParent(); + MachineFrameInfo &MFFrame = MF.getFrameInfo(); + const MCInstrDesc &MCID = MI->getDesc(); + MachineMemOperand::Flags Flags = MachineMemOperand::MONone; + if (MCID.mayLoad()) + Flags |= MachineMemOperand::MOLoad; + if (MCID.mayStore()) + Flags |= MachineMemOperand::MOStore; + int64_t Offset = 0; + Align Alignment = MFFrame.getObjectAlign(FI); + + MachineMemOperand *MMO = + MF.getMachineMemOperand(MachinePointerInfo::getFixedStack(MF, FI, Offset), + Flags, MFFrame.getObjectSize(FI), Alignment); + return MIB.addFrameIndex(FI).addImm(Offset).addMemOperand(MMO); +} + XtensaInstrInfo::XtensaInstrInfo(const XtensaSubtarget &STI) - : XtensaGenInstrInfo(), RI(STI), STI(STI) {} + : XtensaGenInstrInfo(Xtensa::ADJCALLSTACKDOWN, Xtensa::ADJCALLSTACKUP), + RI(STI), STI(STI) {} + +/// Adjust SP by Amount bytes. +void XtensaInstrInfo::adjustStackPtr(unsigned SP, int64_t Amount, + MachineBasicBlock &MBB, + MachineBasicBlock::iterator I) const { + DebugLoc DL = I != MBB.end() ? I->getDebugLoc() : DebugLoc(); + + if (Amount == 0) + return; + + MachineRegisterInfo &RegInfo = MBB.getParent()->getRegInfo(); + const TargetRegisterClass *RC = &Xtensa::ARRegClass; + + // create virtual reg to store immediate + unsigned Reg = RegInfo.createVirtualRegister(RC); + + if (isInt<8>(Amount)) { // addi sp, sp, amount + BuildMI(MBB, I, DL, get(Xtensa::ADDI), Reg).addReg(SP).addImm(Amount); + } else { // Expand immediate that doesn't fit in 8-bit. + unsigned Reg1; + loadImmediate(MBB, I, &Reg1, Amount); + BuildMI(MBB, I, DL, get(Xtensa::ADD), Reg) + .addReg(SP) + .addReg(Reg1, RegState::Kill); + } + + BuildMI(MBB, I, DL, get(Xtensa::OR), SP) + .addReg(Reg, RegState::Kill) + .addReg(Reg, RegState::Kill); +} + +void XtensaInstrInfo::copyPhysReg(MachineBasicBlock &MBB, + MachineBasicBlock::iterator MBBI, + const DebugLoc &DL, MCRegister DestReg, + MCRegister SrcReg, bool KillSrc) const { + // The MOV instruction is not present in core ISA, + // so use OR instruction. + if (Xtensa::ARRegClass.contains(DestReg, SrcReg)) + BuildMI(MBB, MBBI, DL, get(Xtensa::OR), DestReg) + .addReg(SrcReg, getKillRegState(KillSrc)) + .addReg(SrcReg, getKillRegState(KillSrc)); + else + report_fatal_error("Impossible reg-to-reg copy"); +} + +void XtensaInstrInfo::storeRegToStackSlot( + MachineBasicBlock &MBB, MachineBasicBlock::iterator MBBI, Register SrcReg, + bool isKill, int FrameIdx, const TargetRegisterClass *RC, + const TargetRegisterInfo *TRI, Register VReg) const { + DebugLoc DL = MBBI != MBB.end() ? MBBI->getDebugLoc() : DebugLoc(); + unsigned LoadOpcode, StoreOpcode; + getLoadStoreOpcodes(RC, LoadOpcode, StoreOpcode, FrameIdx); + MachineInstrBuilder MIB = BuildMI(MBB, MBBI, DL, get(StoreOpcode)) + .addReg(SrcReg, getKillRegState(isKill)); + addFrameReference(MIB, FrameIdx); +} + +void XtensaInstrInfo::loadRegFromStackSlot(MachineBasicBlock &MBB, + MachineBasicBlock::iterator MBBI, + Register DestReg, int FrameIdx, + const TargetRegisterClass *RC, + const TargetRegisterInfo *TRI, + Register VReg) const { + DebugLoc DL = MBBI != MBB.end() ? MBBI->getDebugLoc() : DebugLoc(); + unsigned LoadOpcode, StoreOpcode; + getLoadStoreOpcodes(RC, LoadOpcode, StoreOpcode, FrameIdx); + addFrameReference(BuildMI(MBB, MBBI, DL, get(LoadOpcode), DestReg), FrameIdx); +} + +void XtensaInstrInfo::getLoadStoreOpcodes(const TargetRegisterClass *RC, + unsigned &LoadOpcode, + unsigned &StoreOpcode, + int64_t offset) const { + assert((RC == &Xtensa::ARRegClass) && + "Unsupported regclass to load or store"); + + LoadOpcode = Xtensa::L32I; + StoreOpcode = Xtensa::S32I; +} + +void XtensaInstrInfo::loadImmediate(MachineBasicBlock &MBB, + MachineBasicBlock::iterator MBBI, + unsigned *Reg, int64_t Value) const { + DebugLoc DL = MBBI != MBB.end() ? MBBI->getDebugLoc() : DebugLoc(); + MachineRegisterInfo &RegInfo = MBB.getParent()->getRegInfo(); + const TargetRegisterClass *RC = &Xtensa::ARRegClass; + + // create virtual reg to store immediate + *Reg = RegInfo.createVirtualRegister(RC); + if (Value >= -2048 && Value <= 2047) { + BuildMI(MBB, MBBI, DL, get(Xtensa::MOVI), *Reg).addImm(Value); + } else if (Value >= -32768 && Value <= 32767) { + int Low = Value & 0xFF; + int High = Value & ~0xFF; + + BuildMI(MBB, MBBI, DL, get(Xtensa::MOVI), *Reg).addImm(Low); + BuildMI(MBB, MBBI, DL, get(Xtensa::ADDMI), *Reg).addReg(*Reg).addImm(High); + } else if (Value >= -4294967296LL && Value <= 4294967295LL) { + // 32 bit arbirary constant + MachineConstantPool *MCP = MBB.getParent()->getConstantPool(); + uint64_t UVal = ((uint64_t)Value) & 0xFFFFFFFFLL; + const Constant *CVal = ConstantInt::get( + Type::getInt32Ty(MBB.getParent()->getFunction().getContext()), UVal, + false); + unsigned Idx = MCP->getConstantPoolIndex(CVal, Align(2U)); + // MCSymbol MSym + BuildMI(MBB, MBBI, DL, get(Xtensa::L32R), *Reg).addConstantPoolIndex(Idx); + } else { + // use L32R to let assembler load immediate best + // TODO replace to L32R + report_fatal_error("Unsupported load immediate value"); + } +} diff --git a/llvm/lib/Target/Xtensa/XtensaInstrInfo.h b/llvm/lib/Target/Xtensa/XtensaInstrInfo.h index 8c73c9bd794081460aa9b862c5f8f2d3bfb11a6f..1acd314e2720a348b19f054003596a09718e24cf 100644 --- a/llvm/lib/Target/Xtensa/XtensaInstrInfo.h +++ b/llvm/lib/Target/Xtensa/XtensaInstrInfo.h @@ -35,9 +35,38 @@ class XtensaInstrInfo : public XtensaGenInstrInfo { public: XtensaInstrInfo(const XtensaSubtarget &STI); + void adjustStackPtr(unsigned SP, int64_t Amount, MachineBasicBlock &MBB, + MachineBasicBlock::iterator I) const; + // Return the XtensaRegisterInfo, which this class owns. const XtensaRegisterInfo &getRegisterInfo() const { return RI; } + void copyPhysReg(MachineBasicBlock &MBB, MachineBasicBlock::iterator MBBI, + const DebugLoc &DL, MCRegister DestReg, MCRegister SrcReg, + bool KillSrc) const override; + + void storeRegToStackSlot(MachineBasicBlock &MBB, + MachineBasicBlock::iterator MBBI, Register SrcReg, + bool isKill, int FrameIndex, + const TargetRegisterClass *RC, + const TargetRegisterInfo *TRI, + Register VReg) const override; + + void loadRegFromStackSlot(MachineBasicBlock &MBB, + MachineBasicBlock::iterator MBBI, Register DestReg, + int FrameIdx, const TargetRegisterClass *RC, + const TargetRegisterInfo *TRI, + Register VReg) const override; + + // Get the load and store opcodes for a given register class and offset. + void getLoadStoreOpcodes(const TargetRegisterClass *RC, unsigned &LoadOpcode, + unsigned &StoreOpcode, int64_t offset) const; + + // Emit code before MBBI in MI to move immediate value Value into + // physical register Reg. + void loadImmediate(MachineBasicBlock &MBB, MachineBasicBlock::iterator MBBI, + unsigned *Reg, int64_t Value) const; + const XtensaSubtarget &getSubtarget() const { return STI; } }; } // end namespace llvm diff --git a/llvm/lib/Target/Xtensa/XtensaInstrInfo.td b/llvm/lib/Target/Xtensa/XtensaInstrInfo.td index 268a9943d8c1604a930d3c9417a4f27000d3bd67..6e9e75257ccf4cb96aeb03038ca2bcc95469e988 100644 --- a/llvm/lib/Target/Xtensa/XtensaInstrInfo.td +++ b/llvm/lib/Target/Xtensa/XtensaInstrInfo.td @@ -14,6 +14,7 @@ include "XtensaInstrFormats.td" include "XtensaOperands.td" +include "XtensaOperators.td" //===----------------------------------------------------------------------===// // Arithmetic & Logical instructions @@ -238,6 +239,34 @@ def L32R : RI16_Inst<0x01, (outs AR:$t), (ins L32Rtarget:$label), let imm16 = label; } +// pcrel addr loading using L32R +def : Pat<(Xtensa_pcrel_wrapper tconstpool : $in), (L32R tconstpool : $in)>; + +// FrameIndexes are legalized when they are operands from load/store +// instructions. The same not happens for stack address copies, so an +// add op with mem ComplexPattern is used and the stack address copy +// can be matched. +// Setting of attribute mayLoad is trick to process instruction operands +// in function XtensaRegisterInfo::eliminateFI + +let isCodeGenOnly = 1, mayLoad = 1 in { + + def LEA_ADD : RRI8_Inst<0x02, (outs AR:$t), (ins mem32:$addr), + "addi\t$t, $addr", + [(set AR:$t, addr_ish4:$addr)]> { + bits<12> addr; + + let r = 0x0C; + let imm8{7-0} = addr{11-4}; + let s{3-0} = addr{3-0}; + } +} + +//extending loads +def : Pat<(i32 (extloadi1 addr_ish1:$addr)), (L8UI addr_ish1:$addr)>; +def : Pat<(i32 (extloadi8 addr_ish1:$addr)), (L8UI addr_ish1:$addr)>; +def : Pat<(i32 (extloadi16 addr_ish2:$addr)), (L16UI addr_ish2:$addr)>; + //===----------------------------------------------------------------------===// // Conditional branch instructions //===----------------------------------------------------------------------===// @@ -426,7 +455,7 @@ let isReturn = 1, isTerminator = 1, isBarrier = 1, Uses = [A0] in { def RET : CALLX_Inst<0x00, 0x00, 0x00, (outs), (ins), - "ret", []> { + "ret", [(Xtensa_ret)]> { let m = 0x2; let n = 0x0; let s = 0; @@ -434,6 +463,14 @@ let isReturn = 1, isTerminator = 1, } } +// Call patterns +def : Pat<(Xtensa_call (i32 tglobaladdr:$dst)), + (CALL0 tglobaladdr:$dst)>; +def : Pat<(Xtensa_call (i32 texternalsym:$dst)), + (CALL0 texternalsym:$dst)>; +def : Pat<(Xtensa_call AR:$dst), + (CALLX0 AR:$dst)>; + //===----------------------------------------------------------------------===// // Mem barrier instructions //===----------------------------------------------------------------------===// @@ -506,3 +543,19 @@ def XSR : RSR_Inst<0x00, 0x01, 0x06, (outs AR:$ard, SR:$srd), (ins AR:$t, SR:$sr "xsr\t$t, $sr", []> { let Constraints = "$ard = $t, $srd = $sr"; } + +//===----------------------------------------------------------------------===// +// Stack allocation +//===----------------------------------------------------------------------===// + +// ADJCALLSTACKDOWN/UP implicitly use/def SP because they may be expanded into +// a stack adjustment and the codegen must know that they may modify the stack +// pointer before prolog-epilog rewriting occurs. +let Defs = [SP], Uses = [SP] in { + def ADJCALLSTACKDOWN : Pseudo<(outs), (ins i32imm:$amt1, i32imm:$amt2), + "#ADJCALLSTACKDOWN", + [(Xtensa_callseq_start timm:$amt1, timm:$amt2)]>; + def ADJCALLSTACKUP : Pseudo<(outs), (ins i32imm:$amt1, i32imm:$amt2), + "#ADJCALLSTACKUP", + [(Xtensa_callseq_end timm:$amt1, timm:$amt2)]>; +} diff --git a/llvm/lib/Target/Xtensa/XtensaOperands.td b/llvm/lib/Target/Xtensa/XtensaOperands.td index 7a1a2e86e8c20fae34d1c80918fe88696576c728..f41081f9bf2f9686f5e56870da2a6db4f847959d 100644 --- a/llvm/lib/Target/Xtensa/XtensaOperands.td +++ b/llvm/lib/Target/Xtensa/XtensaOperands.td @@ -195,7 +195,7 @@ def jumptarget : Operand { let ParserMatchClass = XtensaPCRelTargetAsmOperand; } -def L32Rtarget : Operand { +def L32Rtarget : Operand { let PrintMethod = "printL32RTarget"; let EncoderMethod = "getL32RTargetEncoding"; let DecoderMethod = "decodeL32ROperand"; diff --git a/llvm/lib/Target/Xtensa/XtensaOperators.td b/llvm/lib/Target/Xtensa/XtensaOperators.td new file mode 100644 index 0000000000000000000000000000000000000000..cd4d831c85b581d15834b09a75b594205dd37078 --- /dev/null +++ b/llvm/lib/Target/Xtensa/XtensaOperators.td @@ -0,0 +1,36 @@ +//===- XtensaOperators.td - Xtensa-specific operators ---------*- tblgen-*-===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +//===----------------------------------------------------------------------===// +// Type profiles +//===----------------------------------------------------------------------===// +def SDT_XtensaCallSeqStart : SDCallSeqStart<[SDTCisVT<0, i32>, SDTCisVT<1, i32>]>; +def SDT_XtensaCallSeqEnd : SDCallSeqEnd<[SDTCisVT<0, i32>, SDTCisVT<1, i32>]>; +def SDT_XtensaCall : SDTypeProfile<0, -1, [SDTCisPtrTy<0>]>; + +def SDT_XtensaWrapPtr : SDTypeProfile<1, 1, + [SDTCisSameAs<0, 1>, + SDTCisPtrTy<0>]>; + +//===----------------------------------------------------------------------===// +// Node definitions +//===----------------------------------------------------------------------===// +def Xtensa_call: SDNode<"XtensaISD::CALL", SDT_XtensaCall, + [SDNPHasChain, SDNPOutGlue, SDNPOptInGlue, SDNPVariadic]>; + +def Xtensa_ret: SDNode<"XtensaISD::RET", SDTNone, + [SDNPHasChain, SDNPOptInGlue, SDNPVariadic]>; + +def Xtensa_pcrel_wrapper: SDNode<"XtensaISD::PCREL_WRAPPER", SDT_XtensaWrapPtr, []>; + +def Xtensa_callseq_start: SDNode<"ISD::CALLSEQ_START", SDT_XtensaCallSeqStart, + [SDNPHasChain, SDNPSideEffect, SDNPOutGlue]>; + +def Xtensa_callseq_end : SDNode<"ISD::CALLSEQ_END", SDT_XtensaCallSeqEnd, + [SDNPHasChain, SDNPSideEffect, SDNPOptInGlue, + SDNPOutGlue]>; diff --git a/llvm/lib/Target/Xtensa/XtensaRegisterInfo.cpp b/llvm/lib/Target/Xtensa/XtensaRegisterInfo.cpp index f749cc51f96a04ebe222924ce697e73bcf1de601..bced2d4ad0095b43a61daa9302154014cb77f287 100644 --- a/llvm/lib/Target/Xtensa/XtensaRegisterInfo.cpp +++ b/llvm/lib/Target/Xtensa/XtensaRegisterInfo.cpp @@ -13,6 +13,9 @@ #include "XtensaRegisterInfo.h" #include "XtensaInstrInfo.h" #include "XtensaSubtarget.h" +#include "XtensaUtils.h" +#include "llvm/CodeGen/MachineFrameInfo.h" +#include "llvm/CodeGen/MachineFunction.h" #include "llvm/CodeGen/MachineInstrBuilder.h" #include "llvm/CodeGen/MachineRegisterInfo.h" #include "llvm/Support/Debug.h" @@ -31,15 +34,13 @@ XtensaRegisterInfo::XtensaRegisterInfo(const XtensaSubtarget &STI) const uint16_t * XtensaRegisterInfo::getCalleeSavedRegs(const MachineFunction *MF) const { - // Calling convention is not implemented yet - return nullptr; + return CSR_Xtensa_SaveList; } const uint32_t * XtensaRegisterInfo::getCallPreservedMask(const MachineFunction &MF, CallingConv::ID) const { - // Calling convention is not implemented yet - return nullptr; + return CSR_Xtensa_RegMask; } BitVector XtensaRegisterInfo::getReservedRegs(const MachineFunction &MF) const { @@ -60,7 +61,70 @@ BitVector XtensaRegisterInfo::getReservedRegs(const MachineFunction &MF) const { bool XtensaRegisterInfo::eliminateFrameIndex(MachineBasicBlock::iterator II, int SPAdj, unsigned FIOperandNum, RegScavenger *RS) const { - report_fatal_error("Eliminate frame index not supported yet"); + MachineInstr &MI = *II; + MachineFunction &MF = *MI.getParent()->getParent(); + int FrameIndex = MI.getOperand(FIOperandNum).getIndex(); + uint64_t StackSize = MF.getFrameInfo().getStackSize(); + int64_t SPOffset = MF.getFrameInfo().getObjectOffset(FrameIndex); + MachineFrameInfo &MFI = MF.getFrameInfo(); + const std::vector &CSI = MFI.getCalleeSavedInfo(); + int MinCSFI = 0; + int MaxCSFI = -1; + + if (CSI.size()) { + MinCSFI = CSI[0].getFrameIdx(); + MaxCSFI = CSI[CSI.size() - 1].getFrameIdx(); + } + // The following stack frame objects are always referenced relative to $sp: + // 1. Outgoing arguments. + // 2. Pointer to dynamically allocated stack space. + // 3. Locations for callee-saved registers. + // 4. Locations for eh data registers. + // Everything else is referenced relative to whatever register + // getFrameRegister() returns. + unsigned FrameReg; + if ((FrameIndex >= MinCSFI && FrameIndex <= MaxCSFI)) + FrameReg = Xtensa::SP; + else + FrameReg = getFrameRegister(MF); + + // Calculate final offset. + // - There is no need to change the offset if the frame object is one of the + // following: an outgoing argument, pointer to a dynamically allocated + // stack space or a $gp restore location, + // - If the frame object is any of the following, its offset must be adjusted + // by adding the size of the stack: + // incoming argument, callee-saved register location or local variable. + bool IsKill = false; + int64_t Offset = + SPOffset + (int64_t)StackSize + MI.getOperand(FIOperandNum + 1).getImm(); + + bool Valid = isValidAddrOffset(MI, Offset); + + // If MI is not a debug value, make sure Offset fits in the 16-bit immediate + // field. + if (!MI.isDebugValue() && !Valid) { + MachineBasicBlock &MBB = *MI.getParent(); + DebugLoc DL = II->getDebugLoc(); + unsigned ADD = Xtensa::ADD; + unsigned Reg; + const XtensaInstrInfo &TII = *static_cast( + MBB.getParent()->getSubtarget().getInstrInfo()); + + TII.loadImmediate(MBB, II, &Reg, Offset); + BuildMI(MBB, II, DL, TII.get(ADD), Reg) + .addReg(FrameReg) + .addReg(Reg, RegState::Kill); + + FrameReg = Reg; + Offset = 0; + IsKill = true; + } + + MI.getOperand(FIOperandNum).ChangeToRegister(FrameReg, false, false, IsKill); + MI.getOperand(FIOperandNum + 1).ChangeToImmediate(Offset); + + return false; } Register XtensaRegisterInfo::getFrameRegister(const MachineFunction &MF) const { diff --git a/llvm/lib/Target/Xtensa/XtensaUtils.cpp b/llvm/lib/Target/Xtensa/XtensaUtils.cpp new file mode 100644 index 0000000000000000000000000000000000000000..98e424f6ea4406e3c8340a3bf7aa27e396244e76 --- /dev/null +++ b/llvm/lib/Target/Xtensa/XtensaUtils.cpp @@ -0,0 +1,59 @@ +//===--- XtensaUtils.cpp ---- Xtensa Utility Functions ----------*- C++ -*-===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// +// +// This file contains miscellaneous utility functions. +// +//===----------------------------------------------------------------------===// + +#include "XtensaUtils.h" + +namespace llvm { + +bool isValidAddrOffset(int Scale, int64_t OffsetVal) { + bool Valid = false; + + switch (Scale) { + case 1: + Valid = (OffsetVal >= 0 && OffsetVal <= 255); + break; + case 2: + Valid = (OffsetVal >= 0 && OffsetVal <= 510) && ((OffsetVal & 0x1) == 0); + break; + case 4: + Valid = (OffsetVal >= 0 && OffsetVal <= 1020) && ((OffsetVal & 0x3) == 0); + break; + default: + break; + } + return Valid; +} + +bool isValidAddrOffset(MachineInstr &MI, int64_t Offset) { + int Scale = 0; + + switch (MI.getOpcode()) { + case Xtensa::L8UI: + case Xtensa::S8I: + Scale = 1; + break; + case Xtensa::L16SI: + case Xtensa::L16UI: + case Xtensa::S16I: + Scale = 2; + break; + case Xtensa::LEA_ADD: + return (Offset >= -128 && Offset <= 127); + default: + // assume that MI is 32-bit load/store operation + Scale = 4; + break; + } + return isValidAddrOffset(Scale, Offset); +} + +} // namespace llvm diff --git a/llvm/lib/Target/Xtensa/XtensaUtils.h b/llvm/lib/Target/Xtensa/XtensaUtils.h new file mode 100644 index 0000000000000000000000000000000000000000..2b0ac37a6971a1fe77ad9dc9026ab45843a0b508 --- /dev/null +++ b/llvm/lib/Target/Xtensa/XtensaUtils.h @@ -0,0 +1,27 @@ +//===--- XtensaUtils.h ---- Xtensa Utility Functions ------------*- C++ -*-===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// +// +// This file contains miscellaneous utility functions. +// +//===----------------------------------------------------------------------===// + +#ifndef LLVM_LIB_TARGET_XTENSA_XTENSAUTILS_H +#define LLVM_LIB_TARGET_XTENSA_XTENSAUTILS_H + +#include "XtensaInstrInfo.h" +#include "llvm/CodeGen/MachineInstr.h" + +namespace llvm { +// Check address offset for load/store instructions. +// The offset should be multiple of scale. +bool isValidAddrOffset(int Scale, int64_t OffsetVal); + +// Check address offset for load/store instructions. +bool isValidAddrOffset(MachineInstr &MI, int64_t Offset); +} // namespace llvm +#endif // LLVM_LIB_TARGET_XTENSA_XTENSAUTILS_H diff --git a/llvm/lib/TargetParser/CMakeLists.txt b/llvm/lib/TargetParser/CMakeLists.txt index da1e352b0373387ab738f5b300d66eab088cd402..4b5d582d57a42a566dc6ec89419efc1460e8cb05 100644 --- a/llvm/lib/TargetParser/CMakeLists.txt +++ b/llvm/lib/TargetParser/CMakeLists.txt @@ -20,6 +20,7 @@ add_llvm_component_library(LLVMTargetParser CSKYTargetParser.cpp Host.cpp LoongArchTargetParser.cpp + RISCVISAInfo.cpp RISCVTargetParser.cpp SubtargetFeature.cpp TargetParser.cpp @@ -37,5 +38,7 @@ add_llvm_component_library(LLVMTargetParser Support DEPENDS + ARMTargetParserTableGen + AArch64TargetParserTableGen RISCVTargetParserTableGen ) diff --git a/llvm/lib/TargetParser/Host.cpp b/llvm/lib/TargetParser/Host.cpp index d2c9bae97364e9f7eb1f2b35ec38d9872ead8abe..0a93b06f40c2486e9f7e6adb087f0f8b8b0058f6 100644 --- a/llvm/lib/TargetParser/Host.cpp +++ b/llvm/lib/TargetParser/Host.cpp @@ -245,8 +245,11 @@ StringRef sys::detail::getHostCPUNameForARM(StringRef ProcCpuinfoContent) { .Case("0xd4a", "neoverse-e1") .Case("0xd0c", "neoverse-n1") .Case("0xd49", "neoverse-n2") + .Case("0xd8e", "neoverse-n3") .Case("0xd40", "neoverse-v1") .Case("0xd4f", "neoverse-v2") + .Case("0xd84", "neoverse-v3") + .Case("0xd83", "neoverse-v3ae") .Default("generic"); } diff --git a/llvm/lib/Support/RISCVISAInfo.cpp b/llvm/lib/TargetParser/RISCVISAInfo.cpp similarity index 73% rename from llvm/lib/Support/RISCVISAInfo.cpp rename to llvm/lib/TargetParser/RISCVISAInfo.cpp index fa967403ea449c9cba9bc4ca4a26460d9f9f8a74..ea0b56b9a1339b51280223410d3eb4602a144edf 100644 --- a/llvm/lib/Support/RISCVISAInfo.cpp +++ b/llvm/lib/TargetParser/RISCVISAInfo.cpp @@ -1,4 +1,4 @@ -//===-- RISCVISAInfo.cpp - RISC-V Arch String Parser ------------*- C++ -*-===// +//===-- RISCVISAInfo.cpp - RISC-V Arch String Parser ----------------------===// // // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. // See https://llvm.org/LICENSE.txt for license information. @@ -6,7 +6,7 @@ // //===----------------------------------------------------------------------===// -#include "llvm/Support/RISCVISAInfo.h" +#include "llvm/TargetParser/RISCVISAInfo.h" #include "llvm/ADT/MapVector.h" #include "llvm/ADT/STLExtras.h" #include "llvm/ADT/SetVector.h" @@ -29,7 +29,7 @@ namespace { struct RISCVSupportedExtension { const char *Name; /// Supported version. - RISCVISAInfo::ExtensionVersion Version; + RISCVISAUtils::ExtensionVersion Version; bool operator<(const RISCVSupportedExtension &RHS) const { return StringRef(Name) < StringRef(RHS.Name); @@ -43,210 +43,12 @@ struct RISCVProfile { } // end anonymous namespace -static constexpr StringLiteral AllStdExts = "mafdqlcbkjtpvnh"; - static const char *RISCVGImplications[] = { "i", "m", "a", "f", "d", "zicsr", "zifencei" }; -// NOTE: This table should be sorted alphabetically by extension name. -static const RISCVSupportedExtension SupportedExtensions[] = { - {"a", {2, 1}}, - {"c", {2, 0}}, - {"d", {2, 2}}, - {"e", {2, 0}}, - {"f", {2, 2}}, - {"h", {1, 0}}, - {"i", {2, 1}}, - {"m", {2, 0}}, - - {"shcounterenw", {1, 0}}, - {"shgatpa", {1, 0}}, - {"shtvala", {1, 0}}, - {"shvsatpa", {1, 0}}, - {"shvstvala", {1, 0}}, - {"shvstvecd", {1, 0}}, - {"smaia", {1, 0}}, - {"smepmp", {1, 0}}, - {"ssaia", {1, 0}}, - {"ssccptr", {1, 0}}, - {"sscofpmf", {1, 0}}, - {"sscounterenw", {1, 0}}, - {"ssstateen", {1, 0}}, - {"ssstrict", {1, 0}}, - {"sstc", {1, 0}}, - {"sstvala", {1, 0}}, - {"sstvecd", {1, 0}}, - {"ssu64xl", {1, 0}}, - {"svade", {1, 0}}, - {"svadu", {1, 0}}, - {"svbare", {1, 0}}, - {"svinval", {1, 0}}, - {"svnapot", {1, 0}}, - {"svpbmt", {1, 0}}, - - {"v", {1, 0}}, - - // vendor-defined ('X') extensions - {"xcvalu", {1, 0}}, - {"xcvbi", {1, 0}}, - {"xcvbitmanip", {1, 0}}, - {"xcvelw", {1, 0}}, - {"xcvmac", {1, 0}}, - {"xcvmem", {1, 0}}, - {"xcvsimd", {1, 0}}, - {"xsfcease", {1, 0}}, - {"xsfvcp", {1, 0}}, - {"xsfvfnrclipxfqf", {1, 0}}, - {"xsfvfwmaccqqq", {1, 0}}, - {"xsfvqmaccdod", {1, 0}}, - {"xsfvqmaccqoq", {1, 0}}, - {"xsifivecdiscarddlone", {1, 0}}, - {"xsifivecflushdlone", {1, 0}}, - {"xtheadba", {1, 0}}, - {"xtheadbb", {1, 0}}, - {"xtheadbs", {1, 0}}, - {"xtheadcmo", {1, 0}}, - {"xtheadcondmov", {1, 0}}, - {"xtheadfmemidx", {1, 0}}, - {"xtheadmac", {1, 0}}, - {"xtheadmemidx", {1, 0}}, - {"xtheadmempair", {1, 0}}, - {"xtheadsync", {1, 0}}, - {"xtheadvdot", {1, 0}}, - {"xventanacondops", {1, 0}}, - - {"za128rs", {1, 0}}, - {"za64rs", {1, 0}}, - {"zacas", {1, 0}}, - {"zama16b", {1, 0}}, - {"zawrs", {1, 0}}, - - {"zba", {1, 0}}, - {"zbb", {1, 0}}, - {"zbc", {1, 0}}, - {"zbkb", {1, 0}}, - {"zbkc", {1, 0}}, - {"zbkx", {1, 0}}, - {"zbs", {1, 0}}, - - {"zca", {1, 0}}, - {"zcb", {1, 0}}, - {"zcd", {1, 0}}, - {"zce", {1, 0}}, - {"zcf", {1, 0}}, - {"zcmop", {1, 0}}, - {"zcmp", {1, 0}}, - {"zcmt", {1, 0}}, - - {"zdinx", {1, 0}}, - - {"zfa", {1, 0}}, - {"zfh", {1, 0}}, - {"zfhmin", {1, 0}}, - {"zfinx", {1, 0}}, - - {"zhinx", {1, 0}}, - {"zhinxmin", {1, 0}}, - - {"zic64b", {1, 0}}, - {"zicbom", {1, 0}}, - {"zicbop", {1, 0}}, - {"zicboz", {1, 0}}, - {"ziccamoa", {1, 0}}, - {"ziccif", {1, 0}}, - {"zicclsm", {1, 0}}, - {"ziccrse", {1, 0}}, - {"zicntr", {2, 0}}, - {"zicond", {1, 0}}, - {"zicsr", {2, 0}}, - {"zifencei", {2, 0}}, - {"zihintntl", {1, 0}}, - {"zihintpause", {2, 0}}, - {"zihpm", {2, 0}}, - {"zimop", {1, 0}}, - - {"zk", {1, 0}}, - {"zkn", {1, 0}}, - {"zknd", {1, 0}}, - {"zkne", {1, 0}}, - {"zknh", {1, 0}}, - {"zkr", {1, 0}}, - {"zks", {1, 0}}, - {"zksed", {1, 0}}, - {"zksh", {1, 0}}, - {"zkt", {1, 0}}, - - {"zmmul", {1, 0}}, - - {"zvbb", {1, 0}}, - {"zvbc", {1, 0}}, - - {"zve32f", {1, 0}}, - {"zve32x", {1, 0}}, - {"zve64d", {1, 0}}, - {"zve64f", {1, 0}}, - {"zve64x", {1, 0}}, - - {"zvfh", {1, 0}}, - {"zvfhmin", {1, 0}}, - - // vector crypto - {"zvkb", {1, 0}}, - {"zvkg", {1, 0}}, - {"zvkn", {1, 0}}, - {"zvknc", {1, 0}}, - {"zvkned", {1, 0}}, - {"zvkng", {1, 0}}, - {"zvknha", {1, 0}}, - {"zvknhb", {1, 0}}, - {"zvks", {1, 0}}, - {"zvksc", {1, 0}}, - {"zvksed", {1, 0}}, - {"zvksg", {1, 0}}, - {"zvksh", {1, 0}}, - {"zvkt", {1, 0}}, - - {"zvl1024b", {1, 0}}, - {"zvl128b", {1, 0}}, - {"zvl16384b", {1, 0}}, - {"zvl2048b", {1, 0}}, - {"zvl256b", {1, 0}}, - {"zvl32768b", {1, 0}}, - {"zvl32b", {1, 0}}, - {"zvl4096b", {1, 0}}, - {"zvl512b", {1, 0}}, - {"zvl64b", {1, 0}}, - {"zvl65536b", {1, 0}}, - {"zvl8192b", {1, 0}}, -}; - -// NOTE: This table should be sorted alphabetically by extension name. -// clang-format off -static const RISCVSupportedExtension SupportedExperimentalExtensions[] = { - {"smmpm", {0, 8}}, - {"smnpm", {0, 8}}, - {"ssnpm", {0, 8}}, - {"sspm", {0, 8}}, - {"ssqosid", {1, 0}}, - {"supm", {0, 8}}, - - {"zaamo", {0, 2}}, - {"zabha", {1, 0}}, - {"zalasr", {0, 1}}, - {"zalrsc", {0, 2}}, - - {"zfbfmin", {1, 0}}, - - {"zicfilp", {0, 4}}, - {"zicfiss", {0, 4}}, - - {"ztso", {0, 1}}, - - {"zvfbfmin", {1, 0}}, - {"zvfbfwma", {1, 0}}, -}; -// clang-format on +#define GET_SUPPORTED_EXTENSIONS +#include "llvm/TargetParser/RISCVTargetParserDef.inc" static constexpr RISCVProfile SupportedProfiles[] = { {"rvi20u32", "rv32i"}, @@ -370,7 +172,7 @@ struct LessExtName { }; } // namespace -static std::optional +static std::optional findDefaultVersion(StringRef ExtName) { // Find default version of an extension. // TODO: We might set default version based on profile or ISA spec. @@ -387,7 +189,7 @@ findDefaultVersion(StringRef ExtName) { } void RISCVISAInfo::addExtension(StringRef ExtName, - RISCVISAInfo::ExtensionVersion Version) { + RISCVISAUtils::ExtensionVersion Version) { Exts[ExtName.str()] = Version; } @@ -411,7 +213,7 @@ static StringRef getExtensionType(StringRef Ext) { return StringRef(); } -static std::optional +static std::optional isExperimentalExtension(StringRef Ext) { auto I = llvm::lower_bound(SupportedExperimentalExtensions, Ext, LessExtName()); @@ -468,78 +270,6 @@ bool RISCVISAInfo::hasExtension(StringRef Ext) const { return Exts.count(Ext.str()) != 0; } -// We rank extensions in the following order: -// -Single letter extensions in canonical order. -// -Unknown single letter extensions in alphabetical order. -// -Multi-letter extensions starting with 'z' sorted by canonical order of -// the second letter then sorted alphabetically. -// -Multi-letter extensions starting with 's' in alphabetical order. -// -(TODO) Multi-letter extensions starting with 'zxm' in alphabetical order. -// -X extensions in alphabetical order. -// These flags are used to indicate the category. The first 6 bits store the -// single letter extension rank for single letter and multi-letter extensions -// starting with 'z'. -enum RankFlags { - RF_Z_EXTENSION = 1 << 6, - RF_S_EXTENSION = 1 << 7, - RF_X_EXTENSION = 1 << 8, -}; - -// Get the rank for single-letter extension, lower value meaning higher -// priority. -static unsigned singleLetterExtensionRank(char Ext) { - assert(Ext >= 'a' && Ext <= 'z'); - switch (Ext) { - case 'i': - return 0; - case 'e': - return 1; - } - - size_t Pos = AllStdExts.find(Ext); - if (Pos != StringRef::npos) - return Pos + 2; // Skip 'e' and 'i' from above. - - // If we got an unknown extension letter, then give it an alphabetical - // order, but after all known standard extensions. - return 2 + AllStdExts.size() + (Ext - 'a'); -} - -// Get the rank for multi-letter extension, lower value meaning higher -// priority/order in canonical order. -static unsigned getExtensionRank(const std::string &ExtName) { - assert(ExtName.size() >= 1); - switch (ExtName[0]) { - case 's': - return RF_S_EXTENSION; - case 'z': - assert(ExtName.size() >= 2); - // `z` extension must be sorted by canonical order of second letter. - // e.g. zmx has higher rank than zax. - return RF_Z_EXTENSION | singleLetterExtensionRank(ExtName[1]); - case 'x': - return RF_X_EXTENSION; - default: - assert(ExtName.size() == 1); - return singleLetterExtensionRank(ExtName[0]); - } -} - -// Compare function for extension. -// Only compare the extension name, ignore version comparison. -bool RISCVISAInfo::compareExtension(const std::string &LHS, - const std::string &RHS) { - unsigned LHSRank = getExtensionRank(LHS); - unsigned RHSRank = getExtensionRank(RHS); - - // If the ranks differ, pick the lower rank. - if (LHSRank != RHSRank) - return LHSRank < RHSRank; - - // If the rank is same, it must be sorted by lexicographic order. - return LHS < RHS; -} - std::vector RISCVISAInfo::toFeatures(bool AddAllExtensions, bool IgnoreUnknown) const { std::vector Features; @@ -808,7 +538,7 @@ static Error splitExtsByUnderscore(StringRef Exts, static Error processMultiLetterExtension( StringRef RawExt, - MapVector> &SeenExtMap, bool IgnoreUnknown, bool EnableExperimentalExtension, bool ExperimentalExtensionVersionCheck) { @@ -854,7 +584,7 @@ static Error processMultiLetterExtension( static Error processSingleLetterExtension( StringRef &RawExt, - MapVector> &SeenExtMap, bool IgnoreUnknown, bool EnableExperimentalExtension, bool ExperimentalExtensionVersionCheck) { @@ -930,7 +660,7 @@ RISCVISAInfo::parseArchString(StringRef Arch, bool EnableExperimentalExtension, unsigned XLen = HasRV64 ? 64 : 32; std::unique_ptr ISAInfo(new RISCVISAInfo(XLen)); - MapVector> SeenExtMap; @@ -1007,7 +737,7 @@ RISCVISAInfo::parseArchString(StringRef Arch, bool EnableExperimentalExtension, for (auto &Ext : SplitExts) { StringRef CurrExt = Ext; while (!CurrExt.empty()) { - if (AllStdExts.contains(CurrExt.front())) { + if (RISCVISAUtils::AllStdExts.contains(CurrExt.front())) { if (auto E = processSingleLetterExtension( CurrExt, SeenExtMap, IgnoreUnknown, EnableExperimentalExtension, ExperimentalExtensionVersionCheck)) @@ -1041,7 +771,7 @@ RISCVISAInfo::parseArchString(StringRef Arch, bool EnableExperimentalExtension, // Check all Extensions are supported. for (auto &SeenExtAndVers : SeenExtMap) { const std::string &ExtName = SeenExtAndVers.first; - RISCVISAInfo::ExtensionVersion ExtVers = SeenExtAndVers.second; + RISCVISAUtils::ExtensionVersion ExtVers = SeenExtAndVers.second; if (!RISCVISAInfo::isSupportedExtension(ExtName)) return getStringErrorForInvalidExt(ExtName); @@ -1102,71 +832,19 @@ Error RISCVISAInfo::checkDependency() { return createStringError(errc::invalid_argument, "'zcf' is only supported for 'rv32'"); + if (Exts.count("zacas") && !(Exts.count("a") || Exts.count("zamo"))) + return createStringError( + errc::invalid_argument, + "'zacas' requires 'a' or 'zaamo' extension to also be specified"); + + if (Exts.count("zabha") && !(Exts.count("a") || Exts.count("zamo"))) + return createStringError( + errc::invalid_argument, + "'zabha' requires 'a' or 'zaamo' extension to also be specified"); + return Error::success(); } -static const char *ImpliedExtsD[] = {"f"}; -static const char *ImpliedExtsF[] = {"zicsr"}; -static const char *ImpliedExtsV[] = {"zvl128b", "zve64d"}; -static const char *ImpliedExtsXTHeadVdot[] = {"v"}; -static const char *ImpliedExtsXSfvcp[] = {"zve32x"}; -static const char *ImpliedExtsXSfvfnrclipxfqf[] = {"zve32f"}; -static const char *ImpliedExtsXSfvfwmaccqqq[] = {"zvfbfmin"}; -static const char *ImpliedExtsXSfvqmaccdod[] = {"zve32x"}; -static const char *ImpliedExtsXSfvqmaccqoq[] = {"zve32x"}; -static const char *ImpliedExtsZabha[] = {"a"}; -static const char *ImpliedExtsZacas[] = {"a"}; -static const char *ImpliedExtsZcb[] = {"zca"}; -static const char *ImpliedExtsZcd[] = {"d", "zca"}; -static const char *ImpliedExtsZce[] = {"zcb", "zcmp", "zcmt"}; -static const char *ImpliedExtsZcf[] = {"f", "zca"}; -static const char *ImpliedExtsZcmop[] = {"zca"}; -static const char *ImpliedExtsZcmp[] = {"zca"}; -static const char *ImpliedExtsZcmt[] = {"zca", "zicsr"}; -static const char *ImpliedExtsZdinx[] = {"zfinx"}; -static const char *ImpliedExtsZfa[] = {"f"}; -static const char *ImpliedExtsZfbfmin[] = {"f"}; -static const char *ImpliedExtsZfh[] = {"zfhmin"}; -static const char *ImpliedExtsZfhmin[] = {"f"}; -static const char *ImpliedExtsZfinx[] = {"zicsr"}; -static const char *ImpliedExtsZhinx[] = {"zhinxmin"}; -static const char *ImpliedExtsZhinxmin[] = {"zfinx"}; -static const char *ImpliedExtsZicntr[] = {"zicsr"}; -static const char *ImpliedExtsZicfiss[] = {"zicsr", "zimop"}; -static const char *ImpliedExtsZihpm[] = {"zicsr"}; -static const char *ImpliedExtsZk[] = {"zkn", "zkt", "zkr"}; -static const char *ImpliedExtsZkn[] = {"zbkb", "zbkc", "zbkx", - "zkne", "zknd", "zknh"}; -static const char *ImpliedExtsZks[] = {"zbkb", "zbkc", "zbkx", "zksed", "zksh"}; -static const char *ImpliedExtsZvbb[] = {"zvkb"}; -static const char *ImpliedExtsZve32f[] = {"zve32x", "f"}; -static const char *ImpliedExtsZve32x[] = {"zvl32b", "zicsr"}; -static const char *ImpliedExtsZve64d[] = {"zve64f", "d"}; -static const char *ImpliedExtsZve64f[] = {"zve64x", "zve32f"}; -static const char *ImpliedExtsZve64x[] = {"zve32x", "zvl64b"}; -static const char *ImpliedExtsZvfbfmin[] = {"zve32f"}; -static const char *ImpliedExtsZvfbfwma[] = {"zvfbfmin", "zfbfmin"}; -static const char *ImpliedExtsZvfh[] = {"zvfhmin", "zfhmin"}; -static const char *ImpliedExtsZvfhmin[] = {"zve32f"}; -static const char *ImpliedExtsZvkn[] = {"zvkb", "zvkned", "zvknhb", "zvkt"}; -static const char *ImpliedExtsZvknc[] = {"zvbc", "zvkn"}; -static const char *ImpliedExtsZvkng[] = {"zvkg", "zvkn"}; -static const char *ImpliedExtsZvknhb[] = {"zve64x"}; -static const char *ImpliedExtsZvks[] = {"zvkb", "zvksed", "zvksh", "zvkt"}; -static const char *ImpliedExtsZvksc[] = {"zvbc", "zvks"}; -static const char *ImpliedExtsZvksg[] = {"zvkg", "zvks"}; -static const char *ImpliedExtsZvl1024b[] = {"zvl512b"}; -static const char *ImpliedExtsZvl128b[] = {"zvl64b"}; -static const char *ImpliedExtsZvl16384b[] = {"zvl8192b"}; -static const char *ImpliedExtsZvl2048b[] = {"zvl1024b"}; -static const char *ImpliedExtsZvl256b[] = {"zvl128b"}; -static const char *ImpliedExtsZvl32768b[] = {"zvl16384b"}; -static const char *ImpliedExtsZvl4096b[] = {"zvl2048b"}; -static const char *ImpliedExtsZvl512b[] = {"zvl256b"}; -static const char *ImpliedExtsZvl64b[] = {"zvl32b"}; -static const char *ImpliedExtsZvl65536b[] = {"zvl32768b"}; -static const char *ImpliedExtsZvl8192b[] = {"zvl4096b"}; - struct ImpliedExtsEntry { StringLiteral Name; ArrayRef Exts; @@ -1178,69 +856,8 @@ struct ImpliedExtsEntry { bool operator<(StringRef Other) const { return Name < Other; } }; -// Note: The table needs to be sorted by name. -static constexpr ImpliedExtsEntry ImpliedExts[] = { - {{"d"}, {ImpliedExtsD}}, - {{"f"}, {ImpliedExtsF}}, - {{"v"}, {ImpliedExtsV}}, - {{"xsfvcp"}, {ImpliedExtsXSfvcp}}, - {{"xsfvfnrclipxfqf"}, {ImpliedExtsXSfvfnrclipxfqf}}, - {{"xsfvfwmaccqqq"}, {ImpliedExtsXSfvfwmaccqqq}}, - {{"xsfvqmaccdod"}, {ImpliedExtsXSfvqmaccdod}}, - {{"xsfvqmaccqoq"}, {ImpliedExtsXSfvqmaccqoq}}, - {{"xtheadvdot"}, {ImpliedExtsXTHeadVdot}}, - {{"zabha"}, {ImpliedExtsZabha}}, - {{"zacas"}, {ImpliedExtsZacas}}, - {{"zcb"}, {ImpliedExtsZcb}}, - {{"zcd"}, {ImpliedExtsZcd}}, - {{"zce"}, {ImpliedExtsZce}}, - {{"zcf"}, {ImpliedExtsZcf}}, - {{"zcmop"}, {ImpliedExtsZcmop}}, - {{"zcmp"}, {ImpliedExtsZcmp}}, - {{"zcmt"}, {ImpliedExtsZcmt}}, - {{"zdinx"}, {ImpliedExtsZdinx}}, - {{"zfa"}, {ImpliedExtsZfa}}, - {{"zfbfmin"}, {ImpliedExtsZfbfmin}}, - {{"zfh"}, {ImpliedExtsZfh}}, - {{"zfhmin"}, {ImpliedExtsZfhmin}}, - {{"zfinx"}, {ImpliedExtsZfinx}}, - {{"zhinx"}, {ImpliedExtsZhinx}}, - {{"zhinxmin"}, {ImpliedExtsZhinxmin}}, - {{"zicfiss"}, {ImpliedExtsZicfiss}}, - {{"zicntr"}, {ImpliedExtsZicntr}}, - {{"zihpm"}, {ImpliedExtsZihpm}}, - {{"zk"}, {ImpliedExtsZk}}, - {{"zkn"}, {ImpliedExtsZkn}}, - {{"zks"}, {ImpliedExtsZks}}, - {{"zvbb"}, {ImpliedExtsZvbb}}, - {{"zve32f"}, {ImpliedExtsZve32f}}, - {{"zve32x"}, {ImpliedExtsZve32x}}, - {{"zve64d"}, {ImpliedExtsZve64d}}, - {{"zve64f"}, {ImpliedExtsZve64f}}, - {{"zve64x"}, {ImpliedExtsZve64x}}, - {{"zvfbfmin"}, {ImpliedExtsZvfbfmin}}, - {{"zvfbfwma"}, {ImpliedExtsZvfbfwma}}, - {{"zvfh"}, {ImpliedExtsZvfh}}, - {{"zvfhmin"}, {ImpliedExtsZvfhmin}}, - {{"zvkn"}, {ImpliedExtsZvkn}}, - {{"zvknc"}, {ImpliedExtsZvknc}}, - {{"zvkng"}, {ImpliedExtsZvkng}}, - {{"zvknhb"}, {ImpliedExtsZvknhb}}, - {{"zvks"}, {ImpliedExtsZvks}}, - {{"zvksc"}, {ImpliedExtsZvksc}}, - {{"zvksg"}, {ImpliedExtsZvksg}}, - {{"zvl1024b"}, {ImpliedExtsZvl1024b}}, - {{"zvl128b"}, {ImpliedExtsZvl128b}}, - {{"zvl16384b"}, {ImpliedExtsZvl16384b}}, - {{"zvl2048b"}, {ImpliedExtsZvl2048b}}, - {{"zvl256b"}, {ImpliedExtsZvl256b}}, - {{"zvl32768b"}, {ImpliedExtsZvl32768b}}, - {{"zvl4096b"}, {ImpliedExtsZvl4096b}}, - {{"zvl512b"}, {ImpliedExtsZvl512b}}, - {{"zvl64b"}, {ImpliedExtsZvl64b}}, - {{"zvl65536b"}, {ImpliedExtsZvl65536b}}, - {{"zvl8192b"}, {ImpliedExtsZvl8192b}}, -}; +#define GET_IMPLIED_EXTENSIONS +#include "llvm/TargetParser/RISCVTargetParserDef.inc" void RISCVISAInfo::updateImplication() { bool HasE = Exts.count("e") != 0; diff --git a/llvm/lib/TargetParser/RISCVTargetParser.cpp b/llvm/lib/TargetParser/RISCVTargetParser.cpp index 0d95e3a9b8196293df4cd64b46c9f18c62d3bb22..9003f9beffa7e7a19fb690f2367573d180efd051 100644 --- a/llvm/lib/TargetParser/RISCVTargetParser.cpp +++ b/llvm/lib/TargetParser/RISCVTargetParser.cpp @@ -14,7 +14,7 @@ #include "llvm/TargetParser/RISCVTargetParser.h" #include "llvm/ADT/SmallVector.h" #include "llvm/ADT/StringSwitch.h" -#include "llvm/Support/RISCVISAInfo.h" +#include "llvm/TargetParser/RISCVISAInfo.h" #include "llvm/TargetParser/Triple.h" namespace llvm { diff --git a/llvm/lib/Transforms/Coroutines/CoroInstr.h b/llvm/lib/Transforms/Coroutines/CoroInstr.h index 79e745bb162cdb23c4fa9db751b2fb7802a138ae..a31703fe01304c9311383d0f1bb4b4247f595892 100644 --- a/llvm/lib/Transforms/Coroutines/CoroInstr.h +++ b/llvm/lib/Transforms/Coroutines/CoroInstr.h @@ -78,10 +78,10 @@ public: } }; -/// This represents the llvm.coro.await.suspend instruction. +/// This represents the llvm.coro.await.suspend.{void,bool,handle} instructions. // FIXME: add callback metadata // FIXME: make a proper IntrinisicInst. Currently this is not possible, -// because llvm.coro.await.suspend can be invoked. +// because llvm.coro.await.suspend.* can be invoked. class LLVM_LIBRARY_VISIBILITY CoroAwaitSuspendInst : public CallBase { enum { AwaiterArg, FrameArg, WrapperArg }; diff --git a/llvm/lib/Transforms/IPO/SCCP.cpp b/llvm/lib/Transforms/IPO/SCCP.cpp index f8920541e6fd640ecd7a0cdbd8460c9b0699943e..e591a8e73b1c6feb0c38d0a25fc848ce17ed971c 100644 --- a/llvm/lib/Transforms/IPO/SCCP.cpp +++ b/llvm/lib/Transforms/IPO/SCCP.cpp @@ -281,32 +281,21 @@ static bool runIPSCCP( Function *F = I.first; const ValueLatticeElement &ReturnValue = I.second; - // If there is a known constant range for the return value, add !range - // metadata to the function's call sites. + // If there is a known constant range for the return value, add range + // attribute to the return value. if (ReturnValue.isConstantRange() && !ReturnValue.getConstantRange().isSingleElement()) { // Do not add range metadata if the return value may include undef. if (ReturnValue.isConstantRangeIncludingUndef()) continue; + // Do not touch existing attribute for now. + // TODO: We should be able to take the intersection of the existing + // attribute and the inferred range. + if (F->hasRetAttribute(Attribute::Range)) + continue; auto &CR = ReturnValue.getConstantRange(); - for (User *User : F->users()) { - auto *CB = dyn_cast(User); - if (!CB || CB->getCalledFunction() != F) - continue; - - // Do not touch existing metadata for now. - // TODO: We should be able to take the intersection of the existing - // metadata and the inferred range. - if (CB->getMetadata(LLVMContext::MD_range)) - continue; - - LLVMContext &Context = CB->getParent()->getContext(); - Metadata *RangeMD[] = { - ConstantAsMetadata::get(ConstantInt::get(Context, CR.getLower())), - ConstantAsMetadata::get(ConstantInt::get(Context, CR.getUpper()))}; - CB->setMetadata(LLVMContext::MD_range, MDNode::get(Context, RangeMD)); - } + F->addRangeRetAttr(CR); continue; } if (F->getReturnType()->isVoidTy()) diff --git a/llvm/lib/Transforms/InstCombine/InstCombineAddSub.cpp b/llvm/lib/Transforms/InstCombine/InstCombineAddSub.cpp index fc284bc61cce97c3a5f5eebb1bffb072fb95dadc..51ac77348ed9e34a85b3c03acf9841a786bbde88 100644 --- a/llvm/lib/Transforms/InstCombine/InstCombineAddSub.cpp +++ b/llvm/lib/Transforms/InstCombine/InstCombineAddSub.cpp @@ -1134,6 +1134,8 @@ static bool MulWillOverflow(APInt &C0, APInt &C1, bool IsSigned) { // Simplifies X % C0 + (( X / C0 ) % C1) * C0 to X % (C0 * C1), where (C0 * C1) // does not overflow. +// Simplifies (X / C0) * C1 + (X % C0) * C2 to +// (X / C0) * (C1 - C2 * C0) + X * C2 Value *InstCombinerImpl::SimplifyAddWithRemainder(BinaryOperator &I) { Value *LHS = I.getOperand(0), *RHS = I.getOperand(1); Value *X, *MulOpV; @@ -1161,6 +1163,33 @@ Value *InstCombinerImpl::SimplifyAddWithRemainder(BinaryOperator &I) { } } + // Match I = (X / C0) * C1 + (X % C0) * C2 + Value *Div, *Rem; + APInt C1, C2; + if (!LHS->hasOneUse() || !MatchMul(LHS, Div, C1)) + Div = LHS, C1 = APInt(I.getType()->getScalarSizeInBits(), 1); + if (!RHS->hasOneUse() || !MatchMul(RHS, Rem, C2)) + Rem = RHS, C2 = APInt(I.getType()->getScalarSizeInBits(), 1); + if (match(Div, m_IRem(m_Value(), m_Value()))) { + std::swap(Div, Rem); + std::swap(C1, C2); + } + Value *DivOpV; + APInt DivOpC; + if (MatchRem(Rem, X, C0, IsSigned) && + MatchDiv(Div, DivOpV, DivOpC, IsSigned) && X == DivOpV && C0 == DivOpC) { + APInt NewC = C1 - C2 * C0; + if (!NewC.isZero() && !Rem->hasOneUse()) + return nullptr; + if (!isGuaranteedNotToBeUndef(X, &AC, &I, &DT)) + return nullptr; + Value *MulXC2 = Builder.CreateMul(X, ConstantInt::get(X->getType(), C2)); + if (NewC.isZero()) + return MulXC2; + return Builder.CreateAdd( + Builder.CreateMul(Div, ConstantInt::get(X->getType(), NewC)), MulXC2); + } + return nullptr; } @@ -1972,43 +2001,30 @@ Value *InstCombinerImpl::OptimizePointerDifference(Value *LHS, Value *RHS, if (!GEP1) return nullptr; - if (GEP2) { - // (gep X, ...) - (gep X, ...) - // - // Avoid duplicating the arithmetic if there are more than one non-constant - // indices between the two GEPs and either GEP has a non-constant index and - // multiple users. If zero non-constant index, the result is a constant and - // there is no duplication. If one non-constant index, the result is an add - // or sub with a constant, which is no larger than the original code, and - // there's no duplicated arithmetic, even if either GEP has multiple - // users. If more than one non-constant indices combined, as long as the GEP - // with at least one non-constant index doesn't have multiple users, there - // is no duplication. - unsigned NumNonConstantIndices1 = GEP1->countNonConstantIndices(); - unsigned NumNonConstantIndices2 = GEP2->countNonConstantIndices(); - if (NumNonConstantIndices1 + NumNonConstantIndices2 > 1 && - ((NumNonConstantIndices1 > 0 && !GEP1->hasOneUse()) || - (NumNonConstantIndices2 > 0 && !GEP2->hasOneUse()))) { - return nullptr; - } - } + // To avoid duplicating the offset arithmetic, rewrite the GEP to use the + // computed offset. This may erase the original GEP, so be sure to cache the + // inbounds flag before emitting the offset. + // TODO: We should probably do this even if there is only one GEP. + bool RewriteGEPs = GEP2 != nullptr; // Emit the offset of the GEP and an intptr_t. - Value *Result = EmitGEPOffset(GEP1); + bool GEP1IsInBounds = GEP1->isInBounds(); + Value *Result = EmitGEPOffset(GEP1, RewriteGEPs); // If this is a single inbounds GEP and the original sub was nuw, // then the final multiplication is also nuw. if (auto *I = dyn_cast(Result)) - if (IsNUW && !GEP2 && !Swapped && GEP1->isInBounds() && + if (IsNUW && !GEP2 && !Swapped && GEP1IsInBounds && I->getOpcode() == Instruction::Mul) I->setHasNoUnsignedWrap(); // If we have a 2nd GEP of the same base pointer, subtract the offsets. // If both GEPs are inbounds, then the subtract does not have signed overflow. if (GEP2) { - Value *Offset = EmitGEPOffset(GEP2); + bool GEP2IsInBounds = GEP2->isInBounds(); + Value *Offset = EmitGEPOffset(GEP2, RewriteGEPs); Result = Builder.CreateSub(Result, Offset, "gepdiff", /* NUW */ false, - GEP1->isInBounds() && GEP2->isInBounds()); + GEP1IsInBounds && GEP2IsInBounds); } // If we have p - gep(p, ...) then we have to negate the result. @@ -2752,6 +2768,16 @@ Instruction *InstCombinerImpl::visitFNeg(UnaryOperator &I) { propagateSelectFMF(NewSel, P == X); return NewSel; } + + // -(Cond ? X : C) --> Cond ? -X : -C + // -(Cond ? C : Y) --> Cond ? -C : -Y + if (match(X, m_ImmConstant()) || match(Y, m_ImmConstant())) { + Value *NegX = Builder.CreateFNegFMF(X, &I, X->getName() + ".neg"); + Value *NegY = Builder.CreateFNegFMF(Y, &I, Y->getName() + ".neg"); + SelectInst *NewSel = SelectInst::Create(Cond, NegX, NegY); + propagateSelectFMF(NewSel, /*CommonOperand=*/true); + return NewSel; + } } // fneg (copysign x, y) -> copysign x, (fneg y) diff --git a/llvm/lib/Transforms/InstCombine/InstCombineAndOrXor.cpp b/llvm/lib/Transforms/InstCombine/InstCombineAndOrXor.cpp index e1923a3441790a349a371321f0200f0e5e4e2f3f..ed9a89b14efccaa9c03e978cc03f8a7ad2c4e3b7 100644 --- a/llvm/lib/Transforms/InstCombine/InstCombineAndOrXor.cpp +++ b/llvm/lib/Transforms/InstCombine/InstCombineAndOrXor.cpp @@ -3141,20 +3141,20 @@ Value *InstCombinerImpl::getSelectCondition(Value *A, Value *B, return nullptr; } -/// We have an expression of the form (A & C) | (B & D). Try to simplify this -/// to "A' ? C : D", where A' is a boolean or vector of booleans. +/// We have an expression of the form (A & B) | (C & D). Try to simplify this +/// to "A' ? B : D", where A' is a boolean or vector of booleans. /// When InvertFalseVal is set to true, we try to match the pattern -/// where we have peeked through a 'not' op and A and B are the same: -/// (A & C) | ~(A | D) --> (A & C) | (~A & ~D) --> A' ? C : ~D -Value *InstCombinerImpl::matchSelectFromAndOr(Value *A, Value *C, Value *B, +/// where we have peeked through a 'not' op and A and C are the same: +/// (A & B) | ~(A | D) --> (A & B) | (~A & ~D) --> A' ? B : ~D +Value *InstCombinerImpl::matchSelectFromAndOr(Value *A, Value *B, Value *C, Value *D, bool InvertFalseVal) { // The potential condition of the select may be bitcasted. In that case, look // through its bitcast and the corresponding bitcast of the 'not' condition. Type *OrigType = A->getType(); A = peekThroughBitcast(A, true); - B = peekThroughBitcast(B, true); - if (Value *Cond = getSelectCondition(A, B, InvertFalseVal)) { - // ((bc Cond) & C) | ((bc ~Cond) & D) --> bc (select Cond, (bc C), (bc D)) + C = peekThroughBitcast(C, true); + if (Value *Cond = getSelectCondition(A, C, InvertFalseVal)) { + // ((bc Cond) & B) | ((bc ~Cond) & D) --> bc (select Cond, (bc B), (bc D)) // If this is a vector, we may need to cast to match the condition's length. // The bitcasts will either all exist or all not exist. The builder will // not create unnecessary casts if the types already match. @@ -3168,11 +3168,11 @@ Value *InstCombinerImpl::matchSelectFromAndOr(Value *A, Value *C, Value *B, Type *EltTy = Builder.getIntNTy(SelEltSize / Elts); SelTy = VectorType::get(EltTy, VecTy->getElementCount()); } - Value *BitcastC = Builder.CreateBitCast(C, SelTy); + Value *BitcastB = Builder.CreateBitCast(B, SelTy); if (InvertFalseVal) D = Builder.CreateNot(D); Value *BitcastD = Builder.CreateBitCast(D, SelTy); - Value *Select = Builder.CreateSelect(Cond, BitcastC, BitcastD); + Value *Select = Builder.CreateSelect(Cond, BitcastB, BitcastD); return Builder.CreateBitCast(Select, OrigType); } @@ -3958,6 +3958,10 @@ Instruction *InstCombinerImpl::visitOr(BinaryOperator &I) { /*SimplifyOnly*/ false, *this)) return BinaryOperator::CreateOr(Op0, V); + if (cast(I).isDisjoint()) + if (Value *V = SimplifyAddWithRemainder(I)) + return replaceInstUsesWith(I, V); + return nullptr; } diff --git a/llvm/lib/Transforms/InstCombine/InstCombineCalls.cpp b/llvm/lib/Transforms/InstCombine/InstCombineCalls.cpp index a37a4cde96f899f9ac8c43e491ae80bfad5dc754..e5652458f150b56cc59b11c542f9aaf8b66e7c39 100644 --- a/llvm/lib/Transforms/InstCombine/InstCombineCalls.cpp +++ b/llvm/lib/Transforms/InstCombine/InstCombineCalls.cpp @@ -606,14 +606,13 @@ static Instruction *foldCttzCtlz(IntrinsicInst &II, InstCombinerImpl &IC) { return IC.replaceOperand(II, 1, IC.Builder.getTrue()); } - // Add range metadata since known bits can't completely reflect what we know. - auto *IT = cast(Op0->getType()->getScalarType()); - if (IT && IT->getBitWidth() != 1 && !II.getMetadata(LLVMContext::MD_range)) { - Metadata *LowAndHigh[] = { - ConstantAsMetadata::get(ConstantInt::get(IT, DefiniteZeros)), - ConstantAsMetadata::get(ConstantInt::get(IT, PossibleZeros + 1))}; - II.setMetadata(LLVMContext::MD_range, - MDNode::get(II.getContext(), LowAndHigh)); + // Add range attribute since known bits can't completely reflect what we know. + unsigned BitWidth = Op0->getType()->getScalarSizeInBits(); + if (BitWidth != 1 && !II.hasRetAttr(Attribute::Range) && + !II.getMetadata(LLVMContext::MD_range)) { + ConstantRange Range(APInt(BitWidth, DefiniteZeros), + APInt(BitWidth, PossibleZeros + 1)); + II.addRangeRetAttr(Range); return &II; } @@ -685,16 +684,12 @@ static Instruction *foldCtpop(IntrinsicInst &II, InstCombinerImpl &IC) { Constant::getNullValue(Ty)), Ty); - // Add range metadata since known bits can't completely reflect what we know. - auto *IT = cast(Ty->getScalarType()); - unsigned MinCount = Known.countMinPopulation(); - unsigned MaxCount = Known.countMaxPopulation(); - if (IT->getBitWidth() != 1 && !II.getMetadata(LLVMContext::MD_range)) { - Metadata *LowAndHigh[] = { - ConstantAsMetadata::get(ConstantInt::get(IT, MinCount)), - ConstantAsMetadata::get(ConstantInt::get(IT, MaxCount + 1))}; - II.setMetadata(LLVMContext::MD_range, - MDNode::get(II.getContext(), LowAndHigh)); + // Add range attribute since known bits can't completely reflect what we know. + if (BitWidth != 1 && !II.hasRetAttr(Attribute::Range) && + !II.getMetadata(LLVMContext::MD_range)) { + ConstantRange Range(APInt(BitWidth, Known.countMinPopulation()), + APInt(BitWidth, Known.countMaxPopulation() + 1)); + II.addRangeRetAttr(Range); return &II; } diff --git a/llvm/lib/Transforms/InstCombine/InstCombineCasts.cpp b/llvm/lib/Transforms/InstCombine/InstCombineCasts.cpp index 6ce39be59bda98a2264d72e17e8aa8087e26245c..567b27b46304399cb3b96dc1e2cea5fb24a9ce17 100644 --- a/llvm/lib/Transforms/InstCombine/InstCombineCasts.cpp +++ b/llvm/lib/Transforms/InstCombine/InstCombineCasts.cpp @@ -2050,9 +2050,9 @@ Instruction *InstCombinerImpl::visitPtrToInt(PtrToIntInst &CI) { // the GEP otherwise. if (GEP->hasOneUse() && isa(GEP->getPointerOperand())) { - return replaceInstUsesWith(CI, - Builder.CreateIntCast(EmitGEPOffset(GEP), Ty, - /*isSigned=*/false)); + return replaceInstUsesWith( + CI, Builder.CreateIntCast(EmitGEPOffset(cast(GEP)), Ty, + /*isSigned=*/false)); } } diff --git a/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp b/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp index c2062adcd5b7f78c8568d65062df8a8eda651531..1064340cb53661d8ded822c513956b084f91bf8f 100644 --- a/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp +++ b/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp @@ -816,29 +816,9 @@ Instruction *InstCombinerImpl::foldGEPICmp(GEPOperator *GEPLHS, Value *RHS, } if (GEPsInBounds || CmpInst::isEquality(Cond)) { - auto EmitGEPOffsetAndRewrite = [&](GEPOperator *GEP) { - IRBuilderBase::InsertPointGuard Guard(Builder); - auto *Inst = dyn_cast(GEP); - if (Inst) - Builder.SetInsertPoint(Inst); - - Value *Offset = EmitGEPOffset(GEP); - // If a non-trivial GEP has other uses, rewrite it to avoid duplicating - // the offset arithmetic. - if (Inst && !GEP->hasOneUse() && !GEP->hasAllConstantIndices() && - !GEP->getSourceElementType()->isIntegerTy(8)) { - replaceInstUsesWith(*Inst, - Builder.CreateGEP(Builder.getInt8Ty(), - GEP->getPointerOperand(), - Offset, "", GEPsInBounds)); - eraseInstFromFunction(*Inst); - } - return Offset; - }; - // ((gep Ptr, OFFSET1) cmp (gep Ptr, OFFSET2) ---> (OFFSET1 cmp OFFSET2) - Value *L = EmitGEPOffsetAndRewrite(GEPLHS); - Value *R = EmitGEPOffsetAndRewrite(GEPRHS); + Value *L = EmitGEPOffset(GEPLHS, /*RewriteGEP=*/true); + Value *R = EmitGEPOffset(GEPRHS, /*RewriteGEP=*/true); return new ICmpInst(ICmpInst::getSignedPredicate(Cond), L, R); } } diff --git a/llvm/lib/Transforms/InstCombine/InstCombineInternal.h b/llvm/lib/Transforms/InstCombine/InstCombineInternal.h index 4479afbd09afde315ceb0bc234fb727b0ca73f38..aafb4cf6ca6a62866cb48a3d5a925103b022048c 100644 --- a/llvm/lib/Transforms/InstCombine/InstCombineInternal.h +++ b/llvm/lib/Transforms/InstCombine/InstCombineInternal.h @@ -376,7 +376,7 @@ private: } } - Value *EmitGEPOffset(User *GEP); + Value *EmitGEPOffset(GEPOperator *GEP, bool RewriteGEP = false); Instruction *scalarizePHI(ExtractElementInst &EI, PHINode *PN); Instruction *foldBitcastExtElt(ExtractElementInst &ExtElt); Instruction *foldCastedBitwiseLogic(BinaryOperator &I); diff --git a/llvm/lib/Transforms/InstCombine/InstCombineNegator.cpp b/llvm/lib/Transforms/InstCombine/InstCombineNegator.cpp index d697f361dec023392347c7bdda0d1228ca54a702..ed2a98ba4ae40ede47264d0c0fc9776d43a7ff1a 100644 --- a/llvm/lib/Transforms/InstCombine/InstCombineNegator.cpp +++ b/llvm/lib/Transforms/InstCombine/InstCombineNegator.cpp @@ -320,7 +320,8 @@ std::array Negator::getSortedOperandsOfBinOp(Instruction *I) { return NegatedPHI; } case Instruction::Select: { - if (isKnownNegation(I->getOperand(1), I->getOperand(2))) { + if (isKnownNegation(I->getOperand(1), I->getOperand(2), /*NeedNSW=*/false, + /*AllowPoison=*/false)) { // Of one hand of select is known to be negation of another hand, // just swap the hands around. auto *NewSelect = cast(I->clone()); diff --git a/llvm/lib/Transforms/InstCombine/InstCombineSelect.cpp b/llvm/lib/Transforms/InstCombine/InstCombineSelect.cpp index 73600206a55c145fea16ff180fe8d62f67941173..117eb7a1dcc933d088e2634a718f0bd65274dd39 100644 --- a/llvm/lib/Transforms/InstCombine/InstCombineSelect.cpp +++ b/llvm/lib/Transforms/InstCombine/InstCombineSelect.cpp @@ -1722,11 +1722,11 @@ static Instruction *foldSelectICmpEq(SelectInst &SI, ICmpInst *ICI, return match(CmpRHS, m_Zero()) && match(FalseVal, matchInner); if (NotMask == NotInner) { - return match(FalseVal, - m_c_BinOp(OuterOpc, m_Not(matchInner), m_Specific(CmpRHS))); + return match(FalseVal, m_c_BinOp(OuterOpc, m_NotForbidPoison(matchInner), + m_Specific(CmpRHS))); } else if (NotMask == NotRHS) { - return match(FalseVal, - m_c_BinOp(OuterOpc, matchInner, m_Not(m_Specific(CmpRHS)))); + return match(FalseVal, m_c_BinOp(OuterOpc, matchInner, + m_NotForbidPoison(m_Specific(CmpRHS)))); } else { return match(FalseVal, m_c_BinOp(OuterOpc, matchInner, m_Specific(CmpRHS))); diff --git a/llvm/lib/Transforms/InstCombine/InstCombineShifts.cpp b/llvm/lib/Transforms/InstCombine/InstCombineShifts.cpp index 244f03a1bc2b4cb20a055d358650c74412169fb8..1cb21a1d81af4b2e1421f12602bbc7f4464129ad 100644 --- a/llvm/lib/Transforms/InstCombine/InstCombineShifts.cpp +++ b/llvm/lib/Transforms/InstCombine/InstCombineShifts.cpp @@ -1120,14 +1120,6 @@ Instruction *InstCombinerImpl::visitShl(BinaryOperator &I) { return BinaryOperator::CreateAnd(Trunc, ConstantInt::get(Ty, Mask)); } - if (match(Op0, m_Shl(m_Value(X), m_APInt(C1))) && C1->ult(BitWidth)) { - unsigned AmtSum = ShAmtC + C1->getZExtValue(); - // Oversized shifts are simplified to zero in InstSimplify. - if (AmtSum < BitWidth) - // (X << C1) << C2 --> X << (C1 + C2) - return BinaryOperator::CreateShl(X, ConstantInt::get(Ty, AmtSum)); - } - // If we have an opposite shift by the same amount, we may be able to // reorder binops and shifts to eliminate math/logic. auto isSuitableBinOpcode = [](Instruction::BinaryOps BinOpcode) { @@ -1394,14 +1386,6 @@ Instruction *InstCombinerImpl::visitLShr(BinaryOperator &I) { } } - // (X >>u C1) >>u C --> X >>u (C1 + C) - if (match(Op0, m_LShr(m_Value(X), m_APInt(C1)))) { - // Oversized shifts are simplified to zero in InstSimplify. - unsigned AmtSum = ShAmtC + C1->getZExtValue(); - if (AmtSum < BitWidth) - return BinaryOperator::CreateLShr(X, ConstantInt::get(Ty, AmtSum)); - } - Instruction *TruncSrc; if (match(Op0, m_OneUse(m_Trunc(m_Instruction(TruncSrc)))) && match(TruncSrc, m_LShr(m_Value(X), m_APInt(C1)))) { diff --git a/llvm/lib/Transforms/InstCombine/InstructionCombining.cpp b/llvm/lib/Transforms/InstCombine/InstructionCombining.cpp index f6684834a7722059b1fa92a30b8f0bf56f3a22e8..58b2d8e9dec1c33770b40ef1c70ec150107ac7e6 100644 --- a/llvm/lib/Transforms/InstCombine/InstructionCombining.cpp +++ b/llvm/lib/Transforms/InstCombine/InstructionCombining.cpp @@ -190,8 +190,26 @@ bool InstCombiner::isValidAddrSpaceCast(unsigned FromAS, unsigned ToAS) const { return TTI.isValidAddrSpaceCast(FromAS, ToAS); } -Value *InstCombinerImpl::EmitGEPOffset(User *GEP) { - return llvm::emitGEPOffset(&Builder, DL, GEP); +Value *InstCombinerImpl::EmitGEPOffset(GEPOperator *GEP, bool RewriteGEP) { + if (!RewriteGEP) + return llvm::emitGEPOffset(&Builder, DL, GEP); + + IRBuilderBase::InsertPointGuard Guard(Builder); + auto *Inst = dyn_cast(GEP); + if (Inst) + Builder.SetInsertPoint(Inst); + + Value *Offset = EmitGEPOffset(GEP); + // If a non-trivial GEP has other uses, rewrite it to avoid duplicating + // the offset arithmetic. + if (Inst && !GEP->hasOneUse() && !GEP->hasAllConstantIndices() && + !GEP->getSourceElementType()->isIntegerTy(8)) { + replaceInstUsesWith( + *Inst, Builder.CreateGEP(Builder.getInt8Ty(), GEP->getPointerOperand(), + Offset, "", GEP->isInBounds())); + eraseInstFromFunction(*Inst); + } + return Offset; } /// Legal integers and common types are considered desirable. This is used to @@ -2321,6 +2339,43 @@ static Instruction *foldSelectGEP(GetElementPtrInst &GEP, return SelectInst::Create(Cond, NewTrueC, NewFalseC, "", nullptr, Sel); } +// Canonicalization: +// gep T, (gep i8, base, C1), (Index + C2) into +// gep T, (gep i8, base, C1 + C2 * sizeof(T)), Index +static Instruction *canonicalizeGEPOfConstGEPI8(GetElementPtrInst &GEP, + GEPOperator *Src, + InstCombinerImpl &IC) { + if (GEP.getNumIndices() != 1) + return nullptr; + auto &DL = IC.getDataLayout(); + Value *Base; + const APInt *C1; + if (!match(Src, m_PtrAdd(m_Value(Base), m_APInt(C1)))) + return nullptr; + Value *VarIndex; + const APInt *C2; + Type *PtrTy = Src->getType()->getScalarType(); + unsigned IndexSizeInBits = DL.getIndexTypeSizeInBits(PtrTy); + if (!match(GEP.getOperand(1), m_AddLike(m_Value(VarIndex), m_APInt(C2)))) + return nullptr; + if (C1->getBitWidth() != IndexSizeInBits || + C2->getBitWidth() != IndexSizeInBits) + return nullptr; + Type *BaseType = GEP.getSourceElementType(); + if (isa(BaseType)) + return nullptr; + APInt TypeSize(IndexSizeInBits, DL.getTypeAllocSize(BaseType)); + APInt NewOffset = TypeSize * *C2 + *C1; + if (NewOffset.isZero() || + (Src->hasOneUse() && GEP.getOperand(1)->hasOneUse())) { + Value *GEPConst = + IC.Builder.CreatePtrAdd(Base, IC.Builder.getInt(NewOffset)); + return GetElementPtrInst::Create(BaseType, GEPConst, VarIndex); + } + + return nullptr; +} + Instruction *InstCombinerImpl::visitGEPOfGEP(GetElementPtrInst &GEP, GEPOperator *Src) { // Combine Indices - If the source pointer to this getelementptr instruction @@ -2329,6 +2384,9 @@ Instruction *InstCombinerImpl::visitGEPOfGEP(GetElementPtrInst &GEP, if (!shouldMergeGEPs(*cast(&GEP), *Src)) return nullptr; + if (auto *I = canonicalizeGEPOfConstGEPI8(GEP, Src, *this)) + return I; + // For constant GEPs, use a more general offset-based folding approach. Type *PtrTy = Src->getType()->getScalarType(); if (GEP.hasAllConstantIndices() && diff --git a/llvm/lib/Transforms/Instrumentation/HWAddressSanitizer.cpp b/llvm/lib/Transforms/Instrumentation/HWAddressSanitizer.cpp index a35f24447cc39b7f65f3b0d06b7919a23319ff6e..88b85234034038517fc5f1e55c02c2c3c834e60b 100644 --- a/llvm/lib/Transforms/Instrumentation/HWAddressSanitizer.cpp +++ b/llvm/lib/Transforms/Instrumentation/HWAddressSanitizer.cpp @@ -930,11 +930,33 @@ void HWAddressSanitizer::instrumentMemAccessOutline(Value *Ptr, bool IsWrite, IRBuilder<> IRB(InsertBefore); Module *M = IRB.GetInsertBlock()->getParent()->getParent(); - IRB.CreateCall(Intrinsic::getDeclaration( - M, UseShortGranules - ? Intrinsic::hwasan_check_memaccess_shortgranules - : Intrinsic::hwasan_check_memaccess), - {ShadowBase, Ptr, ConstantInt::get(Int32Ty, AccessInfo)}); + bool useFixedShadowIntrinsic = false; + // The memaccess fixed shadow intrinsic is only supported on AArch64, + // which allows a 16-bit immediate to be left-shifted by 32. + // Since kShadowBaseAlignment == 32, and Linux by default will not + // mmap above 48-bits, practically any valid shadow offset is + // representable. + // In particular, an offset of 4TB (1024 << 32) is representable, and + // ought to be good enough for anybody. + if (TargetTriple.isAArch64() && Mapping.Offset != kDynamicShadowSentinel) { + uint16_t offset_shifted = Mapping.Offset >> 32; + useFixedShadowIntrinsic = (uint64_t)offset_shifted << 32 == Mapping.Offset; + } + + if (useFixedShadowIntrinsic) + IRB.CreateCall( + Intrinsic::getDeclaration( + M, UseShortGranules + ? Intrinsic::hwasan_check_memaccess_shortgranules_fixedshadow + : Intrinsic::hwasan_check_memaccess_fixedshadow), + {Ptr, ConstantInt::get(Int32Ty, AccessInfo), + ConstantInt::get(Int64Ty, Mapping.Offset)}); + else + IRB.CreateCall(Intrinsic::getDeclaration( + M, UseShortGranules + ? Intrinsic::hwasan_check_memaccess_shortgranules + : Intrinsic::hwasan_check_memaccess), + {ShadowBase, Ptr, ConstantInt::get(Int32Ty, AccessInfo)}); } void HWAddressSanitizer::instrumentMemAccessInline(Value *Ptr, bool IsWrite, diff --git a/llvm/lib/Transforms/Instrumentation/MemorySanitizer.cpp b/llvm/lib/Transforms/Instrumentation/MemorySanitizer.cpp index b1fd64fa3b293b1639db25a2d9eae54582d5ac48..66ee2fce8313e85f291d0f9cd854e6a5e5aba572 100644 --- a/llvm/lib/Transforms/Instrumentation/MemorySanitizer.cpp +++ b/llvm/lib/Transforms/Instrumentation/MemorySanitizer.cpp @@ -152,6 +152,7 @@ #include "llvm/ADT/DenseMap.h" #include "llvm/ADT/DepthFirstIterator.h" #include "llvm/ADT/SetVector.h" +#include "llvm/ADT/SmallPtrSet.h" #include "llvm/ADT/SmallVector.h" #include "llvm/ADT/StringExtras.h" #include "llvm/ADT/StringRef.h" @@ -212,6 +213,9 @@ using namespace llvm; DEBUG_COUNTER(DebugInsertCheck, "msan-insert-check", "Controls which checks to insert"); +DEBUG_COUNTER(DebugInstrumentInstruction, "msan-instrument-instruction", + "Controls which instruction to instrument"); + static const unsigned kOriginSize = 4; static const Align kMinOriginAlignment = Align(4); static const Align kShadowTLSAlignment = Align(8); @@ -1336,7 +1340,7 @@ struct MemorySanitizerVisitor : public InstVisitor { } } - // Returns true if Debug Location curresponds to multiple warnings. + // Returns true if Debug Location corresponds to multiple warnings. bool shouldDisambiguateWarningLocation(const DebugLoc &DebugLoc) { if (MS.TrackOrigins < 2) return false; @@ -1461,19 +1465,21 @@ struct MemorySanitizerVisitor : public InstVisitor { } void materializeChecks() { - llvm::stable_sort(InstrumentationList, - [](const ShadowOriginAndInsertPoint &L, - const ShadowOriginAndInsertPoint &R) { - return L.OrigIns < R.OrigIns; - }); +#ifndef NDEBUG + // For assert below. + SmallPtrSet Done; +#endif for (auto I = InstrumentationList.begin(); I != InstrumentationList.end();) { - auto J = - std::find_if(I + 1, InstrumentationList.end(), - [L = I->OrigIns](const ShadowOriginAndInsertPoint &R) { - return L != R.OrigIns; - }); + auto OrigIns = I->OrigIns; + // Checks are grouped by the original instruction. We call all + // `insertShadowCheck` for an instruction at once. + assert(Done.insert(OrigIns).second); + auto J = std::find_if(I + 1, InstrumentationList.end(), + [OrigIns](const ShadowOriginAndInsertPoint &R) { + return OrigIns != R.OrigIns; + }); // Process all checks of instruction at once. materializeInstructionChecks(ArrayRef(I, J)); I = J; @@ -2176,6 +2182,13 @@ struct MemorySanitizerVisitor : public InstVisitor { // Don't want to visit if we're in the prologue if (isInPrologue(I)) return; + if (!DebugCounter::shouldExecute(DebugInstrumentInstruction)) { + LLVM_DEBUG(dbgs() << "Skipping instruction: " << I << "\n"); + // We still need to set the shadow and origin to clean values. + setShadow(&I, getCleanShadow(&I)); + setOrigin(&I, getCleanOrigin()); + return; + } InstVisitor::visit(I); } @@ -2493,6 +2506,8 @@ struct MemorySanitizerVisitor : public InstVisitor { Value *CreateShadowCast(IRBuilder<> &IRB, Value *V, Type *dstTy, bool Signed = false) { Type *srcTy = V->getType(); + if (srcTy == dstTy) + return V; size_t srcSizeInBits = VectorOrPrimitiveTypeSizeInBits(srcTy); size_t dstSizeInBits = VectorOrPrimitiveTypeSizeInBits(dstTy); if (srcSizeInBits > 1 && dstSizeInBits == 1) diff --git a/llvm/lib/Transforms/Instrumentation/PGOInstrumentation.cpp b/llvm/lib/Transforms/Instrumentation/PGOInstrumentation.cpp index 98c6f8cbf5afefadcd6cc5648bffb06e0c9776c1..a7b7556685e44352185374b974221ae34021d7ab 100644 --- a/llvm/lib/Transforms/Instrumentation/PGOInstrumentation.cpp +++ b/llvm/lib/Transforms/Instrumentation/PGOInstrumentation.cpp @@ -1367,6 +1367,7 @@ void PGOUseFunc::populateCoverage(IndexedInstrProfReader *PGOReader) { handleInstrProfError(std::move(Err), MismatchedFuncSum); return; } + IsCS ? NumOfCSPGOFunc++ : NumOfPGOFunc++; std::vector &CountsFromProfile = Result.get().Counts; DenseMap Coverage; diff --git a/llvm/lib/Transforms/Scalar/GVN.cpp b/llvm/lib/Transforms/Scalar/GVN.cpp index 86d5c9909f3dc5a200d1ddd5c1450eab0593de85..b5be8ac24941715b7b2e2ed956ff1b27d313b644 100644 --- a/llvm/lib/Transforms/Scalar/GVN.cpp +++ b/llvm/lib/Transforms/Scalar/GVN.cpp @@ -33,6 +33,7 @@ #include "llvm/Analysis/GlobalsModRef.h" #include "llvm/Analysis/InstructionPrecedenceTracking.h" #include "llvm/Analysis/InstructionSimplify.h" +#include "llvm/Analysis/Loads.h" #include "llvm/Analysis/LoopInfo.h" #include "llvm/Analysis/MemoryBuiltins.h" #include "llvm/Analysis/MemoryDependenceAnalysis.h" @@ -724,6 +725,69 @@ void GVNPass::ValueTable::verifyRemoved(const Value *V) const { "Inst still occurs in value numbering map!"); } +//===----------------------------------------------------------------------===// +// LeaderMap External Functions +//===----------------------------------------------------------------------===// + +/// Push a new Value to the LeaderTable onto the list for its value number. +void GVNPass::LeaderMap::insert(uint32_t N, Value *V, const BasicBlock *BB) { + LeaderListNode &Curr = NumToLeaders[N]; + if (!Curr.Entry.Val) { + Curr.Entry.Val = V; + Curr.Entry.BB = BB; + return; + } + + LeaderListNode *Node = TableAllocator.Allocate(); + Node->Entry.Val = V; + Node->Entry.BB = BB; + Node->Next = Curr.Next; + Curr.Next = Node; +} + +/// Scan the list of values corresponding to a given +/// value number, and remove the given instruction if encountered. +void GVNPass::LeaderMap::erase(uint32_t N, Instruction *I, + const BasicBlock *BB) { + LeaderListNode *Prev = nullptr; + LeaderListNode *Curr = &NumToLeaders[N]; + + while (Curr && (Curr->Entry.Val != I || Curr->Entry.BB != BB)) { + Prev = Curr; + Curr = Curr->Next; + } + + if (!Curr) + return; + + if (Prev) { + Prev->Next = Curr->Next; + } else { + if (!Curr->Next) { + Curr->Entry.Val = nullptr; + Curr->Entry.BB = nullptr; + } else { + LeaderListNode *Next = Curr->Next; + Curr->Entry.Val = Next->Entry.Val; + Curr->Entry.BB = Next->Entry.BB; + Curr->Next = Next->Next; + } + } +} + +void GVNPass::LeaderMap::verifyRemoved(const Value *V) const { + // Walk through the value number scope to make sure the instruction isn't + // ferreted away in it. + for (const auto &I : NumToLeaders) { + (void)I; + assert(I.second.Entry.Val != V && "Inst still in value numbering scope!"); + assert( + std::none_of(leader_iterator(&I.second), leader_iterator(nullptr), + [=](const LeaderTableEntry &E) { return E.Val == V; }) && + "Inst still in value numbering scope!"); + } +} + //===----------------------------------------------------------------------===// // GVN Pass //===----------------------------------------------------------------------===// @@ -1466,7 +1530,7 @@ void GVNPass::eliminatePartiallyRedundantLoad( OldLoad->replaceAllUsesWith(NewLoad); replaceValuesPerBlockEntry(ValuesPerBlock, OldLoad, NewLoad); if (uint32_t ValNo = VN.lookup(OldLoad, false)) - removeFromLeaderTable(ValNo, OldLoad, OldLoad->getParent()); + LeaderTable.erase(ValNo, OldLoad, OldLoad->getParent()); VN.erase(OldLoad); removeInstruction(OldLoad); } @@ -2203,10 +2267,9 @@ GVNPass::ValueTable::assignExpNewValueNum(Expression &Exp) { /// defined in \p BB. bool GVNPass::ValueTable::areAllValsInBB(uint32_t Num, const BasicBlock *BB, GVNPass &Gvn) { - LeaderTableEntry *Vals = &Gvn.LeaderTable[Num]; - while (Vals && Vals->BB == BB) - Vals = Vals->Next; - return !Vals; + return all_of( + Gvn.LeaderTable.getLeaders(Num), + [=](const LeaderMap::LeaderTableEntry &L) { return L.BB == BB; }); } /// Wrap phiTranslateImpl to provide caching functionality. @@ -2228,12 +2291,11 @@ bool GVNPass::ValueTable::areCallValsEqual(uint32_t Num, uint32_t NewNum, const BasicBlock *PhiBlock, GVNPass &Gvn) { CallInst *Call = nullptr; - LeaderTableEntry *Vals = &Gvn.LeaderTable[Num]; - while (Vals) { - Call = dyn_cast(Vals->Val); + auto Leaders = Gvn.LeaderTable.getLeaders(Num); + for (const auto &Entry : Leaders) { + Call = dyn_cast(Entry.Val); if (Call && Call->getParent() == PhiBlock) break; - Vals = Vals->Next; } if (AA->doesNotAccessMemory(Call)) @@ -2326,23 +2388,17 @@ void GVNPass::ValueTable::eraseTranslateCacheEntry( // question. This is fast because dominator tree queries consist of only // a few comparisons of DFS numbers. Value *GVNPass::findLeader(const BasicBlock *BB, uint32_t num) { - LeaderTableEntry Vals = LeaderTable[num]; - if (!Vals.Val) return nullptr; + auto Leaders = LeaderTable.getLeaders(num); + if (Leaders.empty()) + return nullptr; Value *Val = nullptr; - if (DT->dominates(Vals.BB, BB)) { - Val = Vals.Val; - if (isa(Val)) return Val; - } - - LeaderTableEntry* Next = Vals.Next; - while (Next) { - if (DT->dominates(Next->BB, BB)) { - if (isa(Next->Val)) return Next->Val; - if (!Val) Val = Next->Val; + for (const auto &Entry : Leaders) { + if (DT->dominates(Entry.BB, BB)) { + Val = Entry.Val; + if (isa(Val)) + return Val; } - - Next = Next->Next; } return Val; @@ -2419,6 +2475,10 @@ bool GVNPass::propagateEquality(Value *LHS, Value *RHS, if (isa(LHS) || (isa(LHS) && !isa(RHS))) std::swap(LHS, RHS); assert((isa(LHS) || isa(LHS)) && "Unexpected value!"); + const DataLayout &DL = + isa(LHS) + ? cast(LHS)->getParent()->getParent()->getDataLayout() + : cast(LHS)->getModule()->getDataLayout(); // If there is no obvious reason to prefer the left-hand side over the // right-hand side, ensure the longest lived term is on the right-hand side, @@ -2445,23 +2505,32 @@ bool GVNPass::propagateEquality(Value *LHS, Value *RHS, // using the leader table is about compiling faster, not optimizing better). // The leader table only tracks basic blocks, not edges. Only add to if we // have the simple case where the edge dominates the end. - if (RootDominatesEnd && !isa(RHS)) - addToLeaderTable(LVN, RHS, Root.getEnd()); + if (RootDominatesEnd && !isa(RHS) && + canReplacePointersIfEqual(LHS, RHS, DL)) + LeaderTable.insert(LVN, RHS, Root.getEnd()); // Replace all occurrences of 'LHS' with 'RHS' everywhere in the scope. As // LHS always has at least one use that is not dominated by Root, this will // never do anything if LHS has only one use. if (!LHS->hasOneUse()) { + // Create a callback that captures the DL. + auto canReplacePointersCallBack = [&DL](const Use &U, const Value *To) { + return canReplacePointersInUseIfEqual(U, To, DL); + }; unsigned NumReplacements = DominatesByEdge - ? replaceDominatedUsesWith(LHS, RHS, *DT, Root) - : replaceDominatedUsesWith(LHS, RHS, *DT, Root.getStart()); - - Changed |= NumReplacements > 0; - NumGVNEqProp += NumReplacements; - // Cached information for anything that uses LHS will be invalid. - if (MD) - MD->invalidateCachedPointerInfo(LHS); + ? replaceDominatedUsesWithIf(LHS, RHS, *DT, Root, + canReplacePointersCallBack) + : replaceDominatedUsesWithIf(LHS, RHS, *DT, Root.getStart(), + canReplacePointersCallBack); + + if (NumReplacements > 0) { + Changed = true; + NumGVNEqProp += NumReplacements; + // Cached information for anything that uses LHS will be invalid. + if (MD) + MD->invalidateCachedPointerInfo(LHS); + } } // Now try to deduce additional equalities from this one. For example, if @@ -2532,7 +2601,7 @@ bool GVNPass::propagateEquality(Value *LHS, Value *RHS, // The leader table only tracks basic blocks, not edges. Only add to if we // have the simple case where the edge dominates the end. if (RootDominatesEnd) - addToLeaderTable(Num, NotVal, Root.getEnd()); + LeaderTable.insert(Num, NotVal, Root.getEnd()); continue; } @@ -2582,7 +2651,7 @@ bool GVNPass::processInstruction(Instruction *I) { return true; unsigned Num = VN.lookupOrAdd(Load); - addToLeaderTable(Num, Load, Load->getParent()); + LeaderTable.insert(Num, Load, Load->getParent()); return false; } @@ -2650,7 +2719,7 @@ bool GVNPass::processInstruction(Instruction *I) { // Allocations are always uniquely numbered, so we can save time and memory // by fast failing them. if (isa(I) || I->isTerminator() || isa(I)) { - addToLeaderTable(Num, I, I->getParent()); + LeaderTable.insert(Num, I, I->getParent()); return false; } @@ -2658,7 +2727,7 @@ bool GVNPass::processInstruction(Instruction *I) { // need to do a lookup to see if the number already exists // somewhere in the domtree: it can't! if (Num >= NextNum) { - addToLeaderTable(Num, I, I->getParent()); + LeaderTable.insert(Num, I, I->getParent()); return false; } @@ -2667,7 +2736,7 @@ bool GVNPass::processInstruction(Instruction *I) { Value *Repl = findLeader(I->getParent(), Num); if (!Repl) { // Failure, just remember this instance for future use. - addToLeaderTable(Num, I, I->getParent()); + LeaderTable.insert(Num, I, I->getParent()); return false; } @@ -2862,7 +2931,7 @@ bool GVNPass::performScalarPREInsertion(Instruction *Instr, BasicBlock *Pred, VN.add(Instr, Num); // Update the availability map to include the new instruction. - addToLeaderTable(Num, Instr, Pred); + LeaderTable.insert(Num, Instr, Pred); return true; } @@ -3013,13 +3082,13 @@ bool GVNPass::performScalarPRE(Instruction *CurInst) { // After creating a new PHI for ValNo, the phi translate result for ValNo will // be changed, so erase the related stale entries in phi translate cache. VN.eraseTranslateCacheEntry(ValNo, *CurrentBlock); - addToLeaderTable(ValNo, Phi, CurrentBlock); + LeaderTable.insert(ValNo, Phi, CurrentBlock); Phi->setDebugLoc(CurInst->getDebugLoc()); CurInst->replaceAllUsesWith(Phi); if (MD && Phi->getType()->isPtrOrPtrVectorTy()) MD->invalidateCachedPointerInfo(Phi); VN.erase(CurInst); - removeFromLeaderTable(ValNo, CurInst, CurrentBlock); + LeaderTable.erase(ValNo, CurInst, CurrentBlock); LLVM_DEBUG(dbgs() << "GVN PRE removed: " << *CurInst << '\n'); removeInstruction(CurInst); @@ -3113,7 +3182,6 @@ void GVNPass::cleanupGlobalSets() { VN.clear(); LeaderTable.clear(); BlockRPONumber.clear(); - TableAllocator.Reset(); ICF->clear(); InvalidBlockRPONumbers = true; } @@ -3133,18 +3201,7 @@ void GVNPass::removeInstruction(Instruction *I) { /// internal data structures. void GVNPass::verifyRemoved(const Instruction *Inst) const { VN.verifyRemoved(Inst); - - // Walk through the value number scope to make sure the instruction isn't - // ferreted away in it. - for (const auto &I : LeaderTable) { - const LeaderTableEntry *Node = &I.second; - assert(Node->Val != Inst && "Inst still in value numbering scope!"); - - while (Node->Next) { - Node = Node->Next; - assert(Node->Val != Inst && "Inst still in value numbering scope!"); - } - } + LeaderTable.verifyRemoved(Inst); } /// BB is declared dead, which implied other blocks become dead as well. This @@ -3271,7 +3328,7 @@ void GVNPass::assignValNumForDeadCode() { for (BasicBlock *BB : DeadBlocks) { for (Instruction &Inst : *BB) { unsigned ValNum = VN.lookupOrAdd(&Inst); - addToLeaderTable(ValNum, &Inst, BB); + LeaderTable.insert(ValNum, &Inst, BB); } } } diff --git a/llvm/lib/Transforms/Scalar/InductiveRangeCheckElimination.cpp b/llvm/lib/Transforms/Scalar/InductiveRangeCheckElimination.cpp index 9df28747570c4db4552f110b1efa17f333b7ebaa..104e8ceb796700b5881930563c4229d053c5bb92 100644 --- a/llvm/lib/Transforms/Scalar/InductiveRangeCheckElimination.cpp +++ b/llvm/lib/Transforms/Scalar/InductiveRangeCheckElimination.cpp @@ -279,6 +279,9 @@ bool InductiveRangeCheck::parseRangeCheckICmp(Loop *L, ICmpInst *ICI, Value *LHS = ICI->getOperand(0); Value *RHS = ICI->getOperand(1); + if (!LHS->getType()->isIntegerTy()) + return false; + // Canonicalize to the `Index Pred Invariant` comparison if (IsLoopInvariant(LHS)) { std::swap(LHS, RHS); diff --git a/llvm/lib/Transforms/Scalar/JumpThreading.cpp b/llvm/lib/Transforms/Scalar/JumpThreading.cpp index ffcb511e6a83128fed8828cc33bef71de91c1ecd..08d82fa66da30786116aaf3fc144fc4584463157 100644 --- a/llvm/lib/Transforms/Scalar/JumpThreading.cpp +++ b/llvm/lib/Transforms/Scalar/JumpThreading.cpp @@ -1876,7 +1876,7 @@ bool JumpThreadingPass::processBranchOnXOR(BinaryOperator *BO) { static void addPHINodeEntriesForMappedBlock(BasicBlock *PHIBB, BasicBlock *OldPred, BasicBlock *NewPred, - DenseMap &ValueMap) { + ValueToValueMapTy &ValueMap) { for (PHINode &PN : PHIBB->phis()) { // Ok, we have a PHI node. Figure out what the incoming value was for the // DestBlock. @@ -1884,7 +1884,7 @@ static void addPHINodeEntriesForMappedBlock(BasicBlock *PHIBB, // Remap the value if necessary. if (Instruction *Inst = dyn_cast(IV)) { - DenseMap::iterator I = ValueMap.find(Inst); + ValueToValueMapTy::iterator I = ValueMap.find(Inst); if (I != ValueMap.end()) IV = I->second; } @@ -1945,9 +1945,8 @@ bool JumpThreadingPass::maybeMergeBasicBlockIntoOnlyPred(BasicBlock *BB) { /// Update the SSA form. NewBB contains instructions that are copied from BB. /// ValueMapping maps old values in BB to new ones in NewBB. -void JumpThreadingPass::updateSSA( - BasicBlock *BB, BasicBlock *NewBB, - DenseMap &ValueMapping) { +void JumpThreadingPass::updateSSA(BasicBlock *BB, BasicBlock *NewBB, + ValueToValueMapTy &ValueMapping) { // If there were values defined in BB that are used outside the block, then we // now have to update all uses of the value to use either the original value, // the cloned value, or some PHI derived value. This can require arbitrary @@ -2008,14 +2007,15 @@ void JumpThreadingPass::updateSSA( /// Clone instructions in range [BI, BE) to NewBB. For PHI nodes, we only clone /// arguments that come from PredBB. Return the map from the variables in the /// source basic block to the variables in the newly created basic block. -DenseMap -JumpThreadingPass::cloneInstructions(BasicBlock::iterator BI, - BasicBlock::iterator BE, BasicBlock *NewBB, - BasicBlock *PredBB) { + +void JumpThreadingPass::cloneInstructions(ValueToValueMapTy &ValueMapping, + BasicBlock::iterator BI, + BasicBlock::iterator BE, + BasicBlock *NewBB, + BasicBlock *PredBB) { // We are going to have to map operands from the source basic block to the new // copy of the block 'NewBB'. If there are PHI nodes in the source basic // block, evaluate them to account for entry from PredBB. - DenseMap ValueMapping; // Retargets llvm.dbg.value to any renamed variables. auto RetargetDbgValueIfPossible = [&](Instruction *NewInst) -> bool { @@ -2103,7 +2103,7 @@ JumpThreadingPass::cloneInstructions(BasicBlock::iterator BI, // Remap operands to patch up intra-block references. for (unsigned i = 0, e = New->getNumOperands(); i != e; ++i) if (Instruction *Inst = dyn_cast(New->getOperand(i))) { - DenseMap::iterator I = ValueMapping.find(Inst); + ValueToValueMapTy::iterator I = ValueMapping.find(Inst); if (I != ValueMapping.end()) New->setOperand(i, I->second); } @@ -2120,7 +2120,7 @@ JumpThreadingPass::cloneInstructions(BasicBlock::iterator BI, RetargetDbgVariableRecordIfPossible(&DVR); } - return ValueMapping; + return; } /// Attempt to thread through two successive basic blocks. @@ -2295,8 +2295,9 @@ void JumpThreadingPass::threadThroughTwoBasicBlocks(BasicBlock *PredPredBB, // We are going to have to map operands from the original BB block to the new // copy of the block 'NewBB'. If there are PHI nodes in PredBB, evaluate them // to account for entry from PredPredBB. - DenseMap ValueMapping = - cloneInstructions(PredBB->begin(), PredBB->end(), NewBB, PredPredBB); + ValueToValueMapTy ValueMapping; + cloneInstructions(ValueMapping, PredBB->begin(), PredBB->end(), NewBB, + PredPredBB); // Copy the edge probabilities from PredBB to NewBB. if (BPI) @@ -2419,8 +2420,9 @@ void JumpThreadingPass::threadEdge(BasicBlock *BB, } // Copy all the instructions from BB to NewBB except the terminator. - DenseMap ValueMapping = - cloneInstructions(BB->begin(), std::prev(BB->end()), NewBB, PredBB); + ValueToValueMapTy ValueMapping; + cloneInstructions(ValueMapping, BB->begin(), std::prev(BB->end()), NewBB, + PredBB); // We didn't copy the terminator from BB over to NewBB, because there is now // an unconditional jump to SuccBB. Insert the unconditional jump. @@ -2675,7 +2677,7 @@ bool JumpThreadingPass::duplicateCondBranchOnPHIIntoPred( // We are going to have to map operands from the original BB block into the // PredBB block. Evaluate PHI nodes in BB. - DenseMap ValueMapping; + ValueToValueMapTy ValueMapping; BasicBlock::iterator BI = BB->begin(); for (; PHINode *PN = dyn_cast(BI); ++BI) @@ -2689,11 +2691,14 @@ bool JumpThreadingPass::duplicateCondBranchOnPHIIntoPred( // Remap operands to patch up intra-block references. for (unsigned i = 0, e = New->getNumOperands(); i != e; ++i) if (Instruction *Inst = dyn_cast(New->getOperand(i))) { - DenseMap::iterator I = ValueMapping.find(Inst); + ValueToValueMapTy::iterator I = ValueMapping.find(Inst); if (I != ValueMapping.end()) New->setOperand(i, I->second); } + // Remap debug variable operands. + remapDebugVariable(ValueMapping, New); + // If this instruction can be simplified after the operands are updated, // just use the simplified value instead. This frequently happens due to // phi translation. diff --git a/llvm/lib/Transforms/Scalar/LoopLoadElimination.cpp b/llvm/lib/Transforms/Scalar/LoopLoadElimination.cpp index edddfb1b92402f351c3f4d82c0f641e6d86e27cc..059900f357e64bea380de72b4595f9a0aa6f5874 100644 --- a/llvm/lib/Transforms/Scalar/LoopLoadElimination.cpp +++ b/llvm/lib/Transforms/Scalar/LoopLoadElimination.cpp @@ -126,8 +126,10 @@ struct StoreToLoadForwardingCandidate { // We don't need to check non-wrapping here because forward/backward // dependence wouldn't be valid if these weren't monotonic accesses. - auto *Dist = cast( + auto *Dist = dyn_cast( PSE.getSE()->getMinusSCEV(StorePtrSCEV, LoadPtrSCEV)); + if (!Dist) + return false; const APInt &Val = Dist->getAPInt(); return Val == TypeByteSize * StrideLoad; } diff --git a/llvm/lib/Transforms/Utils/BasicBlockUtils.cpp b/llvm/lib/Transforms/Utils/BasicBlockUtils.cpp index 5396038d8b92b7d51327482d37dcbb2b2ff41067..4941f92b94f08203ea86115e4ce26679f93e5ec9 100644 --- a/llvm/lib/Transforms/Utils/BasicBlockUtils.cpp +++ b/llvm/lib/Transforms/Utils/BasicBlockUtils.cpp @@ -333,6 +333,10 @@ bool llvm::MergeBlockIntoPredecessor(BasicBlock *BB, DomTreeUpdater *DTU, // Finally, erase the old block and update dominator info. DeleteDeadBlock(BB, DTU); + // Remove redundant "llvm.dbg" instrunctions after blocks have been merged. + if (PredBB->getParent()->getSubprogram()) + RemoveRedundantDbgInstrs(PredBB); + return true; } diff --git a/llvm/lib/Transforms/Utils/CloneFunction.cpp b/llvm/lib/Transforms/Utils/CloneFunction.cpp index 3eac726994ae1392d70ee03a3ee1de6a2c5a2373..303a09805a9d8473b955287b051cc4f7a18c7518 100644 --- a/llvm/lib/Transforms/Utils/CloneFunction.cpp +++ b/llvm/lib/Transforms/Utils/CloneFunction.cpp @@ -1131,6 +1131,9 @@ BasicBlock *llvm::DuplicateInstructionsInSplitBetween( if (I != ValueMapping.end()) New->setOperand(i, I->second); } + + // Remap debug variable operands. + remapDebugVariable(ValueMapping, New); } return NewBB; diff --git a/llvm/lib/Transforms/Utils/EntryExitInstrumenter.cpp b/llvm/lib/Transforms/Utils/EntryExitInstrumenter.cpp index f4207474e9a68a716ffa25e076393d6afd39ff0d..59a7dd1a00ed48a0186846faf6c23598fb95badd 100644 --- a/llvm/lib/Transforms/Utils/EntryExitInstrumenter.cpp +++ b/llvm/lib/Transforms/Utils/EntryExitInstrumenter.cpp @@ -137,7 +137,8 @@ static bool runOnFunction(Function &F, bool PostInlining) { PreservedAnalyses llvm::EntryExitInstrumenterPass::run(Function &F, FunctionAnalysisManager &AM) { - runOnFunction(F, PostInlining); + if (!runOnFunction(F, PostInlining)) + return PreservedAnalyses::all(); PreservedAnalyses PA; PA.preserveSet(); return PA; diff --git a/llvm/lib/Transforms/Utils/Local.cpp b/llvm/lib/Transforms/Utils/Local.cpp index a42ef0c4e6ae9ed03f2b6f93add92c2ba5b06013..f3cd3104c3128045fd26b9f5daaaa7e98e034dbc 100644 --- a/llvm/lib/Transforms/Utils/Local.cpp +++ b/llvm/lib/Transforms/Utils/Local.cpp @@ -59,6 +59,7 @@ #include "llvm/IR/IntrinsicsWebAssembly.h" #include "llvm/IR/LLVMContext.h" #include "llvm/IR/MDBuilder.h" +#include "llvm/IR/MemoryModelRelaxationAnnotations.h" #include "llvm/IR/Metadata.h" #include "llvm/IR/Module.h" #include "llvm/IR/PatternMatch.h" @@ -3284,6 +3285,9 @@ void llvm::combineMetadata(Instruction *K, const Instruction *J, case LLVMContext::MD_invariant_group: // Preserve !invariant.group in K. break; + case LLVMContext::MD_mmra: + // Combine MMRAs + break; case LLVMContext::MD_align: if (DoesKMove || !K->hasMetadata(LLVMContext::MD_noundef)) K->setMetadata( @@ -3322,6 +3326,16 @@ void llvm::combineMetadata(Instruction *K, const Instruction *J, if (auto *JMD = J->getMetadata(LLVMContext::MD_invariant_group)) if (isa(K) || isa(K)) K->setMetadata(LLVMContext::MD_invariant_group, JMD); + + // Merge MMRAs. + // This is handled separately because we also want to handle cases where K + // doesn't have tags but J does. + auto JMMRA = J->getMetadata(LLVMContext::MD_mmra); + auto KMMRA = K->getMetadata(LLVMContext::MD_mmra); + if (JMMRA || KMMRA) { + K->setMetadata(LLVMContext::MD_mmra, + MMRAMetadata::combine(K->getContext(), JMMRA, KMMRA)); + } } void llvm::combineMetadataForCSE(Instruction *K, const Instruction *J, @@ -3341,7 +3355,8 @@ void llvm::combineMetadataForCSE(Instruction *K, const Instruction *J, LLVMContext::MD_preserve_access_index, LLVMContext::MD_prof, LLVMContext::MD_nontemporal, - LLVMContext::MD_noundef}; + LLVMContext::MD_noundef, + LLVMContext::MD_mmra}; combineMetadata(K, J, KnownIDs, KDominatesJ); } @@ -3429,15 +3444,15 @@ void llvm::patchReplacementInstruction(Instruction *I, Value *Repl) { combineMetadataForCSE(ReplInst, I, false); } -template +template static unsigned replaceDominatedUsesWith(Value *From, Value *To, const RootType &Root, - const DominatesFn &Dominates) { + const ShouldReplaceFn &ShouldReplace) { assert(From->getType() == To->getType()); unsigned Count = 0; for (Use &U : llvm::make_early_inc_range(From->uses())) { - if (!Dominates(Root, U)) + if (!ShouldReplace(Root, U)) continue; LLVM_DEBUG(dbgs() << "Replace dominated use of '"; From->printAsOperand(dbgs()); @@ -3481,6 +3496,26 @@ unsigned llvm::replaceDominatedUsesWith(Value *From, Value *To, return ::replaceDominatedUsesWith(From, To, BB, Dominates); } +unsigned llvm::replaceDominatedUsesWithIf( + Value *From, Value *To, DominatorTree &DT, const BasicBlockEdge &Root, + function_ref ShouldReplace) { + auto DominatesAndShouldReplace = + [&DT, &ShouldReplace, To](const BasicBlockEdge &Root, const Use &U) { + return DT.dominates(Root, U) && ShouldReplace(U, To); + }; + return ::replaceDominatedUsesWith(From, To, Root, DominatesAndShouldReplace); +} + +unsigned llvm::replaceDominatedUsesWithIf( + Value *From, Value *To, DominatorTree &DT, const BasicBlock *BB, + function_ref ShouldReplace) { + auto DominatesAndShouldReplace = [&DT, &ShouldReplace, + To](const BasicBlock *BB, const Use &U) { + return DT.dominates(BB, U) && ShouldReplace(U, To); + }; + return ::replaceDominatedUsesWith(From, To, BB, DominatesAndShouldReplace); +} + bool llvm::callsGCLeafFunction(const CallBase *Call, const TargetLibraryInfo &TLI) { // Check if the function is specifically marked as a gc leaf function. @@ -3650,6 +3685,30 @@ DIExpression *llvm::getExpressionForConstant(DIBuilder &DIB, const Constant &C, return nullptr; } +void llvm::remapDebugVariable(ValueToValueMapTy &Mapping, Instruction *Inst) { + auto RemapDebugOperands = [&Mapping](auto *DV, auto Set) { + for (auto *Op : Set) { + auto I = Mapping.find(Op); + if (I != Mapping.end()) + DV->replaceVariableLocationOp(Op, I->second, /*AllowEmpty=*/true); + } + }; + auto RemapAssignAddress = [&Mapping](auto *DA) { + auto I = Mapping.find(DA->getAddress()); + if (I != Mapping.end()) + DA->setAddress(I->second); + }; + if (auto DVI = dyn_cast(Inst)) + RemapDebugOperands(DVI, DVI->location_ops()); + if (auto DAI = dyn_cast(Inst)) + RemapAssignAddress(DAI); + for (DbgVariableRecord &DVR : filterDbgVars(Inst->getDbgRecordRange())) { + RemapDebugOperands(&DVR, DVR.location_ops()); + if (DVR.isDbgAssign()) + RemapAssignAddress(&DVR); + } +} + namespace { /// A potential constituent of a bitreverse or bswap expression. See diff --git a/llvm/lib/Transforms/Utils/SimplifyCFG.cpp b/llvm/lib/Transforms/Utils/SimplifyCFG.cpp index 0826d748ba0d2a8d85f30c94977c113a3a840928..4db72461c95e47d21932440bb9f5abb6856251fd 100644 --- a/llvm/lib/Transforms/Utils/SimplifyCFG.cpp +++ b/llvm/lib/Transforms/Utils/SimplifyCFG.cpp @@ -51,6 +51,7 @@ #include "llvm/IR/IntrinsicInst.h" #include "llvm/IR/LLVMContext.h" #include "llvm/IR/MDBuilder.h" +#include "llvm/IR/MemoryModelRelaxationAnnotations.h" #include "llvm/IR/Metadata.h" #include "llvm/IR/Module.h" #include "llvm/IR/NoFolder.h" @@ -1677,7 +1678,8 @@ bool SimplifyCFGOpt::hoistCommonCodeFromSuccessors(BasicBlock *BB, for (auto &SuccIter : OtherSuccIterRange) { Instruction *I2 = &*SuccIter; HasTerminator |= I2->isTerminator(); - if (AllInstsAreIdentical && !I1->isIdenticalToWhenDefined(I2)) + if (AllInstsAreIdentical && (!I1->isIdenticalToWhenDefined(I2) || + MMRAMetadata(*I1) != MMRAMetadata(*I2))) AllInstsAreIdentical = false; } @@ -1964,6 +1966,7 @@ static bool canSinkInstructions( } const Instruction *I0 = Insts.front(); + const auto I0MMRA = MMRAMetadata(*I0); for (auto *I : Insts) { if (!I->isSameOperationAs(I0)) return false; @@ -1975,6 +1978,11 @@ static bool canSinkInstructions( return false; if (isa(I) && I->getOperand(0)->isSwiftError()) return false; + + // Treat MMRAs conservatively. This pass can be quite aggressive and + // could drop a lot of MMRAs otherwise. + if (MMRAMetadata(*I) != I0MMRA) + return false; } // All instructions in Insts are known to be the same opcode. If they have a @@ -7516,6 +7524,13 @@ static bool passingValueIsAlwaysUndefined(Value *V, Instruction *I, bool PtrValu SI->getPointerAddressSpace())) && SI->getPointerOperand() == I; + // llvm.assume(false/undef) always triggers immediate UB. + if (auto *Assume = dyn_cast(Use)) { + // Ignore assume operand bundles. + if (I == Assume->getArgOperand(0)) + return true; + } + if (auto *CB = dyn_cast(Use)) { if (C->isNullValue() && NullPointerIsDefined(CB->getFunction())) return false; diff --git a/llvm/lib/Transforms/Vectorize/LoopVectorize.cpp b/llvm/lib/Transforms/Vectorize/LoopVectorize.cpp index 315e644ed4a81482292d727cf13ffe1c5c3beaaa..5a736e3ad56298d709f4b48f6029de419dfaf005 100644 --- a/llvm/lib/Transforms/Vectorize/LoopVectorize.cpp +++ b/llvm/lib/Transforms/Vectorize/LoopVectorize.cpp @@ -9358,6 +9358,14 @@ void VPWidenLoadRecipe::execute(VPTransformState &State) { } } +static Value *reverseMask(IRBuilderBase &Builder, Value *Mask, Value *EVL, + Value *AllTrueMask) { + VectorType *MaskTy = cast(Mask->getType()); + return Builder.CreateIntrinsic(MaskTy, Intrinsic::experimental_vp_reverse, + {Mask, AllTrueMask, EVL}, nullptr, + "vp.reverse.mask"); +} + void VPWidenLoadEVLRecipe::execute(VPTransformState &State) { assert(State.UF == 1 && "Expected only UF == 1 when vectorizing with " "explicit vector length."); @@ -9373,19 +9381,11 @@ void VPWidenLoadEVLRecipe::execute(VPTransformState &State) { CallInst *NewLI; Value *EVL = State.get(getEVL(), VPIteration(0, 0)); Value *Addr = State.get(getAddr(), 0, !CreateGather); - Value *Mask = getMask() - ? State.get(getMask(), 0) - : Builder.CreateVectorSplat(State.VF, Builder.getTrue()); - if (isReverse() && getMask()) { - VectorType *MaskTy = cast(Mask->getType()); - Mask = Builder.CreateIntrinsic( - MaskTy, Intrinsic::experimental_vp_reverse, - {Mask, - Builder.CreateVectorSplat(MaskTy->getElementCount(), - Builder.getTrue()), - EVL}, - nullptr, "vp.reverse.mask"); - } + Value *AllTrueMask = Builder.CreateVectorSplat(State.VF, Builder.getTrue()); + Value *Mask = getMask() ? State.get(getMask(), 0) : AllTrueMask; + if (isReverse() && getMask()) + Mask = reverseMask(Builder, Mask, EVL, AllTrueMask); + if (CreateGather) { NewLI = Builder.CreateIntrinsic(DataTy, Intrinsic::vp_gather, {Addr, Mask, EVL}, @@ -9401,10 +9401,9 @@ void VPWidenLoadEVLRecipe::execute(VPTransformState &State) { State.addMetadata(NewLI, LI); Instruction *Res = NewLI; if (isReverse()) { - Value *MaskVal = - Builder.CreateVectorSplat(DataTy->getElementCount(), Builder.getTrue()); - Res = Builder.CreateIntrinsic(DataTy, Intrinsic::experimental_vp_reverse, - {Res, MaskVal, EVL}, nullptr, "vp.reverse"); + Res = + Builder.CreateIntrinsic(DataTy, Intrinsic::experimental_vp_reverse, + {Res, AllTrueMask, EVL}, nullptr, "vp.reverse"); } State.set(this, Res, 0); } @@ -9464,27 +9463,16 @@ void VPWidenStoreEVLRecipe::execute(VPTransformState &State) { CallInst *NewSI = nullptr; Value *StoredVal = State.get(StoredValue, 0); Value *EVL = State.get(getEVL(), VPIteration(0, 0)); + Value *AllTrueMask = Builder.CreateVectorSplat(State.VF, Builder.getTrue()); if (isReverse()) { auto *StoredValTy = cast(StoredVal->getType()); - Value *MaskVal = Builder.CreateVectorSplat(StoredValTy->getElementCount(), - Builder.getTrue()); StoredVal = Builder.CreateIntrinsic( StoredValTy, Intrinsic::experimental_vp_reverse, - {StoredVal, MaskVal, EVL}, nullptr, "vp.reverse"); - } - Value *Mask = getMask() - ? State.get(getMask(), 0) - : Builder.CreateVectorSplat(State.VF, Builder.getTrue()); - if (isReverse() && getMask()) { - VectorType *MaskTy = cast(Mask->getType()); - Mask = Builder.CreateIntrinsic( - MaskTy, Intrinsic::experimental_vp_reverse, - {Mask, - Builder.CreateVectorSplat(MaskTy->getElementCount(), - Builder.getTrue()), - EVL}, - nullptr, "vp.reverse.mask"); + {StoredVal, AllTrueMask, EVL}, nullptr, "vp.reverse"); } + Value *Mask = getMask() ? State.get(getMask(), 0) : AllTrueMask; + if (isReverse() && getMask()) + Mask = reverseMask(Builder, Mask, EVL, AllTrueMask); Value *Addr = State.get(getAddr(), 0, !CreateScatter); if (CreateScatter) { NewSI = Builder.CreateIntrinsic(Type::getVoidTy(EVL->getContext()), diff --git a/llvm/lib/Transforms/Vectorize/SLPVectorizer.cpp b/llvm/lib/Transforms/Vectorize/SLPVectorizer.cpp index a1a28076881cb5dc75989844b7067232c6d510f3..fbece8c0109c38f73f657458ad49594cdb667253 100644 --- a/llvm/lib/Transforms/Vectorize/SLPVectorizer.cpp +++ b/llvm/lib/Transforms/Vectorize/SLPVectorizer.cpp @@ -1135,6 +1135,7 @@ public: ScalarToTreeEntry.clear(); MultiNodeScalars.clear(); MustGather.clear(); + NonScheduledFirst.clear(); EntryToLastInstruction.clear(); ExternalUses.clear(); ExternalUsesAsGEPs.clear(); @@ -1252,7 +1253,7 @@ public: /// effectively impossible for the backend to undo. /// TODO: If load combining is allowed in the IR optimizer, this analysis /// may not be necessary. - bool isLoadCombineCandidate() const; + bool isLoadCombineCandidate(ArrayRef Stores) const; /// Checks if the given array of loads can be represented as a vectorized, /// scatter or just simple gather. @@ -2356,6 +2357,14 @@ public: bool isAnyGathered(const SmallDenseSet &Vals) const { return any_of(MustGather, [&](Value *V) { return Vals.contains(V); }); } + /// Checks if the given value is gathered in one of the nodes. + bool isGathered(const Value *V) const { + return MustGather.contains(V); + } + /// Checks if the specified value was not schedule. + bool isNotScheduled(const Value *V) const { + return NonScheduledFirst.contains(V); + } /// Check if the value is vectorized in the tree. bool isVectorized(Value *V) const { return getTreeEntry(V); } @@ -3071,6 +3080,9 @@ private: /// A list of scalars that we found that we need to keep as scalars. ValueSet MustGather; + /// A set of first non-schedulable values. + ValueSet NonScheduledFirst; + /// A map between the vectorized entries and the last instructions in the /// bundles. The bundles are built in use order, not in the def order of the /// instructions. So, we cannot rely directly on the last instruction in the @@ -6646,6 +6658,7 @@ void BoUpSLP::buildTree_rec(ArrayRef VL, unsigned Depth, "tryScheduleBundle should cancelScheduling on failure"); newTreeEntry(VL, std::nullopt /*not vectorized*/, S, UserTreeIdx, ReuseShuffleIndicies); + NonScheduledFirst.insert(VL.front()); return; } LLVM_DEBUG(dbgs() << "SLP: We are able to schedule this bundle.\n"); @@ -9587,11 +9600,11 @@ bool BoUpSLP::isLoadCombineReductionCandidate(RecurKind RdxKind) const { /* MatchOr */ false); } -bool BoUpSLP::isLoadCombineCandidate() const { +bool BoUpSLP::isLoadCombineCandidate(ArrayRef Stores) const { // Peek through a final sequence of stores and check if all operations are // likely to be load-combined. - unsigned NumElts = VectorizableTree[0]->Scalars.size(); - for (Value *Scalar : VectorizableTree[0]->Scalars) { + unsigned NumElts = Stores.size(); + for (Value *Scalar : Stores) { Value *X; if (!match(Scalar, m_Store(m_Value(X), m_Value())) || !isLoadCombineCandidateImpl(X, NumElts, TTI, /* MatchOr */ true)) @@ -15072,11 +15085,16 @@ void BoUpSLP::computeMinimumValueSizes() { IsSignedCmp = NodeIdx < VectorizableTree.size() && any_of(VectorizableTree[NodeIdx]->UserTreeIndices, - [](const EdgeInfo &EI) { + [&](const EdgeInfo &EI) { return EI.UserTE->getOpcode() == Instruction::ICmp && - any_of(EI.UserTE->Scalars, [](Value *V) { + any_of(EI.UserTE->Scalars, [&](Value *V) { auto *IC = dyn_cast(V); - return IC && IC->isSigned(); + return IC && + (IC->isSigned() || + !isKnownNonNegative(IC->getOperand(0), + SimplifyQuery(*DL)) || + !isKnownNonNegative(IC->getOperand(1), + SimplifyQuery(*DL))); }); }); } @@ -15205,8 +15223,11 @@ bool SLPVectorizerPass::runImpl(Function &F, ScalarEvolution *SE_, return Changed; } -bool SLPVectorizerPass::vectorizeStoreChain(ArrayRef Chain, BoUpSLP &R, - unsigned Idx, unsigned MinVF) { +std::optional +SLPVectorizerPass::vectorizeStoreChain(ArrayRef Chain, BoUpSLP &R, + unsigned Idx, unsigned MinVF, + unsigned &Size) { + Size = 0; LLVM_DEBUG(dbgs() << "SLP: Analyzing a store chain of length " << Chain.size() << "\n"); const unsigned Sz = R.getVectorElementSize(Chain[0]); @@ -15223,11 +15244,42 @@ bool SLPVectorizerPass::vectorizeStoreChain(ArrayRef Chain, BoUpSLP &R, LLVM_DEBUG(dbgs() << "SLP: Analyzing " << VF << " stores at offset " << Idx << "\n"); + SetVector ValOps; + for (Value *V : Chain) + ValOps.insert(cast(V)->getValueOperand()); + // Operands are not same/alt opcodes or non-power-of-2 uniques - exit. + InstructionsState S = getSameOpcode(ValOps.getArrayRef(), *TLI); + if (all_of(ValOps, IsaPred) && ValOps.size() > 1) { + DenseSet Stores(Chain.begin(), Chain.end()); + bool IsPowerOf2 = + isPowerOf2_32(ValOps.size()) || + (VectorizeNonPowerOf2 && isPowerOf2_32(ValOps.size() + 1)); + if ((!IsPowerOf2 && S.getOpcode() && S.getOpcode() != Instruction::Load && + (!S.MainOp->isSafeToRemove() || + any_of(ValOps.getArrayRef(), + [&](Value *V) { + return !isa(V) && + (V->getNumUses() > Chain.size() || + any_of(V->users(), [&](User *U) { + return !Stores.contains(U); + })); + }))) || + (ValOps.size() > Chain.size() / 2 && !S.getOpcode())) { + Size = (!IsPowerOf2 && S.getOpcode()) ? 1 : 2; + return false; + } + } + if (R.isLoadCombineCandidate(Chain)) + return true; R.buildTree(Chain); - if (R.isTreeTinyAndNotFullyVectorizable()) - return false; - if (R.isLoadCombineCandidate()) + // Check if tree tiny and store itself or its value is not vectorized. + if (R.isTreeTinyAndNotFullyVectorizable()) { + if (R.isGathered(Chain.front()) || + R.isNotScheduled(cast(Chain.front())->getValueOperand())) + return std::nullopt; + Size = R.getTreeSize(); return false; + } R.reorderTopToBottom(); R.reorderBottomToTop(); R.buildExternalUses(); @@ -15235,6 +15287,9 @@ bool SLPVectorizerPass::vectorizeStoreChain(ArrayRef Chain, BoUpSLP &R, R.computeMinimumValueSizes(); R.transformNodes(); + Size = R.getTreeSize(); + if (S.getOpcode() == Instruction::Load) + Size = 2; // cut off masked gather small trees InstructionCost Cost = R.getTreeCost(); LLVM_DEBUG(dbgs() << "SLP: Found cost = " << Cost << " for VF=" << VF << "\n"); @@ -15256,17 +15311,45 @@ bool SLPVectorizerPass::vectorizeStoreChain(ArrayRef Chain, BoUpSLP &R, return false; } -bool SLPVectorizerPass::vectorizeStores(ArrayRef Stores, - BoUpSLP &R) { +/// Checks if the quadratic mean deviation is less than 90% of the mean size. +static bool checkTreeSizes(ArrayRef> Sizes, + bool First) { + unsigned Num = 0; + uint64_t Sum = std::accumulate( + Sizes.begin(), Sizes.end(), static_cast(0), + [&](uint64_t V, const std::pair &Val) { + unsigned Size = First ? Val.first : Val.second; + if (Size == 1) + return V; + ++Num; + return V + Size; + }); + if (Num == 0) + return true; + uint64_t Mean = Sum / Num; + if (Mean == 0) + return true; + uint64_t Dev = std::accumulate( + Sizes.begin(), Sizes.end(), static_cast(0), + [&](uint64_t V, const std::pair &Val) { + unsigned P = First ? Val.first : Val.second; + if (P == 1) + return V; + return V + (P - Mean) * (P - Mean); + }) / + Num; + return Dev * 81 / (Mean * Mean) == 0; +} + +bool SLPVectorizerPass::vectorizeStores( + ArrayRef Stores, BoUpSLP &R, + DenseSet> + &Visited) { // We may run into multiple chains that merge into a single chain. We mark the // stores that we vectorized so that we don't visit the same store twice. BoUpSLP::ValueSet VectorizedStores; bool Changed = false; - // Stores the pair of stores (first_store, last_store) in a range, that were - // already tried to be vectorized. Allows to skip the store ranges that were - // already tried to be vectorized but the attempts were unsuccessful. - DenseSet> TriedSequences; struct StoreDistCompare { bool operator()(const std::pair &Op1, const std::pair &Op2) const { @@ -15294,7 +15377,14 @@ bool SLPVectorizerPass::vectorizeStores(ArrayRef Stores, PrevDist = DataVar.second; }); - if (Operands.size() <= 1) + if (Operands.size() <= 1 || + !Visited + .insert({Operands.front(), + cast(Operands.front())->getValueOperand(), + Operands.back(), + cast(Operands.back())->getValueOperand(), + Operands.size()}) + .second) continue; unsigned MaxVecRegSize = R.getMaxVecRegSize(); @@ -15303,13 +15393,19 @@ bool SLPVectorizerPass::vectorizeStores(ArrayRef Stores, unsigned MaxVF = std::min(R.getMaximumVF(EltSize, Instruction::Store), MaxElts); + unsigned MaxRegVF = MaxVF; auto *Store = cast(Operands[0]); Type *StoreTy = Store->getValueOperand()->getType(); Type *ValueTy = StoreTy; if (auto *Trunc = dyn_cast(Store->getValueOperand())) ValueTy = Trunc->getSrcTy(); - unsigned MinVF = PowerOf2Ceil(TTI->getStoreMinimumVF( - R.getMinVF(DL->getTypeStoreSizeInBits(StoreTy)), StoreTy, ValueTy)); + if (ValueTy == StoreTy && + R.getVectorElementSize(Store->getValueOperand()) <= EltSize) + MaxVF = std::min(MaxVF, bit_floor(Operands.size())); + unsigned MinVF = std::max( + 2, PowerOf2Ceil(TTI->getStoreMinimumVF( + R.getMinVF(DL->getTypeStoreSizeInBits(StoreTy)), StoreTy, + ValueTy))); if (MaxVF < MinVF) { LLVM_DEBUG(dbgs() << "SLP: Vectorization infeasible as MaxVF (" << MaxVF @@ -15324,7 +15420,7 @@ bool SLPVectorizerPass::vectorizeStores(ArrayRef Stores, // consider cases where VF + 1 is a power-of-2, i.e. almost all vector // lanes are used. unsigned CandVF = Operands.size(); - if (isPowerOf2_32(CandVF + 1) && CandVF <= MaxVF) + if (isPowerOf2_32(CandVF + 1) && CandVF <= MaxRegVF) NonPowerOf2VF = CandVF; } @@ -15335,40 +15431,184 @@ bool SLPVectorizerPass::vectorizeStores(ArrayRef Stores, VF = Size > MaxVF ? NonPowerOf2VF : Size; Size *= 2; }); - unsigned StartIdx = 0; - for (unsigned Size : CandidateVFs) { - for (unsigned Cnt = StartIdx, E = Operands.size(); Cnt + Size <= E;) { - ArrayRef Slice = ArrayRef(Operands).slice(Cnt, Size); - assert( - all_of( - Slice, - [&](Value *V) { - return cast(V)->getValueOperand()->getType() == - cast(Slice.front()) - ->getValueOperand() - ->getType(); - }) && - "Expected all operands of same type."); - if (!VectorizedStores.count(Slice.front()) && - !VectorizedStores.count(Slice.back()) && - TriedSequences.insert(std::make_pair(Slice.front(), Slice.back())) - .second && - vectorizeStoreChain(Slice, R, Cnt, MinVF)) { - // Mark the vectorized stores so that we don't vectorize them again. - VectorizedStores.insert(Slice.begin(), Slice.end()); - Changed = true; - // If we vectorized initial block, no need to try to vectorize it - // again. - if (Cnt == StartIdx) - StartIdx += Size; - Cnt += Size; - continue; + unsigned End = Operands.size(); + unsigned Repeat = 0; + constexpr unsigned MaxAttempts = 4; + OwningArrayRef> RangeSizes(Operands.size()); + for_each(RangeSizes, [](std::pair &P) { + P.first = P.second = 1; + }); + DenseMap> NonSchedulable; + auto IsNotVectorized = [](bool First, + const std::pair &P) { + return First ? P.first > 0 : P.second > 0; + }; + auto IsVectorized = [](bool First, + const std::pair &P) { + return First ? P.first == 0 : P.second == 0; + }; + auto VFIsProfitable = [](bool First, unsigned Size, + const std::pair &P) { + return First ? Size >= P.first : Size >= P.second; + }; + auto FirstSizeSame = [](unsigned Size, + const std::pair &P) { + return Size == P.first; + }; + while (true) { + ++Repeat; + bool RepeatChanged = false; + bool AnyProfitableGraph; + for (unsigned Size : CandidateVFs) { + AnyProfitableGraph = false; + unsigned StartIdx = std::distance( + RangeSizes.begin(), + find_if(RangeSizes, std::bind(IsNotVectorized, Size >= MaxRegVF, + std::placeholders::_1))); + while (StartIdx < End) { + unsigned EndIdx = + std::distance(RangeSizes.begin(), + find_if(RangeSizes.drop_front(StartIdx), + std::bind(IsVectorized, Size >= MaxRegVF, + std::placeholders::_1))); + unsigned Sz = EndIdx >= End ? End : EndIdx; + for (unsigned Cnt = StartIdx; Cnt + Size <= Sz;) { + if (!checkTreeSizes(RangeSizes.slice(Cnt, Size), + Size >= MaxRegVF)) { + ++Cnt; + continue; + } + ArrayRef Slice = ArrayRef(Operands).slice(Cnt, Size); + assert(all_of(Slice, + [&](Value *V) { + return cast(V) + ->getValueOperand() + ->getType() == + cast(Slice.front()) + ->getValueOperand() + ->getType(); + }) && + "Expected all operands of same type."); + if (!NonSchedulable.empty()) { + auto [NonSchedSizeMax, NonSchedSizeMin] = + NonSchedulable.lookup(Slice.front()); + if (NonSchedSizeMax > 0 && NonSchedSizeMin <= Size) { + Cnt += NonSchedSizeMax; + continue; + } + } + unsigned TreeSize; + std::optional Res = + vectorizeStoreChain(Slice, R, Cnt, MinVF, TreeSize); + if (!Res) { + NonSchedulable + .try_emplace(Slice.front(), std::make_pair(Size, Size)) + .first->getSecond() + .second = Size; + } else if (*Res) { + // Mark the vectorized stores so that we don't vectorize them + // again. + VectorizedStores.insert(Slice.begin(), Slice.end()); + // Mark the vectorized stores so that we don't vectorize them + // again. + AnyProfitableGraph = RepeatChanged = Changed = true; + // If we vectorized initial block, no need to try to vectorize + // it again. + for_each(RangeSizes.slice(Cnt, Size), + [](std::pair &P) { + P.first = P.second = 0; + }); + if (Cnt < StartIdx + MinVF) { + for_each(RangeSizes.slice(StartIdx, Cnt - StartIdx), + [](std::pair &P) { + P.first = P.second = 0; + }); + StartIdx = Cnt + Size; + } + if (Cnt > Sz - Size - MinVF) { + for_each(RangeSizes.slice(Cnt + Size, Sz - (Cnt + Size)), + [](std::pair &P) { + P.first = P.second = 0; + }); + if (Sz == End) + End = Cnt; + Sz = Cnt; + } + Cnt += Size; + continue; + } + if (Size > 2 && Res && + !all_of(RangeSizes.slice(Cnt, Size), + std::bind(VFIsProfitable, Size >= MaxRegVF, TreeSize, + std::placeholders::_1))) { + Cnt += Size; + continue; + } + // Check for the very big VFs that we're not rebuilding same + // trees, just with larger number of elements. + if (Size > MaxRegVF && TreeSize > 1 && + all_of(RangeSizes.slice(Cnt, Size), + std::bind(FirstSizeSame, TreeSize, + std::placeholders::_1))) { + Cnt += Size; + while (Cnt != Sz && RangeSizes[Cnt].first == TreeSize) + ++Cnt; + continue; + } + if (TreeSize > 1) + for_each(RangeSizes.slice(Cnt, Size), + [&](std::pair &P) { + if (Size >= MaxRegVF) + P.second = std::max(P.second, TreeSize); + else + P.first = std::max(P.first, TreeSize); + }); + ++Cnt; + AnyProfitableGraph = true; + } + if (StartIdx >= End) + break; + if (Sz - StartIdx < Size && Sz - StartIdx >= MinVF) + AnyProfitableGraph = true; + StartIdx = std::distance( + RangeSizes.begin(), + find_if(RangeSizes.drop_front(Sz), + std::bind(IsNotVectorized, Size >= MaxRegVF, + std::placeholders::_1))); } - ++Cnt; + if (!AnyProfitableGraph && Size >= MaxRegVF) + break; } - // Check if the whole array was vectorized already - exit. - if (StartIdx >= Operands.size()) + // All values vectorized - exit. + if (all_of(RangeSizes, [](const std::pair &P) { + return P.first == 0 && P.second == 0; + })) break; + // Check if tried all attempts or no need for the last attempts at all. + if (Repeat >= MaxAttempts || + (Repeat > 1 && (RepeatChanged || !AnyProfitableGraph))) + break; + constexpr unsigned StoresLimit = 64; + const unsigned MaxTotalNum = bit_floor(std::min( + Operands.size(), + static_cast( + End - + std::distance( + RangeSizes.begin(), + find_if(RangeSizes, std::bind(IsNotVectorized, true, + std::placeholders::_1))) + + 1))); + unsigned VF = PowerOf2Ceil(CandidateVFs.front()) * 2; + if (VF > MaxTotalNum || VF >= StoresLimit) + break; + for_each(RangeSizes, [&](std::pair &P) { + if (P.first != 0) + P.first = std::max(P.second, P.first); + }); + // Last attempt to vectorize max number of elements, if all previous + // attempts were unsuccessful because of the cost issues. + CandidateVFs.clear(); + CandidateVFs.push_back(VF); } } }; @@ -18186,6 +18426,7 @@ bool SLPVectorizerPass::vectorizeStoreChains(BoUpSLP &R) { }; // Attempt to sort and vectorize each of the store-groups. + DenseSet> Attempted; for (auto &Pair : Stores) { if (Pair.second.size() < 2) continue; @@ -18203,8 +18444,8 @@ bool SLPVectorizerPass::vectorizeStoreChains(BoUpSLP &R) { Pair.second.rend()); Changed |= tryToVectorizeSequence( ReversedStores, StoreSorter, AreCompatibleStores, - [this, &R](ArrayRef Candidates, bool) { - return vectorizeStores(Candidates, R); + [&](ArrayRef Candidates, bool) { + return vectorizeStores(Candidates, R, Attempted); }, /*MaxVFOnly=*/false, R); } diff --git a/llvm/lib/Transforms/Vectorize/VPlan.h b/llvm/lib/Transforms/Vectorize/VPlan.h index 24b573a0dd328f57a3b1298a19df84cbfcf1ca52..ca6c396738d8e26ac38a55c1768f59b99155f33a 100644 --- a/llvm/lib/Transforms/Vectorize/VPlan.h +++ b/llvm/lib/Transforms/Vectorize/VPlan.h @@ -3279,8 +3279,8 @@ public: private: /// Add to the given dominator tree the header block and every new basic block /// that was created between it and the latch block, inclusive. - static void updateDominatorTree(DominatorTree *DT, BasicBlock *LoopLatchBB, - BasicBlock *LoopPreHeaderBB, + static void updateDominatorTree(DominatorTree *DT, BasicBlock *LoopHeaderBB, + BasicBlock *LoopLatchBB, BasicBlock *LoopExitBB); }; diff --git a/llvm/lib/Transforms/Vectorize/VPlanAnalysis.cpp b/llvm/lib/Transforms/Vectorize/VPlanAnalysis.cpp index ad4ea648cd61481da23e26332b67191a5d4dc8d5..5f93339083f0c2de2b3034430c21bbcb5eb09dc2 100644 --- a/llvm/lib/Transforms/Vectorize/VPlanAnalysis.cpp +++ b/llvm/lib/Transforms/Vectorize/VPlanAnalysis.cpp @@ -35,6 +35,7 @@ Type *VPTypeAnalysis::inferScalarTypeForRecipe(const VPInstruction *R) { CachedTypes[OtherV] = ResTy; return ResTy; } + case Instruction::Or: case Instruction::ICmp: case VPInstruction::FirstOrderRecurrenceSplice: { Type *ResTy = inferScalarType(R->getOperand(0)); @@ -44,6 +45,12 @@ Type *VPTypeAnalysis::inferScalarTypeForRecipe(const VPInstruction *R) { CachedTypes[OtherV] = ResTy; return ResTy; } + case VPInstruction::Not: { + Type *ResTy = inferScalarType(R->getOperand(0)); + assert(IntegerType::get(Ctx, 1) == ResTy && + "unexpected scalar type inferred for operand"); + return ResTy; + } case VPInstruction::PtrAdd: // Return the type based on the pointer argument (i.e. first operand). return inferScalarType(R->getOperand(0)); diff --git a/llvm/lib/Transforms/Vectorize/VectorCombine.cpp b/llvm/lib/Transforms/Vectorize/VectorCombine.cpp index da03a69708ddfc7e95a4fbc0be4c05215f55d5d4..da3c780550a083ce7470b3dfa3e2cee12d5d214c 100644 --- a/llvm/lib/Transforms/Vectorize/VectorCombine.cpp +++ b/llvm/lib/Transforms/Vectorize/VectorCombine.cpp @@ -1395,60 +1395,91 @@ bool VectorCombine::scalarizeLoadExtract(Instruction &I) { return true; } -/// Try to convert "shuffle (binop), (binop)" with a shared binop operand into -/// "binop (shuffle), (shuffle)". +/// Try to convert "shuffle (binop), (binop)" into "binop (shuffle), (shuffle)". bool VectorCombine::foldShuffleOfBinops(Instruction &I) { - auto *VecTy = cast(I.getType()); BinaryOperator *B0, *B1; - ArrayRef Mask; + ArrayRef OldMask; if (!match(&I, m_Shuffle(m_OneUse(m_BinOp(B0)), m_OneUse(m_BinOp(B1)), - m_Mask(Mask))) || - B0->getOpcode() != B1->getOpcode() || B0->getType() != VecTy) + m_Mask(OldMask)))) return false; // Don't introduce poison into div/rem. - if (any_of(Mask, [](int M) { return M == PoisonMaskElem; }) && + if (any_of(OldMask, [](int M) { return M == PoisonMaskElem; }) && B0->isIntDivRem()) return false; - // Try to replace a binop with a shuffle if the shuffle is not costly. - // The new shuffle will choose from a single, common operand, so it may be - // cheaper than the existing two-operand shuffle. - SmallVector UnaryMask = createUnaryMask(Mask, Mask.size()); + // TODO: Add support for addlike etc. Instruction::BinaryOps Opcode = B0->getOpcode(); - InstructionCost BinopCost = TTI.getArithmeticInstrCost(Opcode, VecTy); - InstructionCost ShufCost = TTI.getShuffleCost( - TargetTransformInfo::SK_PermuteSingleSrc, VecTy, UnaryMask); - if (ShufCost > BinopCost) + if (Opcode != B1->getOpcode()) + return false; + + auto *ShuffleDstTy = dyn_cast(I.getType()); + auto *BinOpTy = dyn_cast(B0->getType()); + if (!ShuffleDstTy || !BinOpTy) return false; + unsigned NumSrcElts = BinOpTy->getNumElements(); + // If we have something like "add X, Y" and "add Z, X", swap ops to match. Value *X = B0->getOperand(0), *Y = B0->getOperand(1); Value *Z = B1->getOperand(0), *W = B1->getOperand(1); - if (BinaryOperator::isCommutative(Opcode) && X != Z && Y != W) + if (BinaryOperator::isCommutative(Opcode) && X != Z && Y != W && + (X == W || Y == Z)) std::swap(X, Y); - Value *Shuf0, *Shuf1; + auto ConvertToUnary = [NumSrcElts](int &M) { + if (M >= (int)NumSrcElts) + M -= NumSrcElts; + }; + + SmallVector NewMask0(OldMask.begin(), OldMask.end()); + TargetTransformInfo::ShuffleKind SK0 = TargetTransformInfo::SK_PermuteTwoSrc; if (X == Z) { - // shuf (bo X, Y), (bo X, W) --> bo (shuf X), (shuf Y, W) - Shuf0 = Builder.CreateShuffleVector(X, UnaryMask); - Shuf1 = Builder.CreateShuffleVector(Y, W, Mask); - } else if (Y == W) { - // shuf (bo X, Y), (bo Z, Y) --> bo (shuf X, Z), (shuf Y) - Shuf0 = Builder.CreateShuffleVector(X, Z, Mask); - Shuf1 = Builder.CreateShuffleVector(Y, UnaryMask); - } else { - return false; + llvm::for_each(NewMask0, ConvertToUnary); + SK0 = TargetTransformInfo::SK_PermuteSingleSrc; + Z = PoisonValue::get(BinOpTy); } + SmallVector NewMask1(OldMask.begin(), OldMask.end()); + TargetTransformInfo::ShuffleKind SK1 = TargetTransformInfo::SK_PermuteTwoSrc; + if (Y == W) { + llvm::for_each(NewMask1, ConvertToUnary); + SK1 = TargetTransformInfo::SK_PermuteSingleSrc; + W = PoisonValue::get(BinOpTy); + } + + // Try to replace a binop with a shuffle if the shuffle is not costly. + TTI::TargetCostKind CostKind = TTI::TCK_RecipThroughput; + + InstructionCost OldCost = + TTI.getArithmeticInstrCost(B0->getOpcode(), BinOpTy, CostKind) + + TTI.getArithmeticInstrCost(B1->getOpcode(), BinOpTy, CostKind) + + TTI.getShuffleCost(TargetTransformInfo::SK_PermuteTwoSrc, BinOpTy, + OldMask, CostKind, 0, nullptr, {B0, B1}, &I); + + InstructionCost NewCost = + TTI.getShuffleCost(SK0, BinOpTy, NewMask0, CostKind, 0, nullptr, {X, Z}) + + TTI.getShuffleCost(SK1, BinOpTy, NewMask1, CostKind, 0, nullptr, {Y, W}) + + TTI.getArithmeticInstrCost(Opcode, ShuffleDstTy, CostKind); + + LLVM_DEBUG(dbgs() << "Found a shuffle feeding two binops: " << I + << "\n OldCost: " << OldCost << " vs NewCost: " << NewCost + << "\n"); + if (NewCost >= OldCost) + return false; + + Value *Shuf0 = Builder.CreateShuffleVector(X, Z, NewMask0); + Value *Shuf1 = Builder.CreateShuffleVector(Y, W, NewMask1); Value *NewBO = Builder.CreateBinOp(Opcode, Shuf0, Shuf1); + // Intersect flags from the old binops. if (auto *NewInst = dyn_cast(NewBO)) { NewInst->copyIRFlags(B0); NewInst->andIRFlags(B1); } - // TODO: Add Shuf0/Shuf1 to WorkList? + Worklist.pushValue(Shuf0); + Worklist.pushValue(Shuf1); replaceValue(I, *NewBO); return true; } diff --git a/llvm/test/Analysis/CostModel/AArch64/sve-intrinsics.ll b/llvm/test/Analysis/CostModel/AArch64/sve-intrinsics.ll index 8d5535e2a82f7d56a6b42828e5def1e6a9249df2..7ce3021b00935e38a06cf6037b8950c4eac89e3c 100644 --- a/llvm/test/Analysis/CostModel/AArch64/sve-intrinsics.ll +++ b/llvm/test/Analysis/CostModel/AArch64/sve-intrinsics.ll @@ -693,14 +693,14 @@ define void @get_lane_mask() #0 { ; CHECK-NEXT: Cost Model: Found an estimated cost of 1 for instruction: %mask_nxv2i1_i32 = call @llvm.get.active.lane.mask.nxv2i1.i32(i32 undef, i32 undef) ; CHECK-NEXT: Cost Model: Found an estimated cost of 64 for instruction: %mask_nxv32i1_i64 = call @llvm.get.active.lane.mask.nxv32i1.i64(i64 undef, i64 undef) ; CHECK-NEXT: Cost Model: Found an estimated cost of 8 for instruction: %mask_nxv16i1_i16 = call @llvm.get.active.lane.mask.nxv16i1.i16(i16 undef, i16 undef) -; CHECK-NEXT: Cost Model: Found an estimated cost of 1 for instruction: %mask_v16i1_i64 = call <16 x i1> @llvm.get.active.lane.mask.v16i1.i64(i64 undef, i64 undef) -; CHECK-NEXT: Cost Model: Found an estimated cost of 1 for instruction: %mask_v8i1_i64 = call <8 x i1> @llvm.get.active.lane.mask.v8i1.i64(i64 undef, i64 undef) -; CHECK-NEXT: Cost Model: Found an estimated cost of 1 for instruction: %mask_v4i1_i64 = call <4 x i1> @llvm.get.active.lane.mask.v4i1.i64(i64 undef, i64 undef) -; CHECK-NEXT: Cost Model: Found an estimated cost of 1 for instruction: %mask_v2i1_i64 = call <2 x i1> @llvm.get.active.lane.mask.v2i1.i64(i64 undef, i64 undef) -; CHECK-NEXT: Cost Model: Found an estimated cost of 1 for instruction: %mask_v16i1_i32 = call <16 x i1> @llvm.get.active.lane.mask.v16i1.i32(i32 undef, i32 undef) -; CHECK-NEXT: Cost Model: Found an estimated cost of 1 for instruction: %mask_v8i1_i32 = call <8 x i1> @llvm.get.active.lane.mask.v8i1.i32(i32 undef, i32 undef) -; CHECK-NEXT: Cost Model: Found an estimated cost of 1 for instruction: %mask_v4i1_i32 = call <4 x i1> @llvm.get.active.lane.mask.v4i1.i32(i32 undef, i32 undef) -; CHECK-NEXT: Cost Model: Found an estimated cost of 1 for instruction: %mask_v2i1_i32 = call <2 x i1> @llvm.get.active.lane.mask.v2i1.i32(i32 undef, i32 undef) +; CHECK-NEXT: Cost Model: Found an estimated cost of 32 for instruction: %mask_v16i1_i64 = call <16 x i1> @llvm.get.active.lane.mask.v16i1.i64(i64 undef, i64 undef) +; CHECK-NEXT: Cost Model: Found an estimated cost of 16 for instruction: %mask_v8i1_i64 = call <8 x i1> @llvm.get.active.lane.mask.v8i1.i64(i64 undef, i64 undef) +; CHECK-NEXT: Cost Model: Found an estimated cost of 8 for instruction: %mask_v4i1_i64 = call <4 x i1> @llvm.get.active.lane.mask.v4i1.i64(i64 undef, i64 undef) +; CHECK-NEXT: Cost Model: Found an estimated cost of 4 for instruction: %mask_v2i1_i64 = call <2 x i1> @llvm.get.active.lane.mask.v2i1.i64(i64 undef, i64 undef) +; CHECK-NEXT: Cost Model: Found an estimated cost of 32 for instruction: %mask_v16i1_i32 = call <16 x i1> @llvm.get.active.lane.mask.v16i1.i32(i32 undef, i32 undef) +; CHECK-NEXT: Cost Model: Found an estimated cost of 16 for instruction: %mask_v8i1_i32 = call <8 x i1> @llvm.get.active.lane.mask.v8i1.i32(i32 undef, i32 undef) +; CHECK-NEXT: Cost Model: Found an estimated cost of 8 for instruction: %mask_v4i1_i32 = call <4 x i1> @llvm.get.active.lane.mask.v4i1.i32(i32 undef, i32 undef) +; CHECK-NEXT: Cost Model: Found an estimated cost of 4 for instruction: %mask_v2i1_i32 = call <2 x i1> @llvm.get.active.lane.mask.v2i1.i32(i32 undef, i32 undef) ; CHECK-NEXT: Cost Model: Found an estimated cost of 144 for instruction: %mask_v32i1_i64 = call <32 x i1> @llvm.get.active.lane.mask.v32i1.i64(i64 undef, i64 undef) ; CHECK-NEXT: Cost Model: Found an estimated cost of 22 for instruction: %mask_v16i1_i16 = call <16 x i1> @llvm.get.active.lane.mask.v16i1.i16(i16 undef, i16 undef) ; CHECK-NEXT: Cost Model: Found an estimated cost of 0 for instruction: ret void @@ -716,14 +716,14 @@ define void @get_lane_mask() #0 { ; TYPE_BASED_ONLY-NEXT: Cost Model: Invalid cost for instruction: %mask_nxv2i1_i32 = call @llvm.get.active.lane.mask.nxv2i1.i32(i32 undef, i32 undef) ; TYPE_BASED_ONLY-NEXT: Cost Model: Invalid cost for instruction: %mask_nxv32i1_i64 = call @llvm.get.active.lane.mask.nxv32i1.i64(i64 undef, i64 undef) ; TYPE_BASED_ONLY-NEXT: Cost Model: Invalid cost for instruction: %mask_nxv16i1_i16 = call @llvm.get.active.lane.mask.nxv16i1.i16(i16 undef, i16 undef) -; TYPE_BASED_ONLY-NEXT: Cost Model: Found an estimated cost of 48 for instruction: %mask_v16i1_i64 = call <16 x i1> @llvm.get.active.lane.mask.v16i1.i64(i64 undef, i64 undef) -; TYPE_BASED_ONLY-NEXT: Cost Model: Found an estimated cost of 24 for instruction: %mask_v8i1_i64 = call <8 x i1> @llvm.get.active.lane.mask.v8i1.i64(i64 undef, i64 undef) -; TYPE_BASED_ONLY-NEXT: Cost Model: Found an estimated cost of 12 for instruction: %mask_v4i1_i64 = call <4 x i1> @llvm.get.active.lane.mask.v4i1.i64(i64 undef, i64 undef) -; TYPE_BASED_ONLY-NEXT: Cost Model: Found an estimated cost of 6 for instruction: %mask_v2i1_i64 = call <2 x i1> @llvm.get.active.lane.mask.v2i1.i64(i64 undef, i64 undef) -; TYPE_BASED_ONLY-NEXT: Cost Model: Found an estimated cost of 48 for instruction: %mask_v16i1_i32 = call <16 x i1> @llvm.get.active.lane.mask.v16i1.i32(i32 undef, i32 undef) -; TYPE_BASED_ONLY-NEXT: Cost Model: Found an estimated cost of 24 for instruction: %mask_v8i1_i32 = call <8 x i1> @llvm.get.active.lane.mask.v8i1.i32(i32 undef, i32 undef) -; TYPE_BASED_ONLY-NEXT: Cost Model: Found an estimated cost of 12 for instruction: %mask_v4i1_i32 = call <4 x i1> @llvm.get.active.lane.mask.v4i1.i32(i32 undef, i32 undef) -; TYPE_BASED_ONLY-NEXT: Cost Model: Found an estimated cost of 6 for instruction: %mask_v2i1_i32 = call <2 x i1> @llvm.get.active.lane.mask.v2i1.i32(i32 undef, i32 undef) +; TYPE_BASED_ONLY-NEXT: Cost Model: Found an estimated cost of 32 for instruction: %mask_v16i1_i64 = call <16 x i1> @llvm.get.active.lane.mask.v16i1.i64(i64 undef, i64 undef) +; TYPE_BASED_ONLY-NEXT: Cost Model: Found an estimated cost of 16 for instruction: %mask_v8i1_i64 = call <8 x i1> @llvm.get.active.lane.mask.v8i1.i64(i64 undef, i64 undef) +; TYPE_BASED_ONLY-NEXT: Cost Model: Found an estimated cost of 8 for instruction: %mask_v4i1_i64 = call <4 x i1> @llvm.get.active.lane.mask.v4i1.i64(i64 undef, i64 undef) +; TYPE_BASED_ONLY-NEXT: Cost Model: Found an estimated cost of 4 for instruction: %mask_v2i1_i64 = call <2 x i1> @llvm.get.active.lane.mask.v2i1.i64(i64 undef, i64 undef) +; TYPE_BASED_ONLY-NEXT: Cost Model: Found an estimated cost of 32 for instruction: %mask_v16i1_i32 = call <16 x i1> @llvm.get.active.lane.mask.v16i1.i32(i32 undef, i32 undef) +; TYPE_BASED_ONLY-NEXT: Cost Model: Found an estimated cost of 16 for instruction: %mask_v8i1_i32 = call <8 x i1> @llvm.get.active.lane.mask.v8i1.i32(i32 undef, i32 undef) +; TYPE_BASED_ONLY-NEXT: Cost Model: Found an estimated cost of 8 for instruction: %mask_v4i1_i32 = call <4 x i1> @llvm.get.active.lane.mask.v4i1.i32(i32 undef, i32 undef) +; TYPE_BASED_ONLY-NEXT: Cost Model: Found an estimated cost of 4 for instruction: %mask_v2i1_i32 = call <2 x i1> @llvm.get.active.lane.mask.v2i1.i32(i32 undef, i32 undef) ; TYPE_BASED_ONLY-NEXT: Cost Model: Found an estimated cost of 96 for instruction: %mask_v32i1_i64 = call <32 x i1> @llvm.get.active.lane.mask.v32i1.i64(i64 undef, i64 undef) ; TYPE_BASED_ONLY-NEXT: Cost Model: Found an estimated cost of 48 for instruction: %mask_v16i1_i16 = call <16 x i1> @llvm.get.active.lane.mask.v16i1.i16(i16 undef, i16 undef) ; TYPE_BASED_ONLY-NEXT: Cost Model: Found an estimated cost of 0 for instruction: ret void diff --git a/llvm/test/Analysis/LoopAccessAnalysis/different-strides-safe-dep-due-to-backedge-taken-count.ll b/llvm/test/Analysis/LoopAccessAnalysis/different-strides-safe-dep-due-to-backedge-taken-count.ll new file mode 100644 index 0000000000000000000000000000000000000000..5312c36e436a21203cd6d1d21d3bc9e35b45018a --- /dev/null +++ b/llvm/test/Analysis/LoopAccessAnalysis/different-strides-safe-dep-due-to-backedge-taken-count.ll @@ -0,0 +1,154 @@ +; NOTE: Assertions have been autogenerated by utils/update_analyze_test_checks.py UTC_ARGS: --version 4 +; RUN: opt -passes='print' -disable-output %s 2>&1 | FileCheck %s + +target datalayout = "e-m:o-i64:64-i128:128-n32:64-S128" + +define void @forward_dep_known_safe_due_to_backedge_taken_count(ptr %A) { +; CHECK-LABEL: 'forward_dep_known_safe_due_to_backedge_taken_count' +; CHECK-NEXT: loop: +; CHECK-NEXT: Memory dependences are safe +; CHECK-NEXT: Dependences: +; CHECK-NEXT: Forward: +; CHECK-NEXT: %l = load i32, ptr %gep.mul.2, align 4 -> +; CHECK-NEXT: store i32 %add, ptr %gep, align 4 +; CHECK-EMPTY: +; CHECK-NEXT: Run-time memory checks: +; CHECK-NEXT: Grouped accesses: +; CHECK-EMPTY: +; CHECK-NEXT: Non vectorizable stores to invariant address were not found in loop. +; CHECK-NEXT: SCEV assumptions: +; CHECK-EMPTY: +; CHECK-NEXT: Expressions re-written: +; +entry: + %A.511= getelementptr inbounds i32, ptr %A, i64 511 + br label %loop + +loop: + %iv = phi i64 [ 0, %entry ], [ %iv.next, %loop ] + %iv.mul.2 = shl nuw nsw i64 %iv, 1 + %gep.mul.2 = getelementptr inbounds i32, ptr %A.511, i64 %iv.mul.2 + %l = load i32, ptr %gep.mul.2, align 4 + %add = add nsw i32 %l, 5 + %gep = getelementptr inbounds i32, ptr %A, i64 %iv + store i32 %add, ptr %gep, align 4 + %iv.next = add nuw nsw i64 %iv, 1 + %exitcond.not = icmp eq i64 %iv.next, 256 + br i1 %exitcond.not, label %exit, label %loop + +exit: + ret void +} + +define void @forward_dep_not_known_safe_due_to_backedge_taken_count(ptr %A) { +; CHECK-LABEL: 'forward_dep_not_known_safe_due_to_backedge_taken_count' +; CHECK-NEXT: loop: +; CHECK-NEXT: Memory dependences are safe +; CHECK-NEXT: Dependences: +; CHECK-NEXT: Forward: +; CHECK-NEXT: %l = load i32, ptr %gep.mul.2, align 4 -> +; CHECK-NEXT: store i32 %add, ptr %gep, align 4 +; CHECK-EMPTY: +; CHECK-NEXT: Run-time memory checks: +; CHECK-NEXT: Grouped accesses: +; CHECK-EMPTY: +; CHECK-NEXT: Non vectorizable stores to invariant address were not found in loop. +; CHECK-NEXT: SCEV assumptions: +; CHECK-EMPTY: +; CHECK-NEXT: Expressions re-written: +; +entry: + %A.510 = getelementptr inbounds i32, ptr %A, i64 510 + br label %loop + +loop: + %iv = phi i64 [ 0, %entry ], [ %iv.next, %loop ] + %iv.mul.2 = shl nuw nsw i64 %iv, 1 + %gep.mul.2 = getelementptr inbounds i32, ptr %A.510, i64 %iv.mul.2 + %l = load i32, ptr %gep.mul.2, align 4 + %add = add nsw i32 %l, 5 + %gep = getelementptr inbounds i32, ptr %A, i64 %iv + store i32 %add, ptr %gep, align 4 + %iv.next = add nuw nsw i64 %iv, 1 + %exitcond.not = icmp eq i64 %iv.next, 256 + br i1 %exitcond.not, label %exit, label %loop + +exit: + ret void +} + +define void @unknown_dep_known_safe_due_to_backedge_taken_count(ptr %A) { +; CHECK-LABEL: 'unknown_dep_known_safe_due_to_backedge_taken_count' +; CHECK-NEXT: loop: +; CHECK-NEXT: Report: unsafe dependent memory operations in loop. Use #pragma clang loop distribute(enable) to allow loop distribution to attempt to isolate the offending operations into a separate loop +; CHECK-NEXT: Unknown data dependence. +; CHECK-NEXT: Dependences: +; CHECK-NEXT: Unknown: +; CHECK-NEXT: %l = load i32, ptr %gep, align 4 -> +; CHECK-NEXT: store i32 %add, ptr %gep.mul.2, align 4 +; CHECK-EMPTY: +; CHECK-NEXT: Run-time memory checks: +; CHECK-NEXT: Grouped accesses: +; CHECK-EMPTY: +; CHECK-NEXT: Non vectorizable stores to invariant address were not found in loop. +; CHECK-NEXT: SCEV assumptions: +; CHECK-EMPTY: +; CHECK-NEXT: Expressions re-written: +; +entry: + %A.511 = getelementptr inbounds i32, ptr %A, i64 511 + br label %loop + +loop: + %iv = phi i64 [ 0, %entry ], [ %iv.next, %loop ] + %iv.mul.2 = shl nuw nsw i64 %iv, 1 + %gep = getelementptr inbounds i32, ptr %A, i64 %iv + %l = load i32, ptr %gep, align 4 + %add = add nsw i32 %l, 5 + %gep.mul.2 = getelementptr inbounds i32, ptr %A.511, i64 %iv.mul.2 + store i32 %add, ptr %gep.mul.2, align 4 + %iv.next = add nuw nsw i64 %iv, 1 + %exitcond.not = icmp eq i64 %iv.next, 256 + br i1 %exitcond.not, label %exit, label %loop + +exit: + ret void +} + +define void @unknown_dep_not_known_safe_due_to_backedge_taken_count(ptr %A) { +; CHECK-LABEL: 'unknown_dep_not_known_safe_due_to_backedge_taken_count' +; CHECK-NEXT: loop: +; CHECK-NEXT: Report: unsafe dependent memory operations in loop. Use #pragma clang loop distribute(enable) to allow loop distribution to attempt to isolate the offending operations into a separate loop +; CHECK-NEXT: Unknown data dependence. +; CHECK-NEXT: Dependences: +; CHECK-NEXT: Unknown: +; CHECK-NEXT: %l = load i32, ptr %gep, align 4 -> +; CHECK-NEXT: store i32 %add, ptr %gep.mul.2, align 4 +; CHECK-EMPTY: +; CHECK-NEXT: Run-time memory checks: +; CHECK-NEXT: Grouped accesses: +; CHECK-EMPTY: +; CHECK-NEXT: Non vectorizable stores to invariant address were not found in loop. +; CHECK-NEXT: SCEV assumptions: +; CHECK-EMPTY: +; CHECK-NEXT: Expressions re-written: +; +entry: + %A.510 = getelementptr inbounds i32, ptr %A, i64 510 + br label %loop + +loop: + %iv = phi i64 [ 0, %entry ], [ %iv.next, %loop ] + %iv.mul.2 = shl nuw nsw i64 %iv, 1 + %gep = getelementptr inbounds i32, ptr %A, i64 %iv + %l = load i32, ptr %gep, align 4 + %add = add nsw i32 %l, 5 + %gep.mul.2 = getelementptr inbounds i32, ptr %A.510, i64 %iv.mul.2 + store i32 %add, ptr %gep.mul.2, align 4 + %iv.next = add nuw nsw i64 %iv, 1 + %exitcond.not = icmp eq i64 %iv.next, 256 + br i1 %exitcond.not, label %exit, label %loop + +exit: + ret void +} diff --git a/llvm/test/Analysis/LoopAccessAnalysis/non-constant-strides-forward.ll b/llvm/test/Analysis/LoopAccessAnalysis/non-constant-strides-forward.ll index 51755314896bb3788bb805213a14c9baaaa63375..5f4c732dc19df088e8beb7e942048d7f5c921698 100644 --- a/llvm/test/Analysis/LoopAccessAnalysis/non-constant-strides-forward.ll +++ b/llvm/test/Analysis/LoopAccessAnalysis/non-constant-strides-forward.ll @@ -8,10 +8,9 @@ declare void @llvm.assume(i1) define void @different_non_constant_strides_known_forward(ptr %A) { ; CHECK-LABEL: 'different_non_constant_strides_known_forward' ; CHECK-NEXT: loop: -; CHECK-NEXT: Report: unsafe dependent memory operations in loop. Use #pragma clang loop distribute(enable) to allow loop distribution to attempt to isolate the offending operations into a separate loop -; CHECK-NEXT: Unknown data dependence. +; CHECK-NEXT: Memory dependences are safe ; CHECK-NEXT: Dependences: -; CHECK-NEXT: Unknown: +; CHECK-NEXT: Forward: ; CHECK-NEXT: %l = load i32, ptr %gep.mul.2, align 4 -> ; CHECK-NEXT: store i32 %add, ptr %gep, align 4 ; CHECK-EMPTY: @@ -45,10 +44,9 @@ exit: define void @different_non_constant_strides_known_forward_min_distance_3(ptr %A) { ; CHECK-LABEL: 'different_non_constant_strides_known_forward_min_distance_3' ; CHECK-NEXT: loop: -; CHECK-NEXT: Report: unsafe dependent memory operations in loop. Use #pragma clang loop distribute(enable) to allow loop distribution to attempt to isolate the offending operations into a separate loop -; CHECK-NEXT: Unknown data dependence. +; CHECK-NEXT: Memory dependences are safe ; CHECK-NEXT: Dependences: -; CHECK-NEXT: Unknown: +; CHECK-NEXT: Forward: ; CHECK-NEXT: %l = load i32, ptr %gep.mul.2, align 4 -> ; CHECK-NEXT: store i32 %add, ptr %gep, align 4 ; CHECK-EMPTY: diff --git a/llvm/test/Analysis/ValueTracking/known-non-zero.ll b/llvm/test/Analysis/ValueTracking/known-non-zero.ll index 0159050d925c3eec0d8fa803d9d84b7f4bfe04ca..c00e47fba8c72738c2631ce20bc1c994a9a987c2 100644 --- a/llvm/test/Analysis/ValueTracking/known-non-zero.ll +++ b/llvm/test/Analysis/ValueTracking/known-non-zero.ll @@ -1202,7 +1202,6 @@ define <2 x i1> @cmp_excludes_zero_with_nonsplat_vec_wpoison(<2 x i8> %a, <2 x i ret <2 x i1> %r } - define <2 x i1> @cmp_excludes_zero_with_nonsplat_vec_fail(<2 x i8> %a, <2 x i8> %b) { ; CHECK-LABEL: @cmp_excludes_zero_with_nonsplat_vec_fail( ; CHECK-NEXT: [[C:%.*]] = icmp sge <2 x i8> [[A:%.*]], @@ -1314,8 +1313,8 @@ define i1 @range_attr(i8 range(i8 1, 0) %x, i8 %y) { define i1 @neg_range_attr(i8 range(i8 -1, 1) %x, i8 %y) { ; CHECK-LABEL: @neg_range_attr( -; CHECK-NEXT: [[I:%.*]] = or i8 [[Y:%.*]], [[X:%.*]] -; CHECK-NEXT: [[CMP:%.*]] = icmp eq i8 [[I]], 0 +; CHECK-NEXT: [[OR:%.*]] = or i8 [[Y:%.*]], [[X:%.*]] +; CHECK-NEXT: [[CMP:%.*]] = icmp eq i8 [[OR]], 0 ; CHECK-NEXT: ret i1 [[CMP]] ; %or = or i8 %y, %x @@ -1328,7 +1327,7 @@ declare range(i8 -1, 1) i8 @returns_contain_zero_range_helper() define i1 @range_return(i8 %y) { ; CHECK-LABEL: @range_return( -; CHECK-NEXT: [[I:%.*]] = call i8 @returns_non_zero_range_helper() +; CHECK-NEXT: [[X:%.*]] = call i8 @returns_non_zero_range_helper() ; CHECK-NEXT: ret i1 false ; %x = call i8 @returns_non_zero_range_helper() @@ -1339,8 +1338,8 @@ define i1 @range_return(i8 %y) { define i1 @neg_range_return(i8 %y) { ; CHECK-LABEL: @neg_range_return( -; CHECK-NEXT: [[I:%.*]] = call i8 @returns_contain_zero_range_helper() -; CHECK-NEXT: [[OR:%.*]] = or i8 [[Y:%.*]], [[I]] +; CHECK-NEXT: [[X:%.*]] = call i8 @returns_contain_zero_range_helper() +; CHECK-NEXT: [[OR:%.*]] = or i8 [[Y:%.*]], [[X]] ; CHECK-NEXT: [[CMP:%.*]] = icmp eq i8 [[OR]], 0 ; CHECK-NEXT: ret i1 [[CMP]] ; @@ -1354,7 +1353,7 @@ declare i8 @returns_i8_helper() define i1 @range_call(i8 %y) { ; CHECK-LABEL: @range_call( -; CHECK-NEXT: [[I:%.*]] = call range(i8 1, 0) i8 @returns_i8_helper() +; CHECK-NEXT: [[X:%.*]] = call range(i8 1, 0) i8 @returns_i8_helper() ; CHECK-NEXT: ret i1 false ; %x = call range(i8 1, 0) i8 @returns_i8_helper() @@ -1365,8 +1364,8 @@ define i1 @range_call(i8 %y) { define i1 @neg_range_call(i8 %y) { ; CHECK-LABEL: @neg_range_call( -; CHECK-NEXT: [[I:%.*]] = call range(i8 -1, 1) i8 @returns_i8_helper() -; CHECK-NEXT: [[OR:%.*]] = or i8 [[Y:%.*]], [[I]] +; CHECK-NEXT: [[X:%.*]] = call range(i8 -1, 1) i8 @returns_i8_helper() +; CHECK-NEXT: [[OR:%.*]] = or i8 [[Y:%.*]], [[X]] ; CHECK-NEXT: [[CMP:%.*]] = icmp eq i8 [[OR]], 0 ; CHECK-NEXT: ret i1 [[CMP]] ; @@ -1401,7 +1400,7 @@ declare range(i8 -1, 1) <2 x i8> @returns_contain_zero_range_helper_vec() define <2 x i1> @range_return_vec(<2 x i8> %y) { ; CHECK-LABEL: @range_return_vec( -; CHECK-NEXT: [[I:%.*]] = call <2 x i8> @returns_non_zero_range_helper_vec() +; CHECK-NEXT: [[X:%.*]] = call <2 x i8> @returns_non_zero_range_helper_vec() ; CHECK-NEXT: ret <2 x i1> ; %x = call <2 x i8> @returns_non_zero_range_helper_vec() @@ -1412,8 +1411,8 @@ define <2 x i1> @range_return_vec(<2 x i8> %y) { define <2 x i1> @neg_range_return_vec(<2 x i8> %y) { ; CHECK-LABEL: @neg_range_return_vec( -; CHECK-NEXT: [[I:%.*]] = call <2 x i8> @returns_contain_zero_range_helper_vec() -; CHECK-NEXT: [[OR:%.*]] = or <2 x i8> [[Y:%.*]], [[I]] +; CHECK-NEXT: [[X:%.*]] = call <2 x i8> @returns_contain_zero_range_helper_vec() +; CHECK-NEXT: [[OR:%.*]] = or <2 x i8> [[Y:%.*]], [[X]] ; CHECK-NEXT: [[CMP:%.*]] = icmp ne <2 x i8> [[OR]], zeroinitializer ; CHECK-NEXT: ret <2 x i1> [[CMP]] ; @@ -1427,7 +1426,7 @@ declare <2 x i8> @returns_i8_helper_vec() define <2 x i1> @range_call_vec(<2 x i8> %y) { ; CHECK-LABEL: @range_call_vec( -; CHECK-NEXT: [[I:%.*]] = call range(i8 1, 0) <2 x i8> @returns_i8_helper_vec() +; CHECK-NEXT: [[X:%.*]] = call range(i8 1, 0) <2 x i8> @returns_i8_helper_vec() ; CHECK-NEXT: ret <2 x i1> ; %x = call range(i8 1, 0) <2 x i8> @returns_i8_helper_vec() @@ -1438,8 +1437,8 @@ define <2 x i1> @range_call_vec(<2 x i8> %y) { define <2 x i1> @neg_range_call_vec(<2 x i8> %y) { ; CHECK-LABEL: @neg_range_call_vec( -; CHECK-NEXT: [[I:%.*]] = call range(i8 -1, 1) <2 x i8> @returns_i8_helper_vec() -; CHECK-NEXT: [[OR:%.*]] = or <2 x i8> [[Y:%.*]], [[I]] +; CHECK-NEXT: [[X:%.*]] = call range(i8 -1, 1) <2 x i8> @returns_i8_helper_vec() +; CHECK-NEXT: [[OR:%.*]] = or <2 x i8> [[Y:%.*]], [[X]] ; CHECK-NEXT: [[CMP:%.*]] = icmp ne <2 x i8> [[OR]], zeroinitializer ; CHECK-NEXT: ret <2 x i1> [[CMP]] ; @@ -1449,5 +1448,53 @@ define <2 x i1> @neg_range_call_vec(<2 x i8> %y) { ret <2 x i1> %cmp } +define i1 @trunc_nsw_non_zero(i8 %x) { +; CHECK-LABEL: @trunc_nsw_non_zero( +; CHECK-NEXT: [[X_NE_Z:%.*]] = icmp ne i8 [[X:%.*]], 0 +; CHECK-NEXT: call void @llvm.assume(i1 [[X_NE_Z]]) +; CHECK-NEXT: ret i1 true +; + %x_ne_z = icmp ne i8 %x, 0 + call void @llvm.assume(i1 %x_ne_z) + %v = trunc nsw i8 %x to i4 + %r = icmp ne i4 %v, 0 + ret i1 %r +} + +define i1 @trunc_nuw_non_zero(i8 %xx) { +; CHECK-LABEL: @trunc_nuw_non_zero( +; CHECK-NEXT: ret i1 false +; + %x = add nuw i8 %xx, 1 + %v = trunc nuw i8 %x to i4 + %r = icmp eq i4 %v, 0 + ret i1 %r +} + +define i1 @trunc_non_zero_fail(i8 %x) { +; CHECK-LABEL: @trunc_non_zero_fail( +; CHECK-NEXT: [[X_NE_Z:%.*]] = icmp ne i8 [[X:%.*]], 0 +; CHECK-NEXT: call void @llvm.assume(i1 [[X_NE_Z]]) +; CHECK-NEXT: [[R:%.*]] = trunc i8 [[X]] to i1 +; CHECK-NEXT: ret i1 [[R]] +; + %x_ne_z = icmp ne i8 %x, 0 + call void @llvm.assume(i1 %x_ne_z) + %r = trunc i8 %x to i1 + ret i1 %r +} + +define i1 @trunc_nsw_nuw_non_zero_fail(i8 %xx) { +; CHECK-LABEL: @trunc_nsw_nuw_non_zero_fail( +; CHECK-NEXT: [[X:%.*]] = add nsw i8 [[XX:%.*]], 1 +; CHECK-NEXT: [[V:%.*]] = trunc nuw nsw i8 [[X]] to i4 +; CHECK-NEXT: [[R:%.*]] = icmp eq i4 [[V]], 0 +; CHECK-NEXT: ret i1 [[R]] +; + %x = add nsw i8 %xx, 1 + %v = trunc nsw nuw i8 %x to i4 + %r = icmp eq i4 %v, 0 + ret i1 %r +} declare i32 @llvm.experimental.get.vector.length.i32(i32, i32, i1) diff --git a/llvm/test/CodeGen/AArch64/GlobalISel/combine-udiv.ll b/llvm/test/CodeGen/AArch64/GlobalISel/combine-udiv.ll index 9a525151ca328b61815a32a5e0458be8248834b6..c97a00ccdd455719462ced3dfb0bd3d1a98d8133 100644 --- a/llvm/test/CodeGen/AArch64/GlobalISel/combine-udiv.ll +++ b/llvm/test/CodeGen/AArch64/GlobalISel/combine-udiv.ll @@ -243,3 +243,29 @@ define <8 x i16> @pr38477(<8 x i16> %a0) { %1 = udiv <8 x i16> %a0, ret <8 x i16> %1 } + +define i32 @udiv_div_by_180(i32 %x) +; SDAG-LABEL: udiv_div_by_180: +; SDAG: // %bb.0: +; SDAG-NEXT: mov w8, #5826 // =0x16c2 +; SDAG-NEXT: and w9, w0, #0xff +; SDAG-NEXT: movk w8, #364, lsl #16 +; SDAG-NEXT: umull x8, w9, w8 +; SDAG-NEXT: lsr x0, x8, #32 +; SDAG-NEXT: // kill: def $w0 killed $w0 killed $x0 +; SDAG-NEXT: ret +; +; GISEL-LABEL: udiv_div_by_180: +; GISEL: // %bb.0: +; GISEL-NEXT: uxtb w8, w0 +; GISEL-NEXT: mov w9, #5826 // =0x16c2 +; GISEL-NEXT: movk w9, #364, lsl #16 +; GISEL-NEXT: umull x8, w8, w9 +; GISEL-NEXT: lsr x0, x8, #32 +; GISEL-NEXT: // kill: def $w0 killed $w0 killed $x0 +; GISEL-NEXT: ret +{ + %truncate = and i32 %x, 255 + %udiv = udiv i32 %truncate, 180 + ret i32 %udiv +} diff --git a/llvm/test/CodeGen/AArch64/GlobalISel/legalize-extract-vector-elt.mir b/llvm/test/CodeGen/AArch64/GlobalISel/legalize-extract-vector-elt.mir index c03f51a89dfbdcbd215680a08615ed1af721e16f..323a3993473fcbb839a0176b006e70d5aff06fda 100644 --- a/llvm/test/CodeGen/AArch64/GlobalISel/legalize-extract-vector-elt.mir +++ b/llvm/test/CodeGen/AArch64/GlobalISel/legalize-extract-vector-elt.mir @@ -368,10 +368,10 @@ body: | bb.0: liveins: $x0 ; CHECK-LABEL: name: test_eve_v4p0 - ; CHECK: [[DEF:%[0-9]+]]:_(p0) = G_IMPLICIT_DEF - ; CHECK-NEXT: [[BUILD_VECTOR:%[0-9]+]]:_(<2 x p0>) = G_BUILD_VECTOR [[DEF]](p0), [[DEF]](p0) + ; CHECK: %vec:_(<4 x p0>) = G_IMPLICIT_DEF ; CHECK-NEXT: %idx:_(s64) = G_CONSTANT i64 1 - ; CHECK-NEXT: %eve:_(p0) = G_EXTRACT_VECTOR_ELT [[BUILD_VECTOR]](<2 x p0>), %idx(s64) + ; CHECK-NEXT: [[UV:%[0-9]+]]:_(<2 x p0>), [[UV1:%[0-9]+]]:_(<2 x p0>) = G_UNMERGE_VALUES %vec(<4 x p0>) + ; CHECK-NEXT: %eve:_(p0) = G_EXTRACT_VECTOR_ELT [[UV]](<2 x p0>), %idx(s64) ; CHECK-NEXT: $x0 = COPY %eve(p0) ; CHECK-NEXT: RET_ReallyLR %vec:_(<4 x p0>) = G_IMPLICIT_DEF @@ -452,16 +452,15 @@ body: | bb.0: liveins: $x0 ; CHECK-LABEL: name: test_eve_v4p0_unknown_idx - ; CHECK: [[DEF:%[0-9]+]]:_(p0) = G_IMPLICIT_DEF - ; CHECK-NEXT: [[BUILD_VECTOR:%[0-9]+]]:_(<2 x p0>) = G_BUILD_VECTOR [[DEF]](p0), [[DEF]](p0) - ; CHECK-NEXT: [[BUILD_VECTOR1:%[0-9]+]]:_(<2 x p0>) = G_BUILD_VECTOR [[DEF]](p0), [[DEF]](p0) + ; CHECK: %vec:_(<4 x p0>) = G_IMPLICIT_DEF ; CHECK-NEXT: %idx:_(s64) = COPY $x0 ; CHECK-NEXT: [[FRAME_INDEX:%[0-9]+]]:_(p0) = G_FRAME_INDEX %stack.0 - ; CHECK-NEXT: [[BITCAST:%[0-9]+]]:_(<2 x s64>) = G_BITCAST [[BUILD_VECTOR]](<2 x p0>) + ; CHECK-NEXT: [[UV:%[0-9]+]]:_(<2 x p0>), [[UV1:%[0-9]+]]:_(<2 x p0>) = G_UNMERGE_VALUES %vec(<4 x p0>) + ; CHECK-NEXT: [[BITCAST:%[0-9]+]]:_(<2 x s64>) = G_BITCAST [[UV]](<2 x p0>) ; CHECK-NEXT: G_STORE [[BITCAST]](<2 x s64>), [[FRAME_INDEX]](p0) :: (store (<2 x s64>) into %stack.0, align 32) ; CHECK-NEXT: [[C:%[0-9]+]]:_(s64) = G_CONSTANT i64 16 ; CHECK-NEXT: [[PTR_ADD:%[0-9]+]]:_(p0) = G_PTR_ADD [[FRAME_INDEX]], [[C]](s64) - ; CHECK-NEXT: [[BITCAST1:%[0-9]+]]:_(<2 x s64>) = G_BITCAST [[BUILD_VECTOR1]](<2 x p0>) + ; CHECK-NEXT: [[BITCAST1:%[0-9]+]]:_(<2 x s64>) = G_BITCAST [[UV1]](<2 x p0>) ; CHECK-NEXT: G_STORE [[BITCAST1]](<2 x s64>), [[PTR_ADD]](p0) :: (store (<2 x s64>) into %stack.0 + 16, basealign 32) ; CHECK-NEXT: [[C1:%[0-9]+]]:_(s64) = G_CONSTANT i64 3 ; CHECK-NEXT: [[AND:%[0-9]+]]:_(s64) = G_AND %idx, [[C1]] diff --git a/llvm/test/CodeGen/AArch64/GlobalISel/legalize-fp-arith.mir b/llvm/test/CodeGen/AArch64/GlobalISel/legalize-fp-arith.mir index c687039da0b780554504268b47c4d83ab334410c..be397ede0b8944785f46481c21269f0b0c27be52 100644 --- a/llvm/test/CodeGen/AArch64/GlobalISel/legalize-fp-arith.mir +++ b/llvm/test/CodeGen/AArch64/GlobalISel/legalize-fp-arith.mir @@ -96,10 +96,9 @@ name: test_fmul_v8s32 body: | bb.0.entry: ; CHECK-LABEL: name: test_fmul_v8s32 - ; CHECK: [[DEF:%[0-9]+]]:_(s32) = G_IMPLICIT_DEF - ; CHECK: [[BUILD_VECTOR:%[0-9]+]]:_(<4 x s32>) = G_BUILD_VECTOR [[DEF]](s32), [[DEF]](s32), [[DEF]](s32), [[DEF]](s32) - ; CHECK: [[FMUL:%[0-9]+]]:_(<4 x s32>) = G_FMUL [[BUILD_VECTOR]], [[BUILD_VECTOR]] - ; CHECK: [[FMUL1:%[0-9]+]]:_(<4 x s32>) = G_FMUL [[BUILD_VECTOR]], [[BUILD_VECTOR]] + ; CHECK: [[DEF:%[0-9]+]]:_(<4 x s32>) = G_IMPLICIT_DEF + ; CHECK: [[FMUL:%[0-9]+]]:_(<4 x s32>) = G_FMUL [[DEF]], [[DEF]] + ; CHECK: [[FMUL1:%[0-9]+]]:_(<4 x s32>) = G_FMUL [[DEF]], [[DEF]] ; CHECK: $q0 = COPY [[FMUL]](<4 x s32>) ; CHECK: $q1 = COPY [[FMUL1]](<4 x s32>) %0:_(<8 x s32>) = G_IMPLICIT_DEF diff --git a/llvm/test/CodeGen/AArch64/GlobalISel/legalize-freeze.mir b/llvm/test/CodeGen/AArch64/GlobalISel/legalize-freeze.mir index be674d79b54f1de37728badf2f68e463691bb4fc..3e768c4d7a267cb20cd10a323efb53269e0c1153 100644 --- a/llvm/test/CodeGen/AArch64/GlobalISel/legalize-freeze.mir +++ b/llvm/test/CodeGen/AArch64/GlobalISel/legalize-freeze.mir @@ -130,3 +130,95 @@ body: | %freeze:_(s2) = G_FREEZE %x %ext:_(s64) = G_ZEXT %freeze $x0 = COPY %ext(s64) +... +--- +name: test_freeze_v4s1 +body: | + bb.0.entry: + liveins: $q0 + ; CHECK-LABEL: name: test_freeze_v4s1 + ; CHECK: liveins: $q0 + ; CHECK-NEXT: {{ $}} + ; CHECK-NEXT: [[DEF:%[0-9]+]]:_(<4 x s16>) = G_IMPLICIT_DEF + ; CHECK-NEXT: [[FREEZE:%[0-9]+]]:_(<4 x s16>) = G_FREEZE [[DEF]] + ; CHECK-NEXT: [[ANYEXT:%[0-9]+]]:_(<4 x s32>) = G_ANYEXT [[FREEZE]](<4 x s16>) + ; CHECK-NEXT: [[C:%[0-9]+]]:_(s32) = G_CONSTANT i32 1 + ; CHECK-NEXT: [[BUILD_VECTOR:%[0-9]+]]:_(<4 x s32>) = G_BUILD_VECTOR [[C]](s32), [[C]](s32), [[C]](s32), [[C]](s32) + ; CHECK-NEXT: %ext:_(<4 x s32>) = G_AND [[ANYEXT]], [[BUILD_VECTOR]] + ; CHECK-NEXT: $q0 = COPY %ext(<4 x s32>) + %x:_(<4 x s1>) = G_IMPLICIT_DEF + %freeze:_(<4 x s1>) = G_FREEZE %x + %ext:_(<4 x s32>) = G_ZEXT %freeze + $q0 = COPY %ext(<4 x s32>) +... +--- +name: test_freeze_v3s8 +body: | + bb.0.entry: + liveins: $q0 + ; CHECK-LABEL: name: test_freeze_v3s8 + ; CHECK: liveins: $q0 + ; CHECK-NEXT: {{ $}} + ; CHECK-NEXT: [[DEF:%[0-9]+]]:_(<4 x s16>) = G_IMPLICIT_DEF + ; CHECK-NEXT: [[UV:%[0-9]+]]:_(s16), [[UV1:%[0-9]+]]:_(s16), [[UV2:%[0-9]+]]:_(s16), [[UV3:%[0-9]+]]:_(s16) = G_UNMERGE_VALUES [[DEF]](<4 x s16>) + ; CHECK-NEXT: [[TRUNC:%[0-9]+]]:_(s8) = G_TRUNC [[UV]](s16) + ; CHECK-NEXT: [[TRUNC1:%[0-9]+]]:_(s8) = G_TRUNC [[UV1]](s16) + ; CHECK-NEXT: [[TRUNC2:%[0-9]+]]:_(s8) = G_TRUNC [[UV2]](s16) + ; CHECK-NEXT: [[DEF1:%[0-9]+]]:_(s8) = G_IMPLICIT_DEF + ; CHECK-NEXT: [[BUILD_VECTOR:%[0-9]+]]:_(<8 x s8>) = G_BUILD_VECTOR [[TRUNC]](s8), [[TRUNC1]](s8), [[TRUNC2]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8) + ; CHECK-NEXT: [[ANYEXT:%[0-9]+]]:_(<8 x s16>) = G_ANYEXT [[BUILD_VECTOR]](<8 x s8>) + ; CHECK-NEXT: [[UV4:%[0-9]+]]:_(<4 x s16>), [[UV5:%[0-9]+]]:_(<4 x s16>) = G_UNMERGE_VALUES [[ANYEXT]](<8 x s16>) + ; CHECK-NEXT: [[FREEZE:%[0-9]+]]:_(<4 x s16>) = G_FREEZE [[UV4]] + ; CHECK-NEXT: [[UV6:%[0-9]+]]:_(s16), [[UV7:%[0-9]+]]:_(s16), [[UV8:%[0-9]+]]:_(s16), [[UV9:%[0-9]+]]:_(s16) = G_UNMERGE_VALUES [[FREEZE]](<4 x s16>) + ; CHECK-NEXT: %undef:_(s32) = G_IMPLICIT_DEF + ; CHECK-NEXT: [[ANYEXT1:%[0-9]+]]:_(s32) = G_ANYEXT [[UV6]](s16) + ; CHECK-NEXT: [[C:%[0-9]+]]:_(s32) = G_CONSTANT i32 255 + ; CHECK-NEXT: %ext0:_(s32) = G_AND [[ANYEXT1]], [[C]] + ; CHECK-NEXT: [[ANYEXT2:%[0-9]+]]:_(s32) = G_ANYEXT [[UV7]](s16) + ; CHECK-NEXT: %ext1:_(s32) = G_AND [[ANYEXT2]], [[C]] + ; CHECK-NEXT: [[ANYEXT3:%[0-9]+]]:_(s32) = G_ANYEXT [[UV8]](s16) + ; CHECK-NEXT: %ext2:_(s32) = G_AND [[ANYEXT3]], [[C]] + ; CHECK-NEXT: %res:_(<4 x s32>) = G_BUILD_VECTOR %ext0(s32), %ext1(s32), %ext2(s32), %undef(s32) + ; CHECK-NEXT: $q0 = COPY %res(<4 x s32>) + %x:_(<3 x s8>) = G_IMPLICIT_DEF + %freeze:_(<3 x s8>) = G_FREEZE %x + %ext:_(<3 x s32>) = G_ZEXT %freeze + %undef:_(s32) = G_IMPLICIT_DEF + %ext0:_(s32), %ext1:_(s32), %ext2:_(s32) = G_UNMERGE_VALUES %ext + %res:_(<4 x s32>) = G_BUILD_VECTOR %ext0, %ext1, %ext2, %undef + $q0 = COPY %res(<4 x s32>) +... +--- +name: test_freeze_v4s1_select +body: | + bb.0.entry: + liveins: $q0, $q1 + ; CHECK-LABEL: name: test_freeze_v4s1_select + ; CHECK: liveins: $q0, $q1 + ; CHECK-NEXT: {{ $}} + ; CHECK-NEXT: [[COPY:%[0-9]+]]:_(<4 x s32>) = COPY $q0 + ; CHECK-NEXT: [[COPY1:%[0-9]+]]:_(<4 x s32>) = COPY $q1 + ; CHECK-NEXT: [[C:%[0-9]+]]:_(s32) = G_CONSTANT i32 0 + ; CHECK-NEXT: [[BUILD_VECTOR:%[0-9]+]]:_(<4 x s32>) = G_BUILD_VECTOR [[C]](s32), [[C]](s32), [[C]](s32), [[C]](s32) + ; CHECK-NEXT: [[FCMP:%[0-9]+]]:_(<4 x s32>) = nnan ninf nsz arcp contract afn reassoc G_FCMP floatpred(olt), [[COPY]](<4 x s32>), [[BUILD_VECTOR]] + ; CHECK-NEXT: [[FCMP1:%[0-9]+]]:_(<4 x s32>) = nnan ninf nsz arcp contract afn reassoc G_FCMP floatpred(ogt), [[COPY1]](<4 x s32>), [[COPY]] + ; CHECK-NEXT: [[TRUNC:%[0-9]+]]:_(<4 x s16>) = G_TRUNC [[FCMP1]](<4 x s32>) + ; CHECK-NEXT: [[FREEZE:%[0-9]+]]:_(<4 x s16>) = G_FREEZE [[TRUNC]] + ; CHECK-NEXT: [[TRUNC1:%[0-9]+]]:_(<4 x s16>) = G_TRUNC [[FCMP]](<4 x s32>) + ; CHECK-NEXT: [[AND:%[0-9]+]]:_(<4 x s16>) = G_AND [[TRUNC1]], [[FREEZE]] + ; CHECK-NEXT: [[ANYEXT:%[0-9]+]]:_(<4 x s32>) = G_ANYEXT [[AND]](<4 x s16>) + ; CHECK-NEXT: [[C1:%[0-9]+]]:_(s32) = G_CONSTANT i32 1 + ; CHECK-NEXT: [[BUILD_VECTOR1:%[0-9]+]]:_(<4 x s32>) = G_BUILD_VECTOR [[C1]](s32), [[C1]](s32), [[C1]](s32), [[C1]](s32) + ; CHECK-NEXT: [[AND1:%[0-9]+]]:_(<4 x s32>) = G_AND [[ANYEXT]], [[BUILD_VECTOR1]] + ; CHECK-NEXT: $q0 = COPY [[AND1]](<4 x s32>) + %1:_(<4 x s32>) = COPY $q0 + %2:_(<4 x s32>) = COPY $q1 + %3:_(s32) = G_CONSTANT i32 0 + %4:_(<4 x s32>) = G_BUILD_VECTOR %3, %3, %3, %3 + %5:_(s1) = G_CONSTANT i1 false + %6:_(<4 x s1>) = nnan ninf nsz arcp contract afn reassoc G_FCMP floatpred(olt), %1:_(<4 x s32>), %4:_ + %7:_(<4 x s1>) = nnan ninf nsz arcp contract afn reassoc G_FCMP floatpred(ogt), %2:_(<4 x s32>), %1:_ + %8:_(<4 x s1>) = G_FREEZE %7 + %9:_(<4 x s1>) = G_AND %6, %8 + %10:_(<4 x s32>) = G_ZEXT %9 + $q0 = COPY %10 diff --git a/llvm/test/CodeGen/AArch64/GlobalISel/legalize-insert-vector-elt.mir b/llvm/test/CodeGen/AArch64/GlobalISel/legalize-insert-vector-elt.mir index a74bf9a5438b6055d2d6f7602309bdd61da17332..9a8697c1d9b866581d70efcc978e335a248481ca 100644 --- a/llvm/test/CodeGen/AArch64/GlobalISel/legalize-insert-vector-elt.mir +++ b/llvm/test/CodeGen/AArch64/GlobalISel/legalize-insert-vector-elt.mir @@ -248,19 +248,24 @@ body: | ; CHECK-NEXT: [[TRUNC3:%[0-9]+]]:_(s8) = G_TRUNC [[UV2]](s16) ; CHECK-NEXT: [[TRUNC4:%[0-9]+]]:_(s8) = G_TRUNC [[UV3]](s16) ; CHECK-NEXT: [[TRUNC5:%[0-9]+]]:_(s8) = G_TRUNC [[UV4]](s16) - ; CHECK-NEXT: [[BUILD_VECTOR1:%[0-9]+]]:_(<16 x s8>) = G_BUILD_VECTOR [[TRUNC3]](s8), [[TRUNC4]](s8), [[TRUNC5]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8) - ; CHECK-NEXT: [[BUILD_VECTOR2:%[0-9]+]]:_(<16 x s8>) = G_BUILD_VECTOR [[C]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8) + ; CHECK-NEXT: [[DEF2:%[0-9]+]]:_(<4 x s16>) = G_IMPLICIT_DEF + ; CHECK-NEXT: [[UV6:%[0-9]+]]:_(s16), [[UV7:%[0-9]+]]:_(s16), [[UV8:%[0-9]+]]:_(s16), [[UV9:%[0-9]+]]:_(s16) = G_UNMERGE_VALUES [[DEF2]](<4 x s16>) + ; CHECK-NEXT: [[TRUNC6:%[0-9]+]]:_(s8) = G_TRUNC [[UV6]](s16) + ; CHECK-NEXT: [[TRUNC7:%[0-9]+]]:_(s8) = G_TRUNC [[UV7]](s16) + ; CHECK-NEXT: [[TRUNC8:%[0-9]+]]:_(s8) = G_TRUNC [[UV8]](s16) + ; CHECK-NEXT: [[BUILD_VECTOR1:%[0-9]+]]:_(<16 x s8>) = G_BUILD_VECTOR [[TRUNC3]](s8), [[TRUNC4]](s8), [[TRUNC5]](s8), [[TRUNC6]](s8), [[TRUNC7]](s8), [[TRUNC8]](s8), [[TRUNC6]](s8), [[TRUNC7]](s8), [[TRUNC8]](s8), [[TRUNC6]](s8), [[TRUNC7]](s8), [[TRUNC8]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8) + ; CHECK-NEXT: [[BUILD_VECTOR2:%[0-9]+]]:_(<16 x s8>) = G_BUILD_VECTOR [[C]](s8), [[DEF]](s8), [[DEF]](s8), [[TRUNC6]](s8), [[TRUNC7]](s8), [[TRUNC8]](s8), [[TRUNC6]](s8), [[TRUNC7]](s8), [[TRUNC8]](s8), [[TRUNC6]](s8), [[TRUNC7]](s8), [[TRUNC8]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8) ; CHECK-NEXT: [[SHUF:%[0-9]+]]:_(<16 x s8>) = G_SHUFFLE_VECTOR [[BUILD_VECTOR1]](<16 x s8>), [[BUILD_VECTOR2]], shufflemask(0, 16, 16, 16, 1, 16, 16, 16, 2, 16, 16, 16, undef, undef, undef, undef) ; CHECK-NEXT: [[BITCAST:%[0-9]+]]:_(<4 x s32>) = G_BITCAST [[SHUF]](<16 x s8>) ; CHECK-NEXT: [[UITOFP:%[0-9]+]]:_(<4 x s32>) = G_UITOFP [[BITCAST]](<4 x s32>) - ; CHECK-NEXT: [[UV6:%[0-9]+]]:_(s32), [[UV7:%[0-9]+]]:_(s32), [[UV8:%[0-9]+]]:_(s32), [[UV9:%[0-9]+]]:_(s32) = G_UNMERGE_VALUES [[UITOFP]](<4 x s32>) - ; CHECK-NEXT: G_STORE [[UV6]](s32), [[COPY]](p0) :: (store (s32), align 16) + ; CHECK-NEXT: [[UV10:%[0-9]+]]:_(s32), [[UV11:%[0-9]+]]:_(s32), [[UV12:%[0-9]+]]:_(s32), [[UV13:%[0-9]+]]:_(s32) = G_UNMERGE_VALUES [[UITOFP]](<4 x s32>) + ; CHECK-NEXT: G_STORE [[UV10]](s32), [[COPY]](p0) :: (store (s32), align 16) ; CHECK-NEXT: [[C3:%[0-9]+]]:_(s64) = G_CONSTANT i64 4 ; CHECK-NEXT: [[PTR_ADD:%[0-9]+]]:_(p0) = G_PTR_ADD [[COPY]], [[C3]](s64) - ; CHECK-NEXT: G_STORE [[UV7]](s32), [[PTR_ADD]](p0) :: (store (s32) into unknown-address + 4) + ; CHECK-NEXT: G_STORE [[UV11]](s32), [[PTR_ADD]](p0) :: (store (s32) into unknown-address + 4) ; CHECK-NEXT: [[C4:%[0-9]+]]:_(s64) = G_CONSTANT i64 8 ; CHECK-NEXT: [[PTR_ADD1:%[0-9]+]]:_(p0) = G_PTR_ADD [[COPY]], [[C4]](s64) - ; CHECK-NEXT: G_STORE [[UV8]](s32), [[PTR_ADD1]](p0) :: (store (s32) into unknown-address + 8, align 8) + ; CHECK-NEXT: G_STORE [[UV12]](s32), [[PTR_ADD1]](p0) :: (store (s32) into unknown-address + 8, align 8) ; CHECK-NEXT: G_BR %bb.1 bb.1: liveins: $w1, $w2, $w3, $x0 diff --git a/llvm/test/CodeGen/AArch64/GlobalISel/legalize-itofp.mir b/llvm/test/CodeGen/AArch64/GlobalISel/legalize-itofp.mir index fc417b2eca61892dae22c087e56a79a63af2afd5..69fe50e03df0cd478382ee3502b1bcf9d956eae4 100644 --- a/llvm/test/CodeGen/AArch64/GlobalISel/legalize-itofp.mir +++ b/llvm/test/CodeGen/AArch64/GlobalISel/legalize-itofp.mir @@ -274,12 +274,10 @@ body: | ; CHECK-LABEL: name: test_uitofp_v2s64_v2i1 ; CHECK: liveins: $q0 ; CHECK-NEXT: {{ $}} - ; CHECK-NEXT: [[DEF:%[0-9]+]]:_(s64) = G_IMPLICIT_DEF - ; CHECK-NEXT: [[COPY:%[0-9]+]]:_(s64) = COPY [[DEF]](s64) - ; CHECK-NEXT: [[BUILD_VECTOR:%[0-9]+]]:_(<2 x s64>) = G_BUILD_VECTOR [[DEF]](s64), [[COPY]](s64) + ; CHECK-NEXT: [[DEF:%[0-9]+]]:_(<2 x s64>) = G_IMPLICIT_DEF ; CHECK-NEXT: [[C:%[0-9]+]]:_(s64) = G_CONSTANT i64 1 - ; CHECK-NEXT: [[BUILD_VECTOR1:%[0-9]+]]:_(<2 x s64>) = G_BUILD_VECTOR [[C]](s64), [[C]](s64) - ; CHECK-NEXT: [[AND:%[0-9]+]]:_(<2 x s64>) = G_AND [[BUILD_VECTOR]], [[BUILD_VECTOR1]] + ; CHECK-NEXT: [[BUILD_VECTOR:%[0-9]+]]:_(<2 x s64>) = G_BUILD_VECTOR [[C]](s64), [[C]](s64) + ; CHECK-NEXT: [[AND:%[0-9]+]]:_(<2 x s64>) = G_AND [[DEF]], [[BUILD_VECTOR]] ; CHECK-NEXT: [[UITOFP:%[0-9]+]]:_(<2 x s64>) = G_UITOFP [[AND]](<2 x s64>) ; CHECK-NEXT: $q0 = COPY [[UITOFP]](<2 x s64>) %0:_(<2 x s1>) = G_IMPLICIT_DEF @@ -295,10 +293,8 @@ body: | ; CHECK-LABEL: name: test_sitofp_v2s64_v2i1 ; CHECK: liveins: $q0 ; CHECK-NEXT: {{ $}} - ; CHECK-NEXT: [[DEF:%[0-9]+]]:_(s64) = G_IMPLICIT_DEF - ; CHECK-NEXT: [[COPY:%[0-9]+]]:_(s64) = COPY [[DEF]](s64) - ; CHECK-NEXT: [[BUILD_VECTOR:%[0-9]+]]:_(<2 x s64>) = G_BUILD_VECTOR [[DEF]](s64), [[COPY]](s64) - ; CHECK-NEXT: [[SEXT_INREG:%[0-9]+]]:_(<2 x s64>) = G_SEXT_INREG [[BUILD_VECTOR]], 1 + ; CHECK-NEXT: [[DEF:%[0-9]+]]:_(<2 x s64>) = G_IMPLICIT_DEF + ; CHECK-NEXT: [[SEXT_INREG:%[0-9]+]]:_(<2 x s64>) = G_SEXT_INREG [[DEF]], 1 ; CHECK-NEXT: [[SITOFP:%[0-9]+]]:_(<2 x s64>) = G_SITOFP [[SEXT_INREG]](<2 x s64>) ; CHECK-NEXT: $q0 = COPY [[SITOFP]](<2 x s64>) %0:_(<2 x s1>) = G_IMPLICIT_DEF diff --git a/llvm/test/CodeGen/AArch64/GlobalISel/legalize-load-store.mir b/llvm/test/CodeGen/AArch64/GlobalISel/legalize-load-store.mir index b8328eda9a66189703685833e3c86ba7fe39ae3f..94bdcf74a8aa46d94362e0d1a12464120be4c6d7 100644 --- a/llvm/test/CodeGen/AArch64/GlobalISel/legalize-load-store.mir +++ b/llvm/test/CodeGen/AArch64/GlobalISel/legalize-load-store.mir @@ -328,14 +328,12 @@ body: | ; CHECK-LABEL: name: store_32xs8 ; CHECK: liveins: $x0 ; CHECK-NEXT: {{ $}} - ; CHECK-NEXT: [[DEF:%[0-9]+]]:_(s8) = G_IMPLICIT_DEF - ; CHECK-NEXT: [[BUILD_VECTOR:%[0-9]+]]:_(<16 x s8>) = G_BUILD_VECTOR [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8) - ; CHECK-NEXT: [[BUILD_VECTOR1:%[0-9]+]]:_(<16 x s8>) = G_BUILD_VECTOR [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8) + ; CHECK-NEXT: [[DEF:%[0-9]+]]:_(<16 x s8>) = G_IMPLICIT_DEF ; CHECK-NEXT: %ptr:_(p0) = COPY $x0 - ; CHECK-NEXT: G_STORE [[BUILD_VECTOR]](<16 x s8>), %ptr(p0) :: (store (<16 x s8>), align 32) + ; CHECK-NEXT: G_STORE [[DEF]](<16 x s8>), %ptr(p0) :: (store (<16 x s8>), align 32) ; CHECK-NEXT: [[C:%[0-9]+]]:_(s64) = G_CONSTANT i64 16 ; CHECK-NEXT: [[PTR_ADD:%[0-9]+]]:_(p0) = G_PTR_ADD %ptr, [[C]](s64) - ; CHECK-NEXT: G_STORE [[BUILD_VECTOR1]](<16 x s8>), [[PTR_ADD]](p0) :: (store (<16 x s8>) into unknown-address + 16) + ; CHECK-NEXT: G_STORE [[DEF]](<16 x s8>), [[PTR_ADD]](p0) :: (store (<16 x s8>) into unknown-address + 16) ; CHECK-NEXT: RET_ReallyLR %val:_(<32 x s8>) = G_IMPLICIT_DEF %ptr:_(p0) = COPY $x0 @@ -353,14 +351,12 @@ body: | ; CHECK-LABEL: name: store_16xs16 ; CHECK: liveins: $x0 ; CHECK-NEXT: {{ $}} - ; CHECK-NEXT: [[DEF:%[0-9]+]]:_(s16) = G_IMPLICIT_DEF - ; CHECK-NEXT: [[BUILD_VECTOR:%[0-9]+]]:_(<8 x s16>) = G_BUILD_VECTOR [[DEF]](s16), [[DEF]](s16), [[DEF]](s16), [[DEF]](s16), [[DEF]](s16), [[DEF]](s16), [[DEF]](s16), [[DEF]](s16) - ; CHECK-NEXT: [[BUILD_VECTOR1:%[0-9]+]]:_(<8 x s16>) = G_BUILD_VECTOR [[DEF]](s16), [[DEF]](s16), [[DEF]](s16), [[DEF]](s16), [[DEF]](s16), [[DEF]](s16), [[DEF]](s16), [[DEF]](s16) + ; CHECK-NEXT: [[DEF:%[0-9]+]]:_(<8 x s16>) = G_IMPLICIT_DEF ; CHECK-NEXT: %ptr:_(p0) = COPY $x0 - ; CHECK-NEXT: G_STORE [[BUILD_VECTOR]](<8 x s16>), %ptr(p0) :: (store (<8 x s16>), align 32) + ; CHECK-NEXT: G_STORE [[DEF]](<8 x s16>), %ptr(p0) :: (store (<8 x s16>), align 32) ; CHECK-NEXT: [[C:%[0-9]+]]:_(s64) = G_CONSTANT i64 16 ; CHECK-NEXT: [[PTR_ADD:%[0-9]+]]:_(p0) = G_PTR_ADD %ptr, [[C]](s64) - ; CHECK-NEXT: G_STORE [[BUILD_VECTOR1]](<8 x s16>), [[PTR_ADD]](p0) :: (store (<8 x s16>) into unknown-address + 16) + ; CHECK-NEXT: G_STORE [[DEF]](<8 x s16>), [[PTR_ADD]](p0) :: (store (<8 x s16>) into unknown-address + 16) ; CHECK-NEXT: RET_ReallyLR %val:_(<16 x s16>) = G_IMPLICIT_DEF %ptr:_(p0) = COPY $x0 @@ -378,14 +374,12 @@ body: | ; CHECK-LABEL: name: store_8xs32 ; CHECK: liveins: $x0 ; CHECK-NEXT: {{ $}} - ; CHECK-NEXT: [[DEF:%[0-9]+]]:_(s32) = G_IMPLICIT_DEF - ; CHECK-NEXT: [[BUILD_VECTOR:%[0-9]+]]:_(<4 x s32>) = G_BUILD_VECTOR [[DEF]](s32), [[DEF]](s32), [[DEF]](s32), [[DEF]](s32) - ; CHECK-NEXT: [[BUILD_VECTOR1:%[0-9]+]]:_(<4 x s32>) = G_BUILD_VECTOR [[DEF]](s32), [[DEF]](s32), [[DEF]](s32), [[DEF]](s32) + ; CHECK-NEXT: [[DEF:%[0-9]+]]:_(<4 x s32>) = G_IMPLICIT_DEF ; CHECK-NEXT: %ptr:_(p0) = COPY $x0 - ; CHECK-NEXT: G_STORE [[BUILD_VECTOR]](<4 x s32>), %ptr(p0) :: (store (<4 x s32>), align 32) + ; CHECK-NEXT: G_STORE [[DEF]](<4 x s32>), %ptr(p0) :: (store (<4 x s32>), align 32) ; CHECK-NEXT: [[C:%[0-9]+]]:_(s64) = G_CONSTANT i64 16 ; CHECK-NEXT: [[PTR_ADD:%[0-9]+]]:_(p0) = G_PTR_ADD %ptr, [[C]](s64) - ; CHECK-NEXT: G_STORE [[BUILD_VECTOR1]](<4 x s32>), [[PTR_ADD]](p0) :: (store (<4 x s32>) into unknown-address + 16) + ; CHECK-NEXT: G_STORE [[DEF]](<4 x s32>), [[PTR_ADD]](p0) :: (store (<4 x s32>) into unknown-address + 16) ; CHECK-NEXT: RET_ReallyLR %val:_(<8 x s32>) = G_IMPLICIT_DEF %ptr:_(p0) = COPY $x0 diff --git a/llvm/test/CodeGen/AArch64/GlobalISel/legalize-min-max.mir b/llvm/test/CodeGen/AArch64/GlobalISel/legalize-min-max.mir index cab8a91e447e4e753545e1262326dc4e71ba0be0..35c9538627b354771e90e2d7b27038e420e75b6a 100644 --- a/llvm/test/CodeGen/AArch64/GlobalISel/legalize-min-max.mir +++ b/llvm/test/CodeGen/AArch64/GlobalISel/legalize-min-max.mir @@ -55,10 +55,9 @@ body: | ; CHECK-LABEL: name: v32s8_smin ; CHECK: liveins: $x0, $q0, $q1 ; CHECK-NEXT: {{ $}} - ; CHECK-NEXT: [[DEF:%[0-9]+]]:_(s8) = G_IMPLICIT_DEF - ; CHECK-NEXT: [[BUILD_VECTOR:%[0-9]+]]:_(<16 x s8>) = G_BUILD_VECTOR [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8) - ; CHECK-NEXT: [[SMIN:%[0-9]+]]:_(<16 x s8>) = G_SMIN [[BUILD_VECTOR]], [[BUILD_VECTOR]] - ; CHECK-NEXT: [[SMIN1:%[0-9]+]]:_(<16 x s8>) = G_SMIN [[BUILD_VECTOR]], [[BUILD_VECTOR]] + ; CHECK-NEXT: [[DEF:%[0-9]+]]:_(<16 x s8>) = G_IMPLICIT_DEF + ; CHECK-NEXT: [[SMIN:%[0-9]+]]:_(<16 x s8>) = G_SMIN [[DEF]], [[DEF]] + ; CHECK-NEXT: [[SMIN1:%[0-9]+]]:_(<16 x s8>) = G_SMIN [[DEF]], [[DEF]] ; CHECK-NEXT: [[COPY:%[0-9]+]]:_(p0) = COPY $x0 ; CHECK-NEXT: G_STORE [[SMIN]](<16 x s8>), [[COPY]](p0) :: (store (<16 x s8>), align 32) ; CHECK-NEXT: [[C:%[0-9]+]]:_(s64) = G_CONSTANT i64 16 @@ -125,10 +124,9 @@ body: | ; CHECK-LABEL: name: v16s16_smin ; CHECK: liveins: $x0, $q0, $q1 ; CHECK-NEXT: {{ $}} - ; CHECK-NEXT: [[DEF:%[0-9]+]]:_(s16) = G_IMPLICIT_DEF - ; CHECK-NEXT: [[BUILD_VECTOR:%[0-9]+]]:_(<8 x s16>) = G_BUILD_VECTOR [[DEF]](s16), [[DEF]](s16), [[DEF]](s16), [[DEF]](s16), [[DEF]](s16), [[DEF]](s16), [[DEF]](s16), [[DEF]](s16) - ; CHECK-NEXT: [[SMIN:%[0-9]+]]:_(<8 x s16>) = G_SMIN [[BUILD_VECTOR]], [[BUILD_VECTOR]] - ; CHECK-NEXT: [[SMIN1:%[0-9]+]]:_(<8 x s16>) = G_SMIN [[BUILD_VECTOR]], [[BUILD_VECTOR]] + ; CHECK-NEXT: [[DEF:%[0-9]+]]:_(<8 x s16>) = G_IMPLICIT_DEF + ; CHECK-NEXT: [[SMIN:%[0-9]+]]:_(<8 x s16>) = G_SMIN [[DEF]], [[DEF]] + ; CHECK-NEXT: [[SMIN1:%[0-9]+]]:_(<8 x s16>) = G_SMIN [[DEF]], [[DEF]] ; CHECK-NEXT: [[COPY:%[0-9]+]]:_(p0) = COPY $x0 ; CHECK-NEXT: G_STORE [[SMIN]](<8 x s16>), [[COPY]](p0) :: (store (<8 x s16>), align 32) ; CHECK-NEXT: [[C:%[0-9]+]]:_(s64) = G_CONSTANT i64 16 @@ -195,10 +193,9 @@ body: | ; CHECK-LABEL: name: v8s32_smin ; CHECK: liveins: $x0, $q0, $q1 ; CHECK-NEXT: {{ $}} - ; CHECK-NEXT: [[DEF:%[0-9]+]]:_(s32) = G_IMPLICIT_DEF - ; CHECK-NEXT: [[BUILD_VECTOR:%[0-9]+]]:_(<4 x s32>) = G_BUILD_VECTOR [[DEF]](s32), [[DEF]](s32), [[DEF]](s32), [[DEF]](s32) - ; CHECK-NEXT: [[SMIN:%[0-9]+]]:_(<4 x s32>) = G_SMIN [[BUILD_VECTOR]], [[BUILD_VECTOR]] - ; CHECK-NEXT: [[SMIN1:%[0-9]+]]:_(<4 x s32>) = G_SMIN [[BUILD_VECTOR]], [[BUILD_VECTOR]] + ; CHECK-NEXT: [[DEF:%[0-9]+]]:_(<4 x s32>) = G_IMPLICIT_DEF + ; CHECK-NEXT: [[SMIN:%[0-9]+]]:_(<4 x s32>) = G_SMIN [[DEF]], [[DEF]] + ; CHECK-NEXT: [[SMIN1:%[0-9]+]]:_(<4 x s32>) = G_SMIN [[DEF]], [[DEF]] ; CHECK-NEXT: [[COPY:%[0-9]+]]:_(p0) = COPY $x0 ; CHECK-NEXT: G_STORE [[SMIN]](<4 x s32>), [[COPY]](p0) :: (store (<4 x s32>), align 32) ; CHECK-NEXT: [[C:%[0-9]+]]:_(s64) = G_CONSTANT i64 16 @@ -331,10 +328,9 @@ body: | ; CHECK-LABEL: name: v32s8_umin ; CHECK: liveins: $x0, $q0, $q1 ; CHECK-NEXT: {{ $}} - ; CHECK-NEXT: [[DEF:%[0-9]+]]:_(s8) = G_IMPLICIT_DEF - ; CHECK-NEXT: [[BUILD_VECTOR:%[0-9]+]]:_(<16 x s8>) = G_BUILD_VECTOR [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8) - ; CHECK-NEXT: [[UMIN:%[0-9]+]]:_(<16 x s8>) = G_UMIN [[BUILD_VECTOR]], [[BUILD_VECTOR]] - ; CHECK-NEXT: [[UMIN1:%[0-9]+]]:_(<16 x s8>) = G_UMIN [[BUILD_VECTOR]], [[BUILD_VECTOR]] + ; CHECK-NEXT: [[DEF:%[0-9]+]]:_(<16 x s8>) = G_IMPLICIT_DEF + ; CHECK-NEXT: [[UMIN:%[0-9]+]]:_(<16 x s8>) = G_UMIN [[DEF]], [[DEF]] + ; CHECK-NEXT: [[UMIN1:%[0-9]+]]:_(<16 x s8>) = G_UMIN [[DEF]], [[DEF]] ; CHECK-NEXT: [[COPY:%[0-9]+]]:_(p0) = COPY $x0 ; CHECK-NEXT: G_STORE [[UMIN]](<16 x s8>), [[COPY]](p0) :: (store (<16 x s8>), align 32) ; CHECK-NEXT: [[C:%[0-9]+]]:_(s64) = G_CONSTANT i64 16 @@ -401,10 +397,9 @@ body: | ; CHECK-LABEL: name: v16s16_umin ; CHECK: liveins: $x0, $q0, $q1 ; CHECK-NEXT: {{ $}} - ; CHECK-NEXT: [[DEF:%[0-9]+]]:_(s16) = G_IMPLICIT_DEF - ; CHECK-NEXT: [[BUILD_VECTOR:%[0-9]+]]:_(<8 x s16>) = G_BUILD_VECTOR [[DEF]](s16), [[DEF]](s16), [[DEF]](s16), [[DEF]](s16), [[DEF]](s16), [[DEF]](s16), [[DEF]](s16), [[DEF]](s16) - ; CHECK-NEXT: [[UMIN:%[0-9]+]]:_(<8 x s16>) = G_UMIN [[BUILD_VECTOR]], [[BUILD_VECTOR]] - ; CHECK-NEXT: [[UMIN1:%[0-9]+]]:_(<8 x s16>) = G_UMIN [[BUILD_VECTOR]], [[BUILD_VECTOR]] + ; CHECK-NEXT: [[DEF:%[0-9]+]]:_(<8 x s16>) = G_IMPLICIT_DEF + ; CHECK-NEXT: [[UMIN:%[0-9]+]]:_(<8 x s16>) = G_UMIN [[DEF]], [[DEF]] + ; CHECK-NEXT: [[UMIN1:%[0-9]+]]:_(<8 x s16>) = G_UMIN [[DEF]], [[DEF]] ; CHECK-NEXT: [[COPY:%[0-9]+]]:_(p0) = COPY $x0 ; CHECK-NEXT: G_STORE [[UMIN]](<8 x s16>), [[COPY]](p0) :: (store (<8 x s16>), align 32) ; CHECK-NEXT: [[C:%[0-9]+]]:_(s64) = G_CONSTANT i64 16 @@ -471,10 +466,9 @@ body: | ; CHECK-LABEL: name: v8s32_umin ; CHECK: liveins: $x0, $q0, $q1 ; CHECK-NEXT: {{ $}} - ; CHECK-NEXT: [[DEF:%[0-9]+]]:_(s32) = G_IMPLICIT_DEF - ; CHECK-NEXT: [[BUILD_VECTOR:%[0-9]+]]:_(<4 x s32>) = G_BUILD_VECTOR [[DEF]](s32), [[DEF]](s32), [[DEF]](s32), [[DEF]](s32) - ; CHECK-NEXT: [[UMIN:%[0-9]+]]:_(<4 x s32>) = G_UMIN [[BUILD_VECTOR]], [[BUILD_VECTOR]] - ; CHECK-NEXT: [[UMIN1:%[0-9]+]]:_(<4 x s32>) = G_UMIN [[BUILD_VECTOR]], [[BUILD_VECTOR]] + ; CHECK-NEXT: [[DEF:%[0-9]+]]:_(<4 x s32>) = G_IMPLICIT_DEF + ; CHECK-NEXT: [[UMIN:%[0-9]+]]:_(<4 x s32>) = G_UMIN [[DEF]], [[DEF]] + ; CHECK-NEXT: [[UMIN1:%[0-9]+]]:_(<4 x s32>) = G_UMIN [[DEF]], [[DEF]] ; CHECK-NEXT: [[COPY:%[0-9]+]]:_(p0) = COPY $x0 ; CHECK-NEXT: G_STORE [[UMIN]](<4 x s32>), [[COPY]](p0) :: (store (<4 x s32>), align 32) ; CHECK-NEXT: [[C:%[0-9]+]]:_(s64) = G_CONSTANT i64 16 @@ -629,10 +623,9 @@ body: | ; CHECK-LABEL: name: v32s8_smax ; CHECK: liveins: $x0, $q0, $q1 ; CHECK-NEXT: {{ $}} - ; CHECK-NEXT: [[DEF:%[0-9]+]]:_(s8) = G_IMPLICIT_DEF - ; CHECK-NEXT: [[BUILD_VECTOR:%[0-9]+]]:_(<16 x s8>) = G_BUILD_VECTOR [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8) - ; CHECK-NEXT: [[SMAX:%[0-9]+]]:_(<16 x s8>) = G_SMAX [[BUILD_VECTOR]], [[BUILD_VECTOR]] - ; CHECK-NEXT: [[SMAX1:%[0-9]+]]:_(<16 x s8>) = G_SMAX [[BUILD_VECTOR]], [[BUILD_VECTOR]] + ; CHECK-NEXT: [[DEF:%[0-9]+]]:_(<16 x s8>) = G_IMPLICIT_DEF + ; CHECK-NEXT: [[SMAX:%[0-9]+]]:_(<16 x s8>) = G_SMAX [[DEF]], [[DEF]] + ; CHECK-NEXT: [[SMAX1:%[0-9]+]]:_(<16 x s8>) = G_SMAX [[DEF]], [[DEF]] ; CHECK-NEXT: [[COPY:%[0-9]+]]:_(p0) = COPY $x0 ; CHECK-NEXT: G_STORE [[SMAX]](<16 x s8>), [[COPY]](p0) :: (store (<16 x s8>), align 32) ; CHECK-NEXT: [[C:%[0-9]+]]:_(s64) = G_CONSTANT i64 16 @@ -677,10 +670,9 @@ body: | ; CHECK-LABEL: name: v16s16_smax ; CHECK: liveins: $x0, $q0, $q1 ; CHECK-NEXT: {{ $}} - ; CHECK-NEXT: [[DEF:%[0-9]+]]:_(s16) = G_IMPLICIT_DEF - ; CHECK-NEXT: [[BUILD_VECTOR:%[0-9]+]]:_(<8 x s16>) = G_BUILD_VECTOR [[DEF]](s16), [[DEF]](s16), [[DEF]](s16), [[DEF]](s16), [[DEF]](s16), [[DEF]](s16), [[DEF]](s16), [[DEF]](s16) - ; CHECK-NEXT: [[SMAX:%[0-9]+]]:_(<8 x s16>) = G_SMAX [[BUILD_VECTOR]], [[BUILD_VECTOR]] - ; CHECK-NEXT: [[SMAX1:%[0-9]+]]:_(<8 x s16>) = G_SMAX [[BUILD_VECTOR]], [[BUILD_VECTOR]] + ; CHECK-NEXT: [[DEF:%[0-9]+]]:_(<8 x s16>) = G_IMPLICIT_DEF + ; CHECK-NEXT: [[SMAX:%[0-9]+]]:_(<8 x s16>) = G_SMAX [[DEF]], [[DEF]] + ; CHECK-NEXT: [[SMAX1:%[0-9]+]]:_(<8 x s16>) = G_SMAX [[DEF]], [[DEF]] ; CHECK-NEXT: [[COPY:%[0-9]+]]:_(p0) = COPY $x0 ; CHECK-NEXT: G_STORE [[SMAX]](<8 x s16>), [[COPY]](p0) :: (store (<8 x s16>), align 32) ; CHECK-NEXT: [[C:%[0-9]+]]:_(s64) = G_CONSTANT i64 16 @@ -747,10 +739,9 @@ body: | ; CHECK-LABEL: name: v8s32_smax ; CHECK: liveins: $x0, $q0, $q1 ; CHECK-NEXT: {{ $}} - ; CHECK-NEXT: [[DEF:%[0-9]+]]:_(s32) = G_IMPLICIT_DEF - ; CHECK-NEXT: [[BUILD_VECTOR:%[0-9]+]]:_(<4 x s32>) = G_BUILD_VECTOR [[DEF]](s32), [[DEF]](s32), [[DEF]](s32), [[DEF]](s32) - ; CHECK-NEXT: [[SMAX:%[0-9]+]]:_(<4 x s32>) = G_SMAX [[BUILD_VECTOR]], [[BUILD_VECTOR]] - ; CHECK-NEXT: [[SMAX1:%[0-9]+]]:_(<4 x s32>) = G_SMAX [[BUILD_VECTOR]], [[BUILD_VECTOR]] + ; CHECK-NEXT: [[DEF:%[0-9]+]]:_(<4 x s32>) = G_IMPLICIT_DEF + ; CHECK-NEXT: [[SMAX:%[0-9]+]]:_(<4 x s32>) = G_SMAX [[DEF]], [[DEF]] + ; CHECK-NEXT: [[SMAX1:%[0-9]+]]:_(<4 x s32>) = G_SMAX [[DEF]], [[DEF]] ; CHECK-NEXT: [[COPY:%[0-9]+]]:_(p0) = COPY $x0 ; CHECK-NEXT: G_STORE [[SMAX]](<4 x s32>), [[COPY]](p0) :: (store (<4 x s32>), align 32) ; CHECK-NEXT: [[C:%[0-9]+]]:_(s64) = G_CONSTANT i64 16 @@ -883,10 +874,9 @@ body: | ; CHECK-LABEL: name: v32s8_umax ; CHECK: liveins: $x0, $q0, $q1 ; CHECK-NEXT: {{ $}} - ; CHECK-NEXT: [[DEF:%[0-9]+]]:_(s8) = G_IMPLICIT_DEF - ; CHECK-NEXT: [[BUILD_VECTOR:%[0-9]+]]:_(<16 x s8>) = G_BUILD_VECTOR [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8) - ; CHECK-NEXT: [[UMAX:%[0-9]+]]:_(<16 x s8>) = G_UMAX [[BUILD_VECTOR]], [[BUILD_VECTOR]] - ; CHECK-NEXT: [[UMAX1:%[0-9]+]]:_(<16 x s8>) = G_UMAX [[BUILD_VECTOR]], [[BUILD_VECTOR]] + ; CHECK-NEXT: [[DEF:%[0-9]+]]:_(<16 x s8>) = G_IMPLICIT_DEF + ; CHECK-NEXT: [[UMAX:%[0-9]+]]:_(<16 x s8>) = G_UMAX [[DEF]], [[DEF]] + ; CHECK-NEXT: [[UMAX1:%[0-9]+]]:_(<16 x s8>) = G_UMAX [[DEF]], [[DEF]] ; CHECK-NEXT: [[COPY:%[0-9]+]]:_(p0) = COPY $x0 ; CHECK-NEXT: G_STORE [[UMAX]](<16 x s8>), [[COPY]](p0) :: (store (<16 x s8>), align 32) ; CHECK-NEXT: [[C:%[0-9]+]]:_(s64) = G_CONSTANT i64 16 @@ -953,10 +943,9 @@ body: | ; CHECK-LABEL: name: v16s16_umax ; CHECK: liveins: $x0, $q0, $q1 ; CHECK-NEXT: {{ $}} - ; CHECK-NEXT: [[DEF:%[0-9]+]]:_(s16) = G_IMPLICIT_DEF - ; CHECK-NEXT: [[BUILD_VECTOR:%[0-9]+]]:_(<8 x s16>) = G_BUILD_VECTOR [[DEF]](s16), [[DEF]](s16), [[DEF]](s16), [[DEF]](s16), [[DEF]](s16), [[DEF]](s16), [[DEF]](s16), [[DEF]](s16) - ; CHECK-NEXT: [[UMAX:%[0-9]+]]:_(<8 x s16>) = G_UMAX [[BUILD_VECTOR]], [[BUILD_VECTOR]] - ; CHECK-NEXT: [[UMAX1:%[0-9]+]]:_(<8 x s16>) = G_UMAX [[BUILD_VECTOR]], [[BUILD_VECTOR]] + ; CHECK-NEXT: [[DEF:%[0-9]+]]:_(<8 x s16>) = G_IMPLICIT_DEF + ; CHECK-NEXT: [[UMAX:%[0-9]+]]:_(<8 x s16>) = G_UMAX [[DEF]], [[DEF]] + ; CHECK-NEXT: [[UMAX1:%[0-9]+]]:_(<8 x s16>) = G_UMAX [[DEF]], [[DEF]] ; CHECK-NEXT: [[COPY:%[0-9]+]]:_(p0) = COPY $x0 ; CHECK-NEXT: G_STORE [[UMAX]](<8 x s16>), [[COPY]](p0) :: (store (<8 x s16>), align 32) ; CHECK-NEXT: [[C:%[0-9]+]]:_(s64) = G_CONSTANT i64 16 @@ -1023,10 +1012,9 @@ body: | ; CHECK-LABEL: name: v8s32_umax ; CHECK: liveins: $x0, $q0, $q1 ; CHECK-NEXT: {{ $}} - ; CHECK-NEXT: [[DEF:%[0-9]+]]:_(s32) = G_IMPLICIT_DEF - ; CHECK-NEXT: [[BUILD_VECTOR:%[0-9]+]]:_(<4 x s32>) = G_BUILD_VECTOR [[DEF]](s32), [[DEF]](s32), [[DEF]](s32), [[DEF]](s32) - ; CHECK-NEXT: [[UMAX:%[0-9]+]]:_(<4 x s32>) = G_UMAX [[BUILD_VECTOR]], [[BUILD_VECTOR]] - ; CHECK-NEXT: [[UMAX1:%[0-9]+]]:_(<4 x s32>) = G_UMAX [[BUILD_VECTOR]], [[BUILD_VECTOR]] + ; CHECK-NEXT: [[DEF:%[0-9]+]]:_(<4 x s32>) = G_IMPLICIT_DEF + ; CHECK-NEXT: [[UMAX:%[0-9]+]]:_(<4 x s32>) = G_UMAX [[DEF]], [[DEF]] + ; CHECK-NEXT: [[UMAX1:%[0-9]+]]:_(<4 x s32>) = G_UMAX [[DEF]], [[DEF]] ; CHECK-NEXT: [[COPY:%[0-9]+]]:_(p0) = COPY $x0 ; CHECK-NEXT: G_STORE [[UMAX]](<4 x s32>), [[COPY]](p0) :: (store (<4 x s32>), align 32) ; CHECK-NEXT: [[C:%[0-9]+]]:_(s64) = G_CONSTANT i64 16 diff --git a/llvm/test/CodeGen/AArch64/GlobalISel/legalize-phi.mir b/llvm/test/CodeGen/AArch64/GlobalISel/legalize-phi.mir index 8bd62c5922541501173f3d5827d55a8c3e0eabde..7dbe3fefb6bd69b69c783ad2866c041e707b35ac 100644 --- a/llvm/test/CodeGen/AArch64/GlobalISel/legalize-phi.mir +++ b/llvm/test/CodeGen/AArch64/GlobalISel/legalize-phi.mir @@ -766,22 +766,20 @@ body: | ; CHECK-NEXT: successors: %bb.1(0x50000000), %bb.2(0x30000000) ; CHECK-NEXT: liveins: $x0, $x1 ; CHECK-NEXT: {{ $}} - ; CHECK-NEXT: [[DEF:%[0-9]+]]:_(s32) = G_IMPLICIT_DEF - ; CHECK-NEXT: [[BUILD_VECTOR:%[0-9]+]]:_(<4 x s32>) = G_BUILD_VECTOR [[DEF]](s32), [[DEF]](s32), [[DEF]](s32), [[DEF]](s32) - ; CHECK-NEXT: [[COPY:%[0-9]+]]:_(s32) = COPY [[DEF]](s32) + ; CHECK-NEXT: [[DEF:%[0-9]+]]:_(<4 x s32>) = G_IMPLICIT_DEF + ; CHECK-NEXT: [[DEF1:%[0-9]+]]:_(s32) = G_IMPLICIT_DEF ; CHECK-NEXT: [[C:%[0-9]+]]:_(s32) = G_CONSTANT i32 1 - ; CHECK-NEXT: [[AND:%[0-9]+]]:_(s32) = G_AND [[COPY]], [[C]] + ; CHECK-NEXT: [[AND:%[0-9]+]]:_(s32) = G_AND [[DEF1]], [[C]] ; CHECK-NEXT: G_BRCOND [[AND]](s32), %bb.2 ; CHECK-NEXT: G_BR %bb.1 ; CHECK-NEXT: {{ $}} ; CHECK-NEXT: bb.1: ; CHECK-NEXT: successors: %bb.2(0x80000000) ; CHECK-NEXT: {{ $}} - ; CHECK-NEXT: [[DEF1:%[0-9]+]]:_(s32) = G_IMPLICIT_DEF - ; CHECK-NEXT: [[BUILD_VECTOR1:%[0-9]+]]:_(<4 x s32>) = G_BUILD_VECTOR [[DEF1]](s32), [[DEF1]](s32), [[DEF1]](s32), [[DEF1]](s32) + ; CHECK-NEXT: [[DEF2:%[0-9]+]]:_(<4 x s32>) = G_IMPLICIT_DEF ; CHECK-NEXT: {{ $}} ; CHECK-NEXT: bb.2: - ; CHECK-NEXT: [[PHI:%[0-9]+]]:_(<4 x s32>) = G_PHI [[BUILD_VECTOR1]](<4 x s32>), %bb.1, [[BUILD_VECTOR]](<4 x s32>), %bb.0 + ; CHECK-NEXT: [[PHI:%[0-9]+]]:_(<4 x s32>) = G_PHI [[DEF2]](<4 x s32>), %bb.1, [[DEF]](<4 x s32>), %bb.0 ; CHECK-NEXT: %one:_(s64) = G_CONSTANT i64 1 ; CHECK-NEXT: %extract:_(s32) = G_EXTRACT_VECTOR_ELT [[PHI]](<4 x s32>), %one(s64) ; CHECK-NEXT: $w0 = COPY %extract(s32) @@ -812,8 +810,7 @@ body: | ; CHECK-NEXT: successors: %bb.1(0x50000000), %bb.2(0x30000000) ; CHECK-NEXT: liveins: $x0, $x1 ; CHECK-NEXT: {{ $}} - ; CHECK-NEXT: [[DEF:%[0-9]+]]:_(s16) = G_IMPLICIT_DEF - ; CHECK-NEXT: [[BUILD_VECTOR:%[0-9]+]]:_(<8 x s16>) = G_BUILD_VECTOR [[DEF]](s16), [[DEF]](s16), [[DEF]](s16), [[DEF]](s16), [[DEF]](s16), [[DEF]](s16), [[DEF]](s16), [[DEF]](s16) + ; CHECK-NEXT: [[DEF:%[0-9]+]]:_(<8 x s16>) = G_IMPLICIT_DEF ; CHECK-NEXT: [[DEF1:%[0-9]+]]:_(s32) = G_IMPLICIT_DEF ; CHECK-NEXT: [[C:%[0-9]+]]:_(s32) = G_CONSTANT i32 1 ; CHECK-NEXT: [[AND:%[0-9]+]]:_(s32) = G_AND [[DEF1]], [[C]] @@ -823,11 +820,10 @@ body: | ; CHECK-NEXT: bb.1: ; CHECK-NEXT: successors: %bb.2(0x80000000) ; CHECK-NEXT: {{ $}} - ; CHECK-NEXT: [[DEF2:%[0-9]+]]:_(s16) = G_IMPLICIT_DEF - ; CHECK-NEXT: [[BUILD_VECTOR1:%[0-9]+]]:_(<8 x s16>) = G_BUILD_VECTOR [[DEF2]](s16), [[DEF2]](s16), [[DEF2]](s16), [[DEF2]](s16), [[DEF2]](s16), [[DEF2]](s16), [[DEF2]](s16), [[DEF2]](s16) + ; CHECK-NEXT: [[DEF2:%[0-9]+]]:_(<8 x s16>) = G_IMPLICIT_DEF ; CHECK-NEXT: {{ $}} ; CHECK-NEXT: bb.2: - ; CHECK-NEXT: [[PHI:%[0-9]+]]:_(<8 x s16>) = G_PHI [[BUILD_VECTOR1]](<8 x s16>), %bb.1, [[BUILD_VECTOR]](<8 x s16>), %bb.0 + ; CHECK-NEXT: [[PHI:%[0-9]+]]:_(<8 x s16>) = G_PHI [[DEF2]](<8 x s16>), %bb.1, [[DEF]](<8 x s16>), %bb.0 ; CHECK-NEXT: %one:_(s64) = G_CONSTANT i64 1 ; CHECK-NEXT: %extract:_(s16) = G_EXTRACT_VECTOR_ELT [[PHI]](<8 x s16>), %one(s64) ; CHECK-NEXT: $h0 = COPY %extract(s16) @@ -858,8 +854,7 @@ body: | ; CHECK-NEXT: successors: %bb.1(0x50000000), %bb.2(0x30000000) ; CHECK-NEXT: liveins: $x0, $x1 ; CHECK-NEXT: {{ $}} - ; CHECK-NEXT: [[DEF:%[0-9]+]]:_(s8) = G_IMPLICIT_DEF - ; CHECK-NEXT: [[BUILD_VECTOR:%[0-9]+]]:_(<16 x s8>) = G_BUILD_VECTOR [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8) + ; CHECK-NEXT: [[DEF:%[0-9]+]]:_(<16 x s8>) = G_IMPLICIT_DEF ; CHECK-NEXT: [[DEF1:%[0-9]+]]:_(s32) = G_IMPLICIT_DEF ; CHECK-NEXT: [[C:%[0-9]+]]:_(s32) = G_CONSTANT i32 1 ; CHECK-NEXT: [[AND:%[0-9]+]]:_(s32) = G_AND [[DEF1]], [[C]] @@ -869,11 +864,10 @@ body: | ; CHECK-NEXT: bb.1: ; CHECK-NEXT: successors: %bb.2(0x80000000) ; CHECK-NEXT: {{ $}} - ; CHECK-NEXT: [[DEF2:%[0-9]+]]:_(s8) = G_IMPLICIT_DEF - ; CHECK-NEXT: [[BUILD_VECTOR1:%[0-9]+]]:_(<16 x s8>) = G_BUILD_VECTOR [[DEF2]](s8), [[DEF2]](s8), [[DEF2]](s8), [[DEF2]](s8), [[DEF2]](s8), [[DEF2]](s8), [[DEF2]](s8), [[DEF2]](s8), [[DEF2]](s8), [[DEF2]](s8), [[DEF2]](s8), [[DEF2]](s8), [[DEF2]](s8), [[DEF2]](s8), [[DEF2]](s8), [[DEF2]](s8) + ; CHECK-NEXT: [[DEF2:%[0-9]+]]:_(<16 x s8>) = G_IMPLICIT_DEF ; CHECK-NEXT: {{ $}} ; CHECK-NEXT: bb.2: - ; CHECK-NEXT: [[PHI:%[0-9]+]]:_(<16 x s8>) = G_PHI [[BUILD_VECTOR1]](<16 x s8>), %bb.1, [[BUILD_VECTOR]](<16 x s8>), %bb.0 + ; CHECK-NEXT: [[PHI:%[0-9]+]]:_(<16 x s8>) = G_PHI [[DEF2]](<16 x s8>), %bb.1, [[DEF]](<16 x s8>), %bb.0 ; CHECK-NEXT: %one:_(s64) = G_CONSTANT i64 1 ; CHECK-NEXT: %extract:_(s8) = G_EXTRACT_VECTOR_ELT [[PHI]](<16 x s8>), %one(s64) ; CHECK-NEXT: $b0 = COPY %extract(s8) diff --git a/llvm/test/CodeGen/AArch64/GlobalISel/legalize-select.mir b/llvm/test/CodeGen/AArch64/GlobalISel/legalize-select.mir index e49a94c12ed468b0dedea4a432f2c215c36fd1e0..8b5cac1ec87350ebf6f9809d7d4c5c0257ad629d 100644 --- a/llvm/test/CodeGen/AArch64/GlobalISel/legalize-select.mir +++ b/llvm/test/CodeGen/AArch64/GlobalISel/legalize-select.mir @@ -292,45 +292,47 @@ body: | ; CHECK-NEXT: [[C:%[0-9]+]]:_(s32) = G_CONSTANT i32 4100 ; CHECK-NEXT: [[ICMP2:%[0-9]+]]:_(s32) = G_ICMP intpred(eq), %w0(s32), [[C]] ; CHECK-NEXT: [[SEXT_INREG:%[0-9]+]]:_(s32) = G_SEXT_INREG [[ICMP2]], 1 - ; CHECK-NEXT: [[DEF:%[0-9]+]]:_(s8) = G_IMPLICIT_DEF + ; CHECK-NEXT: [[DEF:%[0-9]+]]:_(<4 x s16>) = G_IMPLICIT_DEF ; CHECK-NEXT: [[C1:%[0-9]+]]:_(s64) = G_CONSTANT i64 0 - ; CHECK-NEXT: [[DEF1:%[0-9]+]]:_(s8) = G_IMPLICIT_DEF - ; CHECK-NEXT: [[BUILD_VECTOR:%[0-9]+]]:_(<8 x s8>) = G_BUILD_VECTOR [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8) - ; CHECK-NEXT: [[ANYEXT:%[0-9]+]]:_(<8 x s16>) = G_ANYEXT [[BUILD_VECTOR]](<8 x s8>) - ; CHECK-NEXT: [[UV:%[0-9]+]]:_(<4 x s16>), [[UV1:%[0-9]+]]:_(<4 x s16>) = G_UNMERGE_VALUES [[ANYEXT]](<8 x s16>) ; CHECK-NEXT: [[TRUNC:%[0-9]+]]:_(s16) = G_TRUNC [[SEXT_INREG]](s32) - ; CHECK-NEXT: [[IVEC:%[0-9]+]]:_(<4 x s16>) = G_INSERT_VECTOR_ELT [[UV]], [[TRUNC]](s16), [[C1]](s64) - ; CHECK-NEXT: [[UV2:%[0-9]+]]:_(s16), [[UV3:%[0-9]+]]:_(s16), [[UV4:%[0-9]+]]:_(s16), [[UV5:%[0-9]+]]:_(s16) = G_UNMERGE_VALUES [[IVEC]](<4 x s16>) - ; CHECK-NEXT: [[TRUNC1:%[0-9]+]]:_(s8) = G_TRUNC [[UV2]](s16) - ; CHECK-NEXT: [[TRUNC2:%[0-9]+]]:_(s8) = G_TRUNC [[UV3]](s16) - ; CHECK-NEXT: [[TRUNC3:%[0-9]+]]:_(s8) = G_TRUNC [[UV4]](s16) - ; CHECK-NEXT: [[TRUNC4:%[0-9]+]]:_(s8) = G_TRUNC [[UV5]](s16) - ; CHECK-NEXT: [[BUILD_VECTOR1:%[0-9]+]]:_(<8 x s8>) = G_BUILD_VECTOR [[TRUNC1]](s8), [[TRUNC2]](s8), [[TRUNC3]](s8), [[TRUNC4]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8) - ; CHECK-NEXT: [[BUILD_VECTOR2:%[0-9]+]]:_(<8 x s8>) = G_BUILD_VECTOR [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8) - ; CHECK-NEXT: [[SHUF:%[0-9]+]]:_(<8 x s8>) = G_SHUFFLE_VECTOR [[BUILD_VECTOR1]](<8 x s8>), [[BUILD_VECTOR2]], shufflemask(0, 0, 0, 0, undef, undef, undef, undef) - ; CHECK-NEXT: [[UV6:%[0-9]+]]:_(<4 x s8>), [[UV7:%[0-9]+]]:_(<4 x s8>) = G_UNMERGE_VALUES [[SHUF]](<8 x s8>) + ; CHECK-NEXT: [[IVEC:%[0-9]+]]:_(<4 x s16>) = G_INSERT_VECTOR_ELT [[DEF]], [[TRUNC]](s16), [[C1]](s64) + ; CHECK-NEXT: [[UV:%[0-9]+]]:_(s16), [[UV1:%[0-9]+]]:_(s16), [[UV2:%[0-9]+]]:_(s16), [[UV3:%[0-9]+]]:_(s16) = G_UNMERGE_VALUES [[IVEC]](<4 x s16>) + ; CHECK-NEXT: [[TRUNC1:%[0-9]+]]:_(s8) = G_TRUNC [[UV]](s16) + ; CHECK-NEXT: [[TRUNC2:%[0-9]+]]:_(s8) = G_TRUNC [[UV1]](s16) + ; CHECK-NEXT: [[TRUNC3:%[0-9]+]]:_(s8) = G_TRUNC [[UV2]](s16) + ; CHECK-NEXT: [[TRUNC4:%[0-9]+]]:_(s8) = G_TRUNC [[UV3]](s16) + ; CHECK-NEXT: [[DEF1:%[0-9]+]]:_(s8) = G_IMPLICIT_DEF + ; CHECK-NEXT: [[BUILD_VECTOR:%[0-9]+]]:_(<8 x s8>) = G_BUILD_VECTOR [[TRUNC1]](s8), [[TRUNC2]](s8), [[TRUNC3]](s8), [[TRUNC4]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8) + ; CHECK-NEXT: [[UV4:%[0-9]+]]:_(s16), [[UV5:%[0-9]+]]:_(s16), [[UV6:%[0-9]+]]:_(s16), [[UV7:%[0-9]+]]:_(s16) = G_UNMERGE_VALUES [[DEF]](<4 x s16>) + ; CHECK-NEXT: [[TRUNC5:%[0-9]+]]:_(s8) = G_TRUNC [[UV4]](s16) + ; CHECK-NEXT: [[TRUNC6:%[0-9]+]]:_(s8) = G_TRUNC [[UV5]](s16) + ; CHECK-NEXT: [[TRUNC7:%[0-9]+]]:_(s8) = G_TRUNC [[UV6]](s16) + ; CHECK-NEXT: [[TRUNC8:%[0-9]+]]:_(s8) = G_TRUNC [[UV7]](s16) + ; CHECK-NEXT: [[BUILD_VECTOR1:%[0-9]+]]:_(<8 x s8>) = G_BUILD_VECTOR [[TRUNC5]](s8), [[TRUNC6]](s8), [[TRUNC7]](s8), [[TRUNC8]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8) + ; CHECK-NEXT: [[SHUF:%[0-9]+]]:_(<8 x s8>) = G_SHUFFLE_VECTOR [[BUILD_VECTOR]](<8 x s8>), [[BUILD_VECTOR1]], shufflemask(0, 0, 0, 0, undef, undef, undef, undef) + ; CHECK-NEXT: [[UV8:%[0-9]+]]:_(<4 x s8>), [[UV9:%[0-9]+]]:_(<4 x s8>) = G_UNMERGE_VALUES [[SHUF]](<8 x s8>) ; CHECK-NEXT: [[C2:%[0-9]+]]:_(s8) = G_CONSTANT i8 1 - ; CHECK-NEXT: [[UV8:%[0-9]+]]:_(s8), [[UV9:%[0-9]+]]:_(s8), [[UV10:%[0-9]+]]:_(s8), [[UV11:%[0-9]+]]:_(s8) = G_UNMERGE_VALUES [[UV6]](<4 x s8>) - ; CHECK-NEXT: [[BUILD_VECTOR3:%[0-9]+]]:_(<8 x s8>) = G_BUILD_VECTOR [[UV8]](s8), [[UV9]](s8), [[UV10]](s8), [[UV11]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8) + ; CHECK-NEXT: [[UV10:%[0-9]+]]:_(s8), [[UV11:%[0-9]+]]:_(s8), [[UV12:%[0-9]+]]:_(s8), [[UV13:%[0-9]+]]:_(s8) = G_UNMERGE_VALUES [[UV8]](<4 x s8>) + ; CHECK-NEXT: [[BUILD_VECTOR2:%[0-9]+]]:_(<8 x s8>) = G_BUILD_VECTOR [[UV10]](s8), [[UV11]](s8), [[UV12]](s8), [[UV13]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8) + ; CHECK-NEXT: [[ANYEXT:%[0-9]+]]:_(<8 x s16>) = G_ANYEXT [[BUILD_VECTOR2]](<8 x s8>) + ; CHECK-NEXT: [[UV14:%[0-9]+]]:_(<4 x s16>), [[UV15:%[0-9]+]]:_(<4 x s16>) = G_UNMERGE_VALUES [[ANYEXT]](<8 x s16>) + ; CHECK-NEXT: [[BUILD_VECTOR3:%[0-9]+]]:_(<8 x s8>) = G_BUILD_VECTOR [[C2]](s8), [[C2]](s8), [[C2]](s8), [[C2]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8) ; CHECK-NEXT: [[ANYEXT1:%[0-9]+]]:_(<8 x s16>) = G_ANYEXT [[BUILD_VECTOR3]](<8 x s8>) - ; CHECK-NEXT: [[UV12:%[0-9]+]]:_(<4 x s16>), [[UV13:%[0-9]+]]:_(<4 x s16>) = G_UNMERGE_VALUES [[ANYEXT1]](<8 x s16>) - ; CHECK-NEXT: [[BUILD_VECTOR4:%[0-9]+]]:_(<8 x s8>) = G_BUILD_VECTOR [[C2]](s8), [[C2]](s8), [[C2]](s8), [[C2]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8) + ; CHECK-NEXT: [[UV16:%[0-9]+]]:_(<4 x s16>), [[UV17:%[0-9]+]]:_(<4 x s16>) = G_UNMERGE_VALUES [[ANYEXT1]](<8 x s16>) + ; CHECK-NEXT: [[XOR:%[0-9]+]]:_(<4 x s16>) = G_XOR [[UV14]], [[UV16]] + ; CHECK-NEXT: [[TRUNC9:%[0-9]+]]:_(<4 x s16>) = G_TRUNC [[ICMP]](<4 x s32>) + ; CHECK-NEXT: [[UV18:%[0-9]+]]:_(s8), [[UV19:%[0-9]+]]:_(s8), [[UV20:%[0-9]+]]:_(s8), [[UV21:%[0-9]+]]:_(s8) = G_UNMERGE_VALUES [[UV8]](<4 x s8>) + ; CHECK-NEXT: [[BUILD_VECTOR4:%[0-9]+]]:_(<8 x s8>) = G_BUILD_VECTOR [[UV18]](s8), [[UV19]](s8), [[UV20]](s8), [[UV21]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8) ; CHECK-NEXT: [[ANYEXT2:%[0-9]+]]:_(<8 x s16>) = G_ANYEXT [[BUILD_VECTOR4]](<8 x s8>) - ; CHECK-NEXT: [[UV14:%[0-9]+]]:_(<4 x s16>), [[UV15:%[0-9]+]]:_(<4 x s16>) = G_UNMERGE_VALUES [[ANYEXT2]](<8 x s16>) - ; CHECK-NEXT: [[XOR:%[0-9]+]]:_(<4 x s16>) = G_XOR [[UV12]], [[UV14]] - ; CHECK-NEXT: [[TRUNC5:%[0-9]+]]:_(<4 x s16>) = G_TRUNC [[ICMP]](<4 x s32>) - ; CHECK-NEXT: [[UV16:%[0-9]+]]:_(s8), [[UV17:%[0-9]+]]:_(s8), [[UV18:%[0-9]+]]:_(s8), [[UV19:%[0-9]+]]:_(s8) = G_UNMERGE_VALUES [[UV6]](<4 x s8>) - ; CHECK-NEXT: [[BUILD_VECTOR5:%[0-9]+]]:_(<8 x s8>) = G_BUILD_VECTOR [[UV16]](s8), [[UV17]](s8), [[UV18]](s8), [[UV19]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8), [[DEF1]](s8) - ; CHECK-NEXT: [[ANYEXT3:%[0-9]+]]:_(<8 x s16>) = G_ANYEXT [[BUILD_VECTOR5]](<8 x s8>) - ; CHECK-NEXT: [[UV20:%[0-9]+]]:_(<4 x s16>), [[UV21:%[0-9]+]]:_(<4 x s16>) = G_UNMERGE_VALUES [[ANYEXT3]](<8 x s16>) - ; CHECK-NEXT: [[AND:%[0-9]+]]:_(<4 x s16>) = G_AND [[TRUNC5]], [[UV20]] - ; CHECK-NEXT: [[TRUNC6:%[0-9]+]]:_(<4 x s16>) = G_TRUNC [[ICMP1]](<4 x s32>) - ; CHECK-NEXT: [[AND1:%[0-9]+]]:_(<4 x s16>) = G_AND [[TRUNC6]], [[XOR]] + ; CHECK-NEXT: [[UV22:%[0-9]+]]:_(<4 x s16>), [[UV23:%[0-9]+]]:_(<4 x s16>) = G_UNMERGE_VALUES [[ANYEXT2]](<8 x s16>) + ; CHECK-NEXT: [[AND:%[0-9]+]]:_(<4 x s16>) = G_AND [[TRUNC9]], [[UV22]] + ; CHECK-NEXT: [[TRUNC10:%[0-9]+]]:_(<4 x s16>) = G_TRUNC [[ICMP1]](<4 x s32>) + ; CHECK-NEXT: [[AND1:%[0-9]+]]:_(<4 x s16>) = G_AND [[TRUNC10]], [[XOR]] ; CHECK-NEXT: [[OR:%[0-9]+]]:_(<4 x s16>) = G_OR [[AND]], [[AND1]] - ; CHECK-NEXT: [[ANYEXT4:%[0-9]+]]:_(<4 x s32>) = G_ANYEXT [[OR]](<4 x s16>) + ; CHECK-NEXT: [[ANYEXT3:%[0-9]+]]:_(<4 x s32>) = G_ANYEXT [[OR]](<4 x s16>) ; CHECK-NEXT: [[C3:%[0-9]+]]:_(s32) = G_CONSTANT i32 1 - ; CHECK-NEXT: [[BUILD_VECTOR6:%[0-9]+]]:_(<4 x s32>) = G_BUILD_VECTOR [[C3]](s32), [[C3]](s32), [[C3]](s32), [[C3]](s32) - ; CHECK-NEXT: %zext_select:_(<4 x s32>) = G_AND [[ANYEXT4]], [[BUILD_VECTOR6]] + ; CHECK-NEXT: [[BUILD_VECTOR5:%[0-9]+]]:_(<4 x s32>) = G_BUILD_VECTOR [[C3]](s32), [[C3]](s32), [[C3]](s32), [[C3]](s32) + ; CHECK-NEXT: %zext_select:_(<4 x s32>) = G_AND [[ANYEXT3]], [[BUILD_VECTOR5]] ; CHECK-NEXT: $q0 = COPY %zext_select(<4 x s32>) ; CHECK-NEXT: RET_ReallyLR implicit $q0 %w0:_(s32) = COPY $w0 diff --git a/llvm/test/CodeGen/AArch64/GlobalISel/legalize-shift.mir b/llvm/test/CodeGen/AArch64/GlobalISel/legalize-shift.mir index 9a9b35cf293da1cb67483e18d91caa3f6c543475..f1d345ff18f7e1d1210ab417bf61789e59c2d9ee 100644 --- a/llvm/test/CodeGen/AArch64/GlobalISel/legalize-shift.mir +++ b/llvm/test/CodeGen/AArch64/GlobalISel/legalize-shift.mir @@ -411,13 +411,9 @@ name: test_ashr_v8s32 body: | bb.0: ; CHECK-LABEL: name: test_ashr_v8s32 - ; CHECK: [[DEF:%[0-9]+]]:_(s32) = G_IMPLICIT_DEF - ; CHECK-NEXT: [[BUILD_VECTOR:%[0-9]+]]:_(<4 x s32>) = G_BUILD_VECTOR [[DEF]](s32), [[DEF]](s32), [[DEF]](s32), [[DEF]](s32) - ; CHECK-NEXT: [[BUILD_VECTOR1:%[0-9]+]]:_(<4 x s32>) = G_BUILD_VECTOR [[DEF]](s32), [[DEF]](s32), [[DEF]](s32), [[DEF]](s32) - ; CHECK-NEXT: [[BUILD_VECTOR2:%[0-9]+]]:_(<4 x s32>) = G_BUILD_VECTOR [[DEF]](s32), [[DEF]](s32), [[DEF]](s32), [[DEF]](s32) - ; CHECK-NEXT: [[BUILD_VECTOR3:%[0-9]+]]:_(<4 x s32>) = G_BUILD_VECTOR [[DEF]](s32), [[DEF]](s32), [[DEF]](s32), [[DEF]](s32) - ; CHECK-NEXT: [[ASHR:%[0-9]+]]:_(<4 x s32>) = G_ASHR [[BUILD_VECTOR]], [[BUILD_VECTOR2]](<4 x s32>) - ; CHECK-NEXT: [[ASHR1:%[0-9]+]]:_(<4 x s32>) = G_ASHR [[BUILD_VECTOR1]], [[BUILD_VECTOR3]](<4 x s32>) + ; CHECK: [[DEF:%[0-9]+]]:_(<4 x s32>) = G_IMPLICIT_DEF + ; CHECK-NEXT: [[ASHR:%[0-9]+]]:_(<4 x s32>) = G_ASHR [[DEF]], [[DEF]](<4 x s32>) + ; CHECK-NEXT: [[ASHR1:%[0-9]+]]:_(<4 x s32>) = G_ASHR [[DEF]], [[DEF]](<4 x s32>) ; CHECK-NEXT: $q0 = COPY [[ASHR]](<4 x s32>) ; CHECK-NEXT: $q1 = COPY [[ASHR1]](<4 x s32>) %0:_(<8 x s32>) = G_IMPLICIT_DEF diff --git a/llvm/test/CodeGen/AArch64/GlobalISel/legalize-shuffle-vector.mir b/llvm/test/CodeGen/AArch64/GlobalISel/legalize-shuffle-vector.mir index 2cfee7bcc462a227f080f769a8a548e2abe7bce8..c92718f9e9b3c7a8f3fb6244b4b5332d84c323de 100644 --- a/llvm/test/CodeGen/AArch64/GlobalISel/legalize-shuffle-vector.mir +++ b/llvm/test/CodeGen/AArch64/GlobalISel/legalize-shuffle-vector.mir @@ -312,9 +312,10 @@ body: | ; CHECK-NEXT: [[COPY:%[0-9]+]]:_(s32) = COPY $w0 ; CHECK-NEXT: [[COPY1:%[0-9]+]]:_(s32) = COPY $w1 ; CHECK-NEXT: [[COPY2:%[0-9]+]]:_(s32) = COPY $w2 - ; CHECK-NEXT: [[DEF:%[0-9]+]]:_(s32) = G_IMPLICIT_DEF - ; CHECK-NEXT: [[BUILD_VECTOR:%[0-9]+]]:_(<4 x s32>) = G_BUILD_VECTOR [[COPY]](s32), [[COPY1]](s32), [[COPY2]](s32), [[DEF]](s32) - ; CHECK-NEXT: [[BUILD_VECTOR1:%[0-9]+]]:_(<4 x s32>) = G_BUILD_VECTOR [[COPY]](s32), [[COPY1]](s32), [[COPY2]](s32), [[DEF]](s32) + ; CHECK-NEXT: [[DEF:%[0-9]+]]:_(<4 x s32>) = G_IMPLICIT_DEF + ; CHECK-NEXT: [[UV:%[0-9]+]]:_(s32), [[UV1:%[0-9]+]]:_(s32), [[UV2:%[0-9]+]]:_(s32), [[UV3:%[0-9]+]]:_(s32) = G_UNMERGE_VALUES [[DEF]](<4 x s32>) + ; CHECK-NEXT: [[BUILD_VECTOR:%[0-9]+]]:_(<4 x s32>) = G_BUILD_VECTOR [[COPY]](s32), [[COPY1]](s32), [[COPY2]](s32), [[UV]](s32) + ; CHECK-NEXT: [[BUILD_VECTOR1:%[0-9]+]]:_(<4 x s32>) = G_BUILD_VECTOR [[COPY]](s32), [[COPY1]](s32), [[COPY2]](s32), [[UV]](s32) ; CHECK-NEXT: [[SHUF:%[0-9]+]]:_(<4 x s32>) = G_SHUFFLE_VECTOR [[BUILD_VECTOR]](<4 x s32>), [[BUILD_VECTOR1]], shufflemask(0, 1, 5, 6) ; CHECK-NEXT: [[C:%[0-9]+]]:_(s64) = G_CONSTANT i64 0 ; CHECK-NEXT: [[EVEC:%[0-9]+]]:_(s32) = G_EXTRACT_VECTOR_ELT [[SHUF]](<4 x s32>), [[C]](s64) diff --git a/llvm/test/CodeGen/AArch64/GlobalISel/legalizer-info-validation.mir b/llvm/test/CodeGen/AArch64/GlobalISel/legalizer-info-validation.mir index 098726b0a980df68353d002572926909443dc86f..20133158e4fa9a6d5c1a9075660bb5dcd9a12255 100644 --- a/llvm/test/CodeGen/AArch64/GlobalISel/legalizer-info-validation.mir +++ b/llvm/test/CodeGen/AArch64/GlobalISel/legalizer-info-validation.mir @@ -71,8 +71,8 @@ # DEBUG-NEXT: .. the first uncovered imm index: 0, OK # # DEBUG-NEXT: G_IMPLICIT_DEF (opcode {{[0-9]+}}): 1 type index, 0 imm indices -# DEBUG-NEXT: .. type index coverage check SKIPPED: user-defined predicate detected -# DEBUG-NEXT: .. imm index coverage check SKIPPED: user-defined predicate detected +# DEBUG-NEXT: .. the first uncovered type index: {{[0-9]+}}, OK +# DEBUG-NEXT: .. the first uncovered imm index: {{[0-9]+}}, OK # # DEBUG-NEXT: G_PHI (opcode {{[0-9]+}}): 1 type index, 0 imm indices # DEBUG-NEXT: .. the first uncovered type index: 1, OK @@ -132,13 +132,13 @@ # # DEBUG-NEXT: G_FREEZE (opcode {{[0-9]+}}): 1 type index, 0 imm indices # DEBUG-NEXT: .. opcode {{[0-9]+}} is aliased to {{[0-9]+}} -# DEBUG-NEXT: .. type index coverage check SKIPPED: user-defined predicate detected -# DEBUG-NEXT: .. imm index coverage check SKIPPED: user-defined predicate detected +# DEBUG-NEXT: .. the first uncovered type index: {{[0-9]+}}, OK +# DEBUG-NEXT: .. the first uncovered imm index: {{[0-9]+}}, OK # DEBUG-NEXT: G_CONSTANT_FOLD_BARRIER (opcode {{[0-9]+}}): 1 type index, 0 imm indices # DEBUG-NEXT: .. opcode {{[0-9]+}} is aliased to {{[0-9]+}} -# DEBUG-NEXT: .. type index coverage check SKIPPED: user-defined predicate detected -# DEBUG-NEXT: .. imm index coverage check SKIPPED: user-defined predicate detected +# DEBUG-NEXT: .. the first uncovered type index: {{[0-9]+}}, OK +# DEBUG-NEXT: .. the first uncovered imm index: {{[0-9]+}}, OK # # DEBUG-NEXT: G_INTRINSIC_FPTRUNC_ROUND (opcode {{[0-9]+}}): 2 type indices, 0 imm indices diff --git a/llvm/test/CodeGen/AArch64/arm64-uzp.ll b/llvm/test/CodeGen/AArch64/arm64-uzp.ll index 6e01ebc95a1cb8fd34eb988500710bc15ffd1404..49a51d96fbc8413a9f40187e6df3d533ddc75a6c 100644 --- a/llvm/test/CodeGen/AArch64/arm64-uzp.ll +++ b/llvm/test/CodeGen/AArch64/arm64-uzp.ll @@ -110,13 +110,9 @@ define <8 x i16> @vuzpQi16_undef1(<8 x i16> %A, <8 x i16> %B) nounwind { define <8 x i16> @vuzpQi16_undef0(<8 x i16> %A, <8 x i16> %B) nounwind { ; CHECK-LABEL: vuzpQi16_undef0: ; CHECK: // %bb.0: -; CHECK-NEXT: adrp x8, .LCPI8_0 -; CHECK-NEXT: // kill: def $q1 killed $q1 killed $q0_q1 def $q0_q1 -; CHECK-NEXT: ldr q2, [x8, :lo12:.LCPI8_0] -; CHECK-NEXT: // kill: def $q0 killed $q0 killed $q0_q1 def $q0_q1 -; CHECK-NEXT: uzp2.8h v3, v0, v1 -; CHECK-NEXT: tbl.16b v0, { v0, v1 }, v2 -; CHECK-NEXT: add.8h v0, v0, v3 +; CHECK-NEXT: uzp1.8h v2, v0, v1 +; CHECK-NEXT: uzp2.8h v0, v0, v1 +; CHECK-NEXT: add.8h v0, v2, v0 ; CHECK-NEXT: ret %tmp3 = shufflevector <8 x i16> %A, <8 x i16> %B, <8 x i32> %tmp4 = shufflevector <8 x i16> %A, <8 x i16> %B, <8 x i32> @@ -127,13 +123,9 @@ define <8 x i16> @vuzpQi16_undef0(<8 x i16> %A, <8 x i16> %B) nounwind { define <8 x i16> @vuzpQi16_undef01(<8 x i16> %A, <8 x i16> %B) nounwind { ; CHECK-LABEL: vuzpQi16_undef01: ; CHECK: // %bb.0: -; CHECK-NEXT: adrp x8, .LCPI9_0 -; CHECK-NEXT: // kill: def $q1 killed $q1 killed $q0_q1 def $q0_q1 -; CHECK-NEXT: ldr q2, [x8, :lo12:.LCPI9_0] -; CHECK-NEXT: // kill: def $q0 killed $q0 killed $q0_q1 def $q0_q1 -; CHECK-NEXT: uzp2.8h v3, v0, v1 -; CHECK-NEXT: tbl.16b v0, { v0, v1 }, v2 -; CHECK-NEXT: add.8h v0, v0, v3 +; CHECK-NEXT: uzp1.8h v2, v0, v1 +; CHECK-NEXT: uzp2.8h v0, v0, v1 +; CHECK-NEXT: add.8h v0, v2, v0 ; CHECK-NEXT: ret %tmp3 = shufflevector <8 x i16> %A, <8 x i16> %B, <8 x i32> %tmp4 = shufflevector <8 x i16> %A, <8 x i16> %B, <8 x i32> @@ -144,13 +136,9 @@ define <8 x i16> @vuzpQi16_undef01(<8 x i16> %A, <8 x i16> %B) nounwind { define <8 x i16> @vuzpQi16_undef012(<8 x i16> %A, <8 x i16> %B) nounwind { ; CHECK-LABEL: vuzpQi16_undef012: ; CHECK: // %bb.0: -; CHECK-NEXT: adrp x8, .LCPI10_0 -; CHECK-NEXT: // kill: def $q1 killed $q1 killed $q0_q1 def $q0_q1 -; CHECK-NEXT: ldr q2, [x8, :lo12:.LCPI10_0] -; CHECK-NEXT: // kill: def $q0 killed $q0 killed $q0_q1 def $q0_q1 -; CHECK-NEXT: uzp2.8h v3, v0, v1 -; CHECK-NEXT: tbl.16b v0, { v0, v1 }, v2 -; CHECK-NEXT: add.8h v0, v0, v3 +; CHECK-NEXT: uzp1.8h v2, v0, v1 +; CHECK-NEXT: uzp2.8h v0, v0, v1 +; CHECK-NEXT: add.8h v0, v2, v0 ; CHECK-NEXT: ret %tmp3 = shufflevector <8 x i16> %A, <8 x i16> %B, <8 x i32> %tmp4 = shufflevector <8 x i16> %A, <8 x i16> %B, <8 x i32> diff --git a/llvm/test/CodeGen/AArch64/arm64-zip.ll b/llvm/test/CodeGen/AArch64/arm64-zip.ll index 349751dda461f9d05d4b2a581094cff6599232fd..4c771cbd2966cc756ade8bc571345fe67c151470 100644 --- a/llvm/test/CodeGen/AArch64/arm64-zip.ll +++ b/llvm/test/CodeGen/AArch64/arm64-zip.ll @@ -142,11 +142,7 @@ define <16 x i8> @vzipQi8_undef(ptr %A, ptr %B) nounwind { define <8 x i16> @vzip1_undef_01(<8 x i16> %A, <8 x i16> %B) nounwind { ; CHECK-LABEL: vzip1_undef_01: ; CHECK: // %bb.0: -; CHECK-NEXT: adrp x8, .LCPI8_0 -; CHECK-NEXT: // kill: def $q1 killed $q1 killed $q0_q1 def $q0_q1 -; CHECK-NEXT: ldr q2, [x8, :lo12:.LCPI8_0] -; CHECK-NEXT: // kill: def $q0 killed $q0 killed $q0_q1 def $q0_q1 -; CHECK-NEXT: tbl.16b v0, { v0, v1 }, v2 +; CHECK-NEXT: zip1.8h v0, v0, v1 ; CHECK-NEXT: ret %s = shufflevector <8 x i16> %A, <8 x i16> %B, <8 x i32> ret <8 x i16> %s @@ -155,11 +151,7 @@ define <8 x i16> @vzip1_undef_01(<8 x i16> %A, <8 x i16> %B) nounwind { define <8 x i16> @vzip1_undef_0(<8 x i16> %A, <8 x i16> %B) nounwind { ; CHECK-LABEL: vzip1_undef_0: ; CHECK: // %bb.0: -; CHECK-NEXT: adrp x8, .LCPI9_0 -; CHECK-NEXT: // kill: def $q1 killed $q1 killed $q0_q1 def $q0_q1 -; CHECK-NEXT: ldr q2, [x8, :lo12:.LCPI9_0] -; CHECK-NEXT: // kill: def $q0 killed $q0 killed $q0_q1 def $q0_q1 -; CHECK-NEXT: tbl.16b v0, { v0, v1 }, v2 +; CHECK-NEXT: zip1.8h v0, v0, v1 ; CHECK-NEXT: ret %s = shufflevector <8 x i16> %A, <8 x i16> %B, <8 x i32> ret <8 x i16> %s @@ -177,11 +169,7 @@ define <8 x i16> @vzip1_undef_1(<8 x i16> %A, <8 x i16> %B) nounwind { define <8 x i16> @vzip1_undef_012(<8 x i16> %A, <8 x i16> %B) nounwind { ; CHECK-LABEL: vzip1_undef_012: ; CHECK: // %bb.0: -; CHECK-NEXT: adrp x8, .LCPI11_0 -; CHECK-NEXT: // kill: def $q1 killed $q1 killed $q0_q1 def $q0_q1 -; CHECK-NEXT: ldr q2, [x8, :lo12:.LCPI11_0] -; CHECK-NEXT: // kill: def $q0 killed $q0 killed $q0_q1 def $q0_q1 -; CHECK-NEXT: tbl.16b v0, { v0, v1 }, v2 +; CHECK-NEXT: zip1.8h v0, v0, v1 ; CHECK-NEXT: ret %s = shufflevector <8 x i16> %A, <8 x i16> %B, <8 x i32> ret <8 x i16> %s diff --git a/llvm/test/CodeGen/AArch64/combine-mul.ll b/llvm/test/CodeGen/AArch64/combine-mul.ll index a2b0425308093d778d56f97dbddc141e7ab91bbc..c49e5ae6620a9ee876e93966756357e254dab393 100644 --- a/llvm/test/CodeGen/AArch64/combine-mul.ll +++ b/llvm/test/CodeGen/AArch64/combine-mul.ll @@ -44,8 +44,7 @@ define <4 x i1> @PR48683_vec_undef(<4 x i32> %x) { define i64 @combine_mul_self_demandedbits(i64 %x) { ; CHECK-LABEL: combine_mul_self_demandedbits: ; CHECK: // %bb.0: -; CHECK-NEXT: mul x8, x0, x0 -; CHECK-NEXT: and x0, x8, #0xfffffffffffffffd +; CHECK-NEXT: mul x0, x0, x0 ; CHECK-NEXT: ret %1 = mul i64 %x, %x %2 = and i64 %1, -3 @@ -77,7 +76,7 @@ define i8 @one_demanded_bit(i8 %x) { define <2 x i64> @one_demanded_bit_splat(<2 x i64> %x) { ; CHECK-LABEL: one_demanded_bit_splat: ; CHECK: // %bb.0: -; CHECK-NEXT: mov w8, #32 +; CHECK-NEXT: mov w8, #32 // =0x20 ; CHECK-NEXT: shl v0.2d, v0.2d, #5 ; CHECK-NEXT: dup v1.2d, x8 ; CHECK-NEXT: and v0.16b, v0.16b, v1.16b @@ -131,7 +130,7 @@ define i32 @squared_demanded_2_low_bits(i32 %x) { define <2 x i64> @squared_demanded_2_low_bits_splat(<2 x i64> %x) { ; CHECK-LABEL: squared_demanded_2_low_bits_splat: ; CHECK: // %bb.0: -; CHECK-NEXT: mov x8, #-2 +; CHECK-NEXT: mov x8, #-2 // =0xfffffffffffffffe ; CHECK-NEXT: dup v1.2d, x8 ; CHECK-NEXT: orr v0.16b, v0.16b, v1.16b ; CHECK-NEXT: ret diff --git a/llvm/test/CodeGen/AArch64/complex-deinterleaving-reductions-scalable.ll b/llvm/test/CodeGen/AArch64/complex-deinterleaving-reductions-scalable.ll index 664d99a3627b58f41b43b796c648b17b36c6c551..5bef95910d9060b31a75180a7cfecec0cf5a452b 100644 --- a/llvm/test/CodeGen/AArch64/complex-deinterleaving-reductions-scalable.ll +++ b/llvm/test/CodeGen/AArch64/complex-deinterleaving-reductions-scalable.ll @@ -17,11 +17,11 @@ define %"class.std::complex" @complex_mul_v2f64(ptr %a, ptr %b) { ; CHECK-NEXT: mov z1.d, #0 // =0x0 ; CHECK-NEXT: cntd x9 ; CHECK-NEXT: ptrue p1.b -; CHECK-NEXT: neg x9, x9 -; CHECK-NEXT: mov w10, #100 // =0x64 +; CHECK-NEXT: neg x10, x9 +; CHECK-NEXT: mov w11, #100 // =0x64 ; CHECK-NEXT: ptrue p0.d ; CHECK-NEXT: mov x8, xzr -; CHECK-NEXT: and x10, x9, x10 +; CHECK-NEXT: and x10, x10, x11 ; CHECK-NEXT: rdvl x11, #2 ; CHECK-NEXT: zip2 z0.d, z1.d, z1.d ; CHECK-NEXT: zip1 z1.d, z1.d, z1.d @@ -33,7 +33,7 @@ define %"class.std::complex" @complex_mul_v2f64(ptr %a, ptr %b) { ; CHECK-NEXT: ld1d { z3.d }, p0/z, [x12, #1, mul vl] ; CHECK-NEXT: ld1b { z4.b }, p1/z, [x1, x8] ; CHECK-NEXT: ld1d { z5.d }, p0/z, [x13, #1, mul vl] -; CHECK-NEXT: adds x10, x10, x9 +; CHECK-NEXT: subs x10, x10, x9 ; CHECK-NEXT: add x8, x8, x11 ; CHECK-NEXT: fcmla z1.d, p0/m, z4.d, z2.d, #0 ; CHECK-NEXT: fcmla z0.d, p0/m, z5.d, z3.d, #0 @@ -106,12 +106,12 @@ define %"class.std::complex" @complex_mul_nonzero_init_v2f64(ptr %a, ptr %b) { ; CHECK-NEXT: cntd x9 ; CHECK-NEXT: fmov d2, #2.00000000 ; CHECK-NEXT: ptrue p0.d, vl1 -; CHECK-NEXT: neg x9, x9 +; CHECK-NEXT: neg x10, x9 ; CHECK-NEXT: ptrue p1.b -; CHECK-NEXT: mov w10, #100 // =0x64 +; CHECK-NEXT: mov w11, #100 // =0x64 ; CHECK-NEXT: mov x8, xzr ; CHECK-NEXT: sel z3.d, p0, z0.d, z1.d -; CHECK-NEXT: and x10, x9, x10 +; CHECK-NEXT: and x10, x10, x11 ; CHECK-NEXT: rdvl x11, #2 ; CHECK-NEXT: mov z1.d, p0/m, z2.d ; CHECK-NEXT: ptrue p0.d @@ -125,7 +125,7 @@ define %"class.std::complex" @complex_mul_nonzero_init_v2f64(ptr %a, ptr %b) { ; CHECK-NEXT: ld1d { z3.d }, p0/z, [x12, #1, mul vl] ; CHECK-NEXT: ld1b { z4.b }, p1/z, [x1, x8] ; CHECK-NEXT: ld1d { z5.d }, p0/z, [x13, #1, mul vl] -; CHECK-NEXT: adds x10, x10, x9 +; CHECK-NEXT: subs x10, x10, x9 ; CHECK-NEXT: add x8, x8, x11 ; CHECK-NEXT: fcmla z1.d, p0/m, z4.d, z2.d, #0 ; CHECK-NEXT: fcmla z0.d, p0/m, z5.d, z3.d, #0 @@ -191,13 +191,13 @@ define %"class.std::complex" @complex_mul_v2f64_unrolled(ptr %a, ptr %b) { ; CHECK: // %bb.0: // %entry ; CHECK-NEXT: mov z1.d, #0 // =0x0 ; CHECK-NEXT: cntw x9 -; CHECK-NEXT: mov w10, #1000 // =0x3e8 -; CHECK-NEXT: neg x9, x9 +; CHECK-NEXT: mov w11, #1000 // =0x3e8 +; CHECK-NEXT: neg x10, x9 ; CHECK-NEXT: rdvl x12, #2 ; CHECK-NEXT: ptrue p1.b ; CHECK-NEXT: ptrue p0.d ; CHECK-NEXT: mov x8, xzr -; CHECK-NEXT: and x10, x9, x10 +; CHECK-NEXT: and x10, x10, x11 ; CHECK-NEXT: zip2 z0.d, z1.d, z1.d ; CHECK-NEXT: zip1 z1.d, z1.d, z1.d ; CHECK-NEXT: add x11, x1, x12 @@ -219,7 +219,7 @@ define %"class.std::complex" @complex_mul_v2f64_unrolled(ptr %a, ptr %b) { ; CHECK-NEXT: ld1d { z17.d }, p0/z, [x15, #1, mul vl] ; CHECK-NEXT: ld1b { z18.b }, p1/z, [x11, x8] ; CHECK-NEXT: ld1d { z19.d }, p0/z, [x17, #1, mul vl] -; CHECK-NEXT: adds x10, x10, x9 +; CHECK-NEXT: subs x10, x10, x9 ; CHECK-NEXT: add x8, x8, x13 ; CHECK-NEXT: fcmla z1.d, p0/m, z7.d, z4.d, #0 ; CHECK-NEXT: fcmla z0.d, p0/m, z16.d, z5.d, #0 diff --git a/llvm/test/CodeGen/AArch64/concatbinop.ll b/llvm/test/CodeGen/AArch64/concatbinop.ll new file mode 100644 index 0000000000000000000000000000000000000000..828182d18b38ce9ecb44f3afe26440e14979caa9 --- /dev/null +++ b/llvm/test/CodeGen/AArch64/concatbinop.ll @@ -0,0 +1,201 @@ +; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py UTC_ARGS: --version 4 +; RUN: llc -mtriple=aarch64 -mattr=+fullfp16 -verify-machineinstrs -o - %s | FileCheck %s + + +define <8 x i16> @concat_add(<4 x i16> %a, <4 x i16> %b, <4 x i16> %c, <4 x i16> %d) { +; CHECK-LABEL: concat_add: +; CHECK: // %bb.0: +; CHECK-NEXT: // kill: def $d1 killed $d1 def $q1 +; CHECK-NEXT: // kill: def $d0 killed $d0 def $q0 +; CHECK-NEXT: // kill: def $d3 killed $d3 def $q3 +; CHECK-NEXT: // kill: def $d2 killed $d2 def $q2 +; CHECK-NEXT: mov v1.d[1], v3.d[0] +; CHECK-NEXT: mov v0.d[1], v2.d[0] +; CHECK-NEXT: add v0.8h, v0.8h, v1.8h +; CHECK-NEXT: ret + %x = add <4 x i16> %a, %b + %y = add <4 x i16> %c, %d + %z = shufflevector <4 x i16> %x, <4 x i16> %y, <8 x i32> + ret <8 x i16> %z +} + +define <8 x i16> @concat_addtunc(<4 x i32> %a, <4 x i32> %b, <4 x i32> %c, <4 x i32> %d) { +; CHECK-LABEL: concat_addtunc: +; CHECK: // %bb.0: +; CHECK-NEXT: add v2.4s, v2.4s, v3.4s +; CHECK-NEXT: add v0.4s, v0.4s, v1.4s +; CHECK-NEXT: uzp1 v0.8h, v0.8h, v2.8h +; CHECK-NEXT: ret + %x = add <4 x i32> %a, %b + %y = add <4 x i32> %c, %d + %xt = trunc <4 x i32> %x to <4 x i16> + %yt = trunc <4 x i32> %y to <4 x i16> + %z = shufflevector <4 x i16> %xt, <4 x i16> %yt, <8 x i32> + ret <8 x i16> %z +} + +define <8 x i16> @concat_addtunc2(<4 x i32> %a, <4 x i32> %b, <4 x i32> %c, <4 x i32> %d) { +; CHECK-LABEL: concat_addtunc2: +; CHECK: // %bb.0: +; CHECK-NEXT: uzp1 v1.8h, v1.8h, v3.8h +; CHECK-NEXT: uzp1 v0.8h, v0.8h, v2.8h +; CHECK-NEXT: add v0.8h, v0.8h, v1.8h +; CHECK-NEXT: ret + %at = trunc <4 x i32> %a to <4 x i16> + %bt = trunc <4 x i32> %b to <4 x i16> + %ct = trunc <4 x i32> %c to <4 x i16> + %dt = trunc <4 x i32> %d to <4 x i16> + %x = add <4 x i16> %at, %bt + %y = add <4 x i16> %ct, %dt + %z = shufflevector <4 x i16> %x, <4 x i16> %y, <8 x i32> + ret <8 x i16> %z +} + +define <8 x i16> @concat_sub(<4 x i16> %a, <4 x i16> %b, <4 x i16> %c, <4 x i16> %d) { +; CHECK-LABEL: concat_sub: +; CHECK: // %bb.0: +; CHECK-NEXT: // kill: def $d1 killed $d1 def $q1 +; CHECK-NEXT: // kill: def $d0 killed $d0 def $q0 +; CHECK-NEXT: // kill: def $d3 killed $d3 def $q3 +; CHECK-NEXT: // kill: def $d2 killed $d2 def $q2 +; CHECK-NEXT: mov v1.d[1], v3.d[0] +; CHECK-NEXT: mov v0.d[1], v2.d[0] +; CHECK-NEXT: sub v0.8h, v0.8h, v1.8h +; CHECK-NEXT: ret + %x = sub <4 x i16> %a, %b + %y = sub <4 x i16> %c, %d + %z = shufflevector <4 x i16> %x, <4 x i16> %y, <8 x i32> + ret <8 x i16> %z +} + +define <8 x i16> @concat_mul(<4 x i16> %a, <4 x i16> %b, <4 x i16> %c, <4 x i16> %d) { +; CHECK-LABEL: concat_mul: +; CHECK: // %bb.0: +; CHECK-NEXT: // kill: def $d1 killed $d1 def $q1 +; CHECK-NEXT: // kill: def $d0 killed $d0 def $q0 +; CHECK-NEXT: // kill: def $d3 killed $d3 def $q3 +; CHECK-NEXT: // kill: def $d2 killed $d2 def $q2 +; CHECK-NEXT: mov v1.d[1], v3.d[0] +; CHECK-NEXT: mov v0.d[1], v2.d[0] +; CHECK-NEXT: mul v0.8h, v0.8h, v1.8h +; CHECK-NEXT: ret + %x = mul <4 x i16> %a, %b + %y = mul <4 x i16> %c, %d + %z = shufflevector <4 x i16> %x, <4 x i16> %y, <8 x i32> + ret <8 x i16> %z +} + +define <8 x i16> @concat_xor(<4 x i16> %a, <4 x i16> %b, <4 x i16> %c, <4 x i16> %d) { +; CHECK-LABEL: concat_xor: +; CHECK: // %bb.0: +; CHECK-NEXT: // kill: def $d1 killed $d1 def $q1 +; CHECK-NEXT: // kill: def $d0 killed $d0 def $q0 +; CHECK-NEXT: // kill: def $d3 killed $d3 def $q3 +; CHECK-NEXT: // kill: def $d2 killed $d2 def $q2 +; CHECK-NEXT: mov v1.d[1], v3.d[0] +; CHECK-NEXT: mov v0.d[1], v2.d[0] +; CHECK-NEXT: eor v0.16b, v0.16b, v1.16b +; CHECK-NEXT: ret + %x = xor <4 x i16> %a, %b + %y = xor <4 x i16> %c, %d + %z = shufflevector <4 x i16> %x, <4 x i16> %y, <8 x i32> + ret <8 x i16> %z +} + +define <8 x half> @concat_fadd(<4 x half> %a, <4 x half> %b, <4 x half> %c, <4 x half> %d) { +; CHECK-LABEL: concat_fadd: +; CHECK: // %bb.0: +; CHECK-NEXT: // kill: def $d1 killed $d1 def $q1 +; CHECK-NEXT: // kill: def $d0 killed $d0 def $q0 +; CHECK-NEXT: // kill: def $d3 killed $d3 def $q3 +; CHECK-NEXT: // kill: def $d2 killed $d2 def $q2 +; CHECK-NEXT: mov v1.d[1], v3.d[0] +; CHECK-NEXT: mov v0.d[1], v2.d[0] +; CHECK-NEXT: fadd v0.8h, v0.8h, v1.8h +; CHECK-NEXT: ret + %x = fadd <4 x half> %a, %b + %y = fadd <4 x half> %c, %d + %z = shufflevector <4 x half> %x, <4 x half> %y, <8 x i32> + ret <8 x half> %z +} + +define <8 x half> @concat_fmul(<4 x half> %a, <4 x half> %b, <4 x half> %c, <4 x half> %d) { +; CHECK-LABEL: concat_fmul: +; CHECK: // %bb.0: +; CHECK-NEXT: // kill: def $d1 killed $d1 def $q1 +; CHECK-NEXT: // kill: def $d0 killed $d0 def $q0 +; CHECK-NEXT: // kill: def $d3 killed $d3 def $q3 +; CHECK-NEXT: // kill: def $d2 killed $d2 def $q2 +; CHECK-NEXT: mov v1.d[1], v3.d[0] +; CHECK-NEXT: mov v0.d[1], v2.d[0] +; CHECK-NEXT: fmul v0.8h, v0.8h, v1.8h +; CHECK-NEXT: ret + %x = fmul <4 x half> %a, %b + %y = fmul <4 x half> %c, %d + %z = shufflevector <4 x half> %x, <4 x half> %y, <8 x i32> + ret <8 x half> %z +} + +define <8 x half> @concat_min(<4 x half> %a, <4 x half> %b, <4 x half> %c, <4 x half> %d) { +; CHECK-LABEL: concat_min: +; CHECK: // %bb.0: +; CHECK-NEXT: // kill: def $d1 killed $d1 def $q1 +; CHECK-NEXT: // kill: def $d0 killed $d0 def $q0 +; CHECK-NEXT: // kill: def $d3 killed $d3 def $q3 +; CHECK-NEXT: // kill: def $d2 killed $d2 def $q2 +; CHECK-NEXT: mov v1.d[1], v3.d[0] +; CHECK-NEXT: mov v0.d[1], v2.d[0] +; CHECK-NEXT: fminnm v0.8h, v0.8h, v1.8h +; CHECK-NEXT: ret + %x = call <4 x half> @llvm.minnum.v4f16(<4 x half> %a, <4 x half> %b) + %y = call <4 x half> @llvm.minnum.v4f16(<4 x half> %c, <4 x half> %d) + %z = shufflevector <4 x half> %x, <4 x half> %y, <8 x i32> + ret <8 x half> %z +} + +define <8 x half> @concat_minmax(<4 x half> %a, <4 x half> %b, <4 x half> %c, <4 x half> %d) { +; CHECK-LABEL: concat_minmax: +; CHECK: // %bb.0: +; CHECK-NEXT: fmaxnm v2.4h, v2.4h, v3.4h +; CHECK-NEXT: fminnm v0.4h, v0.4h, v1.4h +; CHECK-NEXT: mov v0.d[1], v2.d[0] +; CHECK-NEXT: ret + %x = call <4 x half> @llvm.minnum.v4f16(<4 x half> %a, <4 x half> %b) + %y = call <4 x half> @llvm.maxnum.v4f16(<4 x half> %c, <4 x half> %d) + %z = shufflevector <4 x half> %x, <4 x half> %y, <8 x i32> + ret <8 x half> %z +} + +define <16 x i8> @signOf_neon(ptr nocapture noundef readonly %a, ptr nocapture noundef readonly %b) { +; CHECK-LABEL: signOf_neon: +; CHECK: // %bb.0: // %entry +; CHECK-NEXT: ldp q1, q2, [x0] +; CHECK-NEXT: movi v0.16b, #1 +; CHECK-NEXT: ldp q3, q4, [x1] +; CHECK-NEXT: cmhi v5.8h, v1.8h, v3.8h +; CHECK-NEXT: cmhi v6.8h, v2.8h, v4.8h +; CHECK-NEXT: cmhi v1.8h, v3.8h, v1.8h +; CHECK-NEXT: cmhi v2.8h, v4.8h, v2.8h +; CHECK-NEXT: uzp1 v3.16b, v5.16b, v6.16b +; CHECK-NEXT: uzp1 v1.16b, v1.16b, v2.16b +; CHECK-NEXT: and v0.16b, v3.16b, v0.16b +; CHECK-NEXT: orr v0.16b, v0.16b, v1.16b +; CHECK-NEXT: ret +entry: + %0 = load <8 x i16>, ptr %a, align 2 + %add.ptr = getelementptr inbounds i8, ptr %a, i64 16 + %1 = load <8 x i16>, ptr %add.ptr, align 2 + %2 = load <8 x i16>, ptr %b, align 2 + %add.ptr6 = getelementptr inbounds i8, ptr %b, i64 16 + %3 = load <8 x i16>, ptr %add.ptr6, align 2 + %cmp.i33 = icmp ugt <8 x i16> %0, %2 + %cmp.i31 = icmp ugt <8 x i16> %1, %3 + %cmp.i29 = icmp ugt <8 x i16> %2, %0 + %cmp.i = icmp ugt <8 x i16> %3, %1 + %vmovn.i38.neg = zext <8 x i1> %cmp.i33 to <8 x i8> + %vmovn.i37.neg = zext <8 x i1> %cmp.i31 to <8 x i8> + %4 = select <8 x i1> %cmp.i29, <8 x i8> , <8 x i8> %vmovn.i38.neg + %5 = select <8 x i1> %cmp.i, <8 x i8> , <8 x i8> %vmovn.i37.neg + %or.i = shufflevector <8 x i8> %4, <8 x i8> %5, <16 x i32> + ret <16 x i8> %or.i +} diff --git a/llvm/test/CodeGen/AArch64/machine-combiner-subadd2.mir b/llvm/test/CodeGen/AArch64/machine-combiner-subadd2.mir index d1770bb25fae492cd10e84dd5fc5b9b51f6f390f..0b09e8a4b5cd385cb0fd4a3c958f446392dbaef5 100644 --- a/llvm/test/CodeGen/AArch64/machine-combiner-subadd2.mir +++ b/llvm/test/CodeGen/AArch64/machine-combiner-subadd2.mir @@ -237,3 +237,30 @@ body: | RET_ReallyLR implicit $w0 ... +--- +# Drop nowrap flags in SUB + +# CHECK-LABEL: name: test8 +# CHECK: %7:gpr64 = SUBXrr %1, %0 +# CHECK-NEXT: %4:gpr64common = SUBXrr killed %7, killed %2 + +name: test8 +registers: + - { id: 0, class: gpr64 } + - { id: 1, class: gpr64 } + - { id: 2, class: gpr64common } + - { id: 3, class: gpr64 } + - { id: 4, class: gpr64common } + - { id: 5, class: gpr64 } +body: | + bb.0: + %1:gpr64 = COPY $x1 + %0:gpr64 = COPY $x0 + %2:gpr64common = ORRXri %0:gpr64, 4096 + %3:gpr64 = ADDXrr killed %2:gpr64common, %0:gpr64 + %4:gpr64common = nsw SUBSXrr %1:gpr64, killed %3:gpr64, implicit-def dead $nzcv + %5:gpr64 = SUBSXri %4:gpr64common, 0, 0, implicit-def $nzcv + $x0 = COPY %5:gpr64 + RET_ReallyLR implicit $x0 + +... diff --git a/llvm/test/CodeGen/AArch64/mul_pow2.ll b/llvm/test/CodeGen/AArch64/mul_pow2.ll index 90e560af4465a97c54c8599ac320b77cc6e6bea8..0c9ea51ba367e956857ac76d584dece64ce09084 100644 --- a/llvm/test/CodeGen/AArch64/mul_pow2.ll +++ b/llvm/test/CodeGen/AArch64/mul_pow2.ll @@ -410,6 +410,23 @@ define i32 @test11(i32 %x) { ret i32 %mul } +define i32 @test11_fast_shift(i32 %x) "target-features"="+alu-lsl-fast" { +; CHECK-LABEL: test11_fast_shift: +; CHECK: // %bb.0: +; CHECK-NEXT: add w8, w0, w0, lsl #2 +; CHECK-NEXT: add w0, w0, w8, lsl #1 +; CHECK-NEXT: ret +; +; GISEL-LABEL: test11_fast_shift: +; GISEL: // %bb.0: +; GISEL-NEXT: mov w8, #11 // =0xb +; GISEL-NEXT: mul w0, w0, w8 +; GISEL-NEXT: ret + + %mul = mul nsw i32 %x, 11 ; 11 = (((1<<2) + 1) << 1) + 1 + ret i32 %mul +} + define i32 @test12(i32 %x) { ; CHECK-LABEL: test12: ; CHECK: // %bb.0: @@ -545,12 +562,29 @@ define i32 @test45(i32 %x) { ret i32 %mul } -; Negative test: The shift amount 4 larger than 3 +; Negative test: The shift number 5 is out of bound +define i32 @test67_fast_shift(i32 %x) "target-features"="+alu-lsl-fast" { +; CHECK-LABEL: test67_fast_shift: +; CHECK: // %bb.0: +; CHECK-NEXT: mov w8, #67 // =0x43 +; CHECK-NEXT: mul w0, w0, w8 +; CHECK-NEXT: ret +; +; GISEL-LABEL: test67_fast_shift: +; GISEL: // %bb.0: +; GISEL-NEXT: mov w8, #67 // =0x43 +; GISEL-NEXT: mul w0, w0, w8 +; GISEL-NEXT: ret + + %mul = mul nsw i32 %x, 67 ; 67 = (((1<<5) + 1) << 1) + 1 + ret i32 %mul +} + define i32 @test85_fast_shift(i32 %x) "target-features"="+alu-lsl-fast" { ; CHECK-LABEL: test85_fast_shift: ; CHECK: // %bb.0: -; CHECK-NEXT: mov w8, #85 // =0x55 -; CHECK-NEXT: mul w0, w0, w8 +; CHECK-NEXT: add w8, w0, w0, lsl #2 +; CHECK-NEXT: add w0, w8, w8, lsl #4 ; CHECK-NEXT: ret ; ; GISEL-LABEL: test85_fast_shift: @@ -563,7 +597,25 @@ define i32 @test85_fast_shift(i32 %x) "target-features"="+alu-lsl-fast" { ret i32 %mul } -; Negative test: The shift amount 5 larger than 3 +; Negative test: The shift number 5 is out of bound +define i32 @test97_fast_shift(i32 %x) "target-features"="+alu-lsl-fast" { +; CHECK-LABEL: test97_fast_shift: +; CHECK: // %bb.0: +; CHECK-NEXT: mov w8, #97 // =0x61 +; CHECK-NEXT: mul w0, w0, w8 +; CHECK-NEXT: ret +; +; GISEL-LABEL: test97_fast_shift: +; GISEL: // %bb.0: +; GISEL-NEXT: mov w8, #97 // =0x61 +; GISEL-NEXT: mul w0, w0, w8 +; GISEL-NEXT: ret + + %mul = mul nsw i32 %x, 97 ; 97 = ((2 + 1) << 5) + 1 + ret i32 %mul +} + +; Negative test: The shift amount 5 larger than 4 define i32 @test297_fast_shift(i32 %x) "target-features"="+alu-lsl-fast" { ; CHECK-LABEL: test297_fast_shift: ; CHECK: // %bb.0: @@ -858,9 +910,9 @@ define <4 x i32> @muladd_demand_commute(<4 x i32> %x, <4 x i32> %y) { ; ; GISEL-LABEL: muladd_demand_commute: ; GISEL: // %bb.0: -; GISEL-NEXT: adrp x8, .LCPI49_0 +; GISEL-NEXT: adrp x8, .LCPI52_0 ; GISEL-NEXT: movi v3.4s, #1, msl #16 -; GISEL-NEXT: ldr q2, [x8, :lo12:.LCPI49_0] +; GISEL-NEXT: ldr q2, [x8, :lo12:.LCPI52_0] ; GISEL-NEXT: mla v1.4s, v0.4s, v2.4s ; GISEL-NEXT: and v0.16b, v1.16b, v3.16b ; GISEL-NEXT: ret diff --git a/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-bitcast.ll b/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-bitcast.ll index dd72c2b2bd01094bc1e234093e7b37049563b73a..e3cc74f766ee0ecc763da69b1d97d5e0041c67fc 100644 --- a/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-bitcast.ll +++ b/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-bitcast.ll @@ -60,11 +60,8 @@ define void @bitcast_v2i16(ptr %a, ptr %b) { ; CHECK: // %bb.0: ; CHECK-NEXT: sub sp, sp, #16 ; CHECK-NEXT: .cfi_def_cfa_offset 16 -; CHECK-NEXT: ldrh w8, [x0, #2] -; CHECK-NEXT: str w8, [sp, #4] -; CHECK-NEXT: ldrh w8, [x0] -; CHECK-NEXT: str w8, [sp] -; CHECK-NEXT: ldr d0, [sp] +; CHECK-NEXT: ptrue p0.s, vl2 +; CHECK-NEXT: ld1h { z0.s }, p0/z, [x0] ; CHECK-NEXT: mov z1.s, z0.s[1] ; CHECK-NEXT: fmov w8, s0 ; CHECK-NEXT: strh w8, [sp, #8] diff --git a/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-extract-vector-elt.ll b/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-extract-vector-elt.ll index 1b9bb42c8582e1d1e8a43c62e910533a4ac7b7d7..a752e119b2fb2ace8f20cef7cd9637dfd01a639b 100644 --- a/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-extract-vector-elt.ll +++ b/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-extract-vector-elt.ll @@ -90,8 +90,6 @@ define float @extractelement_v8f32(ptr %a) { define double @extractelement_v1f64(<1 x double> %op1) { ; CHECK-LABEL: extractelement_v1f64: ; CHECK: // %bb.0: -; CHECK-NEXT: // kill: def $d0 killed $d0 def $z0 -; CHECK-NEXT: // kill: def $d0 killed $d0 killed $z0 ; CHECK-NEXT: ret %r = extractelement <1 x double> %op1, i64 0 ret double %r diff --git a/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-fp-compares.ll b/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-fp-compares.ll index e92694d1fc80d2eb759032eb0196a703c945b6d5..465cc179a3b989a80ddd783a47bb346fd6869bb4 100644 --- a/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-fp-compares.ll +++ b/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-fp-compares.ll @@ -127,11 +127,9 @@ define void @fcmp_oeq_v8f32(ptr %a, ptr %b, ptr %c) { define <1 x i64> @fcmp_oeq_v1f64(<1 x double> %op1, <1 x double> %op2) { ; CHECK-LABEL: fcmp_oeq_v1f64: ; CHECK: // %bb.0: -; CHECK-NEXT: ptrue p0.d, vl1 -; CHECK-NEXT: // kill: def $d1 killed $d1 def $z1 -; CHECK-NEXT: // kill: def $d0 killed $d0 def $z0 -; CHECK-NEXT: fcmeq p0.d, p0/z, z0.d, z1.d -; CHECK-NEXT: mov z0.d, p0/z, #-1 // =0xffffffffffffffff +; CHECK-NEXT: fcmp d0, d1 +; CHECK-NEXT: csetm x8, eq +; CHECK-NEXT: mov z0.d, x8 ; CHECK-NEXT: // kill: def $d0 killed $d0 killed $z0 ; CHECK-NEXT: ret %cmp = fcmp oeq <1 x double> %op1, %op2 diff --git a/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-fp-fma.ll b/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-fp-fma.ll index 478be9ab76dd9fb32b8f8c03eae6de4f15ea3693..cbe71d715a8fb96e2a2093fd08367a7dd025b655 100644 --- a/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-fp-fma.ll +++ b/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-fp-fma.ll @@ -112,9 +112,6 @@ define void @fma_v8f32(ptr %a, ptr %b, ptr %c) { define <1 x double> @fma_v1f64(<1 x double> %op1, <1 x double> %op2, <1 x double> %op3) { ; CHECK-LABEL: fma_v1f64: ; CHECK: // %bb.0: -; CHECK-NEXT: // kill: def $d0 killed $d0 def $z0 -; CHECK-NEXT: // kill: def $d2 killed $d2 def $z2 -; CHECK-NEXT: // kill: def $d1 killed $d1 def $z1 ; CHECK-NEXT: fmadd d0, d0, d1, d2 ; CHECK-NEXT: ret %mul = fmul contract <1 x double> %op1, %op2 diff --git a/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-fp-minmax.ll b/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-fp-minmax.ll index 4dc034adf459ae2b191bde3885dc5b8fcf348de9..94a74763aa0e9ff3710b0c0366ed87cef453f51e 100644 --- a/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-fp-minmax.ll +++ b/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-fp-minmax.ll @@ -99,8 +99,6 @@ define void @fmaxnm_v8f32(ptr %a, ptr %b) { define <1 x double> @fmaxnm_v1f64(<1 x double> %op1, <1 x double> %op2) { ; CHECK-LABEL: fmaxnm_v1f64: ; CHECK: // %bb.0: -; CHECK-NEXT: // kill: def $d0 killed $d0 def $z0 -; CHECK-NEXT: // kill: def $d1 killed $d1 def $z1 ; CHECK-NEXT: fmaxnm d0, d0, d1 ; CHECK-NEXT: ret %res = call <1 x double> @llvm.maxnum.v1f64(<1 x double> %op1, <1 x double> %op2) @@ -233,8 +231,6 @@ define void @fminnm_v8f32(ptr %a, ptr %b) { define <1 x double> @fminnm_v1f64(<1 x double> %op1, <1 x double> %op2) { ; CHECK-LABEL: fminnm_v1f64: ; CHECK: // %bb.0: -; CHECK-NEXT: // kill: def $d0 killed $d0 def $z0 -; CHECK-NEXT: // kill: def $d1 killed $d1 def $z1 ; CHECK-NEXT: fminnm d0, d0, d1 ; CHECK-NEXT: ret %res = call <1 x double> @llvm.minnum.v1f64(<1 x double> %op1, <1 x double> %op2) @@ -367,8 +363,6 @@ define void @fmax_v8f32(ptr %a, ptr %b) { define <1 x double> @fmax_v1f64(<1 x double> %op1, <1 x double> %op2) { ; CHECK-LABEL: fmax_v1f64: ; CHECK: // %bb.0: -; CHECK-NEXT: // kill: def $d0 killed $d0 def $z0 -; CHECK-NEXT: // kill: def $d1 killed $d1 def $z1 ; CHECK-NEXT: fmax d0, d0, d1 ; CHECK-NEXT: ret %res = call <1 x double> @llvm.maximum.v1f64(<1 x double> %op1, <1 x double> %op2) @@ -501,8 +495,6 @@ define void @fmin_v8f32(ptr %a, ptr %b) { define <1 x double> @fmin_v1f64(<1 x double> %op1, <1 x double> %op2) { ; CHECK-LABEL: fmin_v1f64: ; CHECK: // %bb.0: -; CHECK-NEXT: // kill: def $d0 killed $d0 def $z0 -; CHECK-NEXT: // kill: def $d1 killed $d1 def $z1 ; CHECK-NEXT: fmin d0, d0, d1 ; CHECK-NEXT: ret %res = call <1 x double> @llvm.minimum.v1f64(<1 x double> %op1, <1 x double> %op2) diff --git a/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-fp-reduce.ll b/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-fp-reduce.ll index bd10a0e091c0d4008be637b791095c9f99fddb88..df9613a30e40b0dacc9e3b66eddfb01165198e15 100644 --- a/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-fp-reduce.ll +++ b/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-fp-reduce.ll @@ -144,7 +144,6 @@ define float @fadda_v8f32(float %start, ptr %a) { define double @fadda_v1f64(double %start, <1 x double> %a) { ; CHECK-LABEL: fadda_v1f64: ; CHECK: // %bb.0: -; CHECK-NEXT: // kill: def $d1 killed $d1 def $z1 ; CHECK-NEXT: fadd d0, d0, d1 ; CHECK-NEXT: ret %res = call double @llvm.vector.reduce.fadd.v1f64(double %start, <1 x double> %a) @@ -263,7 +262,6 @@ define float @faddv_v8f32(float %start, ptr %a) { define double @faddv_v1f64(double %start, <1 x double> %a) { ; CHECK-LABEL: faddv_v1f64: ; CHECK: // %bb.0: -; CHECK-NEXT: // kill: def $d1 killed $d1 def $z1 ; CHECK-NEXT: fadd d0, d0, d1 ; CHECK-NEXT: ret %res = call fast double @llvm.vector.reduce.fadd.v1f64(double %start, <1 x double> %a) @@ -379,8 +377,6 @@ define float @fmaxv_v8f32(ptr %a) { define double @fmaxv_v1f64(<1 x double> %a) { ; CHECK-LABEL: fmaxv_v1f64: ; CHECK: // %bb.0: -; CHECK-NEXT: // kill: def $d0 killed $d0 def $z0 -; CHECK-NEXT: // kill: def $d0 killed $d0 killed $z0 ; CHECK-NEXT: ret %res = call double @llvm.vector.reduce.fmax.v1f64(<1 x double> %a) ret double %res @@ -495,8 +491,6 @@ define float @fminv_v8f32(ptr %a) { define double @fminv_v1f64(<1 x double> %a) { ; CHECK-LABEL: fminv_v1f64: ; CHECK: // %bb.0: -; CHECK-NEXT: // kill: def $d0 killed $d0 def $z0 -; CHECK-NEXT: // kill: def $d0 killed $d0 killed $z0 ; CHECK-NEXT: ret %res = call double @llvm.vector.reduce.fmin.v1f64(<1 x double> %a) ret double %res @@ -611,8 +605,6 @@ define float @fmaximumv_v8f32(ptr %a) { define double @fmaximumv_v1f64(<1 x double> %a) { ; CHECK-LABEL: fmaximumv_v1f64: ; CHECK: // %bb.0: -; CHECK-NEXT: // kill: def $d0 killed $d0 def $z0 -; CHECK-NEXT: // kill: def $d0 killed $d0 killed $z0 ; CHECK-NEXT: ret %res = call double @llvm.vector.reduce.fmaximum.v1f64(<1 x double> %a) ret double %res @@ -727,8 +719,6 @@ define float @fminimumv_v8f32(ptr %a) { define double @fminimumv_v1f64(<1 x double> %a) { ; CHECK-LABEL: fminimumv_v1f64: ; CHECK: // %bb.0: -; CHECK-NEXT: // kill: def $d0 killed $d0 def $z0 -; CHECK-NEXT: // kill: def $d0 killed $d0 killed $z0 ; CHECK-NEXT: ret %res = call double @llvm.vector.reduce.fminimum.v1f64(<1 x double> %a) ret double %res diff --git a/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-fp-rounding.ll b/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-fp-rounding.ll index 24832d807c649c00fe301f72b5b4e19aeacd1381..7ddc641f366caaf3905ae6774dd606a6b9c8ce52 100644 --- a/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-fp-rounding.ll +++ b/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-fp-rounding.ll @@ -101,7 +101,6 @@ define void @frintp_v8f32(ptr %a) { define <1 x double> @frintp_v1f64(<1 x double> %op) { ; CHECK-LABEL: frintp_v1f64: ; CHECK: // %bb.0: -; CHECK-NEXT: // kill: def $d0 killed $d0 def $z0 ; CHECK-NEXT: frintp d0, d0 ; CHECK-NEXT: ret %res = call <1 x double> @llvm.ceil.v1f64(<1 x double> %op) @@ -232,7 +231,6 @@ define void @frintm_v8f32(ptr %a) { define <1 x double> @frintm_v1f64(<1 x double> %op) { ; CHECK-LABEL: frintm_v1f64: ; CHECK: // %bb.0: -; CHECK-NEXT: // kill: def $d0 killed $d0 def $z0 ; CHECK-NEXT: frintm d0, d0 ; CHECK-NEXT: ret %res = call <1 x double> @llvm.floor.v1f64(<1 x double> %op) @@ -363,7 +361,6 @@ define void @frinti_v8f32(ptr %a) { define <1 x double> @frinti_v1f64(<1 x double> %op) { ; CHECK-LABEL: frinti_v1f64: ; CHECK: // %bb.0: -; CHECK-NEXT: // kill: def $d0 killed $d0 def $z0 ; CHECK-NEXT: frinti d0, d0 ; CHECK-NEXT: ret %res = call <1 x double> @llvm.nearbyint.v1f64(<1 x double> %op) @@ -494,7 +491,6 @@ define void @frintx_v8f32(ptr %a) { define <1 x double> @frintx_v1f64(<1 x double> %op) { ; CHECK-LABEL: frintx_v1f64: ; CHECK: // %bb.0: -; CHECK-NEXT: // kill: def $d0 killed $d0 def $z0 ; CHECK-NEXT: frintx d0, d0 ; CHECK-NEXT: ret %res = call <1 x double> @llvm.rint.v1f64(<1 x double> %op) @@ -625,7 +621,6 @@ define void @frinta_v8f32(ptr %a) { define <1 x double> @frinta_v1f64(<1 x double> %op) { ; CHECK-LABEL: frinta_v1f64: ; CHECK: // %bb.0: -; CHECK-NEXT: // kill: def $d0 killed $d0 def $z0 ; CHECK-NEXT: frinta d0, d0 ; CHECK-NEXT: ret %res = call <1 x double> @llvm.round.v1f64(<1 x double> %op) @@ -756,7 +751,6 @@ define void @frintn_v8f32(ptr %a) { define <1 x double> @frintn_v1f64(<1 x double> %op) { ; CHECK-LABEL: frintn_v1f64: ; CHECK: // %bb.0: -; CHECK-NEXT: // kill: def $d0 killed $d0 def $z0 ; CHECK-NEXT: frintn d0, d0 ; CHECK-NEXT: ret %res = call <1 x double> @llvm.roundeven.v1f64(<1 x double> %op) @@ -887,7 +881,6 @@ define void @frintz_v8f32(ptr %a) { define <1 x double> @frintz_v1f64(<1 x double> %op) { ; CHECK-LABEL: frintz_v1f64: ; CHECK: // %bb.0: -; CHECK-NEXT: // kill: def $d0 killed $d0 def $z0 ; CHECK-NEXT: frintz d0, d0 ; CHECK-NEXT: ret %res = call <1 x double> @llvm.trunc.v1f64(<1 x double> %op) diff --git a/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-fp-select.ll b/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-fp-select.ll index 132225546fc4fea3ad248971340a6bda99e15672..7d36925fdc57f3ef71b3eee1af2ad2dca01aed9c 100644 --- a/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-fp-select.ll +++ b/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-fp-select.ll @@ -132,16 +132,7 @@ define <1 x double> @select_v1f64(<1 x double> %op1, <1 x double> %op2, i1 %mask ; CHECK-LABEL: select_v1f64: ; CHECK: // %bb.0: ; CHECK-NEXT: tst w0, #0x1 -; CHECK-NEXT: // kill: def $d1 killed $d1 def $z1 -; CHECK-NEXT: // kill: def $d0 killed $d0 def $z0 -; CHECK-NEXT: csetm x8, ne -; CHECK-NEXT: mvn x9, x8 -; CHECK-NEXT: mov z2.d, x8 -; CHECK-NEXT: mov z3.d, x9 -; CHECK-NEXT: and z0.d, z0.d, z2.d -; CHECK-NEXT: and z1.d, z1.d, z3.d -; CHECK-NEXT: orr z0.d, z0.d, z1.d -; CHECK-NEXT: // kill: def $d0 killed $d0 killed $z0 +; CHECK-NEXT: fcsel d0, d0, d1, ne ; CHECK-NEXT: ret %sel = select i1 %mask, <1 x double> %op1, <1 x double> %op2 ret <1 x double> %sel diff --git a/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-fp-to-int.ll b/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-fp-to-int.ll index 58eae212d7999b78dd5c22fe650fe575da360ca0..bf8a335a8503794455530f56dbb2441feb801cf7 100644 --- a/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-fp-to-int.ll +++ b/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-fp-to-int.ll @@ -464,7 +464,6 @@ define void @fcvtzu_v8f32_v8i64(ptr %a, ptr %b) { define <1 x i16> @fcvtzu_v1f64_v1i16(<1 x double> %op1) { ; CHECK-LABEL: fcvtzu_v1f64_v1i16: ; CHECK: // %bb.0: -; CHECK-NEXT: // kill: def $d0 killed $d0 def $z0 ; CHECK-NEXT: fcvtzs w8, d0 ; CHECK-NEXT: mov z0.h, w8 ; CHECK-NEXT: // kill: def $d0 killed $d0 killed $z0 @@ -1215,7 +1214,6 @@ define void @fcvtzs_v8f32_v8i64(ptr %a, ptr %b) { define <1 x i16> @fcvtzs_v1f64_v1i16(<1 x double> %op1) { ; CHECK-LABEL: fcvtzs_v1f64_v1i16: ; CHECK: // %bb.0: -; CHECK-NEXT: // kill: def $d0 killed $d0 def $z0 ; CHECK-NEXT: fcvtzs w8, d0 ; CHECK-NEXT: mov z0.h, w8 ; CHECK-NEXT: // kill: def $d0 killed $d0 killed $z0 diff --git a/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-fp-vselect.ll b/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-fp-vselect.ll index 4c5a6fe2fd23158f4b9c97366ab0df161c60e211..30a4f04a3d2bd62378a7dba57e6c940dfbfb9529 100644 --- a/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-fp-vselect.ll +++ b/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-fp-vselect.ll @@ -149,16 +149,7 @@ define <1 x double> @select_v1f64(<1 x double> %op1, <1 x double> %op2, <1 x i1> ; CHECK-LABEL: select_v1f64: ; CHECK: // %bb.0: ; CHECK-NEXT: tst w0, #0x1 -; CHECK-NEXT: // kill: def $d1 killed $d1 def $z1 -; CHECK-NEXT: // kill: def $d0 killed $d0 def $z0 -; CHECK-NEXT: csetm x8, ne -; CHECK-NEXT: mvn x9, x8 -; CHECK-NEXT: mov z2.d, x8 -; CHECK-NEXT: mov z3.d, x9 -; CHECK-NEXT: and z0.d, z0.d, z2.d -; CHECK-NEXT: and z1.d, z1.d, z3.d -; CHECK-NEXT: orr z0.d, z0.d, z1.d -; CHECK-NEXT: // kill: def $d0 killed $d0 killed $z0 +; CHECK-NEXT: fcsel d0, d0, d1, ne ; CHECK-NEXT: ret %sel = select <1 x i1> %mask, <1 x double> %op1, <1 x double> %op2 ret <1 x double> %sel diff --git a/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-ld2-alloca.ll b/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-ld2-alloca.ll index 1fc51d50b50ae0c02641ace331d14095d8b3e916..efe9066f2c835fec28d4fd768229858d079d7253 100644 --- a/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-ld2-alloca.ll +++ b/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-ld2-alloca.ll @@ -47,6 +47,7 @@ define void @alloc_v6i8(ptr %st_ptr) nounwind { ; CHECK-NEXT: add x20, sp, #24 ; CHECK-NEXT: bl def ; CHECK-NEXT: ptrue p0.b, vl3 +; CHECK-NEXT: ptrue p1.s, vl2 ; CHECK-NEXT: ld2b { z0.b, z1.b }, p0/z, [x20] ; CHECK-NEXT: ptrue p0.h, vl4 ; CHECK-NEXT: mov z2.b, z1.b[3] @@ -63,9 +64,10 @@ define void @alloc_v6i8(ptr %st_ptr) nounwind { ; CHECK-NEXT: add x8, sp, #12 ; CHECK-NEXT: ldr d0, [sp] ; CHECK-NEXT: st1b { z0.h }, p0, [x8] -; CHECK-NEXT: ldrh w8, [sp, #12] +; CHECK-NEXT: ld1h { z0.s }, p1/z, [x8] ; CHECK-NEXT: strb w9, [x19, #2] ; CHECK-NEXT: ldr x30, [sp, #16] // 8-byte Folded Reload +; CHECK-NEXT: fmov w8, s0 ; CHECK-NEXT: strh w8, [x19] ; CHECK-NEXT: ldp x20, x19, [sp, #32] // 16-byte Folded Reload ; CHECK-NEXT: add sp, sp, #48 diff --git a/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-loads.ll b/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-loads.ll index 688c39b89c0df0ebf09d9a1a985a5025d58a06a9..8ca8e6980913590c12a2a449fa2002dece21dd33 100644 --- a/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-loads.ll +++ b/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-loads.ll @@ -45,14 +45,9 @@ define <32 x i8> @load_v32i8(ptr %a) { define <2 x i16> @load_v2i16(ptr %a) { ; CHECK-LABEL: load_v2i16: ; CHECK: // %bb.0: -; CHECK-NEXT: sub sp, sp, #16 -; CHECK-NEXT: .cfi_def_cfa_offset 16 -; CHECK-NEXT: ldrh w8, [x0, #2] -; CHECK-NEXT: str w8, [sp, #12] -; CHECK-NEXT: ldrh w8, [x0] -; CHECK-NEXT: str w8, [sp, #8] -; CHECK-NEXT: ldr d0, [sp, #8] -; CHECK-NEXT: add sp, sp, #16 +; CHECK-NEXT: ptrue p0.s, vl2 +; CHECK-NEXT: ld1h { z0.s }, p0/z, [x0] +; CHECK-NEXT: // kill: def $d0 killed $d0 killed $z0 ; CHECK-NEXT: ret %load = load <2 x i16>, ptr %a ret <2 x i16> %load diff --git a/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-optimize-ptrue.ll b/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-optimize-ptrue.ll index 6fcb95f2833388babe907ccc0326c3655afc46ab..b5adea594242981f948d1cf14d0accd39bf4df95 100644 --- a/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-optimize-ptrue.ll +++ b/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-optimize-ptrue.ll @@ -70,21 +70,11 @@ define void @add_v32i8(ptr %a, ptr %b) { define void @add_v2i16(ptr %a, ptr %b, ptr %c) { ; CHECK-LABEL: add_v2i16: ; CHECK: // %bb.0: -; CHECK-NEXT: sub sp, sp, #16 -; CHECK-NEXT: .cfi_def_cfa_offset 16 -; CHECK-NEXT: ldrh w8, [x0, #2] ; CHECK-NEXT: ptrue p0.s, vl2 -; CHECK-NEXT: str w8, [sp, #4] -; CHECK-NEXT: ldrh w8, [x0] -; CHECK-NEXT: str w8, [sp] -; CHECK-NEXT: ldrh w8, [x1, #2] -; CHECK-NEXT: str w8, [sp, #12] -; CHECK-NEXT: ldrh w8, [x1] -; CHECK-NEXT: str w8, [sp, #8] -; CHECK-NEXT: ldp d0, d1, [sp] +; CHECK-NEXT: ld1h { z0.s }, p0/z, [x0] +; CHECK-NEXT: ld1h { z1.s }, p0/z, [x1] ; CHECK-NEXT: add z0.s, z0.s, z1.s ; CHECK-NEXT: st1h { z0.s }, p0, [x0] -; CHECK-NEXT: add sp, sp, #16 ; CHECK-NEXT: ret %op1 = load <2 x i16>, ptr %a %op2 = load <2 x i16>, ptr %b diff --git a/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-subvector.ll b/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-subvector.ll index 75bae88fc4798ea78a84fdcbbaec17db72783db6..838db0ce8185cfeb324fd49cf99c17aba38a64f9 100644 --- a/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-subvector.ll +++ b/llvm/test/CodeGen/AArch64/sve-streaming-mode-fixed-length-subvector.ll @@ -77,16 +77,9 @@ bb1: define void @subvector_v2i16(ptr %in, ptr %out) { ; CHECK-LABEL: subvector_v2i16: ; CHECK: // %bb.0: // %bb1 -; CHECK-NEXT: sub sp, sp, #16 -; CHECK-NEXT: .cfi_def_cfa_offset 16 -; CHECK-NEXT: ldrh w8, [x0, #2] ; CHECK-NEXT: ptrue p0.s, vl2 -; CHECK-NEXT: str w8, [sp, #12] -; CHECK-NEXT: ldrh w8, [x0] -; CHECK-NEXT: str w8, [sp, #8] -; CHECK-NEXT: ldr d0, [sp, #8] +; CHECK-NEXT: ld1h { z0.s }, p0/z, [x0] ; CHECK-NEXT: st1h { z0.s }, p0, [x1] -; CHECK-NEXT: add sp, sp, #16 ; CHECK-NEXT: ret %a = load <2 x i16>, ptr %in br label %bb1 diff --git a/llvm/test/CodeGen/AArch64/sve-vl-arith.ll b/llvm/test/CodeGen/AArch64/sve-vl-arith.ll index dd4294c8d3bdcc2dd69d685426316d0c8b79e732..de2af590acd1e26ca21ec58b67b7e9969f24efd9 100644 --- a/llvm/test/CodeGen/AArch64/sve-vl-arith.ll +++ b/llvm/test/CodeGen/AArch64/sve-vl-arith.ll @@ -186,8 +186,8 @@ define i64 @incd_scalar_i64(i64 %a) { define i64 @decb_scalar_i64(i64 %a) { ; NO_SCALAR_INC-LABEL: decb_scalar_i64: ; NO_SCALAR_INC: // %bb.0: -; NO_SCALAR_INC-NEXT: rdvl x8, #-2 -; NO_SCALAR_INC-NEXT: add x0, x0, x8 +; NO_SCALAR_INC-NEXT: cnth x8, all, mul #4 +; NO_SCALAR_INC-NEXT: sub x0, x0, x8 ; NO_SCALAR_INC-NEXT: ret ; ; CHECK-LABEL: decb_scalar_i64: @@ -204,8 +204,7 @@ define i64 @dech_scalar_i64(i64 %a) { ; NO_SCALAR_INC-LABEL: dech_scalar_i64: ; NO_SCALAR_INC: // %bb.0: ; NO_SCALAR_INC-NEXT: cnth x8, all, mul #3 -; NO_SCALAR_INC-NEXT: neg x8, x8 -; NO_SCALAR_INC-NEXT: add x0, x0, x8 +; NO_SCALAR_INC-NEXT: sub x0, x0, x8 ; NO_SCALAR_INC-NEXT: ret ; ; CHECK-LABEL: dech_scalar_i64: @@ -222,8 +221,7 @@ define i64 @decw_scalar_i64(i64 %a) { ; NO_SCALAR_INC-LABEL: decw_scalar_i64: ; NO_SCALAR_INC: // %bb.0: ; NO_SCALAR_INC-NEXT: cntw x8, all, mul #3 -; NO_SCALAR_INC-NEXT: neg x8, x8 -; NO_SCALAR_INC-NEXT: add x0, x0, x8 +; NO_SCALAR_INC-NEXT: sub x0, x0, x8 ; NO_SCALAR_INC-NEXT: ret ; ; CHECK-LABEL: decw_scalar_i64: @@ -240,8 +238,7 @@ define i64 @decd_scalar_i64(i64 %a) { ; NO_SCALAR_INC-LABEL: decd_scalar_i64: ; NO_SCALAR_INC: // %bb.0: ; NO_SCALAR_INC-NEXT: cntd x8, all, mul #3 -; NO_SCALAR_INC-NEXT: neg x8, x8 -; NO_SCALAR_INC-NEXT: add x0, x0, x8 +; NO_SCALAR_INC-NEXT: sub x0, x0, x8 ; NO_SCALAR_INC-NEXT: ret ; ; CHECK-LABEL: decd_scalar_i64: @@ -345,8 +342,8 @@ define i32 @incd_scalar_i32(i32 %a) { define i32 @decb_scalar_i32(i32 %a) { ; NO_SCALAR_INC-LABEL: decb_scalar_i32: ; NO_SCALAR_INC: // %bb.0: -; NO_SCALAR_INC-NEXT: rdvl x8, #-4 -; NO_SCALAR_INC-NEXT: add w0, w0, w8 +; NO_SCALAR_INC-NEXT: cnth x8, all, mul #8 +; NO_SCALAR_INC-NEXT: sub w0, w0, w8 ; NO_SCALAR_INC-NEXT: ret ; ; CHECK-LABEL: decb_scalar_i32: @@ -367,8 +364,7 @@ define i32 @dech_scalar_i32(i32 %a) { ; NO_SCALAR_INC-LABEL: dech_scalar_i32: ; NO_SCALAR_INC: // %bb.0: ; NO_SCALAR_INC-NEXT: cnth x8 -; NO_SCALAR_INC-NEXT: neg x8, x8 -; NO_SCALAR_INC-NEXT: add w0, w0, w8 +; NO_SCALAR_INC-NEXT: sub w0, w0, w8 ; NO_SCALAR_INC-NEXT: ret ; ; CHECK-LABEL: dech_scalar_i32: @@ -389,8 +385,7 @@ define i32 @decw_scalar_i32(i32 %a) { ; NO_SCALAR_INC-LABEL: decw_scalar_i32: ; NO_SCALAR_INC: // %bb.0: ; NO_SCALAR_INC-NEXT: cntw x8 -; NO_SCALAR_INC-NEXT: neg x8, x8 -; NO_SCALAR_INC-NEXT: add w0, w0, w8 +; NO_SCALAR_INC-NEXT: sub w0, w0, w8 ; NO_SCALAR_INC-NEXT: ret ; ; CHECK-LABEL: decw_scalar_i32: @@ -411,8 +406,7 @@ define i32 @decd_scalar_i32(i32 %a) { ; NO_SCALAR_INC-LABEL: decd_scalar_i32: ; NO_SCALAR_INC: // %bb.0: ; NO_SCALAR_INC-NEXT: cntd x8 -; NO_SCALAR_INC-NEXT: neg x8, x8 -; NO_SCALAR_INC-NEXT: add w0, w0, w8 +; NO_SCALAR_INC-NEXT: sub w0, w0, w8 ; NO_SCALAR_INC-NEXT: ret ; ; CHECK-LABEL: decd_scalar_i32: diff --git a/llvm/test/CodeGen/AArch64/vecreduce-add.ll b/llvm/test/CodeGen/AArch64/vecreduce-add.ll index 3254c5ebe9c6b1b5b7a18648909bb0604d89c1c8..ab7cea8dfb778994707c4d52cf5f00213cd288da 100644 --- a/llvm/test/CodeGen/AArch64/vecreduce-add.ll +++ b/llvm/test/CodeGen/AArch64/vecreduce-add.ll @@ -2825,10 +2825,11 @@ entry: define i64 @add_pair_v2i16_v2i64_zext(<2 x i16> %x, <2 x i16> %y) { ; CHECK-SD-LABEL: add_pair_v2i16_v2i64_zext: ; CHECK-SD: // %bb.0: // %entry -; CHECK-SD-NEXT: movi d2, #0x00ffff0000ffff -; CHECK-SD-NEXT: and v0.8b, v0.8b, v2.8b -; CHECK-SD-NEXT: and v1.8b, v1.8b, v2.8b +; CHECK-SD-NEXT: // kill: def $d0 killed $d0 def $q0 +; CHECK-SD-NEXT: // kill: def $d1 killed $d1 def $q1 +; CHECK-SD-NEXT: movi v2.2d, #0x00ffff0000ffff ; CHECK-SD-NEXT: mov v0.d[1], v1.d[0] +; CHECK-SD-NEXT: and v0.16b, v0.16b, v2.16b ; CHECK-SD-NEXT: uaddlv d0, v0.4s ; CHECK-SD-NEXT: fmov x0, d0 ; CHECK-SD-NEXT: ret @@ -3578,10 +3579,11 @@ entry: define i64 @add_pair_v2i8_v2i64_zext(<2 x i8> %x, <2 x i8> %y) { ; CHECK-SD-LABEL: add_pair_v2i8_v2i64_zext: ; CHECK-SD: // %bb.0: // %entry -; CHECK-SD-NEXT: movi d2, #0x0000ff000000ff -; CHECK-SD-NEXT: and v0.8b, v0.8b, v2.8b -; CHECK-SD-NEXT: and v1.8b, v1.8b, v2.8b +; CHECK-SD-NEXT: // kill: def $d0 killed $d0 def $q0 +; CHECK-SD-NEXT: // kill: def $d1 killed $d1 def $q1 +; CHECK-SD-NEXT: movi v2.2d, #0x0000ff000000ff ; CHECK-SD-NEXT: mov v0.d[1], v1.d[0] +; CHECK-SD-NEXT: and v0.16b, v0.16b, v2.16b ; CHECK-SD-NEXT: uaddlv d0, v0.4s ; CHECK-SD-NEXT: fmov x0, d0 ; CHECK-SD-NEXT: ret diff --git a/llvm/test/CodeGen/AArch64/vscale-and-sve-cnt-demandedbits.ll b/llvm/test/CodeGen/AArch64/vscale-and-sve-cnt-demandedbits.ll index dbdab799c83522fb39d41b31dd7e27f8e756b172..9572778484f8d388f222716b04fc097d54362042 100644 --- a/llvm/test/CodeGen/AArch64/vscale-and-sve-cnt-demandedbits.ll +++ b/llvm/test/CodeGen/AArch64/vscale-and-sve-cnt-demandedbits.ll @@ -194,7 +194,7 @@ define i32 @vscale_with_multiplier() vscale_range(1,16) { ; CHECK-LABEL: vscale_with_multiplier: ; CHECK: // %bb.0: ; CHECK-NEXT: rdvl x8, #1 -; CHECK-NEXT: mov w9, #5 +; CHECK-NEXT: mov w9, #5 // =0x5 ; CHECK-NEXT: lsr x8, x8, #4 ; CHECK-NEXT: mul x8, x8, x9 ; CHECK-NEXT: and w9, w8, #0x3f @@ -212,7 +212,7 @@ define i32 @vscale_with_negative_multiplier() vscale_range(1,16) { ; CHECK-LABEL: vscale_with_negative_multiplier: ; CHECK: // %bb.0: ; CHECK-NEXT: rdvl x8, #1 -; CHECK-NEXT: mov x9, #-5 +; CHECK-NEXT: mov x9, #-5 // =0xfffffffffffffffb ; CHECK-NEXT: lsr x8, x8, #4 ; CHECK-NEXT: mul x8, x8, x9 ; CHECK-NEXT: and w9, w8, #0xffffffc0 @@ -230,9 +230,9 @@ define i32 @pow2_vscale_with_negative_multiplier() vscale_range(1,16) { ; CHECK-LABEL: pow2_vscale_with_negative_multiplier: ; CHECK: // %bb.0: ; CHECK-NEXT: cntd x8 -; CHECK-NEXT: neg x8, x8 -; CHECK-NEXT: orr w9, w8, #0xfffffff0 -; CHECK-NEXT: add w0, w8, w9 +; CHECK-NEXT: neg x9, x8 +; CHECK-NEXT: orr w9, w9, #0xfffffff0 +; CHECK-NEXT: sub w0, w9, w8 ; CHECK-NEXT: ret %vscale = call i32 @llvm.vscale.i32() %mul = mul i32 %vscale, -2 diff --git a/llvm/test/CodeGen/AMDGPU/GlobalISel/legalize-trap-gfx11.mir b/llvm/test/CodeGen/AMDGPU/GlobalISel/legalize-trap-gfx11.mir new file mode 100644 index 0000000000000000000000000000000000000000..ac98dca00be3df7154e1e4d49261f1d475313d45 --- /dev/null +++ b/llvm/test/CodeGen/AMDGPU/GlobalISel/legalize-trap-gfx11.mir @@ -0,0 +1,49 @@ +# NOTE: Assertions have been autogenerated by utils/update_mir_test_checks.py UTC_ARGS: --version 2 +# RUN: llc -mtriple=amdgcn--amdhsa -mcpu=gfx1100 -o - -run-pass=legalizer %s | FileCheck -check-prefix=GFX1100 %s +# RUN: llc -mtriple=amdgcn--amdhsa -mcpu=gfx11-generic --amdhsa-code-object-version=6 -o - -run-pass=legalizer %s | FileCheck -check-prefix=GFX1100 %s +# RUN: llc -mtriple=amdgcn--amdhsa -mcpu=gfx1150 -o - -run-pass=legalizer %s | FileCheck -check-prefix=GFX1150 %s + +--- +name: test_trap +body: | + bb.0: + ; GFX1100-LABEL: name: test_trap + ; GFX1100: successors: %bb.2(0x80000000) + ; GFX1100-NEXT: {{ $}} + ; GFX1100-NEXT: [[C:%[0-9]+]]:_(s32) = G_CONSTANT i32 0 + ; GFX1100-NEXT: [[C1:%[0-9]+]]:_(p1) = G_CONSTANT i64 0 + ; GFX1100-NEXT: G_STORE [[C]](s32), [[C1]](p1) :: (store (s8), addrspace 1) + ; GFX1100-NEXT: S_TRAP 2 + ; GFX1100-NEXT: [[S_SENDMSG_RTN_B32_:%[0-9]+]]:sreg_32 = S_SENDMSG_RTN_B32 128 + ; GFX1100-NEXT: $ttmp2 = S_MOV_B32 $m0 + ; GFX1100-NEXT: [[S_AND_B32_:%[0-9]+]]:sreg_32 = S_AND_B32 [[S_SENDMSG_RTN_B32_]], 1023, implicit-def $scc + ; GFX1100-NEXT: [[S_OR_B32_:%[0-9]+]]:sreg_32 = S_OR_B32 [[S_AND_B32_]], 1024, implicit-def $scc + ; GFX1100-NEXT: $m0 = S_MOV_B32 [[S_OR_B32_]] + ; GFX1100-NEXT: S_SENDMSG 1, implicit $exec, implicit $m0 + ; GFX1100-NEXT: $m0 = S_MOV_B32 $ttmp2 + ; GFX1100-NEXT: S_BRANCH %bb.2 + ; GFX1100-NEXT: {{ $}} + ; GFX1100-NEXT: .1: + ; GFX1100-NEXT: successors: + ; GFX1100-NEXT: {{ $}} + ; GFX1100-NEXT: G_STORE [[C]](s32), [[C1]](p1) :: (store (s8), addrspace 1) + ; GFX1100-NEXT: {{ $}} + ; GFX1100-NEXT: .2: + ; GFX1100-NEXT: successors: %bb.2(0x80000000) + ; GFX1100-NEXT: {{ $}} + ; GFX1100-NEXT: S_SETHALT 5 + ; GFX1100-NEXT: S_BRANCH %bb.2 + ; + ; GFX1150-LABEL: name: test_trap + ; GFX1150: [[C:%[0-9]+]]:_(s32) = G_CONSTANT i32 0 + ; GFX1150-NEXT: [[C1:%[0-9]+]]:_(p1) = G_CONSTANT i64 0 + ; GFX1150-NEXT: G_STORE [[C]](s32), [[C1]](p1) :: (store (s8), addrspace 1) + ; GFX1150-NEXT: S_TRAP 2 + ; GFX1150-NEXT: G_STORE [[C]](s32), [[C1]](p1) :: (store (s8), addrspace 1) + %0:_(s8) = G_CONSTANT i8 0 + %1:_(p1) = G_CONSTANT i64 0 + G_STORE %0, %1 :: (store 1, addrspace 1) + G_TRAP + G_STORE %0, %1 :: (store 1, addrspace 1) + +... diff --git a/llvm/test/CodeGen/AMDGPU/GlobalISel/mmra.ll b/llvm/test/CodeGen/AMDGPU/GlobalISel/mmra.ll new file mode 100644 index 0000000000000000000000000000000000000000..71a2d3e8a5304f70c7b3d0c2bd41fa2490b954a6 --- /dev/null +++ b/llvm/test/CodeGen/AMDGPU/GlobalISel/mmra.ll @@ -0,0 +1,34 @@ +; NOTE: Assertions have been autogenerated by utils/update_mir_test_checks.py UTC_ARGS: --version 2 +; RUN: llc -global-isel -march=amdgcn -mcpu=gfx900 -stop-after=finalize-isel < %s | FileCheck %s + +declare void @readsMem(ptr) #0 +declare void @writesMem(ptr) #1 + +define void @fence_loads(ptr %ptr) { + ; CHECK-LABEL: name: fence_loads + ; CHECK: bb.1 (%ir-block.0): + ; CHECK-NEXT: liveins: $vgpr0, $vgpr1 + ; CHECK-NEXT: {{ $}} + ; CHECK-NEXT: [[COPY:%[0-9]+]]:vgpr_32 = COPY $vgpr0 + ; CHECK-NEXT: [[COPY1:%[0-9]+]]:vgpr_32 = COPY $vgpr1 + ; CHECK-NEXT: [[REG_SEQUENCE:%[0-9]+]]:vreg_64 = REG_SEQUENCE [[COPY]], %subreg.sub0, [[COPY1]], %subreg.sub1 + ; CHECK-NEXT: ATOMIC_FENCE 5, 1, mmra !0 + ; CHECK-NEXT: [[FLAT_LOAD_UBYTE:%[0-9]+]]:vgpr_32 = FLAT_LOAD_UBYTE [[REG_SEQUENCE]], 0, 0, implicit $exec, implicit $flat_scr, mmra !1 :: (load acquire (s8) from %ir.ptr, align 4) + ; CHECK-NEXT: [[S_MOV_B32_:%[0-9]+]]:sreg_32 = S_MOV_B32 1 + ; CHECK-NEXT: [[COPY2:%[0-9]+]]:vgpr_32 = COPY [[S_MOV_B32_]] + ; CHECK-NEXT: FLAT_STORE_BYTE [[REG_SEQUENCE]], [[COPY2]], 0, 0, implicit $exec, implicit $flat_scr, mmra !2 :: (store release (s8) into %ir.ptr, align 4) + ; CHECK-NEXT: SI_RETURN + fence release, !mmra !0 + %ld = load atomic i8, ptr %ptr acquire, align 4, !mmra !2 + store atomic i8 1, ptr %ptr release, align 4, !mmra !1 + ret void +} + +; TODO: test atomicrmw, cmpxchg - current lowering doesn't work and blows up on i1 PHIs. + +attributes #0 = { memory(read) } +attributes #1 = { memory(write) } + +!0 = !{!"foo", !"bar"} +!1 = !{!"bux", !"baz"} +!2 = !{!0, !1} diff --git a/llvm/test/CodeGen/AMDGPU/atomic_load_local.ll b/llvm/test/CodeGen/AMDGPU/atomic_load_local.ll index bfd18f1b52a51b67ad94c31213e5b2c807b6ef34..a3b6c283512f3ef5c14f808ee20dd1fd8e56e828 100644 --- a/llvm/test/CodeGen/AMDGPU/atomic_load_local.ll +++ b/llvm/test/CodeGen/AMDGPU/atomic_load_local.ll @@ -152,3 +152,57 @@ define ptr addrspace(3) @atomic_load_monotonic_p3i8_offset(ptr addrspace(3) %ptr %load = load atomic ptr addrspace(3), ptr addrspace(3) %gep monotonic, align 4 ret ptr addrspace(3) %load } + +; GCN-LABEL: {{^}}atomic_load_monotonic_f16: +; GCN: s_waitcnt +; GFX9-NOT: s_mov_b32 m0 +; CI-NEXT: s_mov_b32 m0 +; GCN-NEXT: ds_read_u16 v0, v0{{$}} +; GCN-NEXT: s_waitcnt lgkmcnt(0) +; GCN-NEXT: s_setpc_b64 +define i16 @atomic_load_monotonic_f16(ptr addrspace(3) %ptr) { + %load = load atomic half, ptr addrspace(3) %ptr monotonic, align 2 + %ret = bitcast half %load to i16 + ret i16 %ret +} + +; GCN-LABEL: {{^}}atomic_load_monotonic_f16_offset: +; GCN: s_waitcnt +; GFX9-NOT: s_mov_b32 m0 +; CI-NEXT: s_mov_b32 m0 +; GCN-NEXT: ds_read_u16 v0, v0 offset:32{{$}} +; GCN-NEXT: s_waitcnt lgkmcnt(0) +; GCN-NEXT: s_setpc_b64 +define i16 @atomic_load_monotonic_f16_offset(ptr addrspace(3) %ptr) { + %gep = getelementptr inbounds half, ptr addrspace(3) %ptr, i32 16 + %load = load atomic half, ptr addrspace(3) %gep monotonic, align 2 + %ret = bitcast half %load to i16 + ret i16 %ret +} + +; GCN-LABEL: {{^}}atomic_load_monotonic_bf16: +; GCN: s_waitcnt +; GFX9-NOT: s_mov_b32 m0 +; CI-NEXT: s_mov_b32 m0 +; GCN-NEXT: ds_read_u16 v0, v0{{$}} +; GCN-NEXT: s_waitcnt lgkmcnt(0) +; GCN-NEXT: s_setpc_b64 +define i16 @atomic_load_monotonic_bf16(ptr addrspace(3) %ptr) { + %load = load atomic bfloat, ptr addrspace(3) %ptr monotonic, align 2 + %ret = bitcast bfloat %load to i16 + ret i16 %ret +} + +; GCN-LABEL: {{^}}atomic_load_monotonic_bf16_offset: +; GCN: s_waitcnt +; GFX9-NOT: s_mov_b32 m0 +; CI-NEXT: s_mov_b32 m0 +; GCN-NEXT: ds_read_u16 v0, v0 offset:32{{$}} +; GCN-NEXT: s_waitcnt lgkmcnt(0) +; GCN-NEXT: s_setpc_b64 +define i16 @atomic_load_monotonic_bf16_offset(ptr addrspace(3) %ptr) { + %gep = getelementptr inbounds bfloat, ptr addrspace(3) %ptr, i32 16 + %load = load atomic bfloat, ptr addrspace(3) %gep monotonic, align 2 + %ret = bitcast bfloat %load to i16 + ret i16 %ret +} diff --git a/llvm/test/CodeGen/AMDGPU/atomic_store_local.ll b/llvm/test/CodeGen/AMDGPU/atomic_store_local.ll index 71e24c1692c7f4705de14c055e806a631b9f23cc..cd1e1fb1add473f821188c17319bfbad18df9798 100644 --- a/llvm/test/CodeGen/AMDGPU/atomic_store_local.ll +++ b/llvm/test/CodeGen/AMDGPU/atomic_store_local.ll @@ -101,3 +101,56 @@ define void @atomic_store_monotonic_offset_i64(ptr addrspace(3) %ptr, i64 %val) ret void } +; GCN-LABEL: {{^}}atomic_store_monotonic_f16: +; GCN: s_waitcnt +; GFX9-NOT: s_mov_b32 m0 +; CI-NEXT: s_mov_b32 m0 +; GCN-NEXT: ds_write_b16 v0, v1{{$}} +; GCN-NEXT: s_waitcnt lgkmcnt(0) +; GCN-NEXT: s_setpc_b64 +define void @atomic_store_monotonic_f16(ptr addrspace(3) %ptr, i16 %arg.val) { + %val = bitcast i16 %arg.val to half + store atomic half %val, ptr addrspace(3) %ptr monotonic, align 2 + ret void +} + +; GCN-LABEL: {{^}}atomic_store_monotonic_offset_f16: +; GCN: s_waitcnt +; GFX9-NOT: s_mov_b32 m0 +; CI-NEXT: s_mov_b32 m0 +; GCN-NEXT: ds_write_b16 v0, v1 offset:32{{$}} +; GCN-NEXT: s_waitcnt lgkmcnt(0) +; GCN-NEXT: s_setpc_b64 +define void @atomic_store_monotonic_offset_f16(ptr addrspace(3) %ptr, i16 %arg.val) { + %val = bitcast i16 %arg.val to half + %gep = getelementptr inbounds half, ptr addrspace(3) %ptr, i32 16 + store atomic half %val, ptr addrspace(3) %gep monotonic, align 2 + ret void +} + +; GCN-LABEL: {{^}}atomic_store_monotonic_bf16: +; GCN: s_waitcnt +; GFX9-NOT: s_mov_b32 m0 +; CI-NEXT: s_mov_b32 m0 +; GCN-NEXT: ds_write_b16 v0, v1{{$}} +; GCN-NEXT: s_waitcnt lgkmcnt(0) +; GCN-NEXT: s_setpc_b64 +define void @atomic_store_monotonic_bf16(ptr addrspace(3) %ptr, i16 %arg.val) { + %val = bitcast i16 %arg.val to bfloat + store atomic bfloat %val, ptr addrspace(3) %ptr monotonic, align 2 + ret void +} + +; GCN-LABEL: {{^}}atomic_store_monotonic_offset_bf16: +; GCN: s_waitcnt +; GFX9-NOT: s_mov_b32 m0 +; CI-NEXT: s_mov_b32 m0 +; GCN-NEXT: ds_write_b16 v0, v1 offset:32{{$}} +; GCN-NEXT: s_waitcnt lgkmcnt(0) +; GCN-NEXT: s_setpc_b64 +define void @atomic_store_monotonic_offset_bf16(ptr addrspace(3) %ptr, i16 %arg.val) { + %val = bitcast i16 %arg.val to bfloat + %gep = getelementptr inbounds bfloat, ptr addrspace(3) %ptr, i32 16 + store atomic bfloat %val, ptr addrspace(3) %gep monotonic, align 2 + ret void +} diff --git a/llvm/test/CodeGen/AMDGPU/flat_atomics.ll b/llvm/test/CodeGen/AMDGPU/flat_atomics.ll index 06ba60518adc044b4b33d84302cb881bf1785236..e44572985e6d2e09a206afe3d69ad071f01e9c7f 100644 --- a/llvm/test/CodeGen/AMDGPU/flat_atomics.ll +++ b/llvm/test/CodeGen/AMDGPU/flat_atomics.ll @@ -6741,6 +6741,81 @@ entry: ret void } +define amdgpu_kernel void @atomic_store_bf16_offset(bfloat %in, ptr %out) { +; GCN1-LABEL: atomic_store_bf16_offset: +; GCN1: ; %bb.0: +; GCN1-NEXT: s_load_dwordx2 s[2:3], s[0:1], 0xb +; GCN1-NEXT: s_load_dword s0, s[0:1], 0x9 +; GCN1-NEXT: s_waitcnt lgkmcnt(0) +; GCN1-NEXT: v_mov_b32_e32 v0, s2 +; GCN1-NEXT: v_mov_b32_e32 v1, s3 +; GCN1-NEXT: v_mov_b32_e32 v2, s0 +; GCN1-NEXT: flat_store_short v[0:1], v2 +; GCN1-NEXT: s_endpgm +; +; GCN2-LABEL: atomic_store_bf16_offset: +; GCN2: ; %bb.0: +; GCN2-NEXT: s_load_dwordx2 s[2:3], s[0:1], 0x2c +; GCN2-NEXT: s_load_dword s0, s[0:1], 0x24 +; GCN2-NEXT: s_waitcnt lgkmcnt(0) +; GCN2-NEXT: v_mov_b32_e32 v0, s2 +; GCN2-NEXT: v_mov_b32_e32 v1, s3 +; GCN2-NEXT: v_mov_b32_e32 v2, s0 +; GCN2-NEXT: flat_store_short v[0:1], v2 +; GCN2-NEXT: s_endpgm +; +; GCN3-LABEL: atomic_store_bf16_offset: +; GCN3: ; %bb.0: +; GCN3-NEXT: s_load_dwordx2 s[2:3], s[0:1], 0x2c +; GCN3-NEXT: s_load_dword s4, s[0:1], 0x24 +; GCN3-NEXT: s_waitcnt lgkmcnt(0) +; GCN3-NEXT: v_mov_b32_e32 v0, s2 +; GCN3-NEXT: v_mov_b32_e32 v1, s3 +; GCN3-NEXT: v_mov_b32_e32 v2, s4 +; GCN3-NEXT: flat_store_short v[0:1], v2 +; GCN3-NEXT: s_endpgm + %gep = getelementptr bfloat, ptr %out, i64 8 + store atomic bfloat %in, ptr %out seq_cst, align 2 + ret void +} + +define amdgpu_kernel void @atomic_store_bf16(bfloat %in, ptr %out) { +; GCN1-LABEL: atomic_store_bf16: +; GCN1: ; %bb.0: +; GCN1-NEXT: s_load_dwordx2 s[2:3], s[0:1], 0xb +; GCN1-NEXT: s_load_dword s0, s[0:1], 0x9 +; GCN1-NEXT: s_waitcnt lgkmcnt(0) +; GCN1-NEXT: v_mov_b32_e32 v0, s2 +; GCN1-NEXT: v_mov_b32_e32 v1, s3 +; GCN1-NEXT: v_mov_b32_e32 v2, s0 +; GCN1-NEXT: flat_store_short v[0:1], v2 +; GCN1-NEXT: s_endpgm +; +; GCN2-LABEL: atomic_store_bf16: +; GCN2: ; %bb.0: +; GCN2-NEXT: s_load_dwordx2 s[2:3], s[0:1], 0x2c +; GCN2-NEXT: s_load_dword s0, s[0:1], 0x24 +; GCN2-NEXT: s_waitcnt lgkmcnt(0) +; GCN2-NEXT: v_mov_b32_e32 v0, s2 +; GCN2-NEXT: v_mov_b32_e32 v1, s3 +; GCN2-NEXT: v_mov_b32_e32 v2, s0 +; GCN2-NEXT: flat_store_short v[0:1], v2 +; GCN2-NEXT: s_endpgm +; +; GCN3-LABEL: atomic_store_bf16: +; GCN3: ; %bb.0: +; GCN3-NEXT: s_load_dwordx2 s[2:3], s[0:1], 0x2c +; GCN3-NEXT: s_load_dword s4, s[0:1], 0x24 +; GCN3-NEXT: s_waitcnt lgkmcnt(0) +; GCN3-NEXT: v_mov_b32_e32 v0, s2 +; GCN3-NEXT: v_mov_b32_e32 v1, s3 +; GCN3-NEXT: v_mov_b32_e32 v2, s4 +; GCN3-NEXT: flat_store_short v[0:1], v2 +; GCN3-NEXT: s_endpgm + store atomic bfloat %in, ptr %out seq_cst, align 2 + ret void +} + define amdgpu_kernel void @atomic_inc_i32_offset(ptr %out, i32 %in) { ; GCN1-LABEL: atomic_inc_i32_offset: ; GCN1: ; %bb.0: ; %entry @@ -7868,3 +7943,201 @@ entry: store i32 %val, ptr %out2 ret void } + +define amdgpu_kernel void @atomic_load_f16_offset(ptr %in, ptr %out) { +; GCN1-LABEL: atomic_load_f16_offset: +; GCN1: ; %bb.0: +; GCN1-NEXT: s_load_dwordx4 s[0:3], s[0:1], 0x9 +; GCN1-NEXT: s_waitcnt lgkmcnt(0) +; GCN1-NEXT: s_add_u32 s0, s0, 16 +; GCN1-NEXT: s_addc_u32 s1, s1, 0 +; GCN1-NEXT: v_mov_b32_e32 v0, s0 +; GCN1-NEXT: v_mov_b32_e32 v1, s1 +; GCN1-NEXT: flat_load_ushort v2, v[0:1] glc +; GCN1-NEXT: s_waitcnt vmcnt(0) lgkmcnt(0) +; GCN1-NEXT: buffer_wbinvl1_vol +; GCN1-NEXT: v_mov_b32_e32 v0, s2 +; GCN1-NEXT: v_mov_b32_e32 v1, s3 +; GCN1-NEXT: flat_store_short v[0:1], v2 +; GCN1-NEXT: s_endpgm +; +; GCN2-LABEL: atomic_load_f16_offset: +; GCN2: ; %bb.0: +; GCN2-NEXT: s_load_dwordx4 s[0:3], s[0:1], 0x24 +; GCN2-NEXT: s_waitcnt lgkmcnt(0) +; GCN2-NEXT: s_add_u32 s0, s0, 16 +; GCN2-NEXT: s_addc_u32 s1, s1, 0 +; GCN2-NEXT: v_mov_b32_e32 v0, s0 +; GCN2-NEXT: v_mov_b32_e32 v1, s1 +; GCN2-NEXT: flat_load_ushort v2, v[0:1] glc +; GCN2-NEXT: s_waitcnt vmcnt(0) lgkmcnt(0) +; GCN2-NEXT: buffer_wbinvl1_vol +; GCN2-NEXT: v_mov_b32_e32 v0, s2 +; GCN2-NEXT: v_mov_b32_e32 v1, s3 +; GCN2-NEXT: flat_store_short v[0:1], v2 +; GCN2-NEXT: s_endpgm +; +; GCN3-LABEL: atomic_load_f16_offset: +; GCN3: ; %bb.0: +; GCN3-NEXT: s_load_dwordx4 s[0:3], s[0:1], 0x24 +; GCN3-NEXT: s_waitcnt lgkmcnt(0) +; GCN3-NEXT: v_mov_b32_e32 v0, s0 +; GCN3-NEXT: v_mov_b32_e32 v1, s1 +; GCN3-NEXT: flat_load_ushort v2, v[0:1] offset:16 glc +; GCN3-NEXT: s_waitcnt vmcnt(0) lgkmcnt(0) +; GCN3-NEXT: buffer_wbinvl1_vol +; GCN3-NEXT: v_mov_b32_e32 v0, s2 +; GCN3-NEXT: v_mov_b32_e32 v1, s3 +; GCN3-NEXT: flat_store_short v[0:1], v2 +; GCN3-NEXT: s_endpgm + %gep = getelementptr half, ptr %in, i64 8 + %val = load atomic half, ptr %gep seq_cst, align 2 + store half %val, ptr %out + ret void +} + +define amdgpu_kernel void @atomic_load_f16(ptr %in, ptr %out) { +; GCN1-LABEL: atomic_load_f16: +; GCN1: ; %bb.0: +; GCN1-NEXT: s_load_dwordx4 s[0:3], s[0:1], 0x9 +; GCN1-NEXT: s_waitcnt lgkmcnt(0) +; GCN1-NEXT: v_mov_b32_e32 v0, s0 +; GCN1-NEXT: v_mov_b32_e32 v1, s1 +; GCN1-NEXT: flat_load_ushort v2, v[0:1] glc +; GCN1-NEXT: s_waitcnt vmcnt(0) lgkmcnt(0) +; GCN1-NEXT: buffer_wbinvl1_vol +; GCN1-NEXT: v_mov_b32_e32 v0, s2 +; GCN1-NEXT: v_mov_b32_e32 v1, s3 +; GCN1-NEXT: flat_store_short v[0:1], v2 +; GCN1-NEXT: s_endpgm +; +; GCN2-LABEL: atomic_load_f16: +; GCN2: ; %bb.0: +; GCN2-NEXT: s_load_dwordx4 s[0:3], s[0:1], 0x24 +; GCN2-NEXT: s_waitcnt lgkmcnt(0) +; GCN2-NEXT: v_mov_b32_e32 v0, s0 +; GCN2-NEXT: v_mov_b32_e32 v1, s1 +; GCN2-NEXT: flat_load_ushort v2, v[0:1] glc +; GCN2-NEXT: s_waitcnt vmcnt(0) lgkmcnt(0) +; GCN2-NEXT: buffer_wbinvl1_vol +; GCN2-NEXT: v_mov_b32_e32 v0, s2 +; GCN2-NEXT: v_mov_b32_e32 v1, s3 +; GCN2-NEXT: flat_store_short v[0:1], v2 +; GCN2-NEXT: s_endpgm +; +; GCN3-LABEL: atomic_load_f16: +; GCN3: ; %bb.0: +; GCN3-NEXT: s_load_dwordx4 s[0:3], s[0:1], 0x24 +; GCN3-NEXT: s_waitcnt lgkmcnt(0) +; GCN3-NEXT: v_mov_b32_e32 v0, s0 +; GCN3-NEXT: v_mov_b32_e32 v1, s1 +; GCN3-NEXT: flat_load_ushort v2, v[0:1] glc +; GCN3-NEXT: s_waitcnt vmcnt(0) lgkmcnt(0) +; GCN3-NEXT: buffer_wbinvl1_vol +; GCN3-NEXT: v_mov_b32_e32 v0, s2 +; GCN3-NEXT: v_mov_b32_e32 v1, s3 +; GCN3-NEXT: flat_store_short v[0:1], v2 +; GCN3-NEXT: s_endpgm + %val = load atomic half, ptr %in seq_cst, align 2 + store half %val, ptr %out + ret void +} + +define amdgpu_kernel void @atomic_load_bf16_offset(ptr %in, ptr %out) { +; GCN1-LABEL: atomic_load_bf16_offset: +; GCN1: ; %bb.0: +; GCN1-NEXT: s_load_dwordx4 s[0:3], s[0:1], 0x9 +; GCN1-NEXT: s_waitcnt lgkmcnt(0) +; GCN1-NEXT: s_add_u32 s0, s0, 16 +; GCN1-NEXT: s_addc_u32 s1, s1, 0 +; GCN1-NEXT: v_mov_b32_e32 v0, s0 +; GCN1-NEXT: v_mov_b32_e32 v1, s1 +; GCN1-NEXT: flat_load_ushort v2, v[0:1] glc +; GCN1-NEXT: s_waitcnt vmcnt(0) lgkmcnt(0) +; GCN1-NEXT: buffer_wbinvl1_vol +; GCN1-NEXT: v_mov_b32_e32 v0, s2 +; GCN1-NEXT: v_mov_b32_e32 v1, s3 +; GCN1-NEXT: flat_store_short v[0:1], v2 +; GCN1-NEXT: s_endpgm +; +; GCN2-LABEL: atomic_load_bf16_offset: +; GCN2: ; %bb.0: +; GCN2-NEXT: s_load_dwordx4 s[0:3], s[0:1], 0x24 +; GCN2-NEXT: s_waitcnt lgkmcnt(0) +; GCN2-NEXT: s_add_u32 s0, s0, 16 +; GCN2-NEXT: s_addc_u32 s1, s1, 0 +; GCN2-NEXT: v_mov_b32_e32 v0, s0 +; GCN2-NEXT: v_mov_b32_e32 v1, s1 +; GCN2-NEXT: flat_load_ushort v2, v[0:1] glc +; GCN2-NEXT: s_waitcnt vmcnt(0) lgkmcnt(0) +; GCN2-NEXT: buffer_wbinvl1_vol +; GCN2-NEXT: v_mov_b32_e32 v0, s2 +; GCN2-NEXT: v_mov_b32_e32 v1, s3 +; GCN2-NEXT: flat_store_short v[0:1], v2 +; GCN2-NEXT: s_endpgm +; +; GCN3-LABEL: atomic_load_bf16_offset: +; GCN3: ; %bb.0: +; GCN3-NEXT: s_load_dwordx4 s[0:3], s[0:1], 0x24 +; GCN3-NEXT: s_waitcnt lgkmcnt(0) +; GCN3-NEXT: v_mov_b32_e32 v0, s0 +; GCN3-NEXT: v_mov_b32_e32 v1, s1 +; GCN3-NEXT: flat_load_ushort v2, v[0:1] offset:16 glc +; GCN3-NEXT: s_waitcnt vmcnt(0) lgkmcnt(0) +; GCN3-NEXT: buffer_wbinvl1_vol +; GCN3-NEXT: v_mov_b32_e32 v0, s2 +; GCN3-NEXT: v_mov_b32_e32 v1, s3 +; GCN3-NEXT: flat_store_short v[0:1], v2 +; GCN3-NEXT: s_endpgm + %gep = getelementptr bfloat, ptr %in, i64 8 + %val = load atomic bfloat, ptr %gep seq_cst, align 2 + store bfloat %val, ptr %out + ret void +} + +define amdgpu_kernel void @atomic_load_bf16(ptr %in, ptr %out) { +; GCN1-LABEL: atomic_load_bf16: +; GCN1: ; %bb.0: +; GCN1-NEXT: s_load_dwordx4 s[0:3], s[0:1], 0x9 +; GCN1-NEXT: s_waitcnt lgkmcnt(0) +; GCN1-NEXT: v_mov_b32_e32 v0, s0 +; GCN1-NEXT: v_mov_b32_e32 v1, s1 +; GCN1-NEXT: flat_load_ushort v2, v[0:1] glc +; GCN1-NEXT: s_waitcnt vmcnt(0) lgkmcnt(0) +; GCN1-NEXT: buffer_wbinvl1_vol +; GCN1-NEXT: v_mov_b32_e32 v0, s2 +; GCN1-NEXT: v_mov_b32_e32 v1, s3 +; GCN1-NEXT: flat_store_short v[0:1], v2 +; GCN1-NEXT: s_endpgm +; +; GCN2-LABEL: atomic_load_bf16: +; GCN2: ; %bb.0: +; GCN2-NEXT: s_load_dwordx4 s[0:3], s[0:1], 0x24 +; GCN2-NEXT: s_waitcnt lgkmcnt(0) +; GCN2-NEXT: v_mov_b32_e32 v0, s0 +; GCN2-NEXT: v_mov_b32_e32 v1, s1 +; GCN2-NEXT: flat_load_ushort v2, v[0:1] glc +; GCN2-NEXT: s_waitcnt vmcnt(0) lgkmcnt(0) +; GCN2-NEXT: buffer_wbinvl1_vol +; GCN2-NEXT: v_mov_b32_e32 v0, s2 +; GCN2-NEXT: v_mov_b32_e32 v1, s3 +; GCN2-NEXT: flat_store_short v[0:1], v2 +; GCN2-NEXT: s_endpgm +; +; GCN3-LABEL: atomic_load_bf16: +; GCN3: ; %bb.0: +; GCN3-NEXT: s_load_dwordx4 s[0:3], s[0:1], 0x24 +; GCN3-NEXT: s_waitcnt lgkmcnt(0) +; GCN3-NEXT: v_mov_b32_e32 v0, s0 +; GCN3-NEXT: v_mov_b32_e32 v1, s1 +; GCN3-NEXT: flat_load_ushort v2, v[0:1] glc +; GCN3-NEXT: s_waitcnt vmcnt(0) lgkmcnt(0) +; GCN3-NEXT: buffer_wbinvl1_vol +; GCN3-NEXT: v_mov_b32_e32 v0, s2 +; GCN3-NEXT: v_mov_b32_e32 v1, s3 +; GCN3-NEXT: flat_store_short v[0:1], v2 +; GCN3-NEXT: s_endpgm + %val = load atomic bfloat, ptr %in seq_cst, align 2 + store bfloat %val, ptr %out + ret void +} diff --git a/llvm/test/CodeGen/AMDGPU/flat_atomics_i64.ll b/llvm/test/CodeGen/AMDGPU/flat_atomics_i64.ll index 4d36fb3143510b6f5d251c5ea8fe089fa9850040..b8c8d993d389bdc9747348595f666ba4e21e8c4f 100644 --- a/llvm/test/CodeGen/AMDGPU/flat_atomics_i64.ll +++ b/llvm/test/CodeGen/AMDGPU/flat_atomics_i64.ll @@ -3641,7 +3641,7 @@ define amdgpu_kernel void @atomic_xchg_f64_offset(ptr %out, double %in) { ; GFX12-NEXT: v_dual_mov_b32 v2, s2 :: v_dual_mov_b32 v3, s3 ; GFX12-NEXT: flat_atomic_swap_b64 v[0:1], v[2:3] offset:32 ; GFX12-NEXT: s_wait_storecnt_dscnt 0x0 -; GFX12-NEXT: global_inv scope:SCOPE_SYS +; GFX12-NEXT: global_inv scope:SCOPE_DEV ; GFX12-NEXT: s_endpgm entry: %gep = getelementptr double, ptr %out, i64 4 @@ -3688,7 +3688,7 @@ define amdgpu_kernel void @atomic_xchg_pointer_offset(ptr %out, ptr %in) { ; GFX12-NEXT: v_dual_mov_b32 v2, s2 :: v_dual_mov_b32 v3, s3 ; GFX12-NEXT: flat_atomic_swap_b64 v[0:1], v[2:3] offset:32 ; GFX12-NEXT: s_wait_storecnt_dscnt 0x0 -; GFX12-NEXT: global_inv scope:SCOPE_SYS +; GFX12-NEXT: global_inv scope:SCOPE_DEV ; GFX12-NEXT: s_endpgm entry: %gep = getelementptr ptr, ptr %out, i32 4 diff --git a/llvm/test/CodeGen/AMDGPU/global_atomics.ll b/llvm/test/CodeGen/AMDGPU/global_atomics.ll index 674d7a3c5c9b4433ff5e69c562872cff33d152c9..dac3a3db7b450b44501bcb98030dbe9dd86529ac 100644 --- a/llvm/test/CodeGen/AMDGPU/global_atomics.ll +++ b/llvm/test/CodeGen/AMDGPU/global_atomics.ll @@ -6216,6 +6216,81 @@ entry: ret void } +define amdgpu_kernel void @atomic_store_bf16_offset(bfloat %in, ptr addrspace(1) %out) { +; SI-LABEL: atomic_store_bf16_offset: +; SI: ; %bb.0: +; SI-NEXT: s_load_dword s4, s[0:1], 0x9 +; SI-NEXT: s_load_dwordx2 s[0:1], s[0:1], 0xb +; SI-NEXT: s_mov_b32 s3, 0xf000 +; SI-NEXT: s_mov_b32 s2, -1 +; SI-NEXT: s_waitcnt lgkmcnt(0) +; SI-NEXT: v_mov_b32_e32 v0, s4 +; SI-NEXT: buffer_store_short v0, off, s[0:3], 0 offset:16 +; SI-NEXT: s_endpgm +; +; VI-LABEL: atomic_store_bf16_offset: +; VI: ; %bb.0: +; VI-NEXT: s_load_dwordx2 s[2:3], s[0:1], 0x2c +; VI-NEXT: s_load_dword s4, s[0:1], 0x24 +; VI-NEXT: s_waitcnt lgkmcnt(0) +; VI-NEXT: s_add_u32 s0, s2, 16 +; VI-NEXT: s_addc_u32 s1, s3, 0 +; VI-NEXT: v_mov_b32_e32 v0, s0 +; VI-NEXT: v_mov_b32_e32 v1, s1 +; VI-NEXT: v_mov_b32_e32 v2, s4 +; VI-NEXT: flat_store_short v[0:1], v2 +; VI-NEXT: s_endpgm +; +; GFX9-LABEL: atomic_store_bf16_offset: +; GFX9: ; %bb.0: +; GFX9-NEXT: s_load_dword s4, s[0:1], 0x24 +; GFX9-NEXT: s_load_dwordx2 s[2:3], s[0:1], 0x2c +; GFX9-NEXT: v_mov_b32_e32 v0, 0 +; GFX9-NEXT: s_waitcnt lgkmcnt(0) +; GFX9-NEXT: v_mov_b32_e32 v1, s4 +; GFX9-NEXT: global_store_short v0, v1, s[2:3] offset:16 +; GFX9-NEXT: s_endpgm + %gep = getelementptr bfloat, ptr addrspace(1) %out, i64 8 + store atomic bfloat %in, ptr addrspace(1) %gep seq_cst, align 2 + ret void +} + +define amdgpu_kernel void @atomic_store_bf16(bfloat %in, ptr addrspace(1) %out) { +; SI-LABEL: atomic_store_bf16: +; SI: ; %bb.0: +; SI-NEXT: s_load_dword s4, s[0:1], 0x9 +; SI-NEXT: s_load_dwordx2 s[0:1], s[0:1], 0xb +; SI-NEXT: s_mov_b32 s3, 0xf000 +; SI-NEXT: s_mov_b32 s2, -1 +; SI-NEXT: s_waitcnt lgkmcnt(0) +; SI-NEXT: v_mov_b32_e32 v0, s4 +; SI-NEXT: buffer_store_short v0, off, s[0:3], 0 +; SI-NEXT: s_endpgm +; +; VI-LABEL: atomic_store_bf16: +; VI: ; %bb.0: +; VI-NEXT: s_load_dwordx2 s[2:3], s[0:1], 0x2c +; VI-NEXT: s_load_dword s0, s[0:1], 0x24 +; VI-NEXT: s_waitcnt lgkmcnt(0) +; VI-NEXT: v_mov_b32_e32 v0, s2 +; VI-NEXT: v_mov_b32_e32 v1, s3 +; VI-NEXT: v_mov_b32_e32 v2, s0 +; VI-NEXT: flat_store_short v[0:1], v2 +; VI-NEXT: s_endpgm +; +; GFX9-LABEL: atomic_store_bf16: +; GFX9: ; %bb.0: +; GFX9-NEXT: s_load_dword s4, s[0:1], 0x24 +; GFX9-NEXT: s_load_dwordx2 s[2:3], s[0:1], 0x2c +; GFX9-NEXT: v_mov_b32_e32 v0, 0 +; GFX9-NEXT: s_waitcnt lgkmcnt(0) +; GFX9-NEXT: v_mov_b32_e32 v1, s4 +; GFX9-NEXT: global_store_short v0, v1, s[2:3] +; GFX9-NEXT: s_endpgm + store atomic bfloat %in, ptr addrspace(1) %out seq_cst, align 2 + ret void +} + define amdgpu_kernel void @atomic_inc_i32_offset(ptr addrspace(1) %out, i32 %in) { ; SI-LABEL: atomic_inc_i32_offset: ; SI: ; %bb.0: ; %entry @@ -6963,3 +7038,207 @@ entry: store i32 %val, ptr addrspace(1) %out2 ret void } + +define amdgpu_kernel void @atomic_load_f16_offset(ptr addrspace(1) %in, ptr addrspace(1) %out) { +; SI-LABEL: atomic_load_f16_offset: +; SI: ; %bb.0: +; SI-NEXT: s_load_dwordx4 s[0:3], s[0:1], 0x9 +; SI-NEXT: s_mov_b32 s7, 0xf000 +; SI-NEXT: s_mov_b32 s6, -1 +; SI-NEXT: s_waitcnt lgkmcnt(0) +; SI-NEXT: s_mov_b32 s4, s2 +; SI-NEXT: s_mov_b32 s5, s3 +; SI-NEXT: s_mov_b32 s2, s6 +; SI-NEXT: s_mov_b32 s3, s7 +; SI-NEXT: buffer_load_ushort v0, off, s[0:3], 0 offset:16 glc +; SI-NEXT: s_waitcnt vmcnt(0) +; SI-NEXT: buffer_wbinvl1 +; SI-NEXT: buffer_store_short v0, off, s[4:7], 0 +; SI-NEXT: s_endpgm +; +; VI-LABEL: atomic_load_f16_offset: +; VI: ; %bb.0: +; VI-NEXT: s_load_dwordx4 s[0:3], s[0:1], 0x24 +; VI-NEXT: s_mov_b32 s7, 0xf000 +; VI-NEXT: s_mov_b32 s6, -1 +; VI-NEXT: s_waitcnt lgkmcnt(0) +; VI-NEXT: s_mov_b32 s4, s2 +; VI-NEXT: s_mov_b32 s5, s3 +; VI-NEXT: s_mov_b32 s2, s6 +; VI-NEXT: s_mov_b32 s3, s7 +; VI-NEXT: buffer_load_ushort v0, off, s[0:3], 0 offset:16 glc +; VI-NEXT: s_waitcnt vmcnt(0) +; VI-NEXT: buffer_wbinvl1_vol +; VI-NEXT: buffer_store_short v0, off, s[4:7], 0 +; VI-NEXT: s_endpgm +; +; GFX9-LABEL: atomic_load_f16_offset: +; GFX9: ; %bb.0: +; GFX9-NEXT: s_load_dwordx4 s[0:3], s[0:1], 0x24 +; GFX9-NEXT: v_mov_b32_e32 v0, 0 +; GFX9-NEXT: s_waitcnt lgkmcnt(0) +; GFX9-NEXT: global_load_ushort v1, v0, s[0:1] offset:16 glc +; GFX9-NEXT: s_waitcnt vmcnt(0) +; GFX9-NEXT: buffer_wbinvl1_vol +; GFX9-NEXT: global_store_short v0, v1, s[2:3] +; GFX9-NEXT: s_endpgm + %gep = getelementptr half, ptr addrspace(1) %in, i64 8 + %val = load atomic half, ptr addrspace(1) %gep seq_cst, align 2 + store half %val, ptr addrspace(1) %out + ret void +} + +define amdgpu_kernel void @atomic_load_f16_negoffset(ptr addrspace(1) %in, ptr addrspace(1) %out) { +; SI-LABEL: atomic_load_f16_negoffset: +; SI: ; %bb.0: +; SI-NEXT: s_load_dwordx4 s[0:3], s[0:1], 0x9 +; SI-NEXT: s_mov_b32 s7, 0xf000 +; SI-NEXT: s_waitcnt lgkmcnt(0) +; SI-NEXT: s_mov_b32 s4, s2 +; SI-NEXT: s_mov_b32 s5, s3 +; SI-NEXT: s_mov_b32 s2, 0 +; SI-NEXT: s_mov_b32 s3, s7 +; SI-NEXT: v_mov_b32_e32 v0, 0xfffffe00 +; SI-NEXT: v_mov_b32_e32 v1, -1 +; SI-NEXT: buffer_load_ushort v0, v[0:1], s[0:3], 0 addr64 glc +; SI-NEXT: s_waitcnt vmcnt(0) +; SI-NEXT: buffer_wbinvl1 +; SI-NEXT: s_mov_b32 s6, -1 +; SI-NEXT: buffer_store_short v0, off, s[4:7], 0 +; SI-NEXT: s_endpgm +; +; VI-LABEL: atomic_load_f16_negoffset: +; VI: ; %bb.0: +; VI-NEXT: s_load_dwordx4 s[0:3], s[0:1], 0x24 +; VI-NEXT: s_mov_b32 s7, 0xf000 +; VI-NEXT: s_mov_b32 s6, -1 +; VI-NEXT: s_waitcnt lgkmcnt(0) +; VI-NEXT: s_add_u32 s0, s0, 0xfffffe00 +; VI-NEXT: s_addc_u32 s1, s1, -1 +; VI-NEXT: v_mov_b32_e32 v0, s0 +; VI-NEXT: v_mov_b32_e32 v1, s1 +; VI-NEXT: flat_load_ushort v0, v[0:1] glc +; VI-NEXT: s_waitcnt vmcnt(0) +; VI-NEXT: buffer_wbinvl1_vol +; VI-NEXT: s_mov_b32 s4, s2 +; VI-NEXT: s_mov_b32 s5, s3 +; VI-NEXT: buffer_store_short v0, off, s[4:7], 0 +; VI-NEXT: s_endpgm +; +; GFX9-LABEL: atomic_load_f16_negoffset: +; GFX9: ; %bb.0: +; GFX9-NEXT: s_load_dwordx4 s[0:3], s[0:1], 0x24 +; GFX9-NEXT: v_mov_b32_e32 v0, 0 +; GFX9-NEXT: s_waitcnt lgkmcnt(0) +; GFX9-NEXT: global_load_ushort v1, v0, s[0:1] offset:-512 glc +; GFX9-NEXT: s_waitcnt vmcnt(0) +; GFX9-NEXT: buffer_wbinvl1_vol +; GFX9-NEXT: global_store_short v0, v1, s[2:3] +; GFX9-NEXT: s_endpgm + %gep = getelementptr half, ptr addrspace(1) %in, i64 -256 + %val = load atomic half, ptr addrspace(1) %gep seq_cst, align 2 + store half %val, ptr addrspace(1) %out + ret void +} + +define amdgpu_kernel void @atomic_load_bf16_offset(ptr addrspace(1) %in, ptr addrspace(1) %out) { +; SI-LABEL: atomic_load_bf16_offset: +; SI: ; %bb.0: +; SI-NEXT: s_load_dwordx4 s[0:3], s[0:1], 0x9 +; SI-NEXT: s_mov_b32 s7, 0xf000 +; SI-NEXT: s_mov_b32 s6, -1 +; SI-NEXT: s_waitcnt lgkmcnt(0) +; SI-NEXT: s_mov_b32 s4, s2 +; SI-NEXT: s_mov_b32 s5, s3 +; SI-NEXT: s_mov_b32 s2, s6 +; SI-NEXT: s_mov_b32 s3, s7 +; SI-NEXT: buffer_load_ushort v0, off, s[0:3], 0 offset:16 glc +; SI-NEXT: s_waitcnt vmcnt(0) +; SI-NEXT: buffer_wbinvl1 +; SI-NEXT: buffer_store_short v0, off, s[4:7], 0 +; SI-NEXT: s_endpgm +; +; VI-LABEL: atomic_load_bf16_offset: +; VI: ; %bb.0: +; VI-NEXT: s_load_dwordx4 s[0:3], s[0:1], 0x24 +; VI-NEXT: s_mov_b32 s7, 0xf000 +; VI-NEXT: s_mov_b32 s6, -1 +; VI-NEXT: s_waitcnt lgkmcnt(0) +; VI-NEXT: s_mov_b32 s4, s2 +; VI-NEXT: s_mov_b32 s5, s3 +; VI-NEXT: s_mov_b32 s2, s6 +; VI-NEXT: s_mov_b32 s3, s7 +; VI-NEXT: buffer_load_ushort v0, off, s[0:3], 0 offset:16 glc +; VI-NEXT: s_waitcnt vmcnt(0) +; VI-NEXT: buffer_wbinvl1_vol +; VI-NEXT: buffer_store_short v0, off, s[4:7], 0 +; VI-NEXT: s_endpgm +; +; GFX9-LABEL: atomic_load_bf16_offset: +; GFX9: ; %bb.0: +; GFX9-NEXT: s_load_dwordx4 s[0:3], s[0:1], 0x24 +; GFX9-NEXT: v_mov_b32_e32 v0, 0 +; GFX9-NEXT: s_waitcnt lgkmcnt(0) +; GFX9-NEXT: global_load_ushort v1, v0, s[0:1] offset:16 glc +; GFX9-NEXT: s_waitcnt vmcnt(0) +; GFX9-NEXT: buffer_wbinvl1_vol +; GFX9-NEXT: global_store_short v0, v1, s[2:3] +; GFX9-NEXT: s_endpgm + %gep = getelementptr bfloat, ptr addrspace(1) %in, i64 8 + %val = load atomic bfloat, ptr addrspace(1) %gep seq_cst, align 2 + store bfloat %val, ptr addrspace(1) %out + ret void +} + +define amdgpu_kernel void @atomic_load_bf16_negoffset(ptr addrspace(1) %in, ptr addrspace(1) %out) { +; SI-LABEL: atomic_load_bf16_negoffset: +; SI: ; %bb.0: +; SI-NEXT: s_load_dwordx4 s[0:3], s[0:1], 0x9 +; SI-NEXT: s_mov_b32 s7, 0xf000 +; SI-NEXT: s_waitcnt lgkmcnt(0) +; SI-NEXT: s_mov_b32 s4, s2 +; SI-NEXT: s_mov_b32 s5, s3 +; SI-NEXT: s_mov_b32 s2, 0 +; SI-NEXT: s_mov_b32 s3, s7 +; SI-NEXT: v_mov_b32_e32 v0, 0xfffffe00 +; SI-NEXT: v_mov_b32_e32 v1, -1 +; SI-NEXT: buffer_load_ushort v0, v[0:1], s[0:3], 0 addr64 glc +; SI-NEXT: s_waitcnt vmcnt(0) +; SI-NEXT: buffer_wbinvl1 +; SI-NEXT: s_mov_b32 s6, -1 +; SI-NEXT: buffer_store_short v0, off, s[4:7], 0 +; SI-NEXT: s_endpgm +; +; VI-LABEL: atomic_load_bf16_negoffset: +; VI: ; %bb.0: +; VI-NEXT: s_load_dwordx4 s[0:3], s[0:1], 0x24 +; VI-NEXT: s_mov_b32 s7, 0xf000 +; VI-NEXT: s_mov_b32 s6, -1 +; VI-NEXT: s_waitcnt lgkmcnt(0) +; VI-NEXT: s_add_u32 s0, s0, 0xfffffe00 +; VI-NEXT: s_addc_u32 s1, s1, -1 +; VI-NEXT: v_mov_b32_e32 v0, s0 +; VI-NEXT: v_mov_b32_e32 v1, s1 +; VI-NEXT: flat_load_ushort v0, v[0:1] glc +; VI-NEXT: s_waitcnt vmcnt(0) +; VI-NEXT: buffer_wbinvl1_vol +; VI-NEXT: s_mov_b32 s4, s2 +; VI-NEXT: s_mov_b32 s5, s3 +; VI-NEXT: buffer_store_short v0, off, s[4:7], 0 +; VI-NEXT: s_endpgm +; +; GFX9-LABEL: atomic_load_bf16_negoffset: +; GFX9: ; %bb.0: +; GFX9-NEXT: s_load_dwordx4 s[0:3], s[0:1], 0x24 +; GFX9-NEXT: v_mov_b32_e32 v0, 0 +; GFX9-NEXT: s_waitcnt lgkmcnt(0) +; GFX9-NEXT: global_load_ushort v1, v0, s[0:1] offset:-512 glc +; GFX9-NEXT: s_waitcnt vmcnt(0) +; GFX9-NEXT: buffer_wbinvl1_vol +; GFX9-NEXT: global_store_short v0, v1, s[2:3] +; GFX9-NEXT: s_endpgm + %gep = getelementptr bfloat, ptr addrspace(1) %in, i64 -256 + %val = load atomic bfloat, ptr addrspace(1) %gep seq_cst, align 2 + store bfloat %val, ptr addrspace(1) %out + ret void +} diff --git a/llvm/test/CodeGen/AMDGPU/global_atomics_i64.ll b/llvm/test/CodeGen/AMDGPU/global_atomics_i64.ll index 08b068f3588c38b63f4b255a4ecc677d5ab58ecf..f5dbaaff9cf882daa18a79d0cb545498da242e34 100644 --- a/llvm/test/CodeGen/AMDGPU/global_atomics_i64.ll +++ b/llvm/test/CodeGen/AMDGPU/global_atomics_i64.ll @@ -4570,7 +4570,7 @@ define amdgpu_kernel void @atomic_xchg_f64_offset(ptr addrspace(1) %out, double ; GFX12-NEXT: v_mov_b32_e32 v0, s2 ; GFX12-NEXT: global_atomic_swap_b64 v2, v[0:1], s[0:1] offset:32 ; GFX12-NEXT: s_wait_storecnt 0x0 -; GFX12-NEXT: global_inv scope:SCOPE_SYS +; GFX12-NEXT: global_inv scope:SCOPE_DEV ; GFX12-NEXT: s_endpgm entry: %gep = getelementptr double, ptr addrspace(1) %out, i64 4 @@ -4625,7 +4625,7 @@ define amdgpu_kernel void @atomic_xchg_pointer_offset(ptr addrspace(1) %out, ptr ; GFX12-NEXT: v_mov_b32_e32 v0, s2 ; GFX12-NEXT: global_atomic_swap_b64 v2, v[0:1], s[0:1] offset:32 ; GFX12-NEXT: s_wait_storecnt 0x0 -; GFX12-NEXT: global_inv scope:SCOPE_SYS +; GFX12-NEXT: global_inv scope:SCOPE_DEV ; GFX12-NEXT: s_endpgm entry: %gep = getelementptr ptr, ptr addrspace(1) %out, i64 4 diff --git a/llvm/test/CodeGen/AMDGPU/llvm.fptrunc.round.ll b/llvm/test/CodeGen/AMDGPU/llvm.fptrunc.round.ll index a113c07b3e2bea508e4aa7d6d1cf4e7b9f5c2349..b8c16d2ed3b2f1ffa86186464aae5f05b070fd31 100644 --- a/llvm/test/CodeGen/AMDGPU/llvm.fptrunc.round.ll +++ b/llvm/test/CodeGen/AMDGPU/llvm.fptrunc.round.ll @@ -1,52 +1,453 @@ ; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py -; RUN: llc -mtriple=amdgcn -mcpu=gfx1030 -verify-machineinstrs < %s | FileCheck %s -; RUN: llc -mtriple=amdgcn -mcpu=gfx1010 -verify-machineinstrs < %s | FileCheck %s -; RUN: llc -global-isel -mtriple=amdgcn -mcpu=gfx1030 -verify-machineinstrs < %s | FileCheck %s +; RUN: llc -global-isel=0 -mtriple=amdgcn -mcpu=gfx1030 < %s | FileCheck -check-prefixes=CHECK,SDAG %s +; RUN: llc -global-isel=0 -mtriple=amdgcn -mcpu=gfx1010 < %s | FileCheck -check-prefixes=CHECK,SDAG %s +; RUN: llc -global-isel -mtriple=amdgcn -mcpu=gfx1030 < %s | FileCheck -check-prefixes=CHECK,GISEL %s -define amdgpu_gs void @test_fptrunc_round_upward(float %a, i32 %data0, <4 x i32> %data1, ptr addrspace(1) %out) { -; CHECK-LABEL: test_fptrunc_round_upward: +define amdgpu_gs half @v_fptrunc_round_f32_to_f16_upward(float %a) { +; CHECK-LABEL: v_fptrunc_round_f32_to_f16_upward: ; CHECK: ; %bb.0: ; CHECK-NEXT: s_setreg_imm32_b32 hwreg(HW_REG_MODE, 2, 1), 1 ; CHECK-NEXT: v_cvt_f16_f32_e32 v0, v0 -; CHECK-NEXT: global_store_short v[6:7], v0, off -; CHECK-NEXT: s_endpgm - %res = call half @llvm.fptrunc.round(float %a, metadata !"round.upward") - store half %res, ptr addrspace(1) %out, align 4 - ret void +; CHECK-NEXT: ; return to shader part epilog + %res = call half @llvm.fptrunc.round.f16.f32(float %a, metadata !"round.upward") + ret half %res } -define amdgpu_gs void @test_fptrunc_round_downward(float %a, i32 %data0, <4 x i32> %data1, ptr addrspace(1) %out) { -; CHECK-LABEL: test_fptrunc_round_downward: +define amdgpu_gs half @v_fptrunc_round_f32_to_f16_downward(float %a) { +; CHECK-LABEL: v_fptrunc_round_f32_to_f16_downward: ; CHECK: ; %bb.0: ; CHECK-NEXT: s_setreg_imm32_b32 hwreg(HW_REG_MODE, 3, 1), 1 ; CHECK-NEXT: v_cvt_f16_f32_e32 v0, v0 -; CHECK-NEXT: global_store_short v[6:7], v0, off -; CHECK-NEXT: s_endpgm - %res = call half @llvm.fptrunc.round(float %a, metadata !"round.downward") - store half %res, ptr addrspace(1) %out, align 4 - ret void +; CHECK-NEXT: ; return to shader part epilog + %res = call half @llvm.fptrunc.round.f16.f32(float %a, metadata !"round.downward") + ret half %res } -define amdgpu_gs void @test_fptrunc_round_upward_multiple_calls(float %a, float %b, i32 %data0, <4 x i32> %data1, ptr addrspace(1) %out) { -; CHECK-LABEL: test_fptrunc_round_upward_multiple_calls: +define amdgpu_gs void @v_fptrunc_round_f32_to_f16_upward_multiple_calls(float %a, float %b, ptr addrspace(1) %out) { +; CHECK-LABEL: v_fptrunc_round_f32_to_f16_upward_multiple_calls: ; CHECK: ; %bb.0: ; CHECK-NEXT: s_setreg_imm32_b32 hwreg(HW_REG_MODE, 2, 1), 1 ; CHECK-NEXT: v_cvt_f16_f32_e32 v0, v0 -; CHECK-NEXT: v_cvt_f16_f32_e32 v2, v1 +; CHECK-NEXT: v_cvt_f16_f32_e32 v4, v1 ; CHECK-NEXT: s_setreg_imm32_b32 hwreg(HW_REG_MODE, 2, 2), 2 ; CHECK-NEXT: v_cvt_f16_f32_e32 v1, v1 ; CHECK-NEXT: s_setreg_imm32_b32 hwreg(HW_REG_MODE, 3, 1), 0 -; CHECK-NEXT: v_add_f16_e32 v0, v0, v2 +; CHECK-NEXT: v_add_f16_e32 v0, v0, v4 ; CHECK-NEXT: v_add_f16_e32 v0, v1, v0 -; CHECK-NEXT: global_store_short v[7:8], v0, off +; CHECK-NEXT: global_store_short v[2:3], v0, off +; CHECK-NEXT: s_endpgm + %res1 = call half @llvm.fptrunc.round.f16.f32(float %a, metadata !"round.upward") + %res2 = call half @llvm.fptrunc.round.f16.f32(float %b, metadata !"round.upward") + %res3 = call half @llvm.fptrunc.round.f16.f32(float %b, metadata !"round.downward") + %res4 = fadd half %res1, %res2 + %res5 = fadd half %res3, %res4 + store half %res5, ptr addrspace(1) %out, align 4 + ret void +} + +define amdgpu_gs i32 @s_fptrunc_round_f32_to_f16_upward(float inreg %a, ptr addrspace(1) %out) { +; CHECK-LABEL: s_fptrunc_round_f32_to_f16_upward: +; CHECK: ; %bb.0: +; CHECK-NEXT: v_mov_b32_e32 v0, s0 +; CHECK-NEXT: s_setreg_imm32_b32 hwreg(HW_REG_MODE, 2, 1), 1 +; CHECK-NEXT: v_cvt_f16_f32_e32 v0, v0 +; CHECK-NEXT: v_and_b32_e32 v0, 0xffff, v0 +; CHECK-NEXT: v_readfirstlane_b32 s0, v0 +; CHECK-NEXT: ; return to shader part epilog + %res = call half @llvm.fptrunc.round.f16.f32(float %a, metadata !"round.upward") + %bitcast = bitcast half %res to i16 + %ret = zext i16 %bitcast to i32 + ret i32 %ret +} + +define amdgpu_gs i32 @s_fptrunc_round_f32_to_f16_downward(float inreg %a, ptr addrspace(1) %out) { +; CHECK-LABEL: s_fptrunc_round_f32_to_f16_downward: +; CHECK: ; %bb.0: +; CHECK-NEXT: v_mov_b32_e32 v0, s0 +; CHECK-NEXT: s_setreg_imm32_b32 hwreg(HW_REG_MODE, 3, 1), 1 +; CHECK-NEXT: v_cvt_f16_f32_e32 v0, v0 +; CHECK-NEXT: v_and_b32_e32 v0, 0xffff, v0 +; CHECK-NEXT: v_readfirstlane_b32 s0, v0 +; CHECK-NEXT: ; return to shader part epilog + %res = call half @llvm.fptrunc.round.f16.f32(float %a, metadata !"round.downward") + %bitcast = bitcast half %res to i16 + %ret = zext i16 %bitcast to i32 + ret i32 %ret +} + +define amdgpu_gs void @s_fptrunc_round_f32_to_f16_upward_multiple_calls(float inreg %a, float inreg %b, ptr addrspace(1) %out) { +; CHECK-LABEL: s_fptrunc_round_f32_to_f16_upward_multiple_calls: +; CHECK: ; %bb.0: +; CHECK-NEXT: v_mov_b32_e32 v2, s0 +; CHECK-NEXT: v_mov_b32_e32 v3, s1 +; CHECK-NEXT: s_setreg_imm32_b32 hwreg(HW_REG_MODE, 2, 1), 1 +; CHECK-NEXT: v_cvt_f16_f32_e32 v2, v2 +; CHECK-NEXT: v_cvt_f16_f32_e32 v4, v3 +; CHECK-NEXT: s_setreg_imm32_b32 hwreg(HW_REG_MODE, 2, 2), 2 +; CHECK-NEXT: v_cvt_f16_f32_e32 v3, v3 +; CHECK-NEXT: s_setreg_imm32_b32 hwreg(HW_REG_MODE, 3, 1), 0 +; CHECK-NEXT: v_add_f16_e32 v2, v2, v4 +; CHECK-NEXT: v_add_f16_e32 v2, v3, v2 +; CHECK-NEXT: global_store_short v[0:1], v2, off ; CHECK-NEXT: s_endpgm - %res1 = call half @llvm.fptrunc.round(float %a, metadata !"round.upward") - %res2 = call half @llvm.fptrunc.round(float %b, metadata !"round.upward") - %res3 = call half @llvm.fptrunc.round(float %b, metadata !"round.downward") + %res1 = call half @llvm.fptrunc.round.f16.f32(float %a, metadata !"round.upward") + %res2 = call half @llvm.fptrunc.round.f16.f32(float %b, metadata !"round.upward") + %res3 = call half @llvm.fptrunc.round.f16.f32(float %b, metadata !"round.downward") %res4 = fadd half %res1, %res2 %res5 = fadd half %res3, %res4 store half %res5, ptr addrspace(1) %out, align 4 ret void } -declare half @llvm.fptrunc.round(float, metadata) +define amdgpu_gs <2 x half> @v_fptrunc_round_v2f32_to_v2f16_upward(<2 x float> %a) { +; SDAG-LABEL: v_fptrunc_round_v2f32_to_v2f16_upward: +; SDAG: ; %bb.0: +; SDAG-NEXT: s_setreg_imm32_b32 hwreg(HW_REG_MODE, 2, 1), 1 +; SDAG-NEXT: v_cvt_f16_f32_e32 v0, v0 +; SDAG-NEXT: v_cvt_f16_f32_e32 v1, v1 +; SDAG-NEXT: v_perm_b32 v0, v1, v0, 0x5040100 +; SDAG-NEXT: ; return to shader part epilog +; +; GISEL-LABEL: v_fptrunc_round_v2f32_to_v2f16_upward: +; GISEL: ; %bb.0: +; GISEL-NEXT: s_setreg_imm32_b32 hwreg(HW_REG_MODE, 2, 1), 1 +; GISEL-NEXT: v_cvt_f16_f32_e32 v0, v0 +; GISEL-NEXT: v_cvt_f16_f32_e32 v1, v1 +; GISEL-NEXT: v_and_b32_e32 v0, 0xffff, v0 +; GISEL-NEXT: v_lshl_or_b32 v0, v1, 16, v0 +; GISEL-NEXT: ; return to shader part epilog + %res = call <2 x half> @llvm.fptrunc.round.v2f16.v2f32(<2 x float> %a, metadata !"round.upward") + ret <2 x half> %res +} + +define amdgpu_gs <2 x half> @v_fptrunc_round_v2f32_to_v2f16_downward(<2 x float> %a) { +; SDAG-LABEL: v_fptrunc_round_v2f32_to_v2f16_downward: +; SDAG: ; %bb.0: +; SDAG-NEXT: s_setreg_imm32_b32 hwreg(HW_REG_MODE, 3, 1), 1 +; SDAG-NEXT: v_cvt_f16_f32_e32 v0, v0 +; SDAG-NEXT: v_cvt_f16_f32_e32 v1, v1 +; SDAG-NEXT: v_perm_b32 v0, v1, v0, 0x5040100 +; SDAG-NEXT: ; return to shader part epilog +; +; GISEL-LABEL: v_fptrunc_round_v2f32_to_v2f16_downward: +; GISEL: ; %bb.0: +; GISEL-NEXT: s_setreg_imm32_b32 hwreg(HW_REG_MODE, 3, 1), 1 +; GISEL-NEXT: v_cvt_f16_f32_e32 v0, v0 +; GISEL-NEXT: v_cvt_f16_f32_e32 v1, v1 +; GISEL-NEXT: v_and_b32_e32 v0, 0xffff, v0 +; GISEL-NEXT: v_lshl_or_b32 v0, v1, 16, v0 +; GISEL-NEXT: ; return to shader part epilog + %res = call <2 x half> @llvm.fptrunc.round.v2f16.v2f32(<2 x float> %a, metadata !"round.downward") + ret <2 x half> %res +} + +define amdgpu_gs void @v_fptrunc_round_v2f32_to_v2f16_upward_multiple_calls(<2 x float> %a, <2 x float> %b, ptr addrspace(1) %out) { +; SDAG-LABEL: v_fptrunc_round_v2f32_to_v2f16_upward_multiple_calls: +; SDAG: ; %bb.0: +; SDAG-NEXT: s_setreg_imm32_b32 hwreg(HW_REG_MODE, 2, 1), 1 +; SDAG-NEXT: v_cvt_f16_f32_e32 v0, v0 +; SDAG-NEXT: v_cvt_f16_f32_e32 v1, v1 +; SDAG-NEXT: v_cvt_f16_f32_e32 v6, v2 +; SDAG-NEXT: v_cvt_f16_f32_e32 v7, v3 +; SDAG-NEXT: v_perm_b32 v0, v1, v0, 0x5040100 +; SDAG-NEXT: s_setreg_imm32_b32 hwreg(HW_REG_MODE, 2, 2), 2 +; SDAG-NEXT: v_cvt_f16_f32_e32 v1, v2 +; SDAG-NEXT: v_cvt_f16_f32_e32 v2, v3 +; SDAG-NEXT: v_perm_b32 v3, v7, v6, 0x5040100 +; SDAG-NEXT: v_perm_b32 v1, v2, v1, 0x5040100 +; SDAG-NEXT: s_setreg_imm32_b32 hwreg(HW_REG_MODE, 3, 1), 0 +; SDAG-NEXT: v_pk_add_f16 v0, v0, v3 +; SDAG-NEXT: v_pk_add_f16 v0, v1, v0 +; SDAG-NEXT: global_store_dword v[4:5], v0, off +; SDAG-NEXT: s_endpgm +; +; GISEL-LABEL: v_fptrunc_round_v2f32_to_v2f16_upward_multiple_calls: +; GISEL: ; %bb.0: +; GISEL-NEXT: s_setreg_imm32_b32 hwreg(HW_REG_MODE, 2, 1), 1 +; GISEL-NEXT: v_cvt_f16_f32_e32 v0, v0 +; GISEL-NEXT: v_cvt_f16_f32_e32 v6, v2 +; GISEL-NEXT: v_cvt_f16_f32_e32 v1, v1 +; GISEL-NEXT: s_setreg_imm32_b32 hwreg(HW_REG_MODE, 2, 2), 2 +; GISEL-NEXT: v_cvt_f16_f32_e32 v2, v2 +; GISEL-NEXT: s_setreg_imm32_b32 hwreg(HW_REG_MODE, 2, 2), 1 +; GISEL-NEXT: v_cvt_f16_f32_e32 v7, v3 +; GISEL-NEXT: v_and_b32_e32 v0, 0xffff, v0 +; GISEL-NEXT: v_and_b32_e32 v6, 0xffff, v6 +; GISEL-NEXT: s_setreg_imm32_b32 hwreg(HW_REG_MODE, 2, 2), 2 +; GISEL-NEXT: v_cvt_f16_f32_e32 v3, v3 +; GISEL-NEXT: v_and_b32_e32 v2, 0xffff, v2 +; GISEL-NEXT: v_lshl_or_b32 v0, v1, 16, v0 +; GISEL-NEXT: v_lshl_or_b32 v1, v7, 16, v6 +; GISEL-NEXT: v_lshl_or_b32 v2, v3, 16, v2 +; GISEL-NEXT: s_setreg_imm32_b32 hwreg(HW_REG_MODE, 3, 1), 0 +; GISEL-NEXT: v_pk_add_f16 v0, v0, v1 +; GISEL-NEXT: v_pk_add_f16 v0, v2, v0 +; GISEL-NEXT: global_store_dword v[4:5], v0, off +; GISEL-NEXT: s_endpgm + %res1 = call <2 x half> @llvm.fptrunc.round.v2f16.v2f32(<2 x float> %a, metadata !"round.upward") + %res2 = call <2 x half> @llvm.fptrunc.round.v2f16.v2f32(<2 x float> %b, metadata !"round.upward") + %res3 = call <2 x half> @llvm.fptrunc.round.v2f16.v2f32(<2 x float> %b, metadata !"round.downward") + %res4 = fadd <2 x half> %res1, %res2 + %res5 = fadd <2 x half> %res3, %res4 + store <2 x half> %res5, ptr addrspace(1) %out, align 4 + ret void +} + +define amdgpu_gs <2 x i32> @s_fptrunc_round_v2f32_to_v2f16_upward(<2 x float> inreg %a, ptr addrspace(1) %out) { +; CHECK-LABEL: s_fptrunc_round_v2f32_to_v2f16_upward: +; CHECK: ; %bb.0: +; CHECK-NEXT: v_mov_b32_e32 v0, s0 +; CHECK-NEXT: v_mov_b32_e32 v1, s1 +; CHECK-NEXT: s_setreg_imm32_b32 hwreg(HW_REG_MODE, 2, 1), 1 +; CHECK-NEXT: v_cvt_f16_f32_e32 v0, v0 +; CHECK-NEXT: v_cvt_f16_f32_e32 v1, v1 +; CHECK-NEXT: v_and_b32_e32 v0, 0xffff, v0 +; CHECK-NEXT: v_and_b32_e32 v1, 0xffff, v1 +; CHECK-NEXT: v_readfirstlane_b32 s0, v0 +; CHECK-NEXT: v_readfirstlane_b32 s1, v1 +; CHECK-NEXT: ; return to shader part epilog + %res = call <2 x half> @llvm.fptrunc.round.v2f16.v2f32(<2 x float> %a, metadata !"round.upward") + %bitcast = bitcast <2 x half> %res to <2 x i16> + %ret = zext <2 x i16> %bitcast to <2 x i32> + ret <2 x i32> %ret +} + +define amdgpu_gs <2 x i32> @s_fptrunc_round_v2f32_to_v2f16_downward(<2 x float> inreg %a, ptr addrspace(1) %out) { +; CHECK-LABEL: s_fptrunc_round_v2f32_to_v2f16_downward: +; CHECK: ; %bb.0: +; CHECK-NEXT: v_mov_b32_e32 v0, s0 +; CHECK-NEXT: v_mov_b32_e32 v1, s1 +; CHECK-NEXT: s_setreg_imm32_b32 hwreg(HW_REG_MODE, 3, 1), 1 +; CHECK-NEXT: v_cvt_f16_f32_e32 v0, v0 +; CHECK-NEXT: v_cvt_f16_f32_e32 v1, v1 +; CHECK-NEXT: v_and_b32_e32 v0, 0xffff, v0 +; CHECK-NEXT: v_and_b32_e32 v1, 0xffff, v1 +; CHECK-NEXT: v_readfirstlane_b32 s0, v0 +; CHECK-NEXT: v_readfirstlane_b32 s1, v1 +; CHECK-NEXT: ; return to shader part epilog + %res = call <2 x half> @llvm.fptrunc.round.v2f16.v2f32(<2 x float> %a, metadata !"round.downward") + %bitcast = bitcast <2 x half> %res to <2 x i16> + %ret = zext <2 x i16> %bitcast to <2 x i32> + ret <2 x i32> %ret +} + +define amdgpu_gs void @s_fptrunc_round_v2f32_to_v2f16_upward_multiple_calls(<2 x float> inreg %a, <2 x float> inreg %b, ptr addrspace(1) %out) { +; CHECK-LABEL: s_fptrunc_round_v2f32_to_v2f16_upward_multiple_calls: +; CHECK: ; %bb.0: +; CHECK-NEXT: v_mov_b32_e32 v2, s0 +; CHECK-NEXT: v_mov_b32_e32 v3, s2 +; CHECK-NEXT: v_mov_b32_e32 v4, s1 +; CHECK-NEXT: v_mov_b32_e32 v5, s3 +; CHECK-NEXT: s_setreg_imm32_b32 hwreg(HW_REG_MODE, 2, 1), 1 +; CHECK-NEXT: v_cvt_f16_f32_e32 v2, v2 +; CHECK-NEXT: v_cvt_f16_f32_e32 v6, v3 +; CHECK-NEXT: v_cvt_f16_f32_e32 v4, v4 +; CHECK-NEXT: v_cvt_f16_f32_e32 v7, v5 +; CHECK-NEXT: s_setreg_imm32_b32 hwreg(HW_REG_MODE, 2, 2), 2 +; CHECK-NEXT: v_cvt_f16_f32_e32 v3, v3 +; CHECK-NEXT: v_and_b32_e32 v2, 0xffff, v2 +; CHECK-NEXT: v_and_b32_e32 v6, 0xffff, v6 +; CHECK-NEXT: v_and_b32_e32 v3, 0xffff, v3 +; CHECK-NEXT: v_lshl_or_b32 v2, v4, 16, v2 +; CHECK-NEXT: v_cvt_f16_f32_e32 v4, v5 +; CHECK-NEXT: v_lshl_or_b32 v5, v7, 16, v6 +; CHECK-NEXT: v_lshl_or_b32 v3, v4, 16, v3 +; CHECK-NEXT: s_setreg_imm32_b32 hwreg(HW_REG_MODE, 3, 1), 0 +; CHECK-NEXT: v_pk_add_f16 v2, v2, v5 +; CHECK-NEXT: v_pk_add_f16 v2, v3, v2 +; CHECK-NEXT: global_store_dword v[0:1], v2, off +; CHECK-NEXT: s_endpgm + %res1 = call <2 x half> @llvm.fptrunc.round.v2f16.v2f32(<2 x float> %a, metadata !"round.upward") + %res2 = call <2 x half> @llvm.fptrunc.round.v2f16.v2f32(<2 x float> %b, metadata !"round.upward") + %res3 = call <2 x half> @llvm.fptrunc.round.v2f16.v2f32(<2 x float> %b, metadata !"round.downward") + %res4 = fadd <2 x half> %res1, %res2 + %res5 = fadd <2 x half> %res3, %res4 + store <2 x half> %res5, ptr addrspace(1) %out, align 4 + ret void +} + +define amdgpu_gs <3 x half> @v_fptrunc_round_v3f32_to_v3f16_upward(<3 x float> %a) { +; SDAG-LABEL: v_fptrunc_round_v3f32_to_v3f16_upward: +; SDAG: ; %bb.0: +; SDAG-NEXT: s_setreg_imm32_b32 hwreg(HW_REG_MODE, 2, 1), 1 +; SDAG-NEXT: v_cvt_f16_f32_e32 v0, v0 +; SDAG-NEXT: v_cvt_f16_f32_e32 v1, v1 +; SDAG-NEXT: v_perm_b32 v0, v1, v0, 0x5040100 +; SDAG-NEXT: v_cvt_f16_f32_e32 v1, v2 +; SDAG-NEXT: ; return to shader part epilog +; +; GISEL-LABEL: v_fptrunc_round_v3f32_to_v3f16_upward: +; GISEL: ; %bb.0: +; GISEL-NEXT: s_setreg_imm32_b32 hwreg(HW_REG_MODE, 2, 1), 1 +; GISEL-NEXT: v_cvt_f16_f32_e32 v0, v0 +; GISEL-NEXT: v_cvt_f16_f32_e32 v1, v1 +; GISEL-NEXT: v_and_b32_e32 v0, 0xffff, v0 +; GISEL-NEXT: v_lshl_or_b32 v0, v1, 16, v0 +; GISEL-NEXT: v_cvt_f16_f32_e32 v1, v2 +; GISEL-NEXT: ; return to shader part epilog + %res = call <3 x half> @llvm.fptrunc.round.v3f16.v3f32(<3 x float> %a, metadata !"round.upward") + ret <3 x half> %res +} + +define amdgpu_gs <3 x half> @v_fptrunc_round_v3f32_to_v3f16_downward(<3 x float> %a) { +; SDAG-LABEL: v_fptrunc_round_v3f32_to_v3f16_downward: +; SDAG: ; %bb.0: +; SDAG-NEXT: s_setreg_imm32_b32 hwreg(HW_REG_MODE, 3, 1), 1 +; SDAG-NEXT: v_cvt_f16_f32_e32 v0, v0 +; SDAG-NEXT: v_cvt_f16_f32_e32 v1, v1 +; SDAG-NEXT: v_perm_b32 v0, v1, v0, 0x5040100 +; SDAG-NEXT: v_cvt_f16_f32_e32 v1, v2 +; SDAG-NEXT: ; return to shader part epilog +; +; GISEL-LABEL: v_fptrunc_round_v3f32_to_v3f16_downward: +; GISEL: ; %bb.0: +; GISEL-NEXT: s_setreg_imm32_b32 hwreg(HW_REG_MODE, 3, 1), 1 +; GISEL-NEXT: v_cvt_f16_f32_e32 v0, v0 +; GISEL-NEXT: v_cvt_f16_f32_e32 v1, v1 +; GISEL-NEXT: v_and_b32_e32 v0, 0xffff, v0 +; GISEL-NEXT: v_lshl_or_b32 v0, v1, 16, v0 +; GISEL-NEXT: v_cvt_f16_f32_e32 v1, v2 +; GISEL-NEXT: ; return to shader part epilog + %res = call <3 x half> @llvm.fptrunc.round.v3f16.v3f32(<3 x float> %a, metadata !"round.downward") + ret <3 x half> %res +} + +define amdgpu_gs <4 x half> @v_fptrunc_round_v4f32_to_v4f16_upward(<4 x float> %a) { +; SDAG-LABEL: v_fptrunc_round_v4f32_to_v4f16_upward: +; SDAG: ; %bb.0: +; SDAG-NEXT: s_setreg_imm32_b32 hwreg(HW_REG_MODE, 2, 1), 1 +; SDAG-NEXT: v_cvt_f16_f32_e32 v2, v2 +; SDAG-NEXT: v_cvt_f16_f32_e32 v0, v0 +; SDAG-NEXT: v_cvt_f16_f32_e32 v1, v1 +; SDAG-NEXT: v_cvt_f16_f32_e32 v3, v3 +; SDAG-NEXT: v_perm_b32 v0, v1, v0, 0x5040100 +; SDAG-NEXT: v_perm_b32 v1, v3, v2, 0x5040100 +; SDAG-NEXT: ; return to shader part epilog +; +; GISEL-LABEL: v_fptrunc_round_v4f32_to_v4f16_upward: +; GISEL: ; %bb.0: +; GISEL-NEXT: s_setreg_imm32_b32 hwreg(HW_REG_MODE, 2, 1), 1 +; GISEL-NEXT: v_cvt_f16_f32_e32 v0, v0 +; GISEL-NEXT: v_cvt_f16_f32_e32 v2, v2 +; GISEL-NEXT: v_cvt_f16_f32_e32 v1, v1 +; GISEL-NEXT: v_cvt_f16_f32_e32 v3, v3 +; GISEL-NEXT: v_and_b32_e32 v0, 0xffff, v0 +; GISEL-NEXT: v_and_b32_e32 v2, 0xffff, v2 +; GISEL-NEXT: v_lshl_or_b32 v0, v1, 16, v0 +; GISEL-NEXT: v_lshl_or_b32 v1, v3, 16, v2 +; GISEL-NEXT: ; return to shader part epilog + %res = call <4 x half> @llvm.fptrunc.round.v4f16.v4f32(<4 x float> %a, metadata !"round.upward") + ret <4 x half> %res +} + +define amdgpu_gs <4 x half> @v_fptrunc_round_v4f32_to_v4f16_downward(<4 x float> %a) { +; SDAG-LABEL: v_fptrunc_round_v4f32_to_v4f16_downward: +; SDAG: ; %bb.0: +; SDAG-NEXT: s_setreg_imm32_b32 hwreg(HW_REG_MODE, 3, 1), 1 +; SDAG-NEXT: v_cvt_f16_f32_e32 v2, v2 +; SDAG-NEXT: v_cvt_f16_f32_e32 v0, v0 +; SDAG-NEXT: v_cvt_f16_f32_e32 v1, v1 +; SDAG-NEXT: v_cvt_f16_f32_e32 v3, v3 +; SDAG-NEXT: v_perm_b32 v0, v1, v0, 0x5040100 +; SDAG-NEXT: v_perm_b32 v1, v3, v2, 0x5040100 +; SDAG-NEXT: ; return to shader part epilog +; +; GISEL-LABEL: v_fptrunc_round_v4f32_to_v4f16_downward: +; GISEL: ; %bb.0: +; GISEL-NEXT: s_setreg_imm32_b32 hwreg(HW_REG_MODE, 3, 1), 1 +; GISEL-NEXT: v_cvt_f16_f32_e32 v0, v0 +; GISEL-NEXT: v_cvt_f16_f32_e32 v2, v2 +; GISEL-NEXT: v_cvt_f16_f32_e32 v1, v1 +; GISEL-NEXT: v_cvt_f16_f32_e32 v3, v3 +; GISEL-NEXT: v_and_b32_e32 v0, 0xffff, v0 +; GISEL-NEXT: v_and_b32_e32 v2, 0xffff, v2 +; GISEL-NEXT: v_lshl_or_b32 v0, v1, 16, v0 +; GISEL-NEXT: v_lshl_or_b32 v1, v3, 16, v2 +; GISEL-NEXT: ; return to shader part epilog + %res = call <4 x half> @llvm.fptrunc.round.v4f16.v4f32(<4 x float> %a, metadata !"round.downward") + ret <4 x half> %res +} + +define amdgpu_gs <8 x half> @v_fptrunc_round_v8f32_to_v8f16_upward(<8 x float> %a) { +; SDAG-LABEL: v_fptrunc_round_v8f32_to_v8f16_upward: +; SDAG: ; %bb.0: +; SDAG-NEXT: s_setreg_imm32_b32 hwreg(HW_REG_MODE, 2, 1), 1 +; SDAG-NEXT: v_cvt_f16_f32_e32 v6, v6 +; SDAG-NEXT: v_cvt_f16_f32_e32 v4, v4 +; SDAG-NEXT: v_cvt_f16_f32_e32 v2, v2 +; SDAG-NEXT: v_cvt_f16_f32_e32 v0, v0 +; SDAG-NEXT: v_cvt_f16_f32_e32 v1, v1 +; SDAG-NEXT: v_cvt_f16_f32_e32 v3, v3 +; SDAG-NEXT: v_cvt_f16_f32_e32 v5, v5 +; SDAG-NEXT: v_cvt_f16_f32_e32 v7, v7 +; SDAG-NEXT: v_perm_b32 v0, v1, v0, 0x5040100 +; SDAG-NEXT: v_perm_b32 v1, v3, v2, 0x5040100 +; SDAG-NEXT: v_perm_b32 v2, v5, v4, 0x5040100 +; SDAG-NEXT: v_perm_b32 v3, v7, v6, 0x5040100 +; SDAG-NEXT: ; return to shader part epilog +; +; GISEL-LABEL: v_fptrunc_round_v8f32_to_v8f16_upward: +; GISEL: ; %bb.0: +; GISEL-NEXT: s_setreg_imm32_b32 hwreg(HW_REG_MODE, 2, 1), 1 +; GISEL-NEXT: v_cvt_f16_f32_e32 v0, v0 +; GISEL-NEXT: v_cvt_f16_f32_e32 v2, v2 +; GISEL-NEXT: v_cvt_f16_f32_e32 v4, v4 +; GISEL-NEXT: v_cvt_f16_f32_e32 v6, v6 +; GISEL-NEXT: v_cvt_f16_f32_e32 v1, v1 +; GISEL-NEXT: v_cvt_f16_f32_e32 v3, v3 +; GISEL-NEXT: v_cvt_f16_f32_e32 v5, v5 +; GISEL-NEXT: v_cvt_f16_f32_e32 v7, v7 +; GISEL-NEXT: v_and_b32_e32 v0, 0xffff, v0 +; GISEL-NEXT: v_and_b32_e32 v2, 0xffff, v2 +; GISEL-NEXT: v_and_b32_e32 v4, 0xffff, v4 +; GISEL-NEXT: v_and_b32_e32 v6, 0xffff, v6 +; GISEL-NEXT: v_lshl_or_b32 v0, v1, 16, v0 +; GISEL-NEXT: v_lshl_or_b32 v1, v3, 16, v2 +; GISEL-NEXT: v_lshl_or_b32 v2, v5, 16, v4 +; GISEL-NEXT: v_lshl_or_b32 v3, v7, 16, v6 +; GISEL-NEXT: ; return to shader part epilog + %res = call <8 x half> @llvm.fptrunc.round.v8f16.v8f32(<8 x float> %a, metadata !"round.upward") + ret <8 x half> %res +} + +define amdgpu_gs <8 x half> @v_fptrunc_round_v8f32_to_v8f16_downward(<8 x float> %a) { +; SDAG-LABEL: v_fptrunc_round_v8f32_to_v8f16_downward: +; SDAG: ; %bb.0: +; SDAG-NEXT: s_setreg_imm32_b32 hwreg(HW_REG_MODE, 3, 1), 1 +; SDAG-NEXT: v_cvt_f16_f32_e32 v6, v6 +; SDAG-NEXT: v_cvt_f16_f32_e32 v4, v4 +; SDAG-NEXT: v_cvt_f16_f32_e32 v2, v2 +; SDAG-NEXT: v_cvt_f16_f32_e32 v0, v0 +; SDAG-NEXT: v_cvt_f16_f32_e32 v1, v1 +; SDAG-NEXT: v_cvt_f16_f32_e32 v3, v3 +; SDAG-NEXT: v_cvt_f16_f32_e32 v5, v5 +; SDAG-NEXT: v_cvt_f16_f32_e32 v7, v7 +; SDAG-NEXT: v_perm_b32 v0, v1, v0, 0x5040100 +; SDAG-NEXT: v_perm_b32 v1, v3, v2, 0x5040100 +; SDAG-NEXT: v_perm_b32 v2, v5, v4, 0x5040100 +; SDAG-NEXT: v_perm_b32 v3, v7, v6, 0x5040100 +; SDAG-NEXT: ; return to shader part epilog +; +; GISEL-LABEL: v_fptrunc_round_v8f32_to_v8f16_downward: +; GISEL: ; %bb.0: +; GISEL-NEXT: s_setreg_imm32_b32 hwreg(HW_REG_MODE, 3, 1), 1 +; GISEL-NEXT: v_cvt_f16_f32_e32 v0, v0 +; GISEL-NEXT: v_cvt_f16_f32_e32 v2, v2 +; GISEL-NEXT: v_cvt_f16_f32_e32 v4, v4 +; GISEL-NEXT: v_cvt_f16_f32_e32 v6, v6 +; GISEL-NEXT: v_cvt_f16_f32_e32 v1, v1 +; GISEL-NEXT: v_cvt_f16_f32_e32 v3, v3 +; GISEL-NEXT: v_cvt_f16_f32_e32 v5, v5 +; GISEL-NEXT: v_cvt_f16_f32_e32 v7, v7 +; GISEL-NEXT: v_and_b32_e32 v0, 0xffff, v0 +; GISEL-NEXT: v_and_b32_e32 v2, 0xffff, v2 +; GISEL-NEXT: v_and_b32_e32 v4, 0xffff, v4 +; GISEL-NEXT: v_and_b32_e32 v6, 0xffff, v6 +; GISEL-NEXT: v_lshl_or_b32 v0, v1, 16, v0 +; GISEL-NEXT: v_lshl_or_b32 v1, v3, 16, v2 +; GISEL-NEXT: v_lshl_or_b32 v2, v5, 16, v4 +; GISEL-NEXT: v_lshl_or_b32 v3, v7, 16, v6 +; GISEL-NEXT: ; return to shader part epilog + %res = call <8 x half> @llvm.fptrunc.round.v8f16.v8f32(<8 x float> %a, metadata !"round.downward") + ret <8 x half> %res +} diff --git a/llvm/test/CodeGen/AMDGPU/lower-work-group-id-intrinsics-pal.ll b/llvm/test/CodeGen/AMDGPU/lower-work-group-id-intrinsics-pal.ll index cfff0a969da9e7f9c7ca6526d87e29312c6adf0c..14fe4e5f48c67cfdea4c33fe53ca902defb3d618 100644 --- a/llvm/test/CodeGen/AMDGPU/lower-work-group-id-intrinsics-pal.ll +++ b/llvm/test/CodeGen/AMDGPU/lower-work-group-id-intrinsics-pal.ll @@ -1,8 +1,8 @@ ; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py -; RUN: llc -mtriple=amdgcn-amd-hsa -mcpu=gfx900 -mattr=-architected-sgprs -global-isel=0 -verify-machineinstrs < %s | FileCheck -check-prefixes=GFX9,GFX9-SDAG %s -; RUN: llc -mtriple=amdgcn-amd-hsa -mcpu=gfx900 -mattr=-architected-sgprs -global-isel=1 -verify-machineinstrs < %s | FileCheck -check-prefixes=GFX9,GFX9-GISEL %s -; RUN: llc -mtriple=amdgcn-amd-hsa -mcpu=gfx900 -mattr=+architected-sgprs -global-isel=0 -verify-machineinstrs < %s | FileCheck -check-prefixes=GFX9ARCH,GFX9ARCH-SDAG %s -; RUN: llc -mtriple=amdgcn-amd-hsa -mcpu=gfx900 -mattr=+architected-sgprs -global-isel=1 -verify-machineinstrs < %s | FileCheck -check-prefixes=GFX9ARCH,GFX9ARCH-GISEL %s +; RUN: llc -mtriple=amdgcn-amd-hsa -mcpu=gfx900 -mattr=-architected-sgprs -global-isel=0 -verify-machineinstrs < %s | FileCheck -check-prefixes=GFX9 %s +; RUN: llc -mtriple=amdgcn-amd-hsa -mcpu=gfx900 -mattr=-architected-sgprs -global-isel=1 -verify-machineinstrs < %s | FileCheck -check-prefixes=GFX9 %s +; RUN: llc -mtriple=amdgcn-amd-hsa -mcpu=gfx900 -mattr=+architected-sgprs -global-isel=0 -verify-machineinstrs < %s | FileCheck -check-prefixes=GFX9ARCH-SDAG %s +; RUN: llc -mtriple=amdgcn-amd-hsa -mcpu=gfx900 -mattr=+architected-sgprs -global-isel=1 -verify-machineinstrs < %s | FileCheck -check-prefixes=GFX9ARCH-GISEL %s ; RUN: llc -mtriple=amdgcn-amd-amdpal -mcpu=gfx1200 -global-isel=0 -verify-machineinstrs < %s | FileCheck -check-prefixes=GFX12,GFX12-SDAG %s ; RUN: llc -mtriple=amdgcn-amd-amdpal -mcpu=gfx1200 -global-isel=1 -verify-machineinstrs < %s | FileCheck -check-prefixes=GFX12,GFX12-GISEL %s @@ -156,10 +156,37 @@ define amdgpu_gfx void @workgroup_ids_gfx(ptr addrspace(1) %outx, ptr addrspace( ; GFX9-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0) ; GFX9-NEXT: s_setpc_b64 s[30:31] ; -; GFX9ARCH-LABEL: workgroup_ids_gfx: -; GFX9ARCH: ; %bb.0: -; GFX9ARCH-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0) -; GFX9ARCH-NEXT: s_setpc_b64 s[30:31] +; GFX9ARCH-SDAG-LABEL: workgroup_ids_gfx: +; GFX9ARCH-SDAG: ; %bb.0: +; GFX9ARCH-SDAG-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0) +; GFX9ARCH-SDAG-NEXT: v_mov_b32_e32 v6, ttmp9 +; GFX9ARCH-SDAG-NEXT: s_and_b32 s34, ttmp7, 0xffff +; GFX9ARCH-SDAG-NEXT: global_store_dword v[0:1], v6, off +; GFX9ARCH-SDAG-NEXT: s_waitcnt vmcnt(0) +; GFX9ARCH-SDAG-NEXT: v_mov_b32_e32 v0, s34 +; GFX9ARCH-SDAG-NEXT: s_lshr_b32 s34, ttmp7, 16 +; GFX9ARCH-SDAG-NEXT: global_store_dword v[2:3], v0, off +; GFX9ARCH-SDAG-NEXT: s_waitcnt vmcnt(0) +; GFX9ARCH-SDAG-NEXT: v_mov_b32_e32 v0, s34 +; GFX9ARCH-SDAG-NEXT: global_store_dword v[4:5], v0, off +; GFX9ARCH-SDAG-NEXT: s_waitcnt vmcnt(0) +; GFX9ARCH-SDAG-NEXT: s_setpc_b64 s[30:31] +; +; GFX9ARCH-GISEL-LABEL: workgroup_ids_gfx: +; GFX9ARCH-GISEL: ; %bb.0: +; GFX9ARCH-GISEL-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0) +; GFX9ARCH-GISEL-NEXT: v_mov_b32_e32 v6, ttmp9 +; GFX9ARCH-GISEL-NEXT: s_and_b32 s34, ttmp7, 0xffff +; GFX9ARCH-GISEL-NEXT: s_lshr_b32 s35, ttmp7, 16 +; GFX9ARCH-GISEL-NEXT: global_store_dword v[0:1], v6, off +; GFX9ARCH-GISEL-NEXT: s_waitcnt vmcnt(0) +; GFX9ARCH-GISEL-NEXT: v_mov_b32_e32 v0, s34 +; GFX9ARCH-GISEL-NEXT: global_store_dword v[2:3], v0, off +; GFX9ARCH-GISEL-NEXT: s_waitcnt vmcnt(0) +; GFX9ARCH-GISEL-NEXT: v_mov_b32_e32 v0, s35 +; GFX9ARCH-GISEL-NEXT: global_store_dword v[4:5], v0, off +; GFX9ARCH-GISEL-NEXT: s_waitcnt vmcnt(0) +; GFX9ARCH-GISEL-NEXT: s_setpc_b64 s[30:31] ; ; GFX12-LABEL: workgroup_ids_gfx: ; GFX12: ; %bb.0: @@ -168,6 +195,18 @@ define amdgpu_gfx void @workgroup_ids_gfx(ptr addrspace(1) %outx, ptr addrspace( ; GFX12-NEXT: s_wait_samplecnt 0x0 ; GFX12-NEXT: s_wait_bvhcnt 0x0 ; GFX12-NEXT: s_wait_kmcnt 0x0 +; GFX12-NEXT: s_and_b32 s0, ttmp7, 0xffff +; GFX12-NEXT: s_delay_alu instid0(SALU_CYCLE_1) | instskip(SKIP_1) | instid1(SALU_CYCLE_1) +; GFX12-NEXT: v_dual_mov_b32 v6, ttmp9 :: v_dual_mov_b32 v7, s0 +; GFX12-NEXT: s_lshr_b32 s1, ttmp7, 16 +; GFX12-NEXT: v_mov_b32_e32 v8, s1 +; GFX12-NEXT: s_wait_storecnt 0x0 +; GFX12-NEXT: global_store_b32 v[0:1], v6, off scope:SCOPE_SYS +; GFX12-NEXT: s_wait_storecnt 0x0 +; GFX12-NEXT: global_store_b32 v[2:3], v7, off scope:SCOPE_SYS +; GFX12-NEXT: s_wait_storecnt 0x0 +; GFX12-NEXT: global_store_b32 v[4:5], v8, off scope:SCOPE_SYS +; GFX12-NEXT: s_wait_storecnt 0x0 ; GFX12-NEXT: s_setpc_b64 s[30:31] %id.x = call i32 @llvm.amdgcn.workgroup.id.x() %id.y = call i32 @llvm.amdgcn.workgroup.id.y() @@ -177,11 +216,3 @@ define amdgpu_gfx void @workgroup_ids_gfx(ptr addrspace(1) %outx, ptr addrspace( store volatile i32 %id.z, ptr addrspace(1) %outz ret void } - -declare i32 @llvm.amdgcn.workgroup.id.x() -declare i32 @llvm.amdgcn.workgroup.id.y() -declare i32 @llvm.amdgcn.workgroup.id.z() -declare void @llvm.amdgcn.raw.ptr.buffer.store.v3i32(<3 x i32>, ptr addrspace(8), i32, i32, i32 immarg) -;; NOTE: These prefixes are unused and the list is autogenerated. Do not add tests below this line: -; GFX9-GISEL: {{.*}} -; GFX9-SDAG: {{.*}} diff --git a/llvm/test/CodeGen/AMDGPU/mad_64_32.ll b/llvm/test/CodeGen/AMDGPU/mad_64_32.ll index 14bcc4f994f890c0286f75d02ab217c1a19aa790..400298bcff4f9768cbaf7d5bcbb90eb0a4658714 100644 --- a/llvm/test/CodeGen/AMDGPU/mad_64_32.ll +++ b/llvm/test/CodeGen/AMDGPU/mad_64_32.ll @@ -5,6 +5,7 @@ ; RUN: llc -mtriple=amdgcn -mcpu=gfx1100 -verify-machineinstrs < %s | FileCheck -check-prefixes=GFX11,GFX1100 %s ; RUN: llc -mtriple=amdgcn -mcpu=gfx1150 -verify-machineinstrs < %s | FileCheck -check-prefixes=GFX11,GFX1150 %s ; RUN: llc -mtriple=amdgcn -mcpu=gfx1200 -verify-machineinstrs < %s | FileCheck -check-prefixes=GFX12 %s +; RUN: llc -mtriple=amdgcn -mcpu=gfx11-generic --amdhsa-code-object-version=6 -verify-machineinstrs < %s | FileCheck -check-prefixes=GFX11,GFX1100 %s ; On GFX11, ensure vdst and src2 do not partially overlap. Full overlap is ok. diff --git a/llvm/test/CodeGen/AMDGPU/mmra.ll b/llvm/test/CodeGen/AMDGPU/mmra.ll new file mode 100644 index 0000000000000000000000000000000000000000..d9b48f79739b677b6a4d6bfcde153c2bddac69f0 --- /dev/null +++ b/llvm/test/CodeGen/AMDGPU/mmra.ll @@ -0,0 +1,189 @@ +; NOTE: Assertions have been autogenerated by utils/update_mir_test_checks.py UTC_ARGS: --version 2 +; RUN: llc -march=amdgcn -mcpu=gfx900 -stop-after=finalize-isel < %s | FileCheck %s + +declare void @readsMem(ptr) #0 +declare void @writesMem(ptr) #1 + +define void @fence_loads(ptr %ptr) { + ; CHECK-LABEL: name: fence_loads + ; CHECK: bb.0 (%ir-block.0): + ; CHECK-NEXT: liveins: $vgpr0, $vgpr1 + ; CHECK-NEXT: {{ $}} + ; CHECK-NEXT: [[COPY:%[0-9]+]]:vgpr_32 = COPY $vgpr1 + ; CHECK-NEXT: [[COPY1:%[0-9]+]]:vgpr_32 = COPY $vgpr0 + ; CHECK-NEXT: [[DEF:%[0-9]+]]:sgpr_32 = IMPLICIT_DEF + ; CHECK-NEXT: [[DEF1:%[0-9]+]]:sgpr_32 = IMPLICIT_DEF + ; CHECK-NEXT: [[REG_SEQUENCE:%[0-9]+]]:vreg_64 = REG_SEQUENCE [[COPY1]], %subreg.sub0, [[COPY]], %subreg.sub1 + ; CHECK-NEXT: ATOMIC_FENCE 5, 1, mmra !0 + ; CHECK-NEXT: [[COPY2:%[0-9]+]]:vreg_64 = COPY [[REG_SEQUENCE]], mmra !1 + ; CHECK-NEXT: [[FLAT_LOAD_UBYTE:%[0-9]+]]:vgpr_32 = FLAT_LOAD_UBYTE [[COPY2]], 0, 0, implicit $exec, implicit $flat_scr, mmra !1 :: (load acquire (s8) from %ir.ptr, align 4) + ; CHECK-NEXT: [[S_MOV_B32_:%[0-9]+]]:sreg_32 = S_MOV_B32 1, mmra !2 + ; CHECK-NEXT: [[COPY3:%[0-9]+]]:vreg_64 = COPY [[REG_SEQUENCE]], mmra !2 + ; CHECK-NEXT: [[COPY4:%[0-9]+]]:vgpr_32 = COPY [[S_MOV_B32_]], mmra !2 + ; CHECK-NEXT: FLAT_STORE_BYTE [[COPY3]], killed [[COPY4]], 0, 0, implicit $exec, implicit $flat_scr, mmra !2 :: (store release (s8) into %ir.ptr, align 4) + ; CHECK-NEXT: SI_RETURN + fence release, !mmra !0 + %ld = load atomic i8, ptr %ptr acquire, align 4, !mmra !2 + store atomic i8 1, ptr %ptr release, align 4, !mmra !1 + ret void +} + +define void @atomicrmw_acq(ptr %ptr) { + ; CHECK-LABEL: name: atomicrmw_acq + ; CHECK: bb.0 (%ir-block.0): + ; CHECK-NEXT: liveins: $vgpr0, $vgpr1 + ; CHECK-NEXT: {{ $}} + ; CHECK-NEXT: [[COPY:%[0-9]+]]:vgpr_32 = COPY $vgpr1 + ; CHECK-NEXT: [[COPY1:%[0-9]+]]:vgpr_32 = COPY $vgpr0 + ; CHECK-NEXT: [[DEF:%[0-9]+]]:sgpr_32 = IMPLICIT_DEF + ; CHECK-NEXT: [[DEF1:%[0-9]+]]:sgpr_32 = IMPLICIT_DEF + ; CHECK-NEXT: [[REG_SEQUENCE:%[0-9]+]]:vreg_64 = REG_SEQUENCE [[COPY1]], %subreg.sub0, [[COPY]], %subreg.sub1 + ; CHECK-NEXT: [[COPY2:%[0-9]+]]:vreg_64 = COPY [[REG_SEQUENCE]], mmra !1 + ; CHECK-NEXT: [[FLAT_LOAD_UBYTE:%[0-9]+]]:vgpr_32 = FLAT_LOAD_UBYTE killed [[COPY2]], 0, 0, implicit $exec, implicit $flat_scr, mmra !1 :: (load acquire (s8) from %ir.ptr) + ; CHECK-NEXT: SI_RETURN + %old.2 = atomicrmw add ptr %ptr, i8 0 acquire, !mmra !2 + ret void +} + +define void @atomicrmw_rel(ptr %ptr) { + ; CHECK-LABEL: name: atomicrmw_rel + ; CHECK: bb.0 (%ir-block.0): + ; CHECK-NEXT: successors: %bb.1(0x80000000) + ; CHECK-NEXT: liveins: $vgpr0, $vgpr1 + ; CHECK-NEXT: {{ $}} + ; CHECK-NEXT: [[COPY:%[0-9]+]]:vgpr_32 = COPY $vgpr1 + ; CHECK-NEXT: [[COPY1:%[0-9]+]]:vgpr_32 = COPY $vgpr0 + ; CHECK-NEXT: [[DEF:%[0-9]+]]:sgpr_32 = IMPLICIT_DEF + ; CHECK-NEXT: [[DEF1:%[0-9]+]]:sgpr_32 = IMPLICIT_DEF + ; CHECK-NEXT: [[REG_SEQUENCE:%[0-9]+]]:vreg_64 = REG_SEQUENCE [[COPY1]], %subreg.sub0, [[COPY]], %subreg.sub1 + ; CHECK-NEXT: [[COPY2:%[0-9]+]]:vgpr_32 = COPY [[REG_SEQUENCE]].sub1 + ; CHECK-NEXT: [[COPY3:%[0-9]+]]:vgpr_32 = COPY [[REG_SEQUENCE]].sub0 + ; CHECK-NEXT: [[S_MOV_B32_:%[0-9]+]]:sreg_32 = S_MOV_B32 -4 + ; CHECK-NEXT: [[V_AND_B32_e64_:%[0-9]+]]:vgpr_32 = V_AND_B32_e64 [[COPY3]], killed [[S_MOV_B32_]], implicit $exec + ; CHECK-NEXT: [[DEF2:%[0-9]+]]:sgpr_32 = IMPLICIT_DEF + ; CHECK-NEXT: [[DEF3:%[0-9]+]]:sgpr_32 = IMPLICIT_DEF + ; CHECK-NEXT: [[REG_SEQUENCE1:%[0-9]+]]:vreg_64 = REG_SEQUENCE [[V_AND_B32_e64_]], %subreg.sub0, [[COPY2]], %subreg.sub1 + ; CHECK-NEXT: [[COPY4:%[0-9]+]]:vreg_64 = COPY [[REG_SEQUENCE1]] + ; CHECK-NEXT: [[S_MOV_B32_1:%[0-9]+]]:sreg_32 = S_MOV_B32 3 + ; CHECK-NEXT: [[V_AND_B32_e64_1:%[0-9]+]]:vgpr_32 = V_AND_B32_e64 [[COPY3]], [[S_MOV_B32_1]], implicit $exec + ; CHECK-NEXT: [[V_LSHLREV_B32_e64_:%[0-9]+]]:vgpr_32 = V_LSHLREV_B32_e64 [[S_MOV_B32_1]], killed [[V_AND_B32_e64_1]], implicit $exec + ; CHECK-NEXT: [[S_MOV_B32_2:%[0-9]+]]:sreg_32 = S_MOV_B32 255 + ; CHECK-NEXT: [[V_LSHLREV_B32_e64_1:%[0-9]+]]:vgpr_32 = V_LSHLREV_B32_e64 killed [[V_LSHLREV_B32_e64_]], killed [[S_MOV_B32_2]], implicit $exec + ; CHECK-NEXT: [[V_NOT_B32_e32_:%[0-9]+]]:vgpr_32 = V_NOT_B32_e32 [[V_LSHLREV_B32_e64_1]], implicit $exec + ; CHECK-NEXT: [[COPY5:%[0-9]+]]:vreg_64 = COPY [[REG_SEQUENCE1]], mmra !2 + ; CHECK-NEXT: [[FLAT_LOAD_DWORD:%[0-9]+]]:vgpr_32 = FLAT_LOAD_DWORD [[COPY5]], 0, 0, implicit $exec, implicit $flat_scr, mmra !2 :: (load (s32) from %ir.AlignedAddr) + ; CHECK-NEXT: [[S_MOV_B64_:%[0-9]+]]:sreg_64 = S_MOV_B64 0 + ; CHECK-NEXT: {{ $}} + ; CHECK-NEXT: bb.1.atomicrmw.start: + ; CHECK-NEXT: successors: %bb.2(0x04000000), %bb.1(0x7c000000) + ; CHECK-NEXT: {{ $}} + ; CHECK-NEXT: [[PHI:%[0-9]+]]:sreg_64 = PHI [[S_MOV_B64_]], %bb.0, %7, %bb.1 + ; CHECK-NEXT: [[PHI1:%[0-9]+]]:vgpr_32 = PHI [[FLAT_LOAD_DWORD]], %bb.0, %6, %bb.1 + ; CHECK-NEXT: [[V_OR_B32_e64_:%[0-9]+]]:vgpr_32 = V_OR_B32_e64 [[V_NOT_B32_e32_]], [[V_LSHLREV_B32_e64_1]], implicit $exec + ; CHECK-NEXT: [[V_AND_B32_e64_2:%[0-9]+]]:vgpr_32 = V_AND_B32_e64 [[PHI1]], killed [[V_OR_B32_e64_]], implicit $exec + ; CHECK-NEXT: [[DEF4:%[0-9]+]]:sgpr_32 = IMPLICIT_DEF + ; CHECK-NEXT: [[DEF5:%[0-9]+]]:sgpr_32 = IMPLICIT_DEF + ; CHECK-NEXT: [[REG_SEQUENCE2:%[0-9]+]]:vreg_64 = REG_SEQUENCE [[V_AND_B32_e64_2]], %subreg.sub0, [[PHI1]], %subreg.sub1, mmra !2 + ; CHECK-NEXT: [[COPY6:%[0-9]+]]:vreg_64 = COPY [[REG_SEQUENCE2]], mmra !2 + ; CHECK-NEXT: [[FLAT_ATOMIC_CMPSWAP_RTN:%[0-9]+]]:vgpr_32 = FLAT_ATOMIC_CMPSWAP_RTN [[COPY4]], killed [[COPY6]], 0, 1, implicit $exec, implicit $flat_scr, mmra !2 :: (load store release monotonic (s32) on %ir.AlignedAddr) + ; CHECK-NEXT: [[V_CMP_EQ_U32_e64_:%[0-9]+]]:sreg_64 = V_CMP_EQ_U32_e64 [[FLAT_ATOMIC_CMPSWAP_RTN]], [[PHI1]], implicit $exec, mmra !2 + ; CHECK-NEXT: [[SI_IF_BREAK:%[0-9]+]]:sreg_64 = SI_IF_BREAK killed [[V_CMP_EQ_U32_e64_]], [[PHI]], implicit-def dead $scc + ; CHECK-NEXT: SI_LOOP [[SI_IF_BREAK]], %bb.1, implicit-def dead $exec, implicit-def dead $scc, implicit $exec + ; CHECK-NEXT: S_BRANCH %bb.2 + ; CHECK-NEXT: {{ $}} + ; CHECK-NEXT: bb.2.atomicrmw.end: + ; CHECK-NEXT: [[PHI2:%[0-9]+]]:sreg_64 = PHI [[SI_IF_BREAK]], %bb.1 + ; CHECK-NEXT: SI_END_CF [[PHI2]], implicit-def dead $exec, implicit-def dead $scc, implicit $exec + ; CHECK-NEXT: SI_RETURN + %old.2 = atomicrmw add ptr %ptr, i8 0 release, !mmra !1 + ret void +} + +define void @cmpxchg(ptr %ptr) { + ; CHECK-LABEL: name: cmpxchg + ; CHECK: bb.0 (%ir-block.0): + ; CHECK-NEXT: successors: %bb.1(0x80000000) + ; CHECK-NEXT: liveins: $vgpr0, $vgpr1 + ; CHECK-NEXT: {{ $}} + ; CHECK-NEXT: [[COPY:%[0-9]+]]:vgpr_32 = COPY $vgpr1 + ; CHECK-NEXT: [[COPY1:%[0-9]+]]:vgpr_32 = COPY $vgpr0 + ; CHECK-NEXT: [[DEF:%[0-9]+]]:sgpr_32 = IMPLICIT_DEF + ; CHECK-NEXT: [[DEF1:%[0-9]+]]:sgpr_32 = IMPLICIT_DEF + ; CHECK-NEXT: [[REG_SEQUENCE:%[0-9]+]]:vreg_64 = REG_SEQUENCE [[COPY1]], %subreg.sub0, [[COPY]], %subreg.sub1 + ; CHECK-NEXT: [[COPY2:%[0-9]+]]:vgpr_32 = COPY [[REG_SEQUENCE]].sub1 + ; CHECK-NEXT: [[COPY3:%[0-9]+]]:vgpr_32 = COPY [[REG_SEQUENCE]].sub0 + ; CHECK-NEXT: [[S_MOV_B32_:%[0-9]+]]:sreg_32 = S_MOV_B32 -4 + ; CHECK-NEXT: [[V_AND_B32_e64_:%[0-9]+]]:vgpr_32 = V_AND_B32_e64 [[COPY3]], killed [[S_MOV_B32_]], implicit $exec + ; CHECK-NEXT: [[DEF2:%[0-9]+]]:sgpr_32 = IMPLICIT_DEF + ; CHECK-NEXT: [[DEF3:%[0-9]+]]:sgpr_32 = IMPLICIT_DEF + ; CHECK-NEXT: [[REG_SEQUENCE1:%[0-9]+]]:vreg_64 = REG_SEQUENCE [[V_AND_B32_e64_]], %subreg.sub0, [[COPY2]], %subreg.sub1 + ; CHECK-NEXT: [[COPY4:%[0-9]+]]:vreg_64 = COPY [[REG_SEQUENCE1]] + ; CHECK-NEXT: [[S_MOV_B32_1:%[0-9]+]]:sreg_32 = S_MOV_B32 3 + ; CHECK-NEXT: [[V_AND_B32_e64_1:%[0-9]+]]:vgpr_32 = V_AND_B32_e64 [[COPY3]], [[S_MOV_B32_1]], implicit $exec + ; CHECK-NEXT: [[V_LSHLREV_B32_e64_:%[0-9]+]]:vgpr_32 = V_LSHLREV_B32_e64 [[S_MOV_B32_1]], killed [[V_AND_B32_e64_1]], implicit $exec + ; CHECK-NEXT: [[S_MOV_B32_2:%[0-9]+]]:sreg_32 = S_MOV_B32 255 + ; CHECK-NEXT: [[V_LSHLREV_B32_e64_1:%[0-9]+]]:vgpr_32 = V_LSHLREV_B32_e64 [[V_LSHLREV_B32_e64_]], killed [[S_MOV_B32_2]], implicit $exec + ; CHECK-NEXT: [[V_NOT_B32_e32_:%[0-9]+]]:vgpr_32 = V_NOT_B32_e32 killed [[V_LSHLREV_B32_e64_1]], implicit $exec + ; CHECK-NEXT: [[S_MOV_B32_3:%[0-9]+]]:sreg_32 = S_MOV_B32 1 + ; CHECK-NEXT: [[V_LSHLREV_B32_e64_2:%[0-9]+]]:vgpr_32 = V_LSHLREV_B32_e64 [[V_LSHLREV_B32_e64_]], killed [[S_MOV_B32_3]], implicit $exec + ; CHECK-NEXT: [[COPY5:%[0-9]+]]:vreg_64 = COPY [[REG_SEQUENCE1]], mmra !1 + ; CHECK-NEXT: [[FLAT_LOAD_DWORD:%[0-9]+]]:vgpr_32 = FLAT_LOAD_DWORD [[COPY5]], 0, 0, implicit $exec, implicit $flat_scr, mmra !1 :: (load (s32) from %ir.AlignedAddr) + ; CHECK-NEXT: [[V_AND_B32_e64_2:%[0-9]+]]:vgpr_32 = V_AND_B32_e64 killed [[FLAT_LOAD_DWORD]], [[V_NOT_B32_e32_]], implicit $exec + ; CHECK-NEXT: [[S_MOV_B64_:%[0-9]+]]:sreg_64 = S_MOV_B64 0 + ; CHECK-NEXT: [[DEF4:%[0-9]+]]:sreg_64 = IMPLICIT_DEF + ; CHECK-NEXT: {{ $}} + ; CHECK-NEXT: bb.1.partword.cmpxchg.loop: + ; CHECK-NEXT: successors: %bb.2(0x40000000), %bb.3(0x40000000) + ; CHECK-NEXT: {{ $}} + ; CHECK-NEXT: [[PHI:%[0-9]+]]:sreg_64 = PHI [[DEF4]], %bb.0, %12, %bb.3 + ; CHECK-NEXT: [[PHI1:%[0-9]+]]:sreg_64 = PHI [[S_MOV_B64_]], %bb.0, %13, %bb.3 + ; CHECK-NEXT: [[PHI2:%[0-9]+]]:vgpr_32 = PHI [[V_AND_B32_e64_2]], %bb.0, %11, %bb.3 + ; CHECK-NEXT: [[V_OR_B32_e64_:%[0-9]+]]:vgpr_32 = V_OR_B32_e64 [[PHI2]], [[V_LSHLREV_B32_e64_2]], implicit $exec + ; CHECK-NEXT: [[DEF5:%[0-9]+]]:sgpr_32 = IMPLICIT_DEF + ; CHECK-NEXT: [[DEF6:%[0-9]+]]:sgpr_32 = IMPLICIT_DEF + ; CHECK-NEXT: [[REG_SEQUENCE2:%[0-9]+]]:vreg_64 = REG_SEQUENCE [[V_OR_B32_e64_]], %subreg.sub0, [[PHI2]], %subreg.sub1, mmra !1 + ; CHECK-NEXT: [[COPY6:%[0-9]+]]:vreg_64 = COPY [[REG_SEQUENCE2]], mmra !1 + ; CHECK-NEXT: [[FLAT_ATOMIC_CMPSWAP_RTN:%[0-9]+]]:vgpr_32 = FLAT_ATOMIC_CMPSWAP_RTN [[COPY4]], killed [[COPY6]], 0, 1, implicit $exec, implicit $flat_scr, mmra !1 :: (load store acquire acquire (s32) on %ir.AlignedAddr) + ; CHECK-NEXT: [[V_CMP_NE_U32_e64_:%[0-9]+]]:sreg_64 = V_CMP_NE_U32_e64 [[FLAT_ATOMIC_CMPSWAP_RTN]], [[PHI2]], implicit $exec + ; CHECK-NEXT: [[S_MOV_B64_1:%[0-9]+]]:sreg_64 = S_MOV_B64 -1 + ; CHECK-NEXT: [[DEF7:%[0-9]+]]:sreg_32 = IMPLICIT_DEF + ; CHECK-NEXT: [[COPY7:%[0-9]+]]:vgpr_32 = COPY [[DEF7]] + ; CHECK-NEXT: [[S_OR_B64_:%[0-9]+]]:sreg_64 = S_OR_B64 [[PHI]], $exec, implicit-def $scc + ; CHECK-NEXT: [[SI_IF:%[0-9]+]]:sreg_64 = SI_IF killed [[V_CMP_NE_U32_e64_]], %bb.3, implicit-def dead $exec, implicit-def dead $scc, implicit $exec + ; CHECK-NEXT: S_BRANCH %bb.2 + ; CHECK-NEXT: {{ $}} + ; CHECK-NEXT: bb.2.partword.cmpxchg.failure: + ; CHECK-NEXT: successors: %bb.3(0x80000000) + ; CHECK-NEXT: {{ $}} + ; CHECK-NEXT: [[V_AND_B32_e64_3:%[0-9]+]]:vgpr_32 = V_AND_B32_e64 [[FLAT_ATOMIC_CMPSWAP_RTN]], [[V_NOT_B32_e32_]], implicit $exec + ; CHECK-NEXT: [[V_CMP_EQ_U32_e64_:%[0-9]+]]:sreg_64 = V_CMP_EQ_U32_e64 [[PHI2]], [[V_AND_B32_e64_3]], implicit $exec + ; CHECK-NEXT: [[S_ANDN2_B64_:%[0-9]+]]:sreg_64 = S_ANDN2_B64 [[S_OR_B64_]], $exec, implicit-def $scc + ; CHECK-NEXT: [[S_AND_B64_:%[0-9]+]]:sreg_64 = S_AND_B64 [[V_CMP_EQ_U32_e64_]], $exec, implicit-def $scc + ; CHECK-NEXT: [[S_OR_B64_1:%[0-9]+]]:sreg_64 = S_OR_B64 [[S_ANDN2_B64_]], [[S_AND_B64_]], implicit-def $scc + ; CHECK-NEXT: {{ $}} + ; CHECK-NEXT: bb.3.Flow: + ; CHECK-NEXT: successors: %bb.4(0x04000000), %bb.1(0x7c000000) + ; CHECK-NEXT: {{ $}} + ; CHECK-NEXT: [[PHI3:%[0-9]+]]:sreg_64 = PHI [[S_OR_B64_]], %bb.1, [[S_OR_B64_1]], %bb.2 + ; CHECK-NEXT: [[PHI4:%[0-9]+]]:vgpr_32 = PHI [[COPY7]], %bb.1, [[V_AND_B32_e64_3]], %bb.2 + ; CHECK-NEXT: SI_END_CF [[SI_IF]], implicit-def dead $exec, implicit-def dead $scc, implicit $exec + ; CHECK-NEXT: [[COPY8:%[0-9]+]]:sreg_64 = COPY [[PHI3]] + ; CHECK-NEXT: [[SI_IF_BREAK:%[0-9]+]]:sreg_64 = SI_IF_BREAK [[COPY8]], [[PHI1]], implicit-def dead $scc + ; CHECK-NEXT: SI_LOOP [[SI_IF_BREAK]], %bb.1, implicit-def dead $exec, implicit-def dead $scc, implicit $exec + ; CHECK-NEXT: S_BRANCH %bb.4 + ; CHECK-NEXT: {{ $}} + ; CHECK-NEXT: bb.4.partword.cmpxchg.end: + ; CHECK-NEXT: [[PHI5:%[0-9]+]]:sreg_64 = PHI [[SI_IF_BREAK]], %bb.3 + ; CHECK-NEXT: [[PHI6:%[0-9]+]]:vgpr_32 = PHI [[FLAT_ATOMIC_CMPSWAP_RTN]], %bb.3 + ; CHECK-NEXT: SI_END_CF [[PHI5]], implicit-def dead $exec, implicit-def dead $scc, implicit $exec + ; CHECK-NEXT: SI_RETURN + %pair = cmpxchg ptr %ptr, i8 0, i8 1 acquire acquire, !mmra !2 + ret void +} + +attributes #0 = { memory(read) } +attributes #1 = { memory(write) } + +!0 = !{!"foo", !"bar"} +!1 = !{!"bux", !"baz"} +!2 = !{!0, !1} diff --git a/llvm/test/CodeGen/AMDGPU/mode-register-fpconstrain.ll b/llvm/test/CodeGen/AMDGPU/mode-register-fpconstrain.ll new file mode 100644 index 0000000000000000000000000000000000000000..2403aeaa4428ad2523acf28722fc0d0a6535da09 --- /dev/null +++ b/llvm/test/CodeGen/AMDGPU/mode-register-fpconstrain.ll @@ -0,0 +1,43 @@ +; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py UTC_ARGS: --version 4 +; RUN: llc -mtriple=amdgcn-amd-amdhsa -mcpu=gfx900 %s -o - | FileCheck -check-prefix=GCN %s + +; The si-mode-register pass is changing the default mode for FP constrained operations. +; It must ignore for strictfp functions. + +define double @ignoreStrictfp(double noundef %a, double noundef %b) #0 { +; GCN-LABEL: ignoreStrictfp: +; GCN: ; %bb.0: +; GCN-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0) +; GCN-NEXT: s_setreg_imm32_b32 hwreg(HW_REG_MODE, 2, 2), 1 +; GCN-NEXT: s_nop 1 +; GCN-NEXT: s_setreg_imm32_b32 hwreg(HW_REG_MODE, 2, 1), 0 +; GCN-NEXT: v_add_f64 v[0:1], v[0:1], v[2:3] +; GCN-NEXT: s_setpc_b64 s[30:31] + tail call void @llvm.amdgcn.s.setreg(i32 2177, i32 1) + %val = tail call double @llvm.experimental.constrained.fadd.f64(double %a, double %b, metadata !"round.dynamic", metadata !"fpexcept.strict") #0 + ret double %val +} + +define double @set_fpenv(double noundef %a, double noundef %b) #0 { +; GCN-LABEL: set_fpenv: +; GCN: ; %bb.0: ; %entry +; GCN-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0) +; GCN-NEXT: s_setreg_imm32_b32 hwreg(HW_REG_MODE, 0, 23), 4 +; GCN-NEXT: s_setreg_imm32_b32 hwreg(HW_REG_TRAPSTS, 0, 5), 0 +; GCN-NEXT: s_nop 0 +; GCN-NEXT: s_setreg_imm32_b32 hwreg(HW_REG_MODE, 2, 1), 0 +; GCN-NEXT: v_add_f64 v[0:1], v[0:1], v[2:3] +; GCN-NEXT: s_setpc_b64 s[30:31] +entry: + call void @llvm.set.fpenv.i64(i64 4) + %val = tail call double @llvm.experimental.constrained.fadd.f64(double %a, double %b, metadata !"round.dynamic", metadata !"fpexcept.strict") #0 + ret double %val +} + +declare void @llvm.amdgcn.s.setreg(i32 immarg, i32) + +declare double @llvm.experimental.constrained.fadd.f64(double, double, metadata, metadata) + +declare void @llvm.set.fpenv.i64(i64) + +attributes #0 = { strictfp } diff --git a/llvm/test/CodeGen/AMDGPU/trap-abis.ll b/llvm/test/CodeGen/AMDGPU/trap-abis.ll index 3cd6c98ef4b8e0002e58e9524d6d56798c9fcc1b..dcc5fbd142c42723fe6ad74435c5b9e47ab3af2c 100644 --- a/llvm/test/CodeGen/AMDGPU/trap-abis.ll +++ b/llvm/test/CodeGen/AMDGPU/trap-abis.ll @@ -3,6 +3,8 @@ ; RUN: llc %s -o - -mtriple=amdgcn-amd-amdhsa -mcpu=gfx803 -verify-machineinstrs | FileCheck --check-prefix=HSA-TRAP-GFX803 %s ; RUN: llc %s -o - -mtriple=amdgcn-amd-amdhsa -mcpu=gfx900 -verify-machineinstrs | FileCheck --check-prefix=HSA-TRAP-GFX900 %s ; RUN: llc %s -o - -mtriple=amdgcn-amd-amdhsa -mcpu=gfx900 -mattr=-trap-handler -verify-machineinstrs | FileCheck --check-prefix=HSA-NOTRAP-GFX900 %s +; RUN: llc %s -o - -mtriple=amdgcn-amd-amdhsa -mcpu=gfx1100 -verify-machineinstrs | FileCheck --check-prefix=HSA-TRAP-GFX1100 %s +; RUN: llc %s -o - -O0 -mtriple=amdgcn-amd-amdhsa -mcpu=gfx1100 -verify-machineinstrs | FileCheck --check-prefix=HSA-TRAP-GFX1100-O0 %s declare void @llvm.trap() #0 declare void @llvm.debugtrap() #1 @@ -49,6 +51,48 @@ define amdgpu_kernel void @trap(ptr addrspace(1) nocapture readonly %arg0) { ; HSA-NOTRAP-GFX900-NEXT: global_store_dword v0, v1, s[0:1] ; HSA-NOTRAP-GFX900-NEXT: s_waitcnt vmcnt(0) ; HSA-NOTRAP-GFX900-NEXT: s_endpgm +; +; HSA-TRAP-GFX1100-LABEL: trap: +; HSA-TRAP-GFX1100: ; %bb.0: +; HSA-TRAP-GFX1100-NEXT: s_load_b64 s[0:1], s[0:1], 0x0 +; HSA-TRAP-GFX1100-NEXT: v_dual_mov_b32 v0, 0 :: v_dual_mov_b32 v1, 1 +; HSA-TRAP-GFX1100-NEXT: s_mov_b32 ttmp2, m0 +; HSA-TRAP-GFX1100-NEXT: s_waitcnt lgkmcnt(0) +; HSA-TRAP-GFX1100-NEXT: global_store_b32 v0, v1, s[0:1] dlc +; HSA-TRAP-GFX1100-NEXT: s_waitcnt_vscnt null, 0x0 +; HSA-TRAP-GFX1100-NEXT: s_trap 2 +; HSA-TRAP-GFX1100-NEXT: s_sendmsg_rtn_b32 s0, sendmsg(MSG_RTN_GET_DOORBELL) +; HSA-TRAP-GFX1100-NEXT: s_waitcnt lgkmcnt(0) +; HSA-TRAP-GFX1100-NEXT: s_and_b32 s0, s0, 0x3ff +; HSA-TRAP-GFX1100-NEXT: s_delay_alu instid0(SALU_CYCLE_1) | instskip(NEXT) | instid1(SALU_CYCLE_1) +; HSA-TRAP-GFX1100-NEXT: s_bitset1_b32 s0, 10 +; HSA-TRAP-GFX1100-NEXT: s_mov_b32 m0, s0 +; HSA-TRAP-GFX1100-NEXT: s_sendmsg sendmsg(MSG_INTERRUPT) +; HSA-TRAP-GFX1100-NEXT: s_mov_b32 m0, ttmp2 +; HSA-TRAP-GFX1100-NEXT: .LBB0_1: ; =>This Inner Loop Header: Depth=1 +; HSA-TRAP-GFX1100-NEXT: s_sethalt 5 +; HSA-TRAP-GFX1100-NEXT: s_branch .LBB0_1 +; +; HSA-TRAP-GFX1100-O0-LABEL: trap: +; HSA-TRAP-GFX1100-O0: ; %bb.0: +; HSA-TRAP-GFX1100-O0-NEXT: s_load_b64 s[0:1], s[4:5], 0x0 +; HSA-TRAP-GFX1100-O0-NEXT: v_mov_b32_e32 v0, 0 +; HSA-TRAP-GFX1100-O0-NEXT: v_mov_b32_e32 v1, 1 +; HSA-TRAP-GFX1100-O0-NEXT: s_waitcnt lgkmcnt(0) +; HSA-TRAP-GFX1100-O0-NEXT: global_store_b32 v0, v1, s[0:1] dlc +; HSA-TRAP-GFX1100-O0-NEXT: s_waitcnt_vscnt null, 0x0 +; HSA-TRAP-GFX1100-O0-NEXT: s_trap 2 +; HSA-TRAP-GFX1100-O0-NEXT: s_sendmsg_rtn_b32 s0, sendmsg(MSG_RTN_GET_DOORBELL) +; HSA-TRAP-GFX1100-O0-NEXT: s_mov_b32 ttmp2, m0 +; HSA-TRAP-GFX1100-O0-NEXT: s_waitcnt lgkmcnt(0) +; HSA-TRAP-GFX1100-O0-NEXT: s_and_b32 s0, s0, 0x3ff +; HSA-TRAP-GFX1100-O0-NEXT: s_or_b32 s0, s0, 0x400 +; HSA-TRAP-GFX1100-O0-NEXT: s_mov_b32 m0, s0 +; HSA-TRAP-GFX1100-O0-NEXT: s_sendmsg sendmsg(MSG_INTERRUPT) +; HSA-TRAP-GFX1100-O0-NEXT: s_mov_b32 m0, ttmp2 +; HSA-TRAP-GFX1100-O0-NEXT: .LBB0_1: ; =>This Inner Loop Header: Depth=1 +; HSA-TRAP-GFX1100-O0-NEXT: s_sethalt 5 +; HSA-TRAP-GFX1100-O0-NEXT: s_branch .LBB0_1 store volatile i32 1, ptr addrspace(1) %arg0 call void @llvm.trap() unreachable @@ -128,6 +172,84 @@ define amdgpu_kernel void @non_entry_trap(ptr addrspace(1) nocapture readonly %a ; HSA-NOTRAP-GFX900-NEXT: s_endpgm ; HSA-NOTRAP-GFX900-NEXT: .LBB1_2: ; %trap ; HSA-NOTRAP-GFX900-NEXT: s_endpgm +; +; HSA-TRAP-GFX1100-LABEL: non_entry_trap: +; HSA-TRAP-GFX1100: ; %bb.0: ; %entry +; HSA-TRAP-GFX1100-NEXT: s_load_b64 s[0:1], s[0:1], 0x0 +; HSA-TRAP-GFX1100-NEXT: v_mov_b32_e32 v0, 0 +; HSA-TRAP-GFX1100-NEXT: s_waitcnt lgkmcnt(0) +; HSA-TRAP-GFX1100-NEXT: global_load_b32 v1, v0, s[0:1] glc dlc +; HSA-TRAP-GFX1100-NEXT: s_waitcnt vmcnt(0) +; HSA-TRAP-GFX1100-NEXT: v_cmp_eq_u32_e32 vcc_lo, -1, v1 +; HSA-TRAP-GFX1100-NEXT: s_cbranch_vccz .LBB1_2 +; HSA-TRAP-GFX1100-NEXT: ; %bb.1: ; %ret +; HSA-TRAP-GFX1100-NEXT: v_mov_b32_e32 v1, 3 +; HSA-TRAP-GFX1100-NEXT: global_store_b32 v0, v1, s[0:1] dlc +; HSA-TRAP-GFX1100-NEXT: s_waitcnt_vscnt null, 0x0 +; HSA-TRAP-GFX1100-NEXT: s_nop 0 +; HSA-TRAP-GFX1100-NEXT: s_sendmsg sendmsg(MSG_DEALLOC_VGPRS) +; HSA-TRAP-GFX1100-NEXT: s_endpgm +; HSA-TRAP-GFX1100-NEXT: .LBB1_2: ; %trap +; HSA-TRAP-GFX1100-NEXT: s_trap 2 +; HSA-TRAP-GFX1100-NEXT: s_sendmsg_rtn_b32 s0, sendmsg(MSG_RTN_GET_DOORBELL) +; HSA-TRAP-GFX1100-NEXT: s_mov_b32 ttmp2, m0 +; HSA-TRAP-GFX1100-NEXT: s_waitcnt lgkmcnt(0) +; HSA-TRAP-GFX1100-NEXT: s_and_b32 s0, s0, 0x3ff +; HSA-TRAP-GFX1100-NEXT: s_delay_alu instid0(SALU_CYCLE_1) | instskip(NEXT) | instid1(SALU_CYCLE_1) +; HSA-TRAP-GFX1100-NEXT: s_bitset1_b32 s0, 10 +; HSA-TRAP-GFX1100-NEXT: s_mov_b32 m0, s0 +; HSA-TRAP-GFX1100-NEXT: s_sendmsg sendmsg(MSG_INTERRUPT) +; HSA-TRAP-GFX1100-NEXT: s_mov_b32 m0, ttmp2 +; HSA-TRAP-GFX1100-NEXT: .LBB1_3: ; =>This Inner Loop Header: Depth=1 +; HSA-TRAP-GFX1100-NEXT: s_sethalt 5 +; HSA-TRAP-GFX1100-NEXT: s_branch .LBB1_3 +; +; HSA-TRAP-GFX1100-O0-LABEL: non_entry_trap: +; HSA-TRAP-GFX1100-O0: ; %bb.0: ; %entry +; HSA-TRAP-GFX1100-O0-NEXT: ; implicit-def: $vgpr0 : SGPR spill to VGPR lane +; HSA-TRAP-GFX1100-O0-NEXT: s_load_b64 s[0:1], s[4:5], 0x0 +; HSA-TRAP-GFX1100-O0-NEXT: s_waitcnt lgkmcnt(0) +; HSA-TRAP-GFX1100-O0-NEXT: s_mov_b64 s[2:3], s[0:1] +; HSA-TRAP-GFX1100-O0-NEXT: v_writelane_b32 v0, s2, 0 +; HSA-TRAP-GFX1100-O0-NEXT: v_writelane_b32 v0, s3, 1 +; HSA-TRAP-GFX1100-O0-NEXT: s_or_saveexec_b32 s6, -1 +; HSA-TRAP-GFX1100-O0-NEXT: scratch_store_b32 off, v0, off ; 4-byte Folded Spill +; HSA-TRAP-GFX1100-O0-NEXT: s_mov_b32 exec_lo, s6 +; HSA-TRAP-GFX1100-O0-NEXT: v_mov_b32_e32 v0, 0 +; HSA-TRAP-GFX1100-O0-NEXT: global_load_b32 v0, v0, s[0:1] glc dlc +; HSA-TRAP-GFX1100-O0-NEXT: s_waitcnt vmcnt(0) +; HSA-TRAP-GFX1100-O0-NEXT: s_mov_b32 s0, -1 +; HSA-TRAP-GFX1100-O0-NEXT: ; implicit-def: $sgpr1 +; HSA-TRAP-GFX1100-O0-NEXT: v_cmp_eq_u32_e64 s0, v0, s0 +; HSA-TRAP-GFX1100-O0-NEXT: s_and_b32 vcc_lo, exec_lo, s0 +; HSA-TRAP-GFX1100-O0-NEXT: s_cbranch_vccnz .LBB1_2 +; HSA-TRAP-GFX1100-O0-NEXT: ; %bb.1: ; %trap +; HSA-TRAP-GFX1100-O0-NEXT: s_trap 2 +; HSA-TRAP-GFX1100-O0-NEXT: s_sendmsg_rtn_b32 s0, sendmsg(MSG_RTN_GET_DOORBELL) +; HSA-TRAP-GFX1100-O0-NEXT: s_mov_b32 ttmp2, m0 +; HSA-TRAP-GFX1100-O0-NEXT: s_waitcnt lgkmcnt(0) +; HSA-TRAP-GFX1100-O0-NEXT: s_and_b32 s0, s0, 0x3ff +; HSA-TRAP-GFX1100-O0-NEXT: s_or_b32 s0, s0, 0x400 +; HSA-TRAP-GFX1100-O0-NEXT: s_mov_b32 m0, s0 +; HSA-TRAP-GFX1100-O0-NEXT: s_sendmsg sendmsg(MSG_INTERRUPT) +; HSA-TRAP-GFX1100-O0-NEXT: s_mov_b32 m0, ttmp2 +; HSA-TRAP-GFX1100-O0-NEXT: s_branch .LBB1_3 +; HSA-TRAP-GFX1100-O0-NEXT: .LBB1_2: ; %ret +; HSA-TRAP-GFX1100-O0-NEXT: s_or_saveexec_b32 s6, -1 +; HSA-TRAP-GFX1100-O0-NEXT: scratch_load_b32 v0, off, off ; 4-byte Folded Reload +; HSA-TRAP-GFX1100-O0-NEXT: s_mov_b32 exec_lo, s6 +; HSA-TRAP-GFX1100-O0-NEXT: s_waitcnt vmcnt(0) +; HSA-TRAP-GFX1100-O0-NEXT: v_readlane_b32 s0, v0, 0 +; HSA-TRAP-GFX1100-O0-NEXT: v_readlane_b32 s1, v0, 1 +; HSA-TRAP-GFX1100-O0-NEXT: v_mov_b32_e32 v1, 0 +; HSA-TRAP-GFX1100-O0-NEXT: v_mov_b32_e32 v2, 3 +; HSA-TRAP-GFX1100-O0-NEXT: global_store_b32 v1, v2, s[0:1] dlc +; HSA-TRAP-GFX1100-O0-NEXT: s_waitcnt_vscnt null, 0x0 +; HSA-TRAP-GFX1100-O0-NEXT: ; kill: killed $vgpr0 +; HSA-TRAP-GFX1100-O0-NEXT: s_endpgm +; HSA-TRAP-GFX1100-O0-NEXT: .LBB1_3: ; =>This Inner Loop Header: Depth=1 +; HSA-TRAP-GFX1100-O0-NEXT: s_sethalt 5 +; HSA-TRAP-GFX1100-O0-NEXT: s_branch .LBB1_3 entry: %tmp29 = load volatile i32, ptr addrspace(1) %arg0 %cmp = icmp eq i32 %tmp29, -1 @@ -197,6 +319,21 @@ define amdgpu_kernel void @debugtrap(ptr addrspace(1) nocapture readonly %arg0) ; HSA-NOTRAP-GFX900-NEXT: global_store_dword v0, v2, s[0:1] ; HSA-NOTRAP-GFX900-NEXT: s_waitcnt vmcnt(0) ; HSA-NOTRAP-GFX900-NEXT: s_endpgm +; +; HSA-TRAP-GFX1100-LABEL: debugtrap: +; HSA-TRAP-GFX1100: ; %bb.0: +; HSA-TRAP-GFX1100-NEXT: s_load_b64 s[0:1], s[0:1], 0x0 +; HSA-TRAP-GFX1100-NEXT: v_dual_mov_b32 v0, 0 :: v_dual_mov_b32 v1, 1 +; HSA-TRAP-GFX1100-NEXT: v_mov_b32_e32 v2, 2 +; HSA-TRAP-GFX1100-NEXT: s_waitcnt lgkmcnt(0) +; HSA-TRAP-GFX1100-NEXT: global_store_b32 v0, v1, s[0:1] dlc +; HSA-TRAP-GFX1100-NEXT: s_waitcnt_vscnt null, 0x0 +; HSA-TRAP-GFX1100-NEXT: s_trap 3 +; HSA-TRAP-GFX1100-NEXT: global_store_b32 v0, v2, s[0:1] dlc +; HSA-TRAP-GFX1100-NEXT: s_waitcnt_vscnt null, 0x0 +; HSA-TRAP-GFX1100-NEXT: s_nop 0 +; HSA-TRAP-GFX1100-NEXT: s_sendmsg sendmsg(MSG_DEALLOC_VGPRS) +; HSA-TRAP-GFX1100-NEXT: s_endpgm store volatile i32 1, ptr addrspace(1) %arg0 call void @llvm.debugtrap() store volatile i32 2, ptr addrspace(1) %arg0 diff --git a/llvm/test/CodeGen/LoongArch/lasx/ir-instruction/insertelement.ll b/llvm/test/CodeGen/LoongArch/lasx/ir-instruction/insertelement.ll index 6629d34405492cc732406a2b43ccf0e4e1b291b8..25106b456d2f7a6dd9e775a4c431619ff1db9dac 100644 --- a/llvm/test/CodeGen/LoongArch/lasx/ir-instruction/insertelement.ll +++ b/llvm/test/CodeGen/LoongArch/lasx/ir-instruction/insertelement.ll @@ -123,10 +123,9 @@ define void @insert_32xi8_idx(ptr %src, ptr %dst, i8 %in, i32 %idx) nounwind { ; CHECK-NEXT: bstrins.d $sp, $zero, 4, 0 ; CHECK-NEXT: xvld $xr0, $a0, 0 ; CHECK-NEXT: xvst $xr0, $sp, 0 -; CHECK-NEXT: bstrpick.d $a0, $a3, 31, 0 -; CHECK-NEXT: addi.d $a3, $sp, 0 -; CHECK-NEXT: bstrins.d $a3, $a0, 4, 0 -; CHECK-NEXT: st.b $a2, $a3, 0 +; CHECK-NEXT: addi.d $a0, $sp, 0 +; CHECK-NEXT: bstrins.d $a0, $a3, 4, 0 +; CHECK-NEXT: st.b $a2, $a0, 0 ; CHECK-NEXT: xvld $xr0, $sp, 0 ; CHECK-NEXT: xvst $xr0, $a1, 0 ; CHECK-NEXT: addi.d $sp, $fp, -64 @@ -150,10 +149,9 @@ define void @insert_16xi16_idx(ptr %src, ptr %dst, i16 %in, i32 %idx) nounwind { ; CHECK-NEXT: bstrins.d $sp, $zero, 4, 0 ; CHECK-NEXT: xvld $xr0, $a0, 0 ; CHECK-NEXT: xvst $xr0, $sp, 0 -; CHECK-NEXT: bstrpick.d $a0, $a3, 31, 0 -; CHECK-NEXT: addi.d $a3, $sp, 0 -; CHECK-NEXT: bstrins.d $a3, $a0, 4, 1 -; CHECK-NEXT: st.h $a2, $a3, 0 +; CHECK-NEXT: addi.d $a0, $sp, 0 +; CHECK-NEXT: bstrins.d $a0, $a3, 4, 1 +; CHECK-NEXT: st.h $a2, $a0, 0 ; CHECK-NEXT: xvld $xr0, $sp, 0 ; CHECK-NEXT: xvst $xr0, $a1, 0 ; CHECK-NEXT: addi.d $sp, $fp, -64 @@ -177,10 +175,9 @@ define void @insert_8xi32_idx(ptr %src, ptr %dst, i32 %in, i32 %idx) nounwind { ; CHECK-NEXT: bstrins.d $sp, $zero, 4, 0 ; CHECK-NEXT: xvld $xr0, $a0, 0 ; CHECK-NEXT: xvst $xr0, $sp, 0 -; CHECK-NEXT: bstrpick.d $a0, $a3, 31, 0 -; CHECK-NEXT: addi.d $a3, $sp, 0 -; CHECK-NEXT: bstrins.d $a3, $a0, 4, 2 -; CHECK-NEXT: st.w $a2, $a3, 0 +; CHECK-NEXT: addi.d $a0, $sp, 0 +; CHECK-NEXT: bstrins.d $a0, $a3, 4, 2 +; CHECK-NEXT: st.w $a2, $a0, 0 ; CHECK-NEXT: xvld $xr0, $sp, 0 ; CHECK-NEXT: xvst $xr0, $a1, 0 ; CHECK-NEXT: addi.d $sp, $fp, -64 @@ -204,10 +201,9 @@ define void @insert_4xi64_idx(ptr %src, ptr %dst, i64 %in, i32 %idx) nounwind { ; CHECK-NEXT: bstrins.d $sp, $zero, 4, 0 ; CHECK-NEXT: xvld $xr0, $a0, 0 ; CHECK-NEXT: xvst $xr0, $sp, 0 -; CHECK-NEXT: bstrpick.d $a0, $a3, 31, 0 -; CHECK-NEXT: addi.d $a3, $sp, 0 -; CHECK-NEXT: bstrins.d $a3, $a0, 4, 3 -; CHECK-NEXT: st.d $a2, $a3, 0 +; CHECK-NEXT: addi.d $a0, $sp, 0 +; CHECK-NEXT: bstrins.d $a0, $a3, 4, 3 +; CHECK-NEXT: st.d $a2, $a0, 0 ; CHECK-NEXT: xvld $xr0, $sp, 0 ; CHECK-NEXT: xvst $xr0, $a1, 0 ; CHECK-NEXT: addi.d $sp, $fp, -64 @@ -231,10 +227,9 @@ define void @insert_8xfloat_idx(ptr %src, ptr %dst, float %in, i32 %idx) nounwin ; CHECK-NEXT: bstrins.d $sp, $zero, 4, 0 ; CHECK-NEXT: xvld $xr1, $a0, 0 ; CHECK-NEXT: xvst $xr1, $sp, 0 -; CHECK-NEXT: bstrpick.d $a0, $a2, 31, 0 -; CHECK-NEXT: addi.d $a2, $sp, 0 -; CHECK-NEXT: bstrins.d $a2, $a0, 4, 2 -; CHECK-NEXT: fst.s $fa0, $a2, 0 +; CHECK-NEXT: addi.d $a0, $sp, 0 +; CHECK-NEXT: bstrins.d $a0, $a2, 4, 2 +; CHECK-NEXT: fst.s $fa0, $a0, 0 ; CHECK-NEXT: xvld $xr0, $sp, 0 ; CHECK-NEXT: xvst $xr0, $a1, 0 ; CHECK-NEXT: addi.d $sp, $fp, -64 @@ -258,10 +253,9 @@ define void @insert_4xdouble_idx(ptr %src, ptr %dst, double %in, i32 %idx) nounw ; CHECK-NEXT: bstrins.d $sp, $zero, 4, 0 ; CHECK-NEXT: xvld $xr1, $a0, 0 ; CHECK-NEXT: xvst $xr1, $sp, 0 -; CHECK-NEXT: bstrpick.d $a0, $a2, 31, 0 -; CHECK-NEXT: addi.d $a2, $sp, 0 -; CHECK-NEXT: bstrins.d $a2, $a0, 4, 3 -; CHECK-NEXT: fst.d $fa0, $a2, 0 +; CHECK-NEXT: addi.d $a0, $sp, 0 +; CHECK-NEXT: bstrins.d $a0, $a2, 4, 3 +; CHECK-NEXT: fst.d $fa0, $a0, 0 ; CHECK-NEXT: xvld $xr0, $sp, 0 ; CHECK-NEXT: xvst $xr0, $a1, 0 ; CHECK-NEXT: addi.d $sp, $fp, -64 diff --git a/llvm/test/CodeGen/LoongArch/lsx/ir-instruction/insertelement.ll b/llvm/test/CodeGen/LoongArch/lsx/ir-instruction/insertelement.ll index 19171b7d8ed7845ffcf1dcce910c2c4e2b052243..7f232073ae129c4163784e28ae6c8c5be37134b0 100644 --- a/llvm/test/CodeGen/LoongArch/lsx/ir-instruction/insertelement.ll +++ b/llvm/test/CodeGen/LoongArch/lsx/ir-instruction/insertelement.ll @@ -87,10 +87,9 @@ define void @insert_16xi8_idx(ptr %src, ptr %dst, i8 %ins, i32 %idx) nounwind { ; CHECK-NEXT: addi.d $sp, $sp, -16 ; CHECK-NEXT: vld $vr0, $a0, 0 ; CHECK-NEXT: vst $vr0, $sp, 0 -; CHECK-NEXT: bstrpick.d $a0, $a3, 31, 0 -; CHECK-NEXT: addi.d $a3, $sp, 0 -; CHECK-NEXT: bstrins.d $a3, $a0, 3, 0 -; CHECK-NEXT: st.b $a2, $a3, 0 +; CHECK-NEXT: addi.d $a0, $sp, 0 +; CHECK-NEXT: bstrins.d $a0, $a3, 3, 0 +; CHECK-NEXT: st.b $a2, $a0, 0 ; CHECK-NEXT: vld $vr0, $sp, 0 ; CHECK-NEXT: vst $vr0, $a1, 0 ; CHECK-NEXT: addi.d $sp, $sp, 16 @@ -107,10 +106,9 @@ define void @insert_8xi16_idx(ptr %src, ptr %dst, i16 %ins, i32 %idx) nounwind { ; CHECK-NEXT: addi.d $sp, $sp, -16 ; CHECK-NEXT: vld $vr0, $a0, 0 ; CHECK-NEXT: vst $vr0, $sp, 0 -; CHECK-NEXT: bstrpick.d $a0, $a3, 31, 0 -; CHECK-NEXT: addi.d $a3, $sp, 0 -; CHECK-NEXT: bstrins.d $a3, $a0, 3, 1 -; CHECK-NEXT: st.h $a2, $a3, 0 +; CHECK-NEXT: addi.d $a0, $sp, 0 +; CHECK-NEXT: bstrins.d $a0, $a3, 3, 1 +; CHECK-NEXT: st.h $a2, $a0, 0 ; CHECK-NEXT: vld $vr0, $sp, 0 ; CHECK-NEXT: vst $vr0, $a1, 0 ; CHECK-NEXT: addi.d $sp, $sp, 16 @@ -127,10 +125,9 @@ define void @insert_4xi32_idx(ptr %src, ptr %dst, i32 %ins, i32 %idx) nounwind { ; CHECK-NEXT: addi.d $sp, $sp, -16 ; CHECK-NEXT: vld $vr0, $a0, 0 ; CHECK-NEXT: vst $vr0, $sp, 0 -; CHECK-NEXT: bstrpick.d $a0, $a3, 31, 0 -; CHECK-NEXT: addi.d $a3, $sp, 0 -; CHECK-NEXT: bstrins.d $a3, $a0, 3, 2 -; CHECK-NEXT: st.w $a2, $a3, 0 +; CHECK-NEXT: addi.d $a0, $sp, 0 +; CHECK-NEXT: bstrins.d $a0, $a3, 3, 2 +; CHECK-NEXT: st.w $a2, $a0, 0 ; CHECK-NEXT: vld $vr0, $sp, 0 ; CHECK-NEXT: vst $vr0, $a1, 0 ; CHECK-NEXT: addi.d $sp, $sp, 16 @@ -147,10 +144,9 @@ define void @insert_2xi64_idx(ptr %src, ptr %dst, i64 %ins, i32 %idx) nounwind { ; CHECK-NEXT: addi.d $sp, $sp, -16 ; CHECK-NEXT: vld $vr0, $a0, 0 ; CHECK-NEXT: vst $vr0, $sp, 0 -; CHECK-NEXT: bstrpick.d $a0, $a3, 31, 0 -; CHECK-NEXT: addi.d $a3, $sp, 0 -; CHECK-NEXT: bstrins.d $a3, $a0, 3, 3 -; CHECK-NEXT: st.d $a2, $a3, 0 +; CHECK-NEXT: addi.d $a0, $sp, 0 +; CHECK-NEXT: bstrins.d $a0, $a3, 3, 3 +; CHECK-NEXT: st.d $a2, $a0, 0 ; CHECK-NEXT: vld $vr0, $sp, 0 ; CHECK-NEXT: vst $vr0, $a1, 0 ; CHECK-NEXT: addi.d $sp, $sp, 16 @@ -167,10 +163,9 @@ define void @insert_4xfloat_idx(ptr %src, ptr %dst, float %ins, i32 %idx) nounwi ; CHECK-NEXT: addi.d $sp, $sp, -16 ; CHECK-NEXT: vld $vr1, $a0, 0 ; CHECK-NEXT: vst $vr1, $sp, 0 -; CHECK-NEXT: bstrpick.d $a0, $a2, 31, 0 -; CHECK-NEXT: addi.d $a2, $sp, 0 -; CHECK-NEXT: bstrins.d $a2, $a0, 3, 2 -; CHECK-NEXT: fst.s $fa0, $a2, 0 +; CHECK-NEXT: addi.d $a0, $sp, 0 +; CHECK-NEXT: bstrins.d $a0, $a2, 3, 2 +; CHECK-NEXT: fst.s $fa0, $a0, 0 ; CHECK-NEXT: vld $vr0, $sp, 0 ; CHECK-NEXT: vst $vr0, $a1, 0 ; CHECK-NEXT: addi.d $sp, $sp, 16 @@ -187,10 +182,9 @@ define void @insert_2xdouble_idx(ptr %src, ptr %dst, double %ins, i32 %idx) noun ; CHECK-NEXT: addi.d $sp, $sp, -16 ; CHECK-NEXT: vld $vr1, $a0, 0 ; CHECK-NEXT: vst $vr1, $sp, 0 -; CHECK-NEXT: bstrpick.d $a0, $a2, 31, 0 -; CHECK-NEXT: addi.d $a2, $sp, 0 -; CHECK-NEXT: bstrins.d $a2, $a0, 3, 3 -; CHECK-NEXT: fst.d $fa0, $a2, 0 +; CHECK-NEXT: addi.d $a0, $sp, 0 +; CHECK-NEXT: bstrins.d $a0, $a2, 3, 3 +; CHECK-NEXT: fst.d $fa0, $a0, 0 ; CHECK-NEXT: vld $vr0, $sp, 0 ; CHECK-NEXT: vst $vr0, $a1, 0 ; CHECK-NEXT: addi.d $sp, $sp, 16 diff --git a/llvm/test/CodeGen/M68k/Arith/add-with-overflow.ll b/llvm/test/CodeGen/M68k/Arith/add-with-overflow.ll index bd5e593edb33d8ecadb8f4c73bf1068aedab0d5b..70479b0b3ec65c6ce2213038903d4c8f2dcd2cc0 100644 --- a/llvm/test/CodeGen/M68k/Arith/add-with-overflow.ll +++ b/llvm/test/CodeGen/M68k/Arith/add-with-overflow.ll @@ -35,7 +35,7 @@ define fastcc i1 @test6(i32 %v1, i32 %v2, ptr %X) nounwind { ; CHECK-NEXT: ; %bb.1: ; %normal ; CHECK-NEXT: move.l #0, (%a0) ; CHECK-NEXT: .LBB1_2: ; %carry -; CHECK-NEXT: move.b #0, %d0 +; CHECK-NEXT: moveq #0, %d0 ; CHECK-NEXT: rts entry: %t = call {i32, i1} @llvm.uadd.with.overflow.i32(i32 %v1, i32 %v2) diff --git a/llvm/test/CodeGen/M68k/Arith/add.ll b/llvm/test/CodeGen/M68k/Arith/add.ll index 281751e3e183c7ab55161bac600f2d9ecc0b7dde..a9eb0bb815b088b7c402550e8e3fc522b71d89ea 100644 --- a/llvm/test/CodeGen/M68k/Arith/add.ll +++ b/llvm/test/CodeGen/M68k/Arith/add.ll @@ -43,7 +43,7 @@ define fastcc void @test3(ptr inreg %a) nounwind { ; CHECK-NEXT: suba.l #4, %sp ; CHECK-NEXT: movem.l %d2, (0,%sp) ; 8-byte Folded Spill ; CHECK-NEXT: move.l (%a0), %d0 -; CHECK-NEXT: move.l #0, %d1 +; CHECK-NEXT: moveq #0, %d1 ; CHECK-NEXT: move.l #-2147483648, %d2 ; CHECK-NEXT: add.l (4,%a0), %d2 ; CHECK-NEXT: addx.l %d0, %d1 @@ -64,7 +64,7 @@ define fastcc void @test4(ptr inreg %a) nounwind { ; CHECK-NEXT: suba.l #4, %sp ; CHECK-NEXT: movem.l %d2, (0,%sp) ; 8-byte Folded Spill ; CHECK-NEXT: move.l (%a0), %d0 -; CHECK-NEXT: move.l #0, %d1 +; CHECK-NEXT: moveq #0, %d1 ; CHECK-NEXT: move.l #128, %d2 ; CHECK-NEXT: add.l (4,%a0), %d2 ; CHECK-NEXT: addx.l %d0, %d1 diff --git a/llvm/test/CodeGen/M68k/Arith/bitwise.ll b/llvm/test/CodeGen/M68k/Arith/bitwise.ll index 70e4dd42bfb6deafa9a763b7786ab67a218039df..74fc543a5fb8564554bbec0f901a87d442b5f890 100644 --- a/llvm/test/CodeGen/M68k/Arith/bitwise.ll +++ b/llvm/test/CodeGen/M68k/Arith/bitwise.ll @@ -242,7 +242,7 @@ define i64 @lshr64(i64 %a, i64 %b) nounwind { ; CHECK-NEXT: add.l #-32, %d1 ; CHECK-NEXT: bmi .LBB18_1 ; CHECK-NEXT: ; %bb.2: -; CHECK-NEXT: move.l #0, %d0 +; CHECK-NEXT: moveq #0, %d0 ; CHECK-NEXT: bra .LBB18_3 ; CHECK-NEXT: .LBB18_1: ; CHECK-NEXT: move.l %d2, %d0 @@ -301,7 +301,7 @@ define i64 @ashr64(i64 %a, i64 %b) nounwind { ; CHECK-NEXT: add.l #-32, %d3 ; CHECK-NEXT: bmi .LBB19_5 ; CHECK-NEXT: ; %bb.4: -; CHECK-NEXT: move.l #31, %d2 +; CHECK-NEXT: moveq #31, %d2 ; CHECK-NEXT: .LBB19_5: ; CHECK-NEXT: asr.l %d2, %d0 ; CHECK-NEXT: movem.l (0,%sp), %d2-%d3 ; 12-byte Folded Reload @@ -322,7 +322,7 @@ define i64 @shl64(i64 %a, i64 %b) nounwind { ; CHECK-NEXT: add.l #-32, %d0 ; CHECK-NEXT: bmi .LBB20_1 ; CHECK-NEXT: ; %bb.2: -; CHECK-NEXT: move.l #0, %d1 +; CHECK-NEXT: moveq #0, %d1 ; CHECK-NEXT: bra .LBB20_3 ; CHECK-NEXT: .LBB20_1: ; CHECK-NEXT: move.l %d2, %d1 diff --git a/llvm/test/CodeGen/M68k/Arith/divide-by-constant.ll b/llvm/test/CodeGen/M68k/Arith/divide-by-constant.ll index 834dfe1c26f08f65380ab8f698cc81b228a5bac5..fcc8dd3e7662e1e59fdf96103bdecb3a18ac8d88 100644 --- a/llvm/test/CodeGen/M68k/Arith/divide-by-constant.ll +++ b/llvm/test/CodeGen/M68k/Arith/divide-by-constant.ll @@ -40,7 +40,7 @@ define zeroext i8 @test3(i8 zeroext %x, i8 zeroext %c) { ; CHECK-NEXT: move.b (11,%sp), %d0 ; CHECK-NEXT: and.l #255, %d0 ; CHECK-NEXT: muls #171, %d0 -; CHECK-NEXT: move.w #9, %d1 +; CHECK-NEXT: moveq #9, %d1 ; CHECK-NEXT: lsr.w %d1, %d0 ; CHECK-NEXT: and.l #65535, %d0 ; CHECK-NEXT: rts @@ -58,7 +58,7 @@ define signext i16 @test4(i16 signext %x) nounwind { ; CHECK-NEXT: muls #1986, %d0 ; CHECK-NEXT: asr.l #8, %d0 ; CHECK-NEXT: asr.l #8, %d0 -; CHECK-NEXT: move.w #15, %d1 +; CHECK-NEXT: moveq #15, %d1 ; CHECK-NEXT: move.w %d0, %d2 ; CHECK-NEXT: lsr.w %d1, %d2 ; CHECK-NEXT: add.w %d2, %d0 @@ -94,7 +94,7 @@ define signext i16 @test6(i16 signext %x) nounwind { ; CHECK-NEXT: muls #26215, %d0 ; CHECK-NEXT: asr.l #8, %d0 ; CHECK-NEXT: asr.l #8, %d0 -; CHECK-NEXT: move.w #15, %d1 +; CHECK-NEXT: moveq #15, %d1 ; CHECK-NEXT: move.w %d0, %d2 ; CHECK-NEXT: lsr.w %d1, %d2 ; CHECK-NEXT: asr.w #2, %d0 @@ -128,7 +128,7 @@ define i8 @test8(i8 %x) nounwind { ; CHECK-NEXT: lsr.b #1, %d0 ; CHECK-NEXT: and.l #255, %d0 ; CHECK-NEXT: muls #211, %d0 -; CHECK-NEXT: move.w #13, %d1 +; CHECK-NEXT: moveq #13, %d1 ; CHECK-NEXT: lsr.w %d1, %d0 ; CHECK-NEXT: ; kill: def $bd0 killed $bd0 killed $d0 ; CHECK-NEXT: rts @@ -143,7 +143,7 @@ define i8 @test9(i8 %x) nounwind { ; CHECK-NEXT: lsr.b #2, %d0 ; CHECK-NEXT: and.l #255, %d0 ; CHECK-NEXT: muls #71, %d0 -; CHECK-NEXT: move.w #11, %d1 +; CHECK-NEXT: moveq #11, %d1 ; CHECK-NEXT: lsr.w %d1, %d0 ; CHECK-NEXT: ; kill: def $bd0 killed $bd0 killed $d0 ; CHECK-NEXT: rts @@ -156,11 +156,11 @@ define i32 @testsize1(i32 %x) minsize nounwind { ; CHECK: ; %bb.0: ; %entry ; CHECK-NEXT: suba.l #4, %sp ; CHECK-NEXT: movem.l %d2, (0,%sp) ; 8-byte Folded Spill -; CHECK-NEXT: move.l #31, %d1 +; CHECK-NEXT: moveq #31, %d1 ; CHECK-NEXT: move.l (8,%sp), %d0 ; CHECK-NEXT: move.l %d0, %d2 ; CHECK-NEXT: asr.l %d1, %d2 -; CHECK-NEXT: move.l #27, %d1 +; CHECK-NEXT: moveq #27, %d1 ; CHECK-NEXT: lsr.l %d1, %d2 ; CHECK-NEXT: add.l %d2, %d0 ; CHECK-NEXT: asr.l #5, %d0 diff --git a/llvm/test/CodeGen/M68k/Arith/imul.ll b/llvm/test/CodeGen/M68k/Arith/imul.ll index f53568395c29b2a4c359382c7666c390ecaba251..a1846e4d51bd2e32ab33a14cf3831beeab26b034 100644 --- a/llvm/test/CodeGen/M68k/Arith/imul.ll +++ b/llvm/test/CodeGen/M68k/Arith/imul.ll @@ -19,7 +19,7 @@ define i64 @mul4_64(i64 %A) { ; CHECK-NEXT: suba.l #4, %sp ; CHECK-NEXT: .cfi_def_cfa_offset -8 ; CHECK-NEXT: movem.l %d2, (0,%sp) ; 8-byte Folded Spill -; CHECK-NEXT: move.l #30, %d0 +; CHECK-NEXT: moveq #30, %d0 ; CHECK-NEXT: move.l (12,%sp), %d1 ; CHECK-NEXT: move.l %d1, %d2 ; CHECK-NEXT: lsr.l %d0, %d2 @@ -38,7 +38,7 @@ define i32 @mul4096_32(i32 %A) { ; CHECK-LABEL: mul4096_32: ; CHECK: .cfi_startproc ; CHECK-NEXT: ; %bb.0: -; CHECK-NEXT: move.l #12, %d1 +; CHECK-NEXT: moveq #12, %d1 ; CHECK-NEXT: move.l (4,%sp), %d0 ; CHECK-NEXT: lsl.l %d1, %d0 ; CHECK-NEXT: rts @@ -53,11 +53,11 @@ define i64 @mul4096_64(i64 %A) { ; CHECK-NEXT: suba.l #8, %sp ; CHECK-NEXT: .cfi_def_cfa_offset -12 ; CHECK-NEXT: movem.l %d2-%d3, (0,%sp) ; 12-byte Folded Spill -; CHECK-NEXT: move.l #20, %d0 +; CHECK-NEXT: moveq #20, %d0 ; CHECK-NEXT: move.l (16,%sp), %d1 ; CHECK-NEXT: move.l %d1, %d2 ; CHECK-NEXT: lsr.l %d0, %d2 -; CHECK-NEXT: move.l #12, %d3 +; CHECK-NEXT: moveq #12, %d3 ; CHECK-NEXT: move.l (12,%sp), %d0 ; CHECK-NEXT: lsl.l %d3, %d0 ; CHECK-NEXT: or.l %d2, %d0 @@ -73,7 +73,7 @@ define i32 @mulmin4096_32(i32 %A) { ; CHECK-LABEL: mulmin4096_32: ; CHECK: .cfi_startproc ; CHECK-NEXT: ; %bb.0: -; CHECK-NEXT: move.l #12, %d1 +; CHECK-NEXT: moveq #12, %d1 ; CHECK-NEXT: move.l (4,%sp), %d0 ; CHECK-NEXT: lsl.l %d1, %d0 ; CHECK-NEXT: neg.l %d0 @@ -89,11 +89,11 @@ define i64 @mulmin4096_64(i64 %A) { ; CHECK-NEXT: suba.l #8, %sp ; CHECK-NEXT: .cfi_def_cfa_offset -12 ; CHECK-NEXT: movem.l %d2-%d3, (0,%sp) ; 12-byte Folded Spill -; CHECK-NEXT: move.l #20, %d0 +; CHECK-NEXT: moveq #20, %d0 ; CHECK-NEXT: move.l (16,%sp), %d1 ; CHECK-NEXT: move.l %d1, %d2 ; CHECK-NEXT: lsr.l %d0, %d2 -; CHECK-NEXT: move.l #12, %d3 +; CHECK-NEXT: moveq #12, %d3 ; CHECK-NEXT: move.l (12,%sp), %d0 ; CHECK-NEXT: lsl.l %d3, %d0 ; CHECK-NEXT: or.l %d2, %d0 @@ -258,7 +258,7 @@ define i32 @mul0_32(i32 %A) { ; CHECK-LABEL: mul0_32: ; CHECK: .cfi_startproc ; CHECK-NEXT: ; %bb.0: -; CHECK-NEXT: move.l #0, %d0 +; CHECK-NEXT: moveq #0, %d0 ; CHECK-NEXT: rts %mul = mul i32 %A, 0 ret i32 %mul diff --git a/llvm/test/CodeGen/M68k/Arith/smul-with-overflow.ll b/llvm/test/CodeGen/M68k/Arith/smul-with-overflow.ll index 5bd4d5d48bc85927a1821951df5eecc15e552d7d..10a797f134414192f3b371f9040dc66ae9dbf3c2 100644 --- a/llvm/test/CodeGen/M68k/Arith/smul-with-overflow.ll +++ b/llvm/test/CodeGen/M68k/Arith/smul-with-overflow.ll @@ -24,7 +24,7 @@ entry: define zeroext i8 @smul_i8_no_ovf(i8 signext %a, i8 signext %b) nounwind ssp { ; CHECK-LABEL: smul_i8_no_ovf: ; CHECK: ; %bb.0: ; %entry -; CHECK-NEXT: move.l #42, %d0 +; CHECK-NEXT: moveq #42, %d0 ; CHECK-NEXT: rts entry: %smul = tail call { i8, i1 } @llvm.smul.with.overflow.i8(i8 %a, i8 %b) @@ -70,7 +70,7 @@ define fastcc i1 @test1(i32 %v1, i32 %v2) nounwind { ; CHECK-NEXT: lea (no,%pc), %a0 ; CHECK-NEXT: move.l %a0, (%sp) ; CHECK-NEXT: jsr printf@PLT -; CHECK-NEXT: move.b #0, %d0 +; CHECK-NEXT: moveq #0, %d0 ; CHECK-NEXT: adda.l #12, %sp ; CHECK-NEXT: rts ; CHECK-NEXT: .LBB3_1: ; %normal @@ -78,7 +78,7 @@ define fastcc i1 @test1(i32 %v1, i32 %v2) nounwind { ; CHECK-NEXT: lea (ok,%pc), %a0 ; CHECK-NEXT: move.l %a0, (%sp) ; CHECK-NEXT: jsr printf@PLT -; CHECK-NEXT: move.b #1, %d0 +; CHECK-NEXT: moveq #1, %d0 ; CHECK-NEXT: adda.l #12, %sp ; CHECK-NEXT: rts entry: @@ -108,7 +108,7 @@ define fastcc i1 @test2(i32 %v1, i32 %v2) nounwind { ; CHECK-NEXT: lea (no,%pc), %a0 ; CHECK-NEXT: move.l %a0, (%sp) ; CHECK-NEXT: jsr printf@PLT -; CHECK-NEXT: move.b #0, %d0 +; CHECK-NEXT: moveq #0, %d0 ; CHECK-NEXT: adda.l #12, %sp ; CHECK-NEXT: rts ; CHECK-NEXT: .LBB4_2: ; %normal @@ -116,7 +116,7 @@ define fastcc i1 @test2(i32 %v1, i32 %v2) nounwind { ; CHECK-NEXT: lea (ok,%pc), %a0 ; CHECK-NEXT: move.l %a0, (%sp) ; CHECK-NEXT: jsr printf@PLT -; CHECK-NEXT: move.b #1, %d0 +; CHECK-NEXT: moveq #1, %d0 ; CHECK-NEXT: adda.l #12, %sp ; CHECK-NEXT: rts entry: @@ -155,7 +155,7 @@ define i32 @test4(i32 %a, i32 %b) nounwind readnone { ; CHECK: ; %bb.0: ; %entry ; CHECK-NEXT: move.l (8,%sp), %d0 ; CHECK-NEXT: add.l (4,%sp), %d0 -; CHECK-NEXT: move.l #4, %d1 +; CHECK-NEXT: moveq #4, %d1 ; CHECK-NEXT: muls.l %d1, %d0 ; CHECK-NEXT: rts entry: diff --git a/llvm/test/CodeGen/M68k/Arith/sub-with-overflow.ll b/llvm/test/CodeGen/M68k/Arith/sub-with-overflow.ll index 8d47c7ebf7e56f70d8e4aace2e4269f4f505b878..be3223156986e61310d0b859b17de1a9da695c14 100644 --- a/llvm/test/CodeGen/M68k/Arith/sub-with-overflow.ll +++ b/llvm/test/CodeGen/M68k/Arith/sub-with-overflow.ll @@ -19,7 +19,7 @@ define i1 @func1(i32 %v1, i32 %v2) nounwind { ; CHECK-NEXT: lea (no,%pc), %a0 ; CHECK-NEXT: move.l %a0, (%sp) ; CHECK-NEXT: jsr printf@PLT -; CHECK-NEXT: move.b #0, %d0 +; CHECK-NEXT: moveq #0, %d0 ; CHECK-NEXT: adda.l #12, %sp ; CHECK-NEXT: rts ; CHECK-NEXT: .LBB0_1: ; %normal @@ -27,7 +27,7 @@ define i1 @func1(i32 %v1, i32 %v2) nounwind { ; CHECK-NEXT: lea (ok,%pc), %a0 ; CHECK-NEXT: move.l %a0, (%sp) ; CHECK-NEXT: jsr printf@PLT -; CHECK-NEXT: move.b #1, %d0 +; CHECK-NEXT: moveq #1, %d0 ; CHECK-NEXT: adda.l #12, %sp ; CHECK-NEXT: rts entry: @@ -56,7 +56,7 @@ define i1 @func2(i32 %v1, i32 %v2) nounwind { ; CHECK-NEXT: lea (no,%pc), %a0 ; CHECK-NEXT: move.l %a0, (%sp) ; CHECK-NEXT: jsr printf@PLT -; CHECK-NEXT: move.b #0, %d0 +; CHECK-NEXT: moveq #0, %d0 ; CHECK-NEXT: adda.l #12, %sp ; CHECK-NEXT: rts ; CHECK-NEXT: .LBB1_1: ; %normal @@ -64,7 +64,7 @@ define i1 @func2(i32 %v1, i32 %v2) nounwind { ; CHECK-NEXT: lea (ok,%pc), %a0 ; CHECK-NEXT: move.l %a0, (%sp) ; CHECK-NEXT: jsr printf@PLT -; CHECK-NEXT: move.b #1, %d0 +; CHECK-NEXT: moveq #1, %d0 ; CHECK-NEXT: adda.l #12, %sp ; CHECK-NEXT: rts entry: @@ -85,7 +85,7 @@ carry: define i1 @func3(i32 %x) nounwind { ; CHECK-LABEL: func3: ; CHECK: ; %bb.0: ; %entry -; CHECK-NEXT: move.l #-1, %d0 +; CHECK-NEXT: moveq #-1, %d0 ; CHECK-NEXT: add.l (4,%sp), %d0 ; CHECK-NEXT: svs %d0 ; CHECK-NEXT: rts diff --git a/llvm/test/CodeGen/M68k/Arith/sub.ll b/llvm/test/CodeGen/M68k/Arith/sub.ll index fff3601000dfa8debaa968e70fd83bedb1339718..16d0498b3dbbc6fd2b55930b67abfac02a1210ba 100644 --- a/llvm/test/CodeGen/M68k/Arith/sub.ll +++ b/llvm/test/CodeGen/M68k/Arith/sub.ll @@ -7,7 +7,7 @@ define i32 @test1(i32 %x) { ; CHECK-NEXT: ; %bb.0: ; CHECK-NEXT: move.l (4,%sp), %d1 ; CHECK-NEXT: eori.l #31, %d1 -; CHECK-NEXT: move.l #32, %d0 +; CHECK-NEXT: moveq #32, %d0 ; CHECK-NEXT: sub.l %d1, %d0 ; CHECK-NEXT: rts %xor = xor i32 %x, 31 diff --git a/llvm/test/CodeGen/M68k/Arith/umul-with-overflow.ll b/llvm/test/CodeGen/M68k/Arith/umul-with-overflow.ll index fd128a3e52bd3e719c01e5873cba807f688e4b90..3314e65399c4315f858dee9921f2f438f24bbb16 100644 --- a/llvm/test/CodeGen/M68k/Arith/umul-with-overflow.ll +++ b/llvm/test/CodeGen/M68k/Arith/umul-with-overflow.ll @@ -24,7 +24,7 @@ entry: define zeroext i8 @umul_i8_no_ovf(i8 signext %a, i8 signext %b) nounwind ssp { ; CHECK-LABEL: umul_i8_no_ovf: ; CHECK: ; %bb.0: ; %entry -; CHECK-NEXT: move.l #42, %d0 +; CHECK-NEXT: moveq #42, %d0 ; CHECK-NEXT: rts entry: %umul = tail call { i8, i1 } @llvm.umul.with.overflow.i8(i8 %a, i8 %b) @@ -59,7 +59,7 @@ declare {i32, i1} @llvm.umul.with.overflow.i32(i32 %a, i32 %b) define i1 @a(i32 %x) nounwind { ; CHECK-LABEL: a: ; CHECK: ; %bb.0: -; CHECK-NEXT: move.l #3, %d0 +; CHECK-NEXT: moveq #3, %d0 ; CHECK-NEXT: move.l (4,%sp), %d1 ; CHECK-NEXT: mulu.l %d0, %d1 ; CHECK-NEXT: svs %d0 @@ -90,7 +90,7 @@ define i32 @test3(i32 %a, i32 %b) nounwind readnone { ; CHECK: ; %bb.0: ; %entry ; CHECK-NEXT: move.l (8,%sp), %d0 ; CHECK-NEXT: add.l (4,%sp), %d0 -; CHECK-NEXT: move.l #4, %d1 +; CHECK-NEXT: moveq #4, %d1 ; CHECK-NEXT: mulu.l %d1, %d0 ; CHECK-NEXT: rts entry: diff --git a/llvm/test/CodeGen/M68k/CConv/c-call.ll b/llvm/test/CodeGen/M68k/CConv/c-call.ll index a9638eec6a31386fc35d3de73b8fea75e0be7d28..badd4e31f37d182166c81f5d9e1baba7523f40ba 100644 --- a/llvm/test/CodeGen/M68k/CConv/c-call.ll +++ b/llvm/test/CodeGen/M68k/CConv/c-call.ll @@ -14,7 +14,7 @@ define i32 @test1() nounwind { ; CHECK-NEXT: move.l #2, (4,%sp) ; CHECK-NEXT: move.l #1, (%sp) ; CHECK-NEXT: jsr (test1_callee@PLT,%pc) -; CHECK-NEXT: move.l #0, %d0 +; CHECK-NEXT: moveq #0, %d0 ; CHECK-NEXT: adda.l #20, %sp ; CHECK-NEXT: rts entry: @@ -34,7 +34,7 @@ define i16 @test2() nounwind { ; CHECK-NEXT: move.l #2, (4,%sp) ; CHECK-NEXT: move.l #1, (%sp) ; CHECK-NEXT: jsr (test2_callee@PLT,%pc) -; CHECK-NEXT: move.w #0, %d0 +; CHECK-NEXT: moveq #0, %d0 ; CHECK-NEXT: adda.l #20, %sp ; CHECK-NEXT: rts entry: @@ -54,7 +54,7 @@ define i8 @test3() nounwind { ; CHECK-NEXT: move.l #2, (4,%sp) ; CHECK-NEXT: move.l #1, (%sp) ; CHECK-NEXT: jsr (test3_callee@PLT,%pc) -; CHECK-NEXT: move.b #0, %d0 +; CHECK-NEXT: moveq #0, %d0 ; CHECK-NEXT: adda.l #20, %sp ; CHECK-NEXT: rts entry: diff --git a/llvm/test/CodeGen/M68k/CConv/fastcc-call.ll b/llvm/test/CodeGen/M68k/CConv/fastcc-call.ll index 4b0f8ed254a5e69fc6d4ae84ae415577eaf238c8..8d40ebd5228fc9baa149ea6d0eadb03a0e4094ae 100644 --- a/llvm/test/CodeGen/M68k/CConv/fastcc-call.ll +++ b/llvm/test/CodeGen/M68k/CConv/fastcc-call.ll @@ -11,12 +11,12 @@ define i32 @foo1() nounwind uwtable { ; CHECK-NEXT: suba.l #4, %sp ; CHECK-NEXT: .cfi_def_cfa_offset -8 ; CHECK-NEXT: move.l #5, (%sp) -; CHECK-NEXT: move.l #1, %d0 -; CHECK-NEXT: move.l #2, %d1 +; CHECK-NEXT: moveq #1, %d0 +; CHECK-NEXT: moveq #2, %d1 ; CHECK-NEXT: move.l #3, %a0 ; CHECK-NEXT: move.l #4, %a1 ; CHECK-NEXT: jsr (bar1@PLT,%pc) -; CHECK-NEXT: move.l #0, %d0 +; CHECK-NEXT: moveq #0, %d0 ; CHECK-NEXT: adda.l #4, %sp ; CHECK-NEXT: rts entry: @@ -34,11 +34,11 @@ define i32 @foo2() nounwind uwtable { ; CHECK-NEXT: suba.l #12, %sp ; CHECK-NEXT: .cfi_def_cfa_offset -16 ; CHECK-NEXT: lea (8,%sp), %a0 -; CHECK-NEXT: move.l #2, %d0 +; CHECK-NEXT: moveq #2, %d0 ; CHECK-NEXT: lea (4,%sp), %a1 -; CHECK-NEXT: move.l #4, %d1 +; CHECK-NEXT: moveq #4, %d1 ; CHECK-NEXT: jsr (bar2@PLT,%pc) -; CHECK-NEXT: move.l #0, %d0 +; CHECK-NEXT: moveq #0, %d0 ; CHECK-NEXT: adda.l #12, %sp ; CHECK-NEXT: rts entry: diff --git a/llvm/test/CodeGen/M68k/CodeModel/medium-pie-global-access.ll b/llvm/test/CodeGen/M68k/CodeModel/medium-pie-global-access.ll index ce8f2d0a6ba760da3a10d09908ca88d09507653d..3d398afe7dc48747efe6df52f68bd261944ee837 100644 --- a/llvm/test/CodeGen/M68k/CodeModel/medium-pie-global-access.ll +++ b/llvm/test/CodeGen/M68k/CodeModel/medium-pie-global-access.ll @@ -71,7 +71,7 @@ define i32 @my_access_global_store_d() #0 { ; CHECK-NEXT: ; %bb.0: ; %entry ; CHECK-NEXT: move.l (d@GOTPCREL,%pc), %a0 ; CHECK-NEXT: move.l #2, (%a0) -; CHECK-NEXT: move.l #0, %d0 +; CHECK-NEXT: moveq #0, %d0 ; CHECK-NEXT: rts entry: store i32 2, ptr @d, align 4 @@ -105,7 +105,7 @@ define linkonce_odr i32 @bar() comdat { ; CHECK-LABEL: bar: ; CHECK: .cfi_startproc ; CHECK-NEXT: ; %bb.0: ; %entry -; CHECK-NEXT: move.l #0, %d0 +; CHECK-NEXT: moveq #0, %d0 ; CHECK-NEXT: rts entry: ret i32 0 diff --git a/llvm/test/CodeGen/M68k/CodeModel/small-pie-global-access.ll b/llvm/test/CodeGen/M68k/CodeModel/small-pie-global-access.ll index 668f8a96ac6f955d72756ecd26445c8a82cffb3b..030f72bb3753f86a9035bd1efb24254830a02499 100644 --- a/llvm/test/CodeGen/M68k/CodeModel/small-pie-global-access.ll +++ b/llvm/test/CodeGen/M68k/CodeModel/small-pie-global-access.ll @@ -69,7 +69,7 @@ define i32 @my_access_global_store_d() #0 { ; CHECK-NEXT: ; %bb.0: ; %entry ; CHECK-NEXT: move.l (d@GOTPCREL,%pc), %a0 ; CHECK-NEXT: move.l #2, (%a0) -; CHECK-NEXT: move.l #0, %d0 +; CHECK-NEXT: moveq #0, %d0 ; CHECK-NEXT: rts entry: store i32 2, ptr @d, align 4 @@ -103,7 +103,7 @@ define linkonce_odr i32 @bar() comdat { ; CHECK-LABEL: bar: ; CHECK: .cfi_startproc ; CHECK-NEXT: ; %bb.0: ; %entry -; CHECK-NEXT: move.l #0, %d0 +; CHECK-NEXT: moveq #0, %d0 ; CHECK-NEXT: rts entry: ret i32 0 diff --git a/llvm/test/CodeGen/M68k/Control/cmp.ll b/llvm/test/CodeGen/M68k/Control/cmp.ll index 634c08760a4e06c270fdf9edbaa985f1a6f94ff2..d3a8bbb0b0c8fbb142016e457291f283b4b11920 100644 --- a/llvm/test/CodeGen/M68k/Control/cmp.ll +++ b/llvm/test/CodeGen/M68k/Control/cmp.ll @@ -8,10 +8,10 @@ define i32 @test1(ptr %y) nounwind { ; CHECK-NEXT: cmpi.l #0, (%a0) ; CHECK-NEXT: beq .LBB0_2 ; CHECK-NEXT: ; %bb.1: ; %cond_false -; CHECK-NEXT: move.l #0, %d0 +; CHECK-NEXT: moveq #0, %d0 ; CHECK-NEXT: rts ; CHECK-NEXT: .LBB0_2: ; %cond_true -; CHECK-NEXT: move.l #1, %d0 +; CHECK-NEXT: moveq #1, %d0 ; CHECK-NEXT: rts %tmp = load i32, ptr %y ; [#uses=1] %tmp.upgrd.1 = icmp eq i32 %tmp, 0 ; [#uses=1] @@ -33,10 +33,10 @@ define i32 @test2(ptr %y) nounwind { ; CHECK-NEXT: cmpi.l #0, %d0 ; CHECK-NEXT: beq .LBB1_2 ; CHECK-NEXT: ; %bb.1: ; %cond_false -; CHECK-NEXT: move.l #0, %d0 +; CHECK-NEXT: moveq #0, %d0 ; CHECK-NEXT: rts ; CHECK-NEXT: .LBB1_2: ; %cond_true -; CHECK-NEXT: move.l #1, %d0 +; CHECK-NEXT: moveq #1, %d0 ; CHECK-NEXT: rts %tmp = load i32, ptr %y ; [#uses=1] %tmp1 = shl i32 %tmp, 3 ; [#uses=1] @@ -59,10 +59,10 @@ define i8 @test2b(ptr %y) nounwind { ; CHECK-NEXT: cmpi.b #0, %d0 ; CHECK-NEXT: beq .LBB2_2 ; CHECK-NEXT: ; %bb.1: ; %cond_false -; CHECK-NEXT: move.b #0, %d0 +; CHECK-NEXT: moveq #0, %d0 ; CHECK-NEXT: rts ; CHECK-NEXT: .LBB2_2: ; %cond_true -; CHECK-NEXT: move.b #1, %d0 +; CHECK-NEXT: moveq #1, %d0 ; CHECK-NEXT: rts %tmp = load i8, ptr %y ; [#uses=1] %tmp1 = shl i8 %tmp, 3 ; [#uses=1] @@ -84,7 +84,7 @@ define i64 @test3(i64 %x) nounwind { ; CHECK-NEXT: seq %d0 ; CHECK-NEXT: move.l %d0, %d1 ; CHECK-NEXT: and.l #255, %d1 -; CHECK-NEXT: move.l #0, %d0 +; CHECK-NEXT: moveq #0, %d0 ; CHECK-NEXT: rts %t = icmp eq i64 %x, 0 %r = zext i1 %t to i64 @@ -97,7 +97,7 @@ define i64 @test4(i64 %x) nounwind { ; CHECK-NEXT: suba.l #4, %sp ; CHECK-NEXT: movem.l %d2, (0,%sp) ; 8-byte Folded Spill ; CHECK-NEXT: move.l (8,%sp), %d1 -; CHECK-NEXT: move.l #0, %d0 +; CHECK-NEXT: moveq #0, %d0 ; CHECK-NEXT: move.l (12,%sp), %d2 ; CHECK-NEXT: sub.l #1, %d2 ; CHECK-NEXT: subx.l %d0, %d1 @@ -119,11 +119,11 @@ define i32 @test6() nounwind align 2 { ; CHECK-NEXT: or.l (8,%sp), %d0 ; CHECK-NEXT: beq .LBB5_1 ; CHECK-NEXT: ; %bb.2: ; %F -; CHECK-NEXT: move.l #0, %d0 +; CHECK-NEXT: moveq #0, %d0 ; CHECK-NEXT: adda.l #20, %sp ; CHECK-NEXT: rts ; CHECK-NEXT: .LBB5_1: ; %T -; CHECK-NEXT: move.l #1, %d0 +; CHECK-NEXT: moveq #1, %d0 ; CHECK-NEXT: adda.l #20, %sp ; CHECK-NEXT: rts %A = alloca {i64, i64}, align 8 @@ -229,7 +229,7 @@ define zeroext i1 @test15(i32 %bf.load, i32 %n) { ; CHECK-LABEL: test15: ; CHECK: .cfi_startproc ; CHECK-NEXT: ; %bb.0: -; CHECK-NEXT: move.l #16, %d0 +; CHECK-NEXT: moveq #16, %d0 ; CHECK-NEXT: move.l (4,%sp), %d1 ; CHECK-NEXT: lsr.l %d0, %d1 ; CHECK-NEXT: move.l %d1, %d0 @@ -252,7 +252,7 @@ define i8 @test16(i16 signext %L) { ; CHECK-LABEL: test16: ; CHECK: .cfi_startproc ; CHECK-NEXT: ; %bb.0: -; CHECK-NEXT: move.w #15, %d1 +; CHECK-NEXT: moveq #15, %d1 ; CHECK-NEXT: move.w (6,%sp), %d0 ; CHECK-NEXT: lsr.w %d1, %d0 ; CHECK-NEXT: eori.b #1, %d0 @@ -268,7 +268,7 @@ define i8 @test18(i64 %L) { ; CHECK-LABEL: test18: ; CHECK: .cfi_startproc ; CHECK-NEXT: ; %bb.0: -; CHECK-NEXT: move.l #31, %d1 +; CHECK-NEXT: moveq #31, %d1 ; CHECK-NEXT: move.l (4,%sp), %d0 ; CHECK-NEXT: lsr.l %d1, %d0 ; CHECK-NEXT: eori.b #1, %d0 diff --git a/llvm/test/CodeGen/M68k/Control/long-setcc.ll b/llvm/test/CodeGen/M68k/Control/long-setcc.ll index b089af5f2ae87439be4d948f69caac7d57a0c4a9..45a617599c1eb8e33702212485a0422ec590d670 100644 --- a/llvm/test/CodeGen/M68k/Control/long-setcc.ll +++ b/llvm/test/CodeGen/M68k/Control/long-setcc.ll @@ -4,7 +4,7 @@ define i1 @t1(i64 %x) nounwind { ; CHECK-LABEL: t1: ; CHECK: ; %bb.0: -; CHECK-NEXT: move.l #31, %d1 +; CHECK-NEXT: moveq #31, %d1 ; CHECK-NEXT: move.l (4,%sp), %d0 ; CHECK-NEXT: lsr.l %d1, %d0 ; CHECK-NEXT: ; kill: def $bd0 killed $bd0 killed $d0 @@ -26,7 +26,7 @@ define i1 @t2(i64 %x) nounwind { define i1 @t3(i32 %x) nounwind { ; CHECK-LABEL: t3: ; CHECK: ; %bb.0: -; CHECK-NEXT: move.b #0, %d0 +; CHECK-NEXT: moveq #0, %d0 ; CHECK-NEXT: rts %tmp = icmp ugt i32 %x, -1 ret i1 %tmp diff --git a/llvm/test/CodeGen/M68k/Control/setcc.ll b/llvm/test/CodeGen/M68k/Control/setcc.ll index 63856e278c9ee5983b1111ab8435446606c94853..9e03f9b90842ac0811dc23bc529b62c6bbbd1718 100644 --- a/llvm/test/CodeGen/M68k/Control/setcc.ll +++ b/llvm/test/CodeGen/M68k/Control/setcc.ll @@ -40,7 +40,7 @@ define fastcc i64 @t3(i64 %x) nounwind readnone ssp { ; CHECK: ; %bb.0: ; %entry ; CHECK-NEXT: suba.l #4, %sp ; CHECK-NEXT: movem.l %d2, (0,%sp) ; 8-byte Folded Spill -; CHECK-NEXT: move.l #0, %d2 +; CHECK-NEXT: moveq #0, %d2 ; CHECK-NEXT: sub.l #18, %d1 ; CHECK-NEXT: subx.l %d2, %d0 ; CHECK-NEXT: scs %d0 @@ -61,7 +61,7 @@ define i8 @t5(i32 %a) { ; CHECK-LABEL: t5: ; CHECK: .cfi_startproc ; CHECK-NEXT: ; %bb.0: ; %entry -; CHECK-NEXT: move.l #31, %d1 +; CHECK-NEXT: moveq #31, %d1 ; CHECK-NEXT: move.l (4,%sp), %d0 ; CHECK-NEXT: lsr.l %d1, %d0 ; CHECK-NEXT: eori.b #1, %d0 @@ -86,7 +86,7 @@ define zeroext i1 @t6(i32 %a) { ; CHECK-LABEL: t6: ; CHECK: .cfi_startproc ; CHECK-NEXT: ; %bb.0: ; %entry -; CHECK-NEXT: move.l #31, %d0 +; CHECK-NEXT: moveq #31, %d0 ; CHECK-NEXT: move.l (4,%sp), %d1 ; CHECK-NEXT: lsr.l %d0, %d1 ; CHECK-NEXT: eori.b #1, %d1 diff --git a/llvm/test/CodeGen/M68k/PR57660.ll b/llvm/test/CodeGen/M68k/PR57660.ll index 184c30a33d7919cbdbefd066e945f6fe13b58fd4..bad949b08cafac9eca6c0667f19b8512512e34f8 100644 --- a/llvm/test/CodeGen/M68k/PR57660.ll +++ b/llvm/test/CodeGen/M68k/PR57660.ll @@ -7,7 +7,7 @@ define dso_local void @foo1() { ; CHECK-NEXT: ; %bb.0: ; %entry ; CHECK-NEXT: suba.l #2, %sp ; CHECK-NEXT: .cfi_def_cfa_offset -6 -; CHECK-NEXT: move.b #0, %d0 +; CHECK-NEXT: moveq #0, %d0 ; CHECK-NEXT: move.b %d0, (0,%sp) ; 1-byte Folded Spill ; CHECK-NEXT: .LBB0_1: ; %do.body ; CHECK-NEXT: ; =>This Inner Loop Header: Depth=1 diff --git a/llvm/test/CodeGen/M68k/gcc_except_table.ll b/llvm/test/CodeGen/M68k/gcc_except_table.ll index a7d2a6662724ed29c77115bc61f251b1ac3b7864..fe0ed7861dfee88c6305d28967c78115b9dbbe83 100644 --- a/llvm/test/CodeGen/M68k/gcc_except_table.ll +++ b/llvm/test/CodeGen/M68k/gcc_except_table.ll @@ -19,7 +19,7 @@ define i32 @foo() uwtable ssp personality ptr @__gxx_personality_v0 { ; CHECK-NEXT: jsr _Z1fv@PLT ; CHECK-NEXT: .Ltmp1: ; CHECK-NEXT: ; %bb.1: ; %try.cont -; CHECK-NEXT: move.l #0, %d0 +; CHECK-NEXT: moveq #0, %d0 ; CHECK-NEXT: adda.l #4, %sp ; CHECK-NEXT: rts ; CHECK-NEXT: .LBB0_2: ; %lpad diff --git a/llvm/test/CodeGen/M68k/link-unlnk.ll b/llvm/test/CodeGen/M68k/link-unlnk.ll index dfdd80e66ade7871cea5f278cacde323bf98c93f..fe39a9a13494a1be41bdd2a3c3407366c499d20c 100644 --- a/llvm/test/CodeGen/M68k/link-unlnk.ll +++ b/llvm/test/CodeGen/M68k/link-unlnk.ll @@ -105,7 +105,7 @@ define i32 @test_gep() { ; FP-NEXT: .cfi_def_cfa_register %a6 ; FP-NEXT: move.l #21, (-4,%a6) ; FP-NEXT: move.l #12, (-256,%a6) -; FP-NEXT: move.l #0, %d0 +; FP-NEXT: moveq #0, %d0 ; FP-NEXT: unlk %a6 ; FP-NEXT: rts ; @@ -116,7 +116,7 @@ define i32 @test_gep() { ; NO-FP-NEXT: .cfi_def_cfa_offset -260 ; NO-FP-NEXT: move.l #21, (252,%sp) ; NO-FP-NEXT: move.l #12, (0,%sp) -; NO-FP-NEXT: move.l #0, %d0 +; NO-FP-NEXT: moveq #0, %d0 ; NO-FP-NEXT: adda.l #256, %sp ; NO-FP-NEXT: rts entry: diff --git a/llvm/test/CodeGen/Mips/atomic-min-max.ll b/llvm/test/CodeGen/Mips/atomic-min-max.ll index 2f07d70808c16aecaae0a3913245381afad8a739..3d3225509d1ae14eeb2f101538d331ba2db146e3 100644 --- a/llvm/test/CodeGen/Mips/atomic-min-max.ll +++ b/llvm/test/CodeGen/Mips/atomic-min-max.ll @@ -2156,8 +2156,7 @@ define i16 @test_umax_16(ptr nocapture %ptr, i16 signext %val) { ; MIPS32-NEXT: # =>This Inner Loop Header: Depth=1 ; MIPS32-NEXT: ll $2, 0($6) ; MIPS32-NEXT: srav $4, $2, $10 -; MIPS32-NEXT: sll $4, $4, 16 -; MIPS32-NEXT: srl $4, $4, 16 +; MIPS32-NEXT: andi $4, $4, 65535 ; MIPS32-NEXT: or $1, $zero, $4 ; MIPS32-NEXT: sllv $4, $4, $10 ; MIPS32-NEXT: sltu $5, $4, $7 @@ -2695,8 +2694,7 @@ define i16 @test_umin_16(ptr nocapture %ptr, i16 signext %val) { ; MIPS32-NEXT: # =>This Inner Loop Header: Depth=1 ; MIPS32-NEXT: ll $2, 0($6) ; MIPS32-NEXT: srav $4, $2, $10 -; MIPS32-NEXT: sll $4, $4, 16 -; MIPS32-NEXT: srl $4, $4, 16 +; MIPS32-NEXT: andi $4, $4, 65535 ; MIPS32-NEXT: or $1, $zero, $4 ; MIPS32-NEXT: sllv $4, $4, $10 ; MIPS32-NEXT: sltu $5, $4, $7 @@ -4313,8 +4311,7 @@ define i8 @test_umax_8(ptr nocapture %ptr, i8 signext %val) { ; MIPS32-NEXT: # =>This Inner Loop Header: Depth=1 ; MIPS32-NEXT: ll $2, 0($6) ; MIPS32-NEXT: srav $4, $2, $10 -; MIPS32-NEXT: sll $4, $4, 24 -; MIPS32-NEXT: srl $4, $4, 24 +; MIPS32-NEXT: andi $4, $4, 255 ; MIPS32-NEXT: or $1, $zero, $4 ; MIPS32-NEXT: sllv $4, $4, $10 ; MIPS32-NEXT: sltu $5, $4, $7 @@ -4852,8 +4849,7 @@ define i8 @test_umin_8(ptr nocapture %ptr, i8 signext %val) { ; MIPS32-NEXT: # =>This Inner Loop Header: Depth=1 ; MIPS32-NEXT: ll $2, 0($6) ; MIPS32-NEXT: srav $4, $2, $10 -; MIPS32-NEXT: sll $4, $4, 24 -; MIPS32-NEXT: srl $4, $4, 24 +; MIPS32-NEXT: andi $4, $4, 255 ; MIPS32-NEXT: or $1, $zero, $4 ; MIPS32-NEXT: sllv $4, $4, $10 ; MIPS32-NEXT: sltu $5, $4, $7 diff --git a/llvm/test/CodeGen/NVPTX/rsqrt-opt.ll b/llvm/test/CodeGen/NVPTX/rsqrt-opt.ll new file mode 100644 index 0000000000000000000000000000000000000000..9dda6075a23c6dec1e7ff61028e10a1c91fadf1e --- /dev/null +++ b/llvm/test/CodeGen/NVPTX/rsqrt-opt.ll @@ -0,0 +1,75 @@ +; RUN: llc < %s -march=nvptx64 | FileCheck %s --check-prefixes CHECK,CHECK-APPROX-OPT,CHECK-SQRT-NOOPT +; RUN: llc < %s -march=nvptx64 -nvptx-prec-sqrtf32=0 | FileCheck %s --check-prefixes CHECK,CHECK-APPROX-OPT,CHECK-SQRT-OPT +; RUN: llc < %s -march=nvptx64 -nvptx-rsqrt-approx-opt=0 | FileCheck %s --check-prefixes CHECK,CHECK-APPROX-NOOPT,CHECK-SQRT-NOOPT +; +; RUN: %if ptxas %{ llc < %s -march=nvptx64 | %ptxas-verify %} +; RUN: %if ptxas %{ llc < %s -march=nvptx64 -nvptx-prec-sqrtf32=0 | %ptxas-verify %} +; RUN: %if ptxas %{ llc < %s -march=nvptx64 -nvptx-rsqrt-approx-opt=0 | %ptxas-verify %} + + +; CHECK-LABEL: .func{{.*}}test1 +define float @test1(float %in) local_unnamed_addr { +; CHECK-APPROX-OPT: rsqrt.approx.f32 +; CHECK-APPROX-NOOPT: sqrt.approx.f32 +; CHECK-APPROX-NOOPT-NEXT: rcp.rn.f32 + %sqrt = tail call float @llvm.nvvm.sqrt.approx.f(float %in) + %rsqrt = fdiv float 1.0, %sqrt + ret float %rsqrt +} +; CHECK-LABEL: .func{{.*}}test2 +define float @test2(float %in) local_unnamed_addr { +; CHECK-APPROX-OPT: rsqrt.approx.ftz.f32 +; CHECK-APPROX-NOOPT: sqrt.approx.ftz.f32 +; CHECK-APPROX-NOOPT-NEXT: rcp.rn.f32 + %sqrt = tail call float @llvm.nvvm.sqrt.approx.ftz.f(float %in) + %rsqrt = fdiv float 1.0, %sqrt + ret float %rsqrt +} + +; CHECK-LABEL: .func{{.*}}test3 +define float @test3(float %in) local_unnamed_addr { +; CHECK-SQRT-OPT: rsqrt.approx.f32 +; CHECK-SQRT-NOOPT: sqrt.rn.f32 +; CHECK-SQRT-NOOPT-NEXT: rcp.rn.f32 + %sqrt = tail call float @llvm.nvvm.sqrt.f(float %in) + %rsqrt = fdiv float 1.0, %sqrt + ret float %rsqrt +} + +; CHECK-LABEL: .func{{.*}}test4 +define float @test4(float %in) local_unnamed_addr #0 { +; CHECK-SQRT-OPT: rsqrt.approx.ftz.f32 +; CHECK-SQRT-NOOPT: sqrt.rn.ftz.f32 +; CHECK-SQRT-NOOPT-NEXT: rcp.rn.ftz.f32 + %sqrt = tail call float @llvm.nvvm.sqrt.f(float %in) + %rsqrt = fdiv float 1.0, %sqrt + ret float %rsqrt +} + +; CHECK-LABEL: .func{{.*}}test5 +define float @test5(float %in) local_unnamed_addr { +; CHECK-SQRT-OPT: rsqrt.approx.f32 +; CHECK-SQRT-NOOPT: sqrt.rn.f32 +; CHECK-SQRT-NOOPT-NEXT: rcp.rn.f32 + %sqrt = tail call float @llvm.sqrt.f32(float %in) + %rsqrt = fdiv float 1.0, %sqrt + ret float %rsqrt +} + +; CHECK-LABEL: .func{{.*}}test6 +define float @test6(float %in) local_unnamed_addr #0 { +; CHECK-SQRT-OPT: rsqrt.approx.ftz.f32 +; CHECK-SQRT-NOOPT: sqrt.rn.ftz.f32 +; CHECK-SQRT-NOOPT-NEXT: rcp.rn.ftz.f32 + %sqrt = tail call float @llvm.sqrt.f32(float %in) + %rsqrt = fdiv float 1.0, %sqrt + ret float %rsqrt +} + + +declare float @llvm.nvvm.sqrt.f(float) +declare float @llvm.nvvm.sqrt.approx.f(float) +declare float @llvm.nvvm.sqrt.approx.ftz.f(float) +declare float @llvm.sqrt.f32(float) + +attributes #0 = { "denormal-fp-math-f32" = "preserve-sign" } diff --git a/llvm/test/CodeGen/NVPTX/rsqrt.ll b/llvm/test/CodeGen/NVPTX/rsqrt.ll new file mode 100644 index 0000000000000000000000000000000000000000..c7367245c532e33bc7f692ca03850b784229a699 --- /dev/null +++ b/llvm/test/CodeGen/NVPTX/rsqrt.ll @@ -0,0 +1,35 @@ +; RUN: llc < %s -march=nvptx64 | FileCheck %s +; RUN: %if ptxas %{ llc < %s -march=nvptx64 | %ptxas-verify %} + +; CHECK-LABEL: .func{{.*}}test1 +define float @test1(float %in) local_unnamed_addr { +; CHECK: rsqrt.approx.f32 + %call = call float @llvm.nvvm.rsqrt.approx.f(float %in) + ret float %call +} + +; CHECK-LABEL: .func{{.*}}test2 +define double @test2(double %in) local_unnamed_addr { +; CHECK: rsqrt.approx.f64 + %call = call double @llvm.nvvm.rsqrt.approx.d(double %in) + ret double %call +} + +; CHECK-LABEL: .func{{.*}}test3 +define float @test3(float %in) local_unnamed_addr { +; CHECK: rsqrt.approx.ftz.f32 + %call = tail call float @llvm.nvvm.rsqrt.approx.ftz.f(float %in) + ret float %call +} + +; CHECK-LABEL: .func{{.*}}test4 +define double @test4(double %in) local_unnamed_addr { +; CHECK: rsqrt.approx.ftz.f64 + %call = tail call double @llvm.nvvm.rsqrt.approx.ftz.d(double %in) + ret double %call +} + +declare float @llvm.nvvm.rsqrt.approx.ftz.f(float) +declare double @llvm.nvvm.rsqrt.approx.ftz.d(double) +declare float @llvm.nvvm.rsqrt.approx.f(float) +declare double @llvm.nvvm.rsqrt.approx.d(double) diff --git a/llvm/test/CodeGen/PowerPC/legalize-vaarg.ll b/llvm/test/CodeGen/PowerPC/legalize-vaarg.ll index 8980049969da430b480f05df68b4ccddbfe5b919..b7f8b8af2472aa3071663bb6fefc4f4557ef9a8e 100644 --- a/llvm/test/CodeGen/PowerPC/legalize-vaarg.ll +++ b/llvm/test/CodeGen/PowerPC/legalize-vaarg.ll @@ -1,7 +1,6 @@ ; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py ;RUN: llc < %s --mtriple=powerpc64-unknown-linux-gnu -mattr=+altivec | FileCheck %s -check-prefix=BE ;RUN: llc < %s --mtriple=powerpc64le-unknown-linux-gnu -mattr=+altivec | FileCheck %s -check-prefix=LE -;RUN: llc < %s --mtriple=powerpc64-unknown-linux-gnu -mattr=+altivec -ppc-gather-alias-max-depth=0 | FileCheck %s -check-prefix=FORWARD define <8 x i32> @test_large_vec_vaarg(i32 %n, ...) { ; BE-LABEL: test_large_vec_vaarg: @@ -36,22 +35,6 @@ define <8 x i32> @test_large_vec_vaarg(i32 %n, ...) { ; LE-NEXT: lxvd2x 0, 0, 3 ; LE-NEXT: xxswapd 35, 0 ; LE-NEXT: blr -; -; FORWARD-LABEL: test_large_vec_vaarg: -; FORWARD: # %bb.0: -; FORWARD-NEXT: ld 3, -8(1) -; FORWARD-NEXT: addi 3, 3, 15 -; FORWARD-NEXT: rldicr 3, 3, 0, 59 -; FORWARD-NEXT: addi 4, 3, 16 -; FORWARD-NEXT: std 4, -8(1) -; FORWARD-NEXT: ld 4, -8(1) -; FORWARD-NEXT: lvx 2, 0, 3 -; FORWARD-NEXT: addi 4, 4, 15 -; FORWARD-NEXT: rldicr 3, 4, 0, 59 -; FORWARD-NEXT: addi 4, 3, 16 -; FORWARD-NEXT: std 4, -8(1) -; FORWARD-NEXT: lvx 3, 0, 3 -; FORWARD-NEXT: blr %args = alloca ptr, align 4 %x = va_arg ptr %args, <8 x i32> ret <8 x i32> %x diff --git a/llvm/test/CodeGen/RISCV/O0-pipeline.ll b/llvm/test/CodeGen/RISCV/O0-pipeline.ll index faf37545e1a1171c70a7e52eaf85f865aa4013f0..56bd4bd0c08f0961e2b85d7dc36394207ac1ad7f 100644 --- a/llvm/test/CodeGen/RISCV/O0-pipeline.ll +++ b/llvm/test/CodeGen/RISCV/O0-pipeline.ll @@ -47,6 +47,10 @@ ; CHECK-NEXT: Eliminate PHI nodes for register allocation ; CHECK-NEXT: Two-Address instruction pass ; CHECK-NEXT: Fast Register Allocator +; CHECK-NEXT: MachineDominator Tree Construction +; CHECK-NEXT: Slot index numbering +; CHECK-NEXT: Live Interval Analysis +; CHECK-NEXT: RISC-V Coalesce VSETVLI pass ; CHECK-NEXT: Fast Register Allocator ; CHECK-NEXT: Remove Redundant DEBUG_VALUE analysis ; CHECK-NEXT: Fixup Statepoint Caller Saved diff --git a/llvm/test/CodeGen/RISCV/O3-pipeline.ll b/llvm/test/CodeGen/RISCV/O3-pipeline.ll index 90472f246918f342f683dd09edd6507b6706cb0e..4121d111091117e07ac6804d91dcd8fd73c008a5 100644 --- a/llvm/test/CodeGen/RISCV/O3-pipeline.ll +++ b/llvm/test/CodeGen/RISCV/O3-pipeline.ll @@ -143,6 +143,7 @@ ; CHECK-NEXT: Machine Optimization Remark Emitter ; CHECK-NEXT: Greedy Register Allocator ; CHECK-NEXT: Virtual Register Rewriter +; CHECK-NEXT: RISC-V Coalesce VSETVLI pass ; CHECK-NEXT: Virtual Register Map ; CHECK-NEXT: Live Register Matrix ; CHECK-NEXT: Greedy Register Allocator diff --git a/llvm/test/CodeGen/RISCV/addimm-mulimm.ll b/llvm/test/CodeGen/RISCV/addimm-mulimm.ll index 48fa69e10456563d70d026ca7109d40106b80dd0..8fb251a75bd142c9691ba3c4bb0595a6d2438ced 100644 --- a/llvm/test/CodeGen/RISCV/addimm-mulimm.ll +++ b/llvm/test/CodeGen/RISCV/addimm-mulimm.ll @@ -10,15 +10,17 @@ define i32 @add_mul_combine_accept_a1(i32 %x) { ; RV32IMB-LABEL: add_mul_combine_accept_a1: ; RV32IMB: # %bb.0: -; RV32IMB-NEXT: li a1, 29 -; RV32IMB-NEXT: mul a0, a0, a1 +; RV32IMB-NEXT: sh1add a1, a0, a0 +; RV32IMB-NEXT: slli a0, a0, 5 +; RV32IMB-NEXT: sub a0, a0, a1 ; RV32IMB-NEXT: addi a0, a0, 1073 ; RV32IMB-NEXT: ret ; ; RV64IMB-LABEL: add_mul_combine_accept_a1: ; RV64IMB: # %bb.0: -; RV64IMB-NEXT: li a1, 29 -; RV64IMB-NEXT: mul a0, a0, a1 +; RV64IMB-NEXT: sh1add a1, a0, a0 +; RV64IMB-NEXT: slli a0, a0, 5 +; RV64IMB-NEXT: subw a0, a0, a1 ; RV64IMB-NEXT: addiw a0, a0, 1073 ; RV64IMB-NEXT: ret %tmp0 = add i32 %x, 37 @@ -29,15 +31,17 @@ define i32 @add_mul_combine_accept_a1(i32 %x) { define signext i32 @add_mul_combine_accept_a2(i32 signext %x) { ; RV32IMB-LABEL: add_mul_combine_accept_a2: ; RV32IMB: # %bb.0: -; RV32IMB-NEXT: li a1, 29 -; RV32IMB-NEXT: mul a0, a0, a1 +; RV32IMB-NEXT: sh1add a1, a0, a0 +; RV32IMB-NEXT: slli a0, a0, 5 +; RV32IMB-NEXT: sub a0, a0, a1 ; RV32IMB-NEXT: addi a0, a0, 1073 ; RV32IMB-NEXT: ret ; ; RV64IMB-LABEL: add_mul_combine_accept_a2: ; RV64IMB: # %bb.0: -; RV64IMB-NEXT: li a1, 29 -; RV64IMB-NEXT: mul a0, a0, a1 +; RV64IMB-NEXT: sh1add a1, a0, a0 +; RV64IMB-NEXT: slli a0, a0, 5 +; RV64IMB-NEXT: subw a0, a0, a1 ; RV64IMB-NEXT: addiw a0, a0, 1073 ; RV64IMB-NEXT: ret %tmp0 = add i32 %x, 37 @@ -49,10 +53,14 @@ define i64 @add_mul_combine_accept_a3(i64 %x) { ; RV32IMB-LABEL: add_mul_combine_accept_a3: ; RV32IMB: # %bb.0: ; RV32IMB-NEXT: li a2, 29 -; RV32IMB-NEXT: mul a1, a1, a2 -; RV32IMB-NEXT: mulhu a3, a0, a2 -; RV32IMB-NEXT: add a1, a3, a1 -; RV32IMB-NEXT: mul a2, a0, a2 +; RV32IMB-NEXT: mulhu a2, a0, a2 +; RV32IMB-NEXT: sh1add a3, a1, a1 +; RV32IMB-NEXT: slli a1, a1, 5 +; RV32IMB-NEXT: sub a1, a1, a3 +; RV32IMB-NEXT: add a1, a2, a1 +; RV32IMB-NEXT: sh1add a2, a0, a0 +; RV32IMB-NEXT: slli a0, a0, 5 +; RV32IMB-NEXT: sub a2, a0, a2 ; RV32IMB-NEXT: addi a0, a2, 1073 ; RV32IMB-NEXT: sltu a2, a0, a2 ; RV32IMB-NEXT: add a1, a1, a2 @@ -60,8 +68,9 @@ define i64 @add_mul_combine_accept_a3(i64 %x) { ; ; RV64IMB-LABEL: add_mul_combine_accept_a3: ; RV64IMB: # %bb.0: -; RV64IMB-NEXT: li a1, 29 -; RV64IMB-NEXT: mul a0, a0, a1 +; RV64IMB-NEXT: sh1add a1, a0, a0 +; RV64IMB-NEXT: slli a0, a0, 5 +; RV64IMB-NEXT: sub a0, a0, a1 ; RV64IMB-NEXT: addi a0, a0, 1073 ; RV64IMB-NEXT: ret %tmp0 = add i64 %x, 37 @@ -72,8 +81,9 @@ define i64 @add_mul_combine_accept_a3(i64 %x) { define i32 @add_mul_combine_accept_b1(i32 %x) { ; RV32IMB-LABEL: add_mul_combine_accept_b1: ; RV32IMB: # %bb.0: -; RV32IMB-NEXT: li a1, 23 -; RV32IMB-NEXT: mul a0, a0, a1 +; RV32IMB-NEXT: sh3add a1, a0, a0 +; RV32IMB-NEXT: slli a0, a0, 5 +; RV32IMB-NEXT: sub a0, a0, a1 ; RV32IMB-NEXT: lui a1, 50 ; RV32IMB-NEXT: addi a1, a1, 1119 ; RV32IMB-NEXT: add a0, a0, a1 @@ -81,8 +91,9 @@ define i32 @add_mul_combine_accept_b1(i32 %x) { ; ; RV64IMB-LABEL: add_mul_combine_accept_b1: ; RV64IMB: # %bb.0: -; RV64IMB-NEXT: li a1, 23 -; RV64IMB-NEXT: mul a0, a0, a1 +; RV64IMB-NEXT: sh3add a1, a0, a0 +; RV64IMB-NEXT: slli a0, a0, 5 +; RV64IMB-NEXT: subw a0, a0, a1 ; RV64IMB-NEXT: lui a1, 50 ; RV64IMB-NEXT: addi a1, a1, 1119 ; RV64IMB-NEXT: addw a0, a0, a1 @@ -95,8 +106,9 @@ define i32 @add_mul_combine_accept_b1(i32 %x) { define signext i32 @add_mul_combine_accept_b2(i32 signext %x) { ; RV32IMB-LABEL: add_mul_combine_accept_b2: ; RV32IMB: # %bb.0: -; RV32IMB-NEXT: li a1, 23 -; RV32IMB-NEXT: mul a0, a0, a1 +; RV32IMB-NEXT: sh3add a1, a0, a0 +; RV32IMB-NEXT: slli a0, a0, 5 +; RV32IMB-NEXT: sub a0, a0, a1 ; RV32IMB-NEXT: lui a1, 50 ; RV32IMB-NEXT: addi a1, a1, 1119 ; RV32IMB-NEXT: add a0, a0, a1 @@ -104,8 +116,9 @@ define signext i32 @add_mul_combine_accept_b2(i32 signext %x) { ; ; RV64IMB-LABEL: add_mul_combine_accept_b2: ; RV64IMB: # %bb.0: -; RV64IMB-NEXT: li a1, 23 -; RV64IMB-NEXT: mul a0, a0, a1 +; RV64IMB-NEXT: sh3add a1, a0, a0 +; RV64IMB-NEXT: slli a0, a0, 5 +; RV64IMB-NEXT: subw a0, a0, a1 ; RV64IMB-NEXT: lui a1, 50 ; RV64IMB-NEXT: addi a1, a1, 1119 ; RV64IMB-NEXT: addw a0, a0, a1 @@ -119,10 +132,14 @@ define i64 @add_mul_combine_accept_b3(i64 %x) { ; RV32IMB-LABEL: add_mul_combine_accept_b3: ; RV32IMB: # %bb.0: ; RV32IMB-NEXT: li a2, 23 -; RV32IMB-NEXT: mul a1, a1, a2 -; RV32IMB-NEXT: mulhu a3, a0, a2 -; RV32IMB-NEXT: add a1, a3, a1 -; RV32IMB-NEXT: mul a2, a0, a2 +; RV32IMB-NEXT: mulhu a2, a0, a2 +; RV32IMB-NEXT: sh3add a3, a1, a1 +; RV32IMB-NEXT: slli a1, a1, 5 +; RV32IMB-NEXT: sub a1, a1, a3 +; RV32IMB-NEXT: add a1, a2, a1 +; RV32IMB-NEXT: sh3add a2, a0, a0 +; RV32IMB-NEXT: slli a0, a0, 5 +; RV32IMB-NEXT: sub a2, a0, a2 ; RV32IMB-NEXT: lui a0, 50 ; RV32IMB-NEXT: addi a0, a0, 1119 ; RV32IMB-NEXT: add a0, a2, a0 @@ -132,8 +149,9 @@ define i64 @add_mul_combine_accept_b3(i64 %x) { ; ; RV64IMB-LABEL: add_mul_combine_accept_b3: ; RV64IMB: # %bb.0: -; RV64IMB-NEXT: li a1, 23 -; RV64IMB-NEXT: mul a0, a0, a1 +; RV64IMB-NEXT: sh3add a1, a0, a0 +; RV64IMB-NEXT: slli a0, a0, 5 +; RV64IMB-NEXT: sub a0, a0, a1 ; RV64IMB-NEXT: lui a1, 50 ; RV64IMB-NEXT: addiw a1, a1, 1119 ; RV64IMB-NEXT: add a0, a0, a1 @@ -147,15 +165,17 @@ define i32 @add_mul_combine_reject_a1(i32 %x) { ; RV32IMB-LABEL: add_mul_combine_reject_a1: ; RV32IMB: # %bb.0: ; RV32IMB-NEXT: addi a0, a0, 1971 -; RV32IMB-NEXT: li a1, 29 -; RV32IMB-NEXT: mul a0, a0, a1 +; RV32IMB-NEXT: sh1add a1, a0, a0 +; RV32IMB-NEXT: slli a0, a0, 5 +; RV32IMB-NEXT: sub a0, a0, a1 ; RV32IMB-NEXT: ret ; ; RV64IMB-LABEL: add_mul_combine_reject_a1: ; RV64IMB: # %bb.0: ; RV64IMB-NEXT: addi a0, a0, 1971 -; RV64IMB-NEXT: li a1, 29 -; RV64IMB-NEXT: mulw a0, a0, a1 +; RV64IMB-NEXT: sh1add a1, a0, a0 +; RV64IMB-NEXT: slli a0, a0, 5 +; RV64IMB-NEXT: subw a0, a0, a1 ; RV64IMB-NEXT: ret %tmp0 = add i32 %x, 1971 %tmp1 = mul i32 %tmp0, 29 @@ -166,15 +186,17 @@ define signext i32 @add_mul_combine_reject_a2(i32 signext %x) { ; RV32IMB-LABEL: add_mul_combine_reject_a2: ; RV32IMB: # %bb.0: ; RV32IMB-NEXT: addi a0, a0, 1971 -; RV32IMB-NEXT: li a1, 29 -; RV32IMB-NEXT: mul a0, a0, a1 +; RV32IMB-NEXT: sh1add a1, a0, a0 +; RV32IMB-NEXT: slli a0, a0, 5 +; RV32IMB-NEXT: sub a0, a0, a1 ; RV32IMB-NEXT: ret ; ; RV64IMB-LABEL: add_mul_combine_reject_a2: ; RV64IMB: # %bb.0: ; RV64IMB-NEXT: addi a0, a0, 1971 -; RV64IMB-NEXT: li a1, 29 -; RV64IMB-NEXT: mulw a0, a0, a1 +; RV64IMB-NEXT: sh1add a1, a0, a0 +; RV64IMB-NEXT: slli a0, a0, 5 +; RV64IMB-NEXT: subw a0, a0, a1 ; RV64IMB-NEXT: ret %tmp0 = add i32 %x, 1971 %tmp1 = mul i32 %tmp0, 29 @@ -185,10 +207,14 @@ define i64 @add_mul_combine_reject_a3(i64 %x) { ; RV32IMB-LABEL: add_mul_combine_reject_a3: ; RV32IMB: # %bb.0: ; RV32IMB-NEXT: li a2, 29 -; RV32IMB-NEXT: mul a1, a1, a2 -; RV32IMB-NEXT: mulhu a3, a0, a2 -; RV32IMB-NEXT: add a1, a3, a1 -; RV32IMB-NEXT: mul a2, a0, a2 +; RV32IMB-NEXT: mulhu a2, a0, a2 +; RV32IMB-NEXT: sh1add a3, a1, a1 +; RV32IMB-NEXT: slli a1, a1, 5 +; RV32IMB-NEXT: sub a1, a1, a3 +; RV32IMB-NEXT: add a1, a2, a1 +; RV32IMB-NEXT: sh1add a2, a0, a0 +; RV32IMB-NEXT: slli a0, a0, 5 +; RV32IMB-NEXT: sub a2, a0, a2 ; RV32IMB-NEXT: lui a0, 14 ; RV32IMB-NEXT: addi a0, a0, -185 ; RV32IMB-NEXT: add a0, a2, a0 @@ -199,8 +225,9 @@ define i64 @add_mul_combine_reject_a3(i64 %x) { ; RV64IMB-LABEL: add_mul_combine_reject_a3: ; RV64IMB: # %bb.0: ; RV64IMB-NEXT: addi a0, a0, 1971 -; RV64IMB-NEXT: li a1, 29 -; RV64IMB-NEXT: mul a0, a0, a1 +; RV64IMB-NEXT: sh1add a1, a0, a0 +; RV64IMB-NEXT: slli a0, a0, 5 +; RV64IMB-NEXT: sub a0, a0, a1 ; RV64IMB-NEXT: ret %tmp0 = add i64 %x, 1971 %tmp1 = mul i64 %tmp0, 29 @@ -251,10 +278,12 @@ define i64 @add_mul_combine_reject_c3(i64 %x) { ; RV32IMB-LABEL: add_mul_combine_reject_c3: ; RV32IMB: # %bb.0: ; RV32IMB-NEXT: li a2, 73 -; RV32IMB-NEXT: mul a1, a1, a2 -; RV32IMB-NEXT: mulhu a3, a0, a2 -; RV32IMB-NEXT: add a1, a3, a1 -; RV32IMB-NEXT: mul a2, a0, a2 +; RV32IMB-NEXT: mulhu a2, a0, a2 +; RV32IMB-NEXT: sh3add a3, a1, a1 +; RV32IMB-NEXT: sh3add a1, a3, a1 +; RV32IMB-NEXT: add a1, a2, a1 +; RV32IMB-NEXT: sh3add a2, a0, a0 +; RV32IMB-NEXT: sh3add a2, a2, a0 ; RV32IMB-NEXT: lui a0, 18 ; RV32IMB-NEXT: addi a0, a0, -728 ; RV32IMB-NEXT: add a0, a2, a0 @@ -343,15 +372,17 @@ define i32 @add_mul_combine_reject_e1(i32 %x) { ; RV32IMB-LABEL: add_mul_combine_reject_e1: ; RV32IMB: # %bb.0: ; RV32IMB-NEXT: addi a0, a0, 1971 -; RV32IMB-NEXT: li a1, 29 -; RV32IMB-NEXT: mul a0, a0, a1 +; RV32IMB-NEXT: sh1add a1, a0, a0 +; RV32IMB-NEXT: slli a0, a0, 5 +; RV32IMB-NEXT: sub a0, a0, a1 ; RV32IMB-NEXT: ret ; ; RV64IMB-LABEL: add_mul_combine_reject_e1: ; RV64IMB: # %bb.0: ; RV64IMB-NEXT: addi a0, a0, 1971 -; RV64IMB-NEXT: li a1, 29 -; RV64IMB-NEXT: mulw a0, a0, a1 +; RV64IMB-NEXT: sh1add a1, a0, a0 +; RV64IMB-NEXT: slli a0, a0, 5 +; RV64IMB-NEXT: subw a0, a0, a1 ; RV64IMB-NEXT: ret %tmp0 = mul i32 %x, 29 %tmp1 = add i32 %tmp0, 57159 @@ -362,15 +393,17 @@ define signext i32 @add_mul_combine_reject_e2(i32 signext %x) { ; RV32IMB-LABEL: add_mul_combine_reject_e2: ; RV32IMB: # %bb.0: ; RV32IMB-NEXT: addi a0, a0, 1971 -; RV32IMB-NEXT: li a1, 29 -; RV32IMB-NEXT: mul a0, a0, a1 +; RV32IMB-NEXT: sh1add a1, a0, a0 +; RV32IMB-NEXT: slli a0, a0, 5 +; RV32IMB-NEXT: sub a0, a0, a1 ; RV32IMB-NEXT: ret ; ; RV64IMB-LABEL: add_mul_combine_reject_e2: ; RV64IMB: # %bb.0: ; RV64IMB-NEXT: addi a0, a0, 1971 -; RV64IMB-NEXT: li a1, 29 -; RV64IMB-NEXT: mulw a0, a0, a1 +; RV64IMB-NEXT: sh1add a1, a0, a0 +; RV64IMB-NEXT: slli a0, a0, 5 +; RV64IMB-NEXT: subw a0, a0, a1 ; RV64IMB-NEXT: ret %tmp0 = mul i32 %x, 29 %tmp1 = add i32 %tmp0, 57159 @@ -381,10 +414,14 @@ define i64 @add_mul_combine_reject_e3(i64 %x) { ; RV32IMB-LABEL: add_mul_combine_reject_e3: ; RV32IMB: # %bb.0: ; RV32IMB-NEXT: li a2, 29 -; RV32IMB-NEXT: mul a1, a1, a2 -; RV32IMB-NEXT: mulhu a3, a0, a2 -; RV32IMB-NEXT: add a1, a3, a1 -; RV32IMB-NEXT: mul a2, a0, a2 +; RV32IMB-NEXT: mulhu a2, a0, a2 +; RV32IMB-NEXT: sh1add a3, a1, a1 +; RV32IMB-NEXT: slli a1, a1, 5 +; RV32IMB-NEXT: sub a1, a1, a3 +; RV32IMB-NEXT: add a1, a2, a1 +; RV32IMB-NEXT: sh1add a2, a0, a0 +; RV32IMB-NEXT: slli a0, a0, 5 +; RV32IMB-NEXT: sub a2, a0, a2 ; RV32IMB-NEXT: lui a0, 14 ; RV32IMB-NEXT: addi a0, a0, -185 ; RV32IMB-NEXT: add a0, a2, a0 @@ -395,8 +432,9 @@ define i64 @add_mul_combine_reject_e3(i64 %x) { ; RV64IMB-LABEL: add_mul_combine_reject_e3: ; RV64IMB: # %bb.0: ; RV64IMB-NEXT: addi a0, a0, 1971 -; RV64IMB-NEXT: li a1, 29 -; RV64IMB-NEXT: mul a0, a0, a1 +; RV64IMB-NEXT: sh1add a1, a0, a0 +; RV64IMB-NEXT: slli a0, a0, 5 +; RV64IMB-NEXT: sub a0, a0, a1 ; RV64IMB-NEXT: ret %tmp0 = mul i64 %x, 29 %tmp1 = add i64 %tmp0, 57159 @@ -407,16 +445,18 @@ define i32 @add_mul_combine_reject_f1(i32 %x) { ; RV32IMB-LABEL: add_mul_combine_reject_f1: ; RV32IMB: # %bb.0: ; RV32IMB-NEXT: addi a0, a0, 1972 -; RV32IMB-NEXT: li a1, 29 -; RV32IMB-NEXT: mul a0, a0, a1 +; RV32IMB-NEXT: sh1add a1, a0, a0 +; RV32IMB-NEXT: slli a0, a0, 5 +; RV32IMB-NEXT: sub a0, a0, a1 ; RV32IMB-NEXT: addi a0, a0, 11 ; RV32IMB-NEXT: ret ; ; RV64IMB-LABEL: add_mul_combine_reject_f1: ; RV64IMB: # %bb.0: ; RV64IMB-NEXT: addi a0, a0, 1972 -; RV64IMB-NEXT: li a1, 29 -; RV64IMB-NEXT: mul a0, a0, a1 +; RV64IMB-NEXT: sh1add a1, a0, a0 +; RV64IMB-NEXT: slli a0, a0, 5 +; RV64IMB-NEXT: subw a0, a0, a1 ; RV64IMB-NEXT: addiw a0, a0, 11 ; RV64IMB-NEXT: ret %tmp0 = mul i32 %x, 29 @@ -428,16 +468,18 @@ define signext i32 @add_mul_combine_reject_f2(i32 signext %x) { ; RV32IMB-LABEL: add_mul_combine_reject_f2: ; RV32IMB: # %bb.0: ; RV32IMB-NEXT: addi a0, a0, 1972 -; RV32IMB-NEXT: li a1, 29 -; RV32IMB-NEXT: mul a0, a0, a1 +; RV32IMB-NEXT: sh1add a1, a0, a0 +; RV32IMB-NEXT: slli a0, a0, 5 +; RV32IMB-NEXT: sub a0, a0, a1 ; RV32IMB-NEXT: addi a0, a0, 11 ; RV32IMB-NEXT: ret ; ; RV64IMB-LABEL: add_mul_combine_reject_f2: ; RV64IMB: # %bb.0: ; RV64IMB-NEXT: addi a0, a0, 1972 -; RV64IMB-NEXT: li a1, 29 -; RV64IMB-NEXT: mul a0, a0, a1 +; RV64IMB-NEXT: sh1add a1, a0, a0 +; RV64IMB-NEXT: slli a0, a0, 5 +; RV64IMB-NEXT: subw a0, a0, a1 ; RV64IMB-NEXT: addiw a0, a0, 11 ; RV64IMB-NEXT: ret %tmp0 = mul i32 %x, 29 @@ -449,10 +491,14 @@ define i64 @add_mul_combine_reject_f3(i64 %x) { ; RV32IMB-LABEL: add_mul_combine_reject_f3: ; RV32IMB: # %bb.0: ; RV32IMB-NEXT: li a2, 29 -; RV32IMB-NEXT: mul a1, a1, a2 -; RV32IMB-NEXT: mulhu a3, a0, a2 -; RV32IMB-NEXT: add a1, a3, a1 -; RV32IMB-NEXT: mul a2, a0, a2 +; RV32IMB-NEXT: mulhu a2, a0, a2 +; RV32IMB-NEXT: sh1add a3, a1, a1 +; RV32IMB-NEXT: slli a1, a1, 5 +; RV32IMB-NEXT: sub a1, a1, a3 +; RV32IMB-NEXT: add a1, a2, a1 +; RV32IMB-NEXT: sh1add a2, a0, a0 +; RV32IMB-NEXT: slli a0, a0, 5 +; RV32IMB-NEXT: sub a2, a0, a2 ; RV32IMB-NEXT: lui a0, 14 ; RV32IMB-NEXT: addi a0, a0, -145 ; RV32IMB-NEXT: add a0, a2, a0 @@ -463,8 +509,9 @@ define i64 @add_mul_combine_reject_f3(i64 %x) { ; RV64IMB-LABEL: add_mul_combine_reject_f3: ; RV64IMB: # %bb.0: ; RV64IMB-NEXT: addi a0, a0, 1972 -; RV64IMB-NEXT: li a1, 29 -; RV64IMB-NEXT: mul a0, a0, a1 +; RV64IMB-NEXT: sh1add a1, a0, a0 +; RV64IMB-NEXT: slli a0, a0, 5 +; RV64IMB-NEXT: sub a0, a0, a1 ; RV64IMB-NEXT: addi a0, a0, 11 ; RV64IMB-NEXT: ret %tmp0 = mul i64 %x, 29 @@ -518,10 +565,12 @@ define i64 @add_mul_combine_reject_g3(i64 %x) { ; RV32IMB-LABEL: add_mul_combine_reject_g3: ; RV32IMB: # %bb.0: ; RV32IMB-NEXT: li a2, 73 -; RV32IMB-NEXT: mul a1, a1, a2 -; RV32IMB-NEXT: mulhu a3, a0, a2 -; RV32IMB-NEXT: add a1, a3, a1 -; RV32IMB-NEXT: mul a2, a0, a2 +; RV32IMB-NEXT: mulhu a2, a0, a2 +; RV32IMB-NEXT: sh3add a3, a1, a1 +; RV32IMB-NEXT: sh3add a1, a3, a1 +; RV32IMB-NEXT: add a1, a2, a1 +; RV32IMB-NEXT: sh3add a2, a0, a0 +; RV32IMB-NEXT: sh3add a2, a2, a0 ; RV32IMB-NEXT: lui a0, 2 ; RV32IMB-NEXT: addi a0, a0, -882 ; RV32IMB-NEXT: add a0, a2, a0 diff --git a/llvm/test/CodeGen/RISCV/alu64.ll b/llvm/test/CodeGen/RISCV/alu64.ll index d2ee80e6aa9513db80f344d4a55dc3170e69312d..f032756e007b684a4ddbd50bbc119f69f0236bd0 100644 --- a/llvm/test/CodeGen/RISCV/alu64.ll +++ b/llvm/test/CodeGen/RISCV/alu64.ll @@ -57,8 +57,8 @@ define i64 @sltiu(i64 %a) nounwind { ; ; RV32I-LABEL: sltiu: ; RV32I: # %bb.0: -; RV32I-NEXT: seqz a1, a1 ; RV32I-NEXT: sltiu a0, a0, 3 +; RV32I-NEXT: seqz a1, a1 ; RV32I-NEXT: and a0, a1, a0 ; RV32I-NEXT: li a1, 0 ; RV32I-NEXT: ret diff --git a/llvm/test/CodeGen/RISCV/atomicrmw-uinc-udec-wrap.ll b/llvm/test/CodeGen/RISCV/atomicrmw-uinc-udec-wrap.ll index f96e1bad2e3895ff93e2a3fd5d02525bccef14f9..a5a2ae79966c3f47eb66912273ce0d2c17cdf5f6 100644 --- a/llvm/test/CodeGen/RISCV/atomicrmw-uinc-udec-wrap.ll +++ b/llvm/test/CodeGen/RISCV/atomicrmw-uinc-udec-wrap.ll @@ -372,10 +372,10 @@ define i32 @atomicrmw_uinc_wrap_i32(ptr %ptr, i32 %val) { ; RV32IA-NEXT: # =>This Loop Header: Depth=1 ; RV32IA-NEXT: # Child Loop BB2_3 Depth 2 ; RV32IA-NEXT: mv a3, a2 -; RV32IA-NEXT: addi a4, a2, 1 -; RV32IA-NEXT: sltu a2, a2, a1 -; RV32IA-NEXT: neg a2, a2 -; RV32IA-NEXT: and a4, a2, a4 +; RV32IA-NEXT: addi a2, a2, 1 +; RV32IA-NEXT: sltu a4, a3, a1 +; RV32IA-NEXT: neg a4, a4 +; RV32IA-NEXT: and a4, a4, a2 ; RV32IA-NEXT: .LBB2_3: # %atomicrmw.start ; RV32IA-NEXT: # Parent Loop BB2_1 Depth=1 ; RV32IA-NEXT: # => This Inner Loop Header: Depth=2 @@ -607,10 +607,10 @@ define i64 @atomicrmw_uinc_wrap_i64(ptr %ptr, i64 %val) { ; RV64IA-NEXT: # =>This Loop Header: Depth=1 ; RV64IA-NEXT: # Child Loop BB3_3 Depth 2 ; RV64IA-NEXT: mv a3, a2 -; RV64IA-NEXT: addi a4, a2, 1 -; RV64IA-NEXT: sltu a2, a2, a1 -; RV64IA-NEXT: neg a2, a2 -; RV64IA-NEXT: and a4, a2, a4 +; RV64IA-NEXT: addi a2, a2, 1 +; RV64IA-NEXT: sltu a4, a3, a1 +; RV64IA-NEXT: neg a4, a4 +; RV64IA-NEXT: and a4, a4, a2 ; RV64IA-NEXT: .LBB3_3: # %atomicrmw.start ; RV64IA-NEXT: # Parent Loop BB3_1 Depth=1 ; RV64IA-NEXT: # => This Inner Loop Header: Depth=2 diff --git a/llvm/test/CodeGen/RISCV/attributes.ll b/llvm/test/CodeGen/RISCV/attributes.ll index 080783fdeec0241082ae43e15a3b72eb545c66b4..141d5ea4182892d5cb0b1e6f7dd9ddcf779814a7 100644 --- a/llvm/test/CodeGen/RISCV/attributes.ll +++ b/llvm/test/CodeGen/RISCV/attributes.ll @@ -112,12 +112,12 @@ ; RUN: llc -mtriple=riscv32 -mattr=+experimental-zvfbfmin %s -o - | FileCheck --check-prefixes=CHECK,RV32ZVFBFMIN %s ; RUN: llc -mtriple=riscv32 -mattr=+experimental-zvfbfwma %s -o - | FileCheck --check-prefixes=CHECK,RV32ZVFBFWMA %s ; RUN: llc -mtriple=riscv32 -mattr=+experimental-zaamo %s -o - | FileCheck --check-prefix=RV32ZAAMO %s -; RUN: llc -mtriple=riscv32 -mattr=+zacas %s -o - | FileCheck --check-prefix=RV32ZACAS %s +; RUN: llc -mtriple=riscv32 -mattr=+a,zacas %s -o - | FileCheck --check-prefix=RV32ZACAS %s ; RUN: llc -mtriple=riscv32 -mattr=+experimental-zalasr %s -o - | FileCheck --check-prefix=RV32ZALASR %s ; RUN: llc -mtriple=riscv32 -mattr=+experimental-zalrsc %s -o - | FileCheck --check-prefix=RV32ZALRSC %s ; RUN: llc -mtriple=riscv32 -mattr=+zama16b %s -o - | FileCheck --check-prefixes=CHECK,RV32ZAMA16B %s ; RUN: llc -mtriple=riscv32 -mattr=+experimental-zicfilp %s -o - | FileCheck --check-prefix=RV32ZICFILP %s -; RUN: llc -mtriple=riscv32 -mattr=+experimental-zabha %s -o - | FileCheck --check-prefix=RV32ZABHA %s +; RUN: llc -mtriple=riscv32 -mattr=+a,+experimental-zabha %s -o - | FileCheck --check-prefix=RV32ZABHA %s ; RUN: llc -mtriple=riscv32 -mattr=+experimental-ssnpm %s -o - | FileCheck --check-prefix=RV32SSNPM %s ; RUN: llc -mtriple=riscv32 -mattr=+experimental-smnpm %s -o - | FileCheck --check-prefix=RV32SMNPM %s ; RUN: llc -mtriple=riscv32 -mattr=+experimental-smmpm %s -o - | FileCheck --check-prefix=RV32SMMPM %s @@ -244,11 +244,11 @@ ; RUN: llc -mtriple=riscv64 -mattr=+experimental-zvfbfmin %s -o - | FileCheck --check-prefixes=CHECK,RV64ZVFBFMIN %s ; RUN: llc -mtriple=riscv64 -mattr=+experimental-zvfbfwma %s -o - | FileCheck --check-prefixes=CHECK,RV64ZVFBFWMA %s ; RUN: llc -mtriple=riscv64 -mattr=+experimental-zaamo %s -o - | FileCheck --check-prefix=RV64ZAAMO %s -; RUN: llc -mtriple=riscv64 -mattr=+zacas %s -o - | FileCheck --check-prefix=RV64ZACAS %s +; RUN: llc -mtriple=riscv64 -mattr=+a,zacas %s -o - | FileCheck --check-prefix=RV64ZACAS %s ; RUN: llc -mtriple=riscv64 -mattr=+experimental-zalasr %s -o - | FileCheck --check-prefix=RV64ZALASR %s ; RUN: llc -mtriple=riscv64 -mattr=+experimental-zalrsc %s -o - | FileCheck --check-prefix=RV64ZALRSC %s ; RUN: llc -mtriple=riscv64 -mattr=+experimental-zicfilp %s -o - | FileCheck --check-prefix=RV64ZICFILP %s -; RUN: llc -mtriple=riscv64 -mattr=+experimental-zabha %s -o - | FileCheck --check-prefix=RV64ZABHA %s +; RUN: llc -mtriple=riscv64 -mattr=+a,+experimental-zabha %s -o - | FileCheck --check-prefix=RV64ZABHA %s ; RUN: llc -mtriple=riscv64 -mattr=+experimental-ssnpm %s -o - | FileCheck --check-prefix=RV64SSNPM %s ; RUN: llc -mtriple=riscv64 -mattr=+experimental-smnpm %s -o - | FileCheck --check-prefix=RV64SMNPM %s ; RUN: llc -mtriple=riscv64 -mattr=+experimental-smmpm %s -o - | FileCheck --check-prefix=RV64SMMPM %s @@ -326,7 +326,7 @@ ; RV32XSFVFWMACCQQQ: .attribute 5, "rv32i2p1_f2p2_zicsr2p0_zve32f1p0_zve32x1p0_zvfbfmin1p0_zvl32b1p0_xsfvfwmaccqqq1p0" ; RV32XTHEADCMO: .attribute 5, "rv32i2p1_xtheadcmo1p0" ; RV32XTHEADCONDMOV: .attribute 5, "rv32i2p1_xtheadcondmov1p0" -; RV32XTHEADFMEMIDX: .attribute 5, "rv32i2p1_f2p2_zicsr2p0_xtheadfmemidx1p0" +; RV32XTHEADFMEMIDX: .attribute 5, "rv32i2p1_xtheadfmemidx1p0" ; RV32XTHEADMAC: .attribute 5, "rv32i2p1_xtheadmac1p0" ; RV32XTHEADMEMIDX: .attribute 5, "rv32i2p1_xtheadmemidx1p0" ; RV32XTHEADMEMPAIR: .attribute 5, "rv32i2p1_xtheadmempair1p0" @@ -452,7 +452,7 @@ ; RV64XTHEADBS: .attribute 5, "rv64i2p1_xtheadbs1p0" ; RV64XTHEADCMO: .attribute 5, "rv64i2p1_xtheadcmo1p0" ; RV64XTHEADCONDMOV: .attribute 5, "rv64i2p1_xtheadcondmov1p0" -; RV64XTHEADFMEMIDX: .attribute 5, "rv64i2p1_f2p2_zicsr2p0_xtheadfmemidx1p0" +; RV64XTHEADFMEMIDX: .attribute 5, "rv64i2p1_xtheadfmemidx1p0" ; RV64XTHEADMAC: .attribute 5, "rv64i2p1_xtheadmac1p0" ; RV64XTHEADMEMIDX: .attribute 5, "rv64i2p1_xtheadmemidx1p0" ; RV64XTHEADMEMPAIR: .attribute 5, "rv64i2p1_xtheadmempair1p0" diff --git a/llvm/test/CodeGen/RISCV/bfloat-convert.ll b/llvm/test/CodeGen/RISCV/bfloat-convert.ll index 9e2b0b5c3cbb411a78cef1901c91e2af049b6168..770dcccee882bec40c19875a7fec5acd1b826527 100644 --- a/llvm/test/CodeGen/RISCV/bfloat-convert.ll +++ b/llvm/test/CodeGen/RISCV/bfloat-convert.ll @@ -456,92 +456,80 @@ define i64 @fcvt_l_bf16(bfloat %a) nounwind { define i64 @fcvt_l_bf16_sat(bfloat %a) nounwind { ; RV32IZFBFMIN-LABEL: fcvt_l_bf16_sat: ; RV32IZFBFMIN: # %bb.0: # %start -; RV32IZFBFMIN-NEXT: addi sp, sp, -32 -; RV32IZFBFMIN-NEXT: sw ra, 28(sp) # 4-byte Folded Spill -; RV32IZFBFMIN-NEXT: sw s0, 24(sp) # 4-byte Folded Spill -; RV32IZFBFMIN-NEXT: sw s1, 20(sp) # 4-byte Folded Spill -; RV32IZFBFMIN-NEXT: sw s2, 16(sp) # 4-byte Folded Spill -; RV32IZFBFMIN-NEXT: sw s3, 12(sp) # 4-byte Folded Spill -; RV32IZFBFMIN-NEXT: fsw fs0, 8(sp) # 4-byte Folded Spill -; RV32IZFBFMIN-NEXT: lui a0, %hi(.LCPI10_0) -; RV32IZFBFMIN-NEXT: flw fa5, %lo(.LCPI10_0)(a0) +; RV32IZFBFMIN-NEXT: addi sp, sp, -16 +; RV32IZFBFMIN-NEXT: sw ra, 12(sp) # 4-byte Folded Spill +; RV32IZFBFMIN-NEXT: sw s0, 8(sp) # 4-byte Folded Spill +; RV32IZFBFMIN-NEXT: fsw fs0, 4(sp) # 4-byte Folded Spill ; RV32IZFBFMIN-NEXT: fcvt.s.bf16 fs0, fa0 -; RV32IZFBFMIN-NEXT: flt.s s0, fa5, fs0 -; RV32IZFBFMIN-NEXT: neg s1, s0 ; RV32IZFBFMIN-NEXT: lui a0, 913408 ; RV32IZFBFMIN-NEXT: fmv.w.x fa5, a0 -; RV32IZFBFMIN-NEXT: fle.s s2, fa5, fs0 -; RV32IZFBFMIN-NEXT: neg s3, s2 +; RV32IZFBFMIN-NEXT: fle.s s0, fa5, fs0 ; RV32IZFBFMIN-NEXT: fmv.s fa0, fs0 ; RV32IZFBFMIN-NEXT: call __fixsfdi -; RV32IZFBFMIN-NEXT: and a0, s3, a0 -; RV32IZFBFMIN-NEXT: or a0, s1, a0 -; RV32IZFBFMIN-NEXT: feq.s a2, fs0, fs0 -; RV32IZFBFMIN-NEXT: neg a2, a2 ; RV32IZFBFMIN-NEXT: lui a4, 524288 -; RV32IZFBFMIN-NEXT: lui a3, 524288 -; RV32IZFBFMIN-NEXT: beqz s2, .LBB10_2 +; RV32IZFBFMIN-NEXT: lui a2, 524288 +; RV32IZFBFMIN-NEXT: beqz s0, .LBB10_2 ; RV32IZFBFMIN-NEXT: # %bb.1: # %start -; RV32IZFBFMIN-NEXT: mv a3, a1 +; RV32IZFBFMIN-NEXT: mv a2, a1 ; RV32IZFBFMIN-NEXT: .LBB10_2: # %start -; RV32IZFBFMIN-NEXT: and a0, a2, a0 -; RV32IZFBFMIN-NEXT: beqz s0, .LBB10_4 +; RV32IZFBFMIN-NEXT: lui a1, %hi(.LCPI10_0) +; RV32IZFBFMIN-NEXT: flw fa5, %lo(.LCPI10_0)(a1) +; RV32IZFBFMIN-NEXT: flt.s a3, fa5, fs0 +; RV32IZFBFMIN-NEXT: beqz a3, .LBB10_4 ; RV32IZFBFMIN-NEXT: # %bb.3: -; RV32IZFBFMIN-NEXT: addi a3, a4, -1 +; RV32IZFBFMIN-NEXT: addi a2, a4, -1 ; RV32IZFBFMIN-NEXT: .LBB10_4: # %start -; RV32IZFBFMIN-NEXT: and a1, a2, a3 -; RV32IZFBFMIN-NEXT: lw ra, 28(sp) # 4-byte Folded Reload -; RV32IZFBFMIN-NEXT: lw s0, 24(sp) # 4-byte Folded Reload -; RV32IZFBFMIN-NEXT: lw s1, 20(sp) # 4-byte Folded Reload -; RV32IZFBFMIN-NEXT: lw s2, 16(sp) # 4-byte Folded Reload -; RV32IZFBFMIN-NEXT: lw s3, 12(sp) # 4-byte Folded Reload -; RV32IZFBFMIN-NEXT: flw fs0, 8(sp) # 4-byte Folded Reload -; RV32IZFBFMIN-NEXT: addi sp, sp, 32 +; RV32IZFBFMIN-NEXT: feq.s a1, fs0, fs0 +; RV32IZFBFMIN-NEXT: neg a4, a1 +; RV32IZFBFMIN-NEXT: and a1, a4, a2 +; RV32IZFBFMIN-NEXT: neg a2, a3 +; RV32IZFBFMIN-NEXT: neg a3, s0 +; RV32IZFBFMIN-NEXT: and a0, a3, a0 +; RV32IZFBFMIN-NEXT: or a0, a2, a0 +; RV32IZFBFMIN-NEXT: and a0, a4, a0 +; RV32IZFBFMIN-NEXT: lw ra, 12(sp) # 4-byte Folded Reload +; RV32IZFBFMIN-NEXT: lw s0, 8(sp) # 4-byte Folded Reload +; RV32IZFBFMIN-NEXT: flw fs0, 4(sp) # 4-byte Folded Reload +; RV32IZFBFMIN-NEXT: addi sp, sp, 16 ; RV32IZFBFMIN-NEXT: ret ; ; R32IDZFBFMIN-LABEL: fcvt_l_bf16_sat: ; R32IDZFBFMIN: # %bb.0: # %start -; R32IDZFBFMIN-NEXT: addi sp, sp, -32 -; R32IDZFBFMIN-NEXT: sw ra, 28(sp) # 4-byte Folded Spill -; R32IDZFBFMIN-NEXT: sw s0, 24(sp) # 4-byte Folded Spill -; R32IDZFBFMIN-NEXT: sw s1, 20(sp) # 4-byte Folded Spill -; R32IDZFBFMIN-NEXT: sw s2, 16(sp) # 4-byte Folded Spill -; R32IDZFBFMIN-NEXT: sw s3, 12(sp) # 4-byte Folded Spill +; R32IDZFBFMIN-NEXT: addi sp, sp, -16 +; R32IDZFBFMIN-NEXT: sw ra, 12(sp) # 4-byte Folded Spill +; R32IDZFBFMIN-NEXT: sw s0, 8(sp) # 4-byte Folded Spill ; R32IDZFBFMIN-NEXT: fsd fs0, 0(sp) # 8-byte Folded Spill -; R32IDZFBFMIN-NEXT: lui a0, %hi(.LCPI10_0) -; R32IDZFBFMIN-NEXT: flw fa5, %lo(.LCPI10_0)(a0) ; R32IDZFBFMIN-NEXT: fcvt.s.bf16 fs0, fa0 -; R32IDZFBFMIN-NEXT: flt.s s0, fa5, fs0 -; R32IDZFBFMIN-NEXT: neg s1, s0 ; R32IDZFBFMIN-NEXT: lui a0, 913408 ; R32IDZFBFMIN-NEXT: fmv.w.x fa5, a0 -; R32IDZFBFMIN-NEXT: fle.s s2, fa5, fs0 -; R32IDZFBFMIN-NEXT: neg s3, s2 +; R32IDZFBFMIN-NEXT: fle.s s0, fa5, fs0 ; R32IDZFBFMIN-NEXT: fmv.s fa0, fs0 ; R32IDZFBFMIN-NEXT: call __fixsfdi -; R32IDZFBFMIN-NEXT: and a0, s3, a0 -; R32IDZFBFMIN-NEXT: or a0, s1, a0 -; R32IDZFBFMIN-NEXT: feq.s a2, fs0, fs0 -; R32IDZFBFMIN-NEXT: neg a2, a2 ; R32IDZFBFMIN-NEXT: lui a4, 524288 -; R32IDZFBFMIN-NEXT: lui a3, 524288 -; R32IDZFBFMIN-NEXT: beqz s2, .LBB10_2 +; R32IDZFBFMIN-NEXT: lui a2, 524288 +; R32IDZFBFMIN-NEXT: beqz s0, .LBB10_2 ; R32IDZFBFMIN-NEXT: # %bb.1: # %start -; R32IDZFBFMIN-NEXT: mv a3, a1 +; R32IDZFBFMIN-NEXT: mv a2, a1 ; R32IDZFBFMIN-NEXT: .LBB10_2: # %start -; R32IDZFBFMIN-NEXT: and a0, a2, a0 -; R32IDZFBFMIN-NEXT: beqz s0, .LBB10_4 +; R32IDZFBFMIN-NEXT: lui a1, %hi(.LCPI10_0) +; R32IDZFBFMIN-NEXT: flw fa5, %lo(.LCPI10_0)(a1) +; R32IDZFBFMIN-NEXT: flt.s a3, fa5, fs0 +; R32IDZFBFMIN-NEXT: beqz a3, .LBB10_4 ; R32IDZFBFMIN-NEXT: # %bb.3: -; R32IDZFBFMIN-NEXT: addi a3, a4, -1 +; R32IDZFBFMIN-NEXT: addi a2, a4, -1 ; R32IDZFBFMIN-NEXT: .LBB10_4: # %start -; R32IDZFBFMIN-NEXT: and a1, a2, a3 -; R32IDZFBFMIN-NEXT: lw ra, 28(sp) # 4-byte Folded Reload -; R32IDZFBFMIN-NEXT: lw s0, 24(sp) # 4-byte Folded Reload -; R32IDZFBFMIN-NEXT: lw s1, 20(sp) # 4-byte Folded Reload -; R32IDZFBFMIN-NEXT: lw s2, 16(sp) # 4-byte Folded Reload -; R32IDZFBFMIN-NEXT: lw s3, 12(sp) # 4-byte Folded Reload +; R32IDZFBFMIN-NEXT: feq.s a1, fs0, fs0 +; R32IDZFBFMIN-NEXT: neg a4, a1 +; R32IDZFBFMIN-NEXT: and a1, a4, a2 +; R32IDZFBFMIN-NEXT: neg a2, a3 +; R32IDZFBFMIN-NEXT: neg a3, s0 +; R32IDZFBFMIN-NEXT: and a0, a3, a0 +; R32IDZFBFMIN-NEXT: or a0, a2, a0 +; R32IDZFBFMIN-NEXT: and a0, a4, a0 +; R32IDZFBFMIN-NEXT: lw ra, 12(sp) # 4-byte Folded Reload +; R32IDZFBFMIN-NEXT: lw s0, 8(sp) # 4-byte Folded Reload ; R32IDZFBFMIN-NEXT: fld fs0, 0(sp) # 8-byte Folded Reload -; R32IDZFBFMIN-NEXT: addi sp, sp, 32 +; R32IDZFBFMIN-NEXT: addi sp, sp, 16 ; R32IDZFBFMIN-NEXT: ret ; ; RV32ID-LABEL: fcvt_l_bf16_sat: diff --git a/llvm/test/CodeGen/RISCV/bitreverse-shift.ll b/llvm/test/CodeGen/RISCV/bitreverse-shift.ll index f29b16991726266d1f44e232fea49e67a9fa51c0..b0281ba7d2385401971f120b690a0ae37d43177a 100644 --- a/llvm/test/CodeGen/RISCV/bitreverse-shift.ll +++ b/llvm/test/CodeGen/RISCV/bitreverse-shift.ll @@ -4,7 +4,7 @@ ; RUN: llc -mtriple=riscv64 -mattr=+zbkb -verify-machineinstrs < %s \ ; RUN: | FileCheck %s -check-prefixes=RV64ZBKB -; TODO: These tests can be optmised +; TODO: These tests can be optimised ; fold (bitreverse(srl (bitreverse c), x)) -> (shl c, x) ; fold (bitreverse(shl (bitreverse c), x)) -> (srl c, x) diff --git a/llvm/test/CodeGen/RISCV/double-convert.ll b/llvm/test/CodeGen/RISCV/double-convert.ll index c147d6ec6d9b15b4c5caa8c71edc718b276f5151..6024a29da33d2e3c2dc9c8ffb4f73933e8779d86 100644 --- a/llvm/test/CodeGen/RISCV/double-convert.ll +++ b/llvm/test/CodeGen/RISCV/double-convert.ll @@ -692,28 +692,27 @@ define i64 @fcvt_l_d_sat(double %a) nounwind { ; RV32IFD-NEXT: fmv.d fs0, fa0 ; RV32IFD-NEXT: fle.d s0, fa5, fa0 ; RV32IFD-NEXT: call __fixdfdi -; RV32IFD-NEXT: lui a3, 524288 -; RV32IFD-NEXT: li a4, 1 +; RV32IFD-NEXT: lui a4, 524288 ; RV32IFD-NEXT: lui a2, 524288 -; RV32IFD-NEXT: bne s0, a4, .LBB12_2 +; RV32IFD-NEXT: beqz s0, .LBB12_2 ; RV32IFD-NEXT: # %bb.1: # %start ; RV32IFD-NEXT: mv a2, a1 ; RV32IFD-NEXT: .LBB12_2: # %start ; RV32IFD-NEXT: lui a1, %hi(.LCPI12_1) ; RV32IFD-NEXT: fld fa5, %lo(.LCPI12_1)(a1) -; RV32IFD-NEXT: flt.d a4, fa5, fs0 -; RV32IFD-NEXT: beqz a4, .LBB12_4 +; RV32IFD-NEXT: flt.d a3, fa5, fs0 +; RV32IFD-NEXT: beqz a3, .LBB12_4 ; RV32IFD-NEXT: # %bb.3: -; RV32IFD-NEXT: addi a2, a3, -1 +; RV32IFD-NEXT: addi a2, a4, -1 ; RV32IFD-NEXT: .LBB12_4: # %start ; RV32IFD-NEXT: feq.d a1, fs0, fs0 -; RV32IFD-NEXT: neg a3, a1 -; RV32IFD-NEXT: and a1, a3, a2 -; RV32IFD-NEXT: neg a2, a4 -; RV32IFD-NEXT: neg a4, s0 -; RV32IFD-NEXT: and a0, a4, a0 -; RV32IFD-NEXT: or a0, a2, a0 +; RV32IFD-NEXT: neg a4, a1 +; RV32IFD-NEXT: and a1, a4, a2 +; RV32IFD-NEXT: neg a2, a3 +; RV32IFD-NEXT: neg a3, s0 ; RV32IFD-NEXT: and a0, a3, a0 +; RV32IFD-NEXT: or a0, a2, a0 +; RV32IFD-NEXT: and a0, a4, a0 ; RV32IFD-NEXT: lw ra, 12(sp) # 4-byte Folded Reload ; RV32IFD-NEXT: lw s0, 8(sp) # 4-byte Folded Reload ; RV32IFD-NEXT: fld fs0, 0(sp) # 8-byte Folded Reload @@ -790,33 +789,32 @@ define i64 @fcvt_l_d_sat(double %a) nounwind { ; RV32I-NEXT: sw s3, 12(sp) # 4-byte Folded Spill ; RV32I-NEXT: sw s4, 8(sp) # 4-byte Folded Spill ; RV32I-NEXT: sw s5, 4(sp) # 4-byte Folded Spill -; RV32I-NEXT: sw s6, 0(sp) # 4-byte Folded Spill ; RV32I-NEXT: mv s0, a1 ; RV32I-NEXT: mv s1, a0 +; RV32I-NEXT: lui a3, 278016 +; RV32I-NEXT: addi a3, a3, -1 +; RV32I-NEXT: li a2, -1 +; RV32I-NEXT: call __gtdf2 +; RV32I-NEXT: mv s2, a0 ; RV32I-NEXT: lui a3, 802304 +; RV32I-NEXT: mv a0, s1 +; RV32I-NEXT: mv a1, s0 ; RV32I-NEXT: li a2, 0 ; RV32I-NEXT: call __gedf2 -; RV32I-NEXT: mv s2, a0 +; RV32I-NEXT: mv s3, a0 ; RV32I-NEXT: mv a0, s1 ; RV32I-NEXT: mv a1, s0 ; RV32I-NEXT: call __fixdfdi -; RV32I-NEXT: mv s3, a0 -; RV32I-NEXT: mv s4, a1 -; RV32I-NEXT: lui s6, 524288 -; RV32I-NEXT: bgez s2, .LBB12_2 +; RV32I-NEXT: mv s4, a0 +; RV32I-NEXT: mv s5, a1 +; RV32I-NEXT: lui a0, 524288 +; RV32I-NEXT: bgez s3, .LBB12_2 ; RV32I-NEXT: # %bb.1: # %start -; RV32I-NEXT: lui s4, 524288 +; RV32I-NEXT: lui s5, 524288 ; RV32I-NEXT: .LBB12_2: # %start -; RV32I-NEXT: lui a3, 278016 -; RV32I-NEXT: addi a3, a3, -1 -; RV32I-NEXT: li a2, -1 -; RV32I-NEXT: mv a0, s1 -; RV32I-NEXT: mv a1, s0 -; RV32I-NEXT: call __gtdf2 -; RV32I-NEXT: mv s5, a0 -; RV32I-NEXT: blez a0, .LBB12_4 +; RV32I-NEXT: blez s2, .LBB12_4 ; RV32I-NEXT: # %bb.3: # %start -; RV32I-NEXT: addi s4, s6, -1 +; RV32I-NEXT: addi s5, a0, -1 ; RV32I-NEXT: .LBB12_4: # %start ; RV32I-NEXT: mv a0, s1 ; RV32I-NEXT: mv a1, s0 @@ -825,11 +823,11 @@ define i64 @fcvt_l_d_sat(double %a) nounwind { ; RV32I-NEXT: call __unorddf2 ; RV32I-NEXT: snez a0, a0 ; RV32I-NEXT: addi a0, a0, -1 -; RV32I-NEXT: and a1, a0, s4 -; RV32I-NEXT: slti a2, s2, 0 +; RV32I-NEXT: and a1, a0, s5 +; RV32I-NEXT: slti a2, s3, 0 ; RV32I-NEXT: addi a2, a2, -1 -; RV32I-NEXT: and a2, a2, s3 -; RV32I-NEXT: sgtz a3, s5 +; RV32I-NEXT: and a2, a2, s4 +; RV32I-NEXT: sgtz a3, s2 ; RV32I-NEXT: neg a3, a3 ; RV32I-NEXT: or a2, a3, a2 ; RV32I-NEXT: and a0, a0, a2 @@ -840,7 +838,6 @@ define i64 @fcvt_l_d_sat(double %a) nounwind { ; RV32I-NEXT: lw s3, 12(sp) # 4-byte Folded Reload ; RV32I-NEXT: lw s4, 8(sp) # 4-byte Folded Reload ; RV32I-NEXT: lw s5, 4(sp) # 4-byte Folded Reload -; RV32I-NEXT: lw s6, 0(sp) # 4-byte Folded Reload ; RV32I-NEXT: addi sp, sp, 32 ; RV32I-NEXT: ret ; @@ -949,22 +946,23 @@ define i64 @fcvt_lu_d_sat(double %a) nounwind { ; RV32IFD-NEXT: addi sp, sp, -16 ; RV32IFD-NEXT: sw ra, 12(sp) # 4-byte Folded Spill ; RV32IFD-NEXT: sw s0, 8(sp) # 4-byte Folded Spill -; RV32IFD-NEXT: sw s1, 4(sp) # 4-byte Folded Spill -; RV32IFD-NEXT: lui a0, %hi(.LCPI14_0) -; RV32IFD-NEXT: fld fa5, %lo(.LCPI14_0)(a0) -; RV32IFD-NEXT: flt.d a0, fa5, fa0 -; RV32IFD-NEXT: neg s0, a0 +; RV32IFD-NEXT: fsd fs0, 0(sp) # 8-byte Folded Spill +; RV32IFD-NEXT: fmv.d fs0, fa0 ; RV32IFD-NEXT: fcvt.d.w fa5, zero ; RV32IFD-NEXT: fle.d a0, fa5, fa0 -; RV32IFD-NEXT: neg s1, a0 +; RV32IFD-NEXT: neg s0, a0 ; RV32IFD-NEXT: call __fixunsdfdi -; RV32IFD-NEXT: and a0, s1, a0 -; RV32IFD-NEXT: or a0, s0, a0 -; RV32IFD-NEXT: and a1, s1, a1 -; RV32IFD-NEXT: or a1, s0, a1 +; RV32IFD-NEXT: lui a2, %hi(.LCPI14_0) +; RV32IFD-NEXT: fld fa5, %lo(.LCPI14_0)(a2) +; RV32IFD-NEXT: and a0, s0, a0 +; RV32IFD-NEXT: flt.d a2, fa5, fs0 +; RV32IFD-NEXT: neg a2, a2 +; RV32IFD-NEXT: or a0, a2, a0 +; RV32IFD-NEXT: and a1, s0, a1 +; RV32IFD-NEXT: or a1, a2, a1 ; RV32IFD-NEXT: lw ra, 12(sp) # 4-byte Folded Reload ; RV32IFD-NEXT: lw s0, 8(sp) # 4-byte Folded Reload -; RV32IFD-NEXT: lw s1, 4(sp) # 4-byte Folded Reload +; RV32IFD-NEXT: fld fs0, 0(sp) # 8-byte Folded Reload ; RV32IFD-NEXT: addi sp, sp, 16 ; RV32IFD-NEXT: ret ; @@ -983,27 +981,24 @@ define i64 @fcvt_lu_d_sat(double %a) nounwind { ; RV32IZFINXZDINX-NEXT: sw ra, 12(sp) # 4-byte Folded Spill ; RV32IZFINXZDINX-NEXT: sw s0, 8(sp) # 4-byte Folded Spill ; RV32IZFINXZDINX-NEXT: sw s1, 4(sp) # 4-byte Folded Spill -; RV32IZFINXZDINX-NEXT: sw s2, 0(sp) # 4-byte Folded Spill ; RV32IZFINXZDINX-NEXT: mv s1, a1 -; RV32IZFINXZDINX-NEXT: fcvt.d.w a2, zero ; RV32IZFINXZDINX-NEXT: mv s0, a0 -; RV32IZFINXZDINX-NEXT: fle.d a0, a2, s0 -; RV32IZFINXZDINX-NEXT: neg s2, a0 -; RV32IZFINXZDINX-NEXT: mv a0, s0 ; RV32IZFINXZDINX-NEXT: call __fixunsdfdi -; RV32IZFINXZDINX-NEXT: lui a2, %hi(.LCPI14_0) -; RV32IZFINXZDINX-NEXT: lw a3, %lo(.LCPI14_0+4)(a2) -; RV32IZFINXZDINX-NEXT: lw a2, %lo(.LCPI14_0)(a2) -; RV32IZFINXZDINX-NEXT: and a0, s2, a0 -; RV32IZFINXZDINX-NEXT: flt.d a2, a2, s0 +; RV32IZFINXZDINX-NEXT: fcvt.d.w a2, zero +; RV32IZFINXZDINX-NEXT: lui a4, %hi(.LCPI14_0) +; RV32IZFINXZDINX-NEXT: lw a5, %lo(.LCPI14_0+4)(a4) +; RV32IZFINXZDINX-NEXT: lw a4, %lo(.LCPI14_0)(a4) +; RV32IZFINXZDINX-NEXT: fle.d a2, a2, s0 ; RV32IZFINXZDINX-NEXT: neg a2, a2 -; RV32IZFINXZDINX-NEXT: or a0, a2, a0 -; RV32IZFINXZDINX-NEXT: and a1, s2, a1 -; RV32IZFINXZDINX-NEXT: or a1, a2, a1 +; RV32IZFINXZDINX-NEXT: and a0, a2, a0 +; RV32IZFINXZDINX-NEXT: flt.d a3, a4, s0 +; RV32IZFINXZDINX-NEXT: neg a3, a3 +; RV32IZFINXZDINX-NEXT: or a0, a3, a0 +; RV32IZFINXZDINX-NEXT: and a1, a2, a1 +; RV32IZFINXZDINX-NEXT: or a1, a3, a1 ; RV32IZFINXZDINX-NEXT: lw ra, 12(sp) # 4-byte Folded Reload ; RV32IZFINXZDINX-NEXT: lw s0, 8(sp) # 4-byte Folded Reload ; RV32IZFINXZDINX-NEXT: lw s1, 4(sp) # 4-byte Folded Reload -; RV32IZFINXZDINX-NEXT: lw s2, 0(sp) # 4-byte Folded Reload ; RV32IZFINXZDINX-NEXT: addi sp, sp, 16 ; RV32IZFINXZDINX-NEXT: ret ; diff --git a/llvm/test/CodeGen/RISCV/double-round-conv-sat.ll b/llvm/test/CodeGen/RISCV/double-round-conv-sat.ll index f1c56b320b76c467d90022ba99d556bc8945fc55..927eee2e9e54512e44d1f43babdfa2d6ee5599ca 100644 --- a/llvm/test/CodeGen/RISCV/double-round-conv-sat.ll +++ b/llvm/test/CodeGen/RISCV/double-round-conv-sat.ll @@ -53,28 +53,27 @@ define i64 @test_floor_si64(double %x) nounwind { ; RV32IFD-NEXT: fmv.d fs0, fa0 ; RV32IFD-NEXT: fle.d s0, fa5, fa0 ; RV32IFD-NEXT: call __fixdfdi -; RV32IFD-NEXT: lui a3, 524288 -; RV32IFD-NEXT: li a4, 1 +; RV32IFD-NEXT: lui a4, 524288 ; RV32IFD-NEXT: lui a2, 524288 -; RV32IFD-NEXT: bne s0, a4, .LBB1_2 +; RV32IFD-NEXT: beqz s0, .LBB1_2 ; RV32IFD-NEXT: # %bb.1: ; RV32IFD-NEXT: mv a2, a1 ; RV32IFD-NEXT: .LBB1_2: ; RV32IFD-NEXT: lui a1, %hi(.LCPI1_1) ; RV32IFD-NEXT: fld fa5, %lo(.LCPI1_1)(a1) -; RV32IFD-NEXT: flt.d a4, fa5, fs0 -; RV32IFD-NEXT: beqz a4, .LBB1_4 +; RV32IFD-NEXT: flt.d a3, fa5, fs0 +; RV32IFD-NEXT: beqz a3, .LBB1_4 ; RV32IFD-NEXT: # %bb.3: -; RV32IFD-NEXT: addi a2, a3, -1 +; RV32IFD-NEXT: addi a2, a4, -1 ; RV32IFD-NEXT: .LBB1_4: ; RV32IFD-NEXT: feq.d a1, fs0, fs0 -; RV32IFD-NEXT: neg a3, a1 -; RV32IFD-NEXT: and a1, a3, a2 -; RV32IFD-NEXT: neg a2, a4 -; RV32IFD-NEXT: neg a4, s0 -; RV32IFD-NEXT: and a0, a4, a0 -; RV32IFD-NEXT: or a0, a2, a0 +; RV32IFD-NEXT: neg a4, a1 +; RV32IFD-NEXT: and a1, a4, a2 +; RV32IFD-NEXT: neg a2, a3 +; RV32IFD-NEXT: neg a3, s0 ; RV32IFD-NEXT: and a0, a3, a0 +; RV32IFD-NEXT: or a0, a2, a0 +; RV32IFD-NEXT: and a0, a4, a0 ; RV32IFD-NEXT: lw ra, 12(sp) # 4-byte Folded Reload ; RV32IFD-NEXT: lw s0, 8(sp) # 4-byte Folded Reload ; RV32IFD-NEXT: fld fs0, 0(sp) # 8-byte Folded Reload @@ -299,28 +298,27 @@ define i64 @test_ceil_si64(double %x) nounwind { ; RV32IFD-NEXT: fmv.d fs0, fa0 ; RV32IFD-NEXT: fle.d s0, fa5, fa0 ; RV32IFD-NEXT: call __fixdfdi -; RV32IFD-NEXT: lui a3, 524288 -; RV32IFD-NEXT: li a4, 1 +; RV32IFD-NEXT: lui a4, 524288 ; RV32IFD-NEXT: lui a2, 524288 -; RV32IFD-NEXT: bne s0, a4, .LBB5_2 +; RV32IFD-NEXT: beqz s0, .LBB5_2 ; RV32IFD-NEXT: # %bb.1: ; RV32IFD-NEXT: mv a2, a1 ; RV32IFD-NEXT: .LBB5_2: ; RV32IFD-NEXT: lui a1, %hi(.LCPI5_1) ; RV32IFD-NEXT: fld fa5, %lo(.LCPI5_1)(a1) -; RV32IFD-NEXT: flt.d a4, fa5, fs0 -; RV32IFD-NEXT: beqz a4, .LBB5_4 +; RV32IFD-NEXT: flt.d a3, fa5, fs0 +; RV32IFD-NEXT: beqz a3, .LBB5_4 ; RV32IFD-NEXT: # %bb.3: -; RV32IFD-NEXT: addi a2, a3, -1 +; RV32IFD-NEXT: addi a2, a4, -1 ; RV32IFD-NEXT: .LBB5_4: ; RV32IFD-NEXT: feq.d a1, fs0, fs0 -; RV32IFD-NEXT: neg a3, a1 -; RV32IFD-NEXT: and a1, a3, a2 -; RV32IFD-NEXT: neg a2, a4 -; RV32IFD-NEXT: neg a4, s0 -; RV32IFD-NEXT: and a0, a4, a0 -; RV32IFD-NEXT: or a0, a2, a0 +; RV32IFD-NEXT: neg a4, a1 +; RV32IFD-NEXT: and a1, a4, a2 +; RV32IFD-NEXT: neg a2, a3 +; RV32IFD-NEXT: neg a3, s0 ; RV32IFD-NEXT: and a0, a3, a0 +; RV32IFD-NEXT: or a0, a2, a0 +; RV32IFD-NEXT: and a0, a4, a0 ; RV32IFD-NEXT: lw ra, 12(sp) # 4-byte Folded Reload ; RV32IFD-NEXT: lw s0, 8(sp) # 4-byte Folded Reload ; RV32IFD-NEXT: fld fs0, 0(sp) # 8-byte Folded Reload @@ -545,28 +543,27 @@ define i64 @test_trunc_si64(double %x) nounwind { ; RV32IFD-NEXT: fmv.d fs0, fa0 ; RV32IFD-NEXT: fle.d s0, fa5, fa0 ; RV32IFD-NEXT: call __fixdfdi -; RV32IFD-NEXT: lui a3, 524288 -; RV32IFD-NEXT: li a4, 1 +; RV32IFD-NEXT: lui a4, 524288 ; RV32IFD-NEXT: lui a2, 524288 -; RV32IFD-NEXT: bne s0, a4, .LBB9_2 +; RV32IFD-NEXT: beqz s0, .LBB9_2 ; RV32IFD-NEXT: # %bb.1: ; RV32IFD-NEXT: mv a2, a1 ; RV32IFD-NEXT: .LBB9_2: ; RV32IFD-NEXT: lui a1, %hi(.LCPI9_1) ; RV32IFD-NEXT: fld fa5, %lo(.LCPI9_1)(a1) -; RV32IFD-NEXT: flt.d a4, fa5, fs0 -; RV32IFD-NEXT: beqz a4, .LBB9_4 +; RV32IFD-NEXT: flt.d a3, fa5, fs0 +; RV32IFD-NEXT: beqz a3, .LBB9_4 ; RV32IFD-NEXT: # %bb.3: -; RV32IFD-NEXT: addi a2, a3, -1 +; RV32IFD-NEXT: addi a2, a4, -1 ; RV32IFD-NEXT: .LBB9_4: ; RV32IFD-NEXT: feq.d a1, fs0, fs0 -; RV32IFD-NEXT: neg a3, a1 -; RV32IFD-NEXT: and a1, a3, a2 -; RV32IFD-NEXT: neg a2, a4 -; RV32IFD-NEXT: neg a4, s0 -; RV32IFD-NEXT: and a0, a4, a0 -; RV32IFD-NEXT: or a0, a2, a0 +; RV32IFD-NEXT: neg a4, a1 +; RV32IFD-NEXT: and a1, a4, a2 +; RV32IFD-NEXT: neg a2, a3 +; RV32IFD-NEXT: neg a3, s0 ; RV32IFD-NEXT: and a0, a3, a0 +; RV32IFD-NEXT: or a0, a2, a0 +; RV32IFD-NEXT: and a0, a4, a0 ; RV32IFD-NEXT: lw ra, 12(sp) # 4-byte Folded Reload ; RV32IFD-NEXT: lw s0, 8(sp) # 4-byte Folded Reload ; RV32IFD-NEXT: fld fs0, 0(sp) # 8-byte Folded Reload @@ -791,28 +788,27 @@ define i64 @test_round_si64(double %x) nounwind { ; RV32IFD-NEXT: fmv.d fs0, fa0 ; RV32IFD-NEXT: fle.d s0, fa5, fa0 ; RV32IFD-NEXT: call __fixdfdi -; RV32IFD-NEXT: lui a3, 524288 -; RV32IFD-NEXT: li a4, 1 +; RV32IFD-NEXT: lui a4, 524288 ; RV32IFD-NEXT: lui a2, 524288 -; RV32IFD-NEXT: bne s0, a4, .LBB13_2 +; RV32IFD-NEXT: beqz s0, .LBB13_2 ; RV32IFD-NEXT: # %bb.1: ; RV32IFD-NEXT: mv a2, a1 ; RV32IFD-NEXT: .LBB13_2: ; RV32IFD-NEXT: lui a1, %hi(.LCPI13_1) ; RV32IFD-NEXT: fld fa5, %lo(.LCPI13_1)(a1) -; RV32IFD-NEXT: flt.d a4, fa5, fs0 -; RV32IFD-NEXT: beqz a4, .LBB13_4 +; RV32IFD-NEXT: flt.d a3, fa5, fs0 +; RV32IFD-NEXT: beqz a3, .LBB13_4 ; RV32IFD-NEXT: # %bb.3: -; RV32IFD-NEXT: addi a2, a3, -1 +; RV32IFD-NEXT: addi a2, a4, -1 ; RV32IFD-NEXT: .LBB13_4: ; RV32IFD-NEXT: feq.d a1, fs0, fs0 -; RV32IFD-NEXT: neg a3, a1 -; RV32IFD-NEXT: and a1, a3, a2 -; RV32IFD-NEXT: neg a2, a4 -; RV32IFD-NEXT: neg a4, s0 -; RV32IFD-NEXT: and a0, a4, a0 -; RV32IFD-NEXT: or a0, a2, a0 +; RV32IFD-NEXT: neg a4, a1 +; RV32IFD-NEXT: and a1, a4, a2 +; RV32IFD-NEXT: neg a2, a3 +; RV32IFD-NEXT: neg a3, s0 ; RV32IFD-NEXT: and a0, a3, a0 +; RV32IFD-NEXT: or a0, a2, a0 +; RV32IFD-NEXT: and a0, a4, a0 ; RV32IFD-NEXT: lw ra, 12(sp) # 4-byte Folded Reload ; RV32IFD-NEXT: lw s0, 8(sp) # 4-byte Folded Reload ; RV32IFD-NEXT: fld fs0, 0(sp) # 8-byte Folded Reload @@ -1037,28 +1033,27 @@ define i64 @test_roundeven_si64(double %x) nounwind { ; RV32IFD-NEXT: fmv.d fs0, fa0 ; RV32IFD-NEXT: fle.d s0, fa5, fa0 ; RV32IFD-NEXT: call __fixdfdi -; RV32IFD-NEXT: lui a3, 524288 -; RV32IFD-NEXT: li a4, 1 +; RV32IFD-NEXT: lui a4, 524288 ; RV32IFD-NEXT: lui a2, 524288 -; RV32IFD-NEXT: bne s0, a4, .LBB17_2 +; RV32IFD-NEXT: beqz s0, .LBB17_2 ; RV32IFD-NEXT: # %bb.1: ; RV32IFD-NEXT: mv a2, a1 ; RV32IFD-NEXT: .LBB17_2: ; RV32IFD-NEXT: lui a1, %hi(.LCPI17_1) ; RV32IFD-NEXT: fld fa5, %lo(.LCPI17_1)(a1) -; RV32IFD-NEXT: flt.d a4, fa5, fs0 -; RV32IFD-NEXT: beqz a4, .LBB17_4 +; RV32IFD-NEXT: flt.d a3, fa5, fs0 +; RV32IFD-NEXT: beqz a3, .LBB17_4 ; RV32IFD-NEXT: # %bb.3: -; RV32IFD-NEXT: addi a2, a3, -1 +; RV32IFD-NEXT: addi a2, a4, -1 ; RV32IFD-NEXT: .LBB17_4: ; RV32IFD-NEXT: feq.d a1, fs0, fs0 -; RV32IFD-NEXT: neg a3, a1 -; RV32IFD-NEXT: and a1, a3, a2 -; RV32IFD-NEXT: neg a2, a4 -; RV32IFD-NEXT: neg a4, s0 -; RV32IFD-NEXT: and a0, a4, a0 -; RV32IFD-NEXT: or a0, a2, a0 +; RV32IFD-NEXT: neg a4, a1 +; RV32IFD-NEXT: and a1, a4, a2 +; RV32IFD-NEXT: neg a2, a3 +; RV32IFD-NEXT: neg a3, s0 ; RV32IFD-NEXT: and a0, a3, a0 +; RV32IFD-NEXT: or a0, a2, a0 +; RV32IFD-NEXT: and a0, a4, a0 ; RV32IFD-NEXT: lw ra, 12(sp) # 4-byte Folded Reload ; RV32IFD-NEXT: lw s0, 8(sp) # 4-byte Folded Reload ; RV32IFD-NEXT: fld fs0, 0(sp) # 8-byte Folded Reload @@ -1283,28 +1278,27 @@ define i64 @test_rint_si64(double %x) nounwind { ; RV32IFD-NEXT: fmv.d fs0, fa0 ; RV32IFD-NEXT: fle.d s0, fa5, fa0 ; RV32IFD-NEXT: call __fixdfdi -; RV32IFD-NEXT: lui a3, 524288 -; RV32IFD-NEXT: li a4, 1 +; RV32IFD-NEXT: lui a4, 524288 ; RV32IFD-NEXT: lui a2, 524288 -; RV32IFD-NEXT: bne s0, a4, .LBB21_2 +; RV32IFD-NEXT: beqz s0, .LBB21_2 ; RV32IFD-NEXT: # %bb.1: ; RV32IFD-NEXT: mv a2, a1 ; RV32IFD-NEXT: .LBB21_2: ; RV32IFD-NEXT: lui a1, %hi(.LCPI21_1) ; RV32IFD-NEXT: fld fa5, %lo(.LCPI21_1)(a1) -; RV32IFD-NEXT: flt.d a4, fa5, fs0 -; RV32IFD-NEXT: beqz a4, .LBB21_4 +; RV32IFD-NEXT: flt.d a3, fa5, fs0 +; RV32IFD-NEXT: beqz a3, .LBB21_4 ; RV32IFD-NEXT: # %bb.3: -; RV32IFD-NEXT: addi a2, a3, -1 +; RV32IFD-NEXT: addi a2, a4, -1 ; RV32IFD-NEXT: .LBB21_4: ; RV32IFD-NEXT: feq.d a1, fs0, fs0 -; RV32IFD-NEXT: neg a3, a1 -; RV32IFD-NEXT: and a1, a3, a2 -; RV32IFD-NEXT: neg a2, a4 -; RV32IFD-NEXT: neg a4, s0 -; RV32IFD-NEXT: and a0, a4, a0 -; RV32IFD-NEXT: or a0, a2, a0 +; RV32IFD-NEXT: neg a4, a1 +; RV32IFD-NEXT: and a1, a4, a2 +; RV32IFD-NEXT: neg a2, a3 +; RV32IFD-NEXT: neg a3, s0 ; RV32IFD-NEXT: and a0, a3, a0 +; RV32IFD-NEXT: or a0, a2, a0 +; RV32IFD-NEXT: and a0, a4, a0 ; RV32IFD-NEXT: lw ra, 12(sp) # 4-byte Folded Reload ; RV32IFD-NEXT: lw s0, 8(sp) # 4-byte Folded Reload ; RV32IFD-NEXT: fld fs0, 0(sp) # 8-byte Folded Reload diff --git a/llvm/test/CodeGen/RISCV/float-convert.ll b/llvm/test/CodeGen/RISCV/float-convert.ll index 653b64ec730496d2654599cfbb7f042ce2dae866..7eabd3f5f2273af5dcb5bdfa454b803d38d0ec94 100644 --- a/llvm/test/CodeGen/RISCV/float-convert.ll +++ b/llvm/test/CodeGen/RISCV/float-convert.ll @@ -275,26 +275,24 @@ define i32 @fcvt_wu_s_sat(float %a) nounwind { ; RV32I-NEXT: sw ra, 12(sp) # 4-byte Folded Spill ; RV32I-NEXT: sw s0, 8(sp) # 4-byte Folded Spill ; RV32I-NEXT: sw s1, 4(sp) # 4-byte Folded Spill -; RV32I-NEXT: sw s2, 0(sp) # 4-byte Folded Spill ; RV32I-NEXT: mv s0, a0 -; RV32I-NEXT: lui a1, 325632 -; RV32I-NEXT: addi a1, a1, -1 -; RV32I-NEXT: call __gtsf2 -; RV32I-NEXT: sgtz a0, a0 -; RV32I-NEXT: neg s1, a0 -; RV32I-NEXT: mv a0, s0 ; RV32I-NEXT: li a1, 0 ; RV32I-NEXT: call __gesf2 ; RV32I-NEXT: slti a0, a0, 0 -; RV32I-NEXT: addi s2, a0, -1 +; RV32I-NEXT: addi s1, a0, -1 ; RV32I-NEXT: mv a0, s0 ; RV32I-NEXT: call __fixunssfsi -; RV32I-NEXT: and a0, s2, a0 -; RV32I-NEXT: or a0, s1, a0 +; RV32I-NEXT: and s1, s1, a0 +; RV32I-NEXT: lui a1, 325632 +; RV32I-NEXT: addi a1, a1, -1 +; RV32I-NEXT: mv a0, s0 +; RV32I-NEXT: call __gtsf2 +; RV32I-NEXT: sgtz a0, a0 +; RV32I-NEXT: neg a0, a0 +; RV32I-NEXT: or a0, a0, s1 ; RV32I-NEXT: lw ra, 12(sp) # 4-byte Folded Reload ; RV32I-NEXT: lw s0, 8(sp) # 4-byte Folded Reload ; RV32I-NEXT: lw s1, 4(sp) # 4-byte Folded Reload -; RV32I-NEXT: lw s2, 0(sp) # 4-byte Folded Reload ; RV32I-NEXT: addi sp, sp, 16 ; RV32I-NEXT: ret ; @@ -618,38 +616,36 @@ define i64 @fcvt_l_s_sat(float %a) nounwind { ; RV32IF-NEXT: addi sp, sp, -16 ; RV32IF-NEXT: sw ra, 12(sp) # 4-byte Folded Spill ; RV32IF-NEXT: sw s0, 8(sp) # 4-byte Folded Spill -; RV32IF-NEXT: sw s1, 4(sp) # 4-byte Folded Spill -; RV32IF-NEXT: fsw fs0, 0(sp) # 4-byte Folded Spill +; RV32IF-NEXT: fsw fs0, 4(sp) # 4-byte Folded Spill ; RV32IF-NEXT: fmv.s fs0, fa0 ; RV32IF-NEXT: lui a0, 913408 ; RV32IF-NEXT: fmv.w.x fa5, a0 ; RV32IF-NEXT: fle.s s0, fa5, fa0 -; RV32IF-NEXT: neg s1, s0 ; RV32IF-NEXT: call __fixsfdi -; RV32IF-NEXT: lui a2, %hi(.LCPI12_0) -; RV32IF-NEXT: flw fa5, %lo(.LCPI12_0)(a2) -; RV32IF-NEXT: and a0, s1, a0 -; RV32IF-NEXT: flt.s a3, fa5, fs0 -; RV32IF-NEXT: neg a2, a3 -; RV32IF-NEXT: or a0, a2, a0 -; RV32IF-NEXT: feq.s a2, fs0, fs0 -; RV32IF-NEXT: neg a2, a2 -; RV32IF-NEXT: lui a5, 524288 ; RV32IF-NEXT: lui a4, 524288 +; RV32IF-NEXT: lui a2, 524288 ; RV32IF-NEXT: beqz s0, .LBB12_2 ; RV32IF-NEXT: # %bb.1: # %start -; RV32IF-NEXT: mv a4, a1 +; RV32IF-NEXT: mv a2, a1 ; RV32IF-NEXT: .LBB12_2: # %start -; RV32IF-NEXT: and a0, a2, a0 +; RV32IF-NEXT: lui a1, %hi(.LCPI12_0) +; RV32IF-NEXT: flw fa5, %lo(.LCPI12_0)(a1) +; RV32IF-NEXT: flt.s a3, fa5, fs0 ; RV32IF-NEXT: beqz a3, .LBB12_4 ; RV32IF-NEXT: # %bb.3: -; RV32IF-NEXT: addi a4, a5, -1 +; RV32IF-NEXT: addi a2, a4, -1 ; RV32IF-NEXT: .LBB12_4: # %start -; RV32IF-NEXT: and a1, a2, a4 +; RV32IF-NEXT: feq.s a1, fs0, fs0 +; RV32IF-NEXT: neg a4, a1 +; RV32IF-NEXT: and a1, a4, a2 +; RV32IF-NEXT: neg a2, s0 +; RV32IF-NEXT: and a0, a2, a0 +; RV32IF-NEXT: neg a2, a3 +; RV32IF-NEXT: or a0, a2, a0 +; RV32IF-NEXT: and a0, a4, a0 ; RV32IF-NEXT: lw ra, 12(sp) # 4-byte Folded Reload ; RV32IF-NEXT: lw s0, 8(sp) # 4-byte Folded Reload -; RV32IF-NEXT: lw s1, 4(sp) # 4-byte Folded Reload -; RV32IF-NEXT: flw fs0, 0(sp) # 4-byte Folded Reload +; RV32IF-NEXT: flw fs0, 4(sp) # 4-byte Folded Reload ; RV32IF-NEXT: addi sp, sp, 16 ; RV32IF-NEXT: ret ; @@ -867,22 +863,23 @@ define i64 @fcvt_lu_s_sat(float %a) nounwind { ; RV32IF-NEXT: addi sp, sp, -16 ; RV32IF-NEXT: sw ra, 12(sp) # 4-byte Folded Spill ; RV32IF-NEXT: sw s0, 8(sp) # 4-byte Folded Spill -; RV32IF-NEXT: sw s1, 4(sp) # 4-byte Folded Spill -; RV32IF-NEXT: lui a0, %hi(.LCPI14_0) -; RV32IF-NEXT: flw fa5, %lo(.LCPI14_0)(a0) -; RV32IF-NEXT: flt.s a0, fa5, fa0 -; RV32IF-NEXT: neg s0, a0 +; RV32IF-NEXT: fsw fs0, 4(sp) # 4-byte Folded Spill +; RV32IF-NEXT: fmv.s fs0, fa0 ; RV32IF-NEXT: fmv.w.x fa5, zero ; RV32IF-NEXT: fle.s a0, fa5, fa0 -; RV32IF-NEXT: neg s1, a0 +; RV32IF-NEXT: neg s0, a0 ; RV32IF-NEXT: call __fixunssfdi -; RV32IF-NEXT: and a0, s1, a0 -; RV32IF-NEXT: or a0, s0, a0 -; RV32IF-NEXT: and a1, s1, a1 -; RV32IF-NEXT: or a1, s0, a1 +; RV32IF-NEXT: lui a2, %hi(.LCPI14_0) +; RV32IF-NEXT: flw fa5, %lo(.LCPI14_0)(a2) +; RV32IF-NEXT: and a0, s0, a0 +; RV32IF-NEXT: flt.s a2, fa5, fs0 +; RV32IF-NEXT: neg a2, a2 +; RV32IF-NEXT: or a0, a2, a0 +; RV32IF-NEXT: and a1, s0, a1 +; RV32IF-NEXT: or a1, a2, a1 ; RV32IF-NEXT: lw ra, 12(sp) # 4-byte Folded Reload ; RV32IF-NEXT: lw s0, 8(sp) # 4-byte Folded Reload -; RV32IF-NEXT: lw s1, 4(sp) # 4-byte Folded Reload +; RV32IF-NEXT: flw fs0, 4(sp) # 4-byte Folded Reload ; RV32IF-NEXT: addi sp, sp, 16 ; RV32IF-NEXT: ret ; @@ -901,17 +898,19 @@ define i64 @fcvt_lu_s_sat(float %a) nounwind { ; RV32IZFINX-NEXT: sw ra, 12(sp) # 4-byte Folded Spill ; RV32IZFINX-NEXT: sw s0, 8(sp) # 4-byte Folded Spill ; RV32IZFINX-NEXT: sw s1, 4(sp) # 4-byte Folded Spill -; RV32IZFINX-NEXT: lui a1, %hi(.LCPI14_0) -; RV32IZFINX-NEXT: lw a1, %lo(.LCPI14_0)(a1) -; RV32IZFINX-NEXT: flt.s a1, a1, a0 -; RV32IZFINX-NEXT: neg s0, a1 -; RV32IZFINX-NEXT: fle.s a1, zero, a0 -; RV32IZFINX-NEXT: neg s1, a1 +; RV32IZFINX-NEXT: mv s0, a0 +; RV32IZFINX-NEXT: fle.s a0, zero, a0 +; RV32IZFINX-NEXT: neg s1, a0 +; RV32IZFINX-NEXT: mv a0, s0 ; RV32IZFINX-NEXT: call __fixunssfdi +; RV32IZFINX-NEXT: lui a2, %hi(.LCPI14_0) +; RV32IZFINX-NEXT: lw a2, %lo(.LCPI14_0)(a2) ; RV32IZFINX-NEXT: and a0, s1, a0 -; RV32IZFINX-NEXT: or a0, s0, a0 +; RV32IZFINX-NEXT: flt.s a2, a2, s0 +; RV32IZFINX-NEXT: neg a2, a2 +; RV32IZFINX-NEXT: or a0, a2, a0 ; RV32IZFINX-NEXT: and a1, s1, a1 -; RV32IZFINX-NEXT: or a1, s0, a1 +; RV32IZFINX-NEXT: or a1, a2, a1 ; RV32IZFINX-NEXT: lw ra, 12(sp) # 4-byte Folded Reload ; RV32IZFINX-NEXT: lw s0, 8(sp) # 4-byte Folded Reload ; RV32IZFINX-NEXT: lw s1, 4(sp) # 4-byte Folded Reload @@ -929,33 +928,36 @@ define i64 @fcvt_lu_s_sat(float %a) nounwind { ; ; RV32I-LABEL: fcvt_lu_s_sat: ; RV32I: # %bb.0: # %start -; RV32I-NEXT: addi sp, sp, -16 -; RV32I-NEXT: sw ra, 12(sp) # 4-byte Folded Spill -; RV32I-NEXT: sw s0, 8(sp) # 4-byte Folded Spill -; RV32I-NEXT: sw s1, 4(sp) # 4-byte Folded Spill -; RV32I-NEXT: sw s2, 0(sp) # 4-byte Folded Spill +; RV32I-NEXT: addi sp, sp, -32 +; RV32I-NEXT: sw ra, 28(sp) # 4-byte Folded Spill +; RV32I-NEXT: sw s0, 24(sp) # 4-byte Folded Spill +; RV32I-NEXT: sw s1, 20(sp) # 4-byte Folded Spill +; RV32I-NEXT: sw s2, 16(sp) # 4-byte Folded Spill +; RV32I-NEXT: sw s3, 12(sp) # 4-byte Folded Spill ; RV32I-NEXT: mv s0, a0 -; RV32I-NEXT: lui a1, 391168 -; RV32I-NEXT: addi a1, a1, -1 -; RV32I-NEXT: call __gtsf2 -; RV32I-NEXT: sgtz a0, a0 -; RV32I-NEXT: neg s1, a0 -; RV32I-NEXT: mv a0, s0 ; RV32I-NEXT: li a1, 0 ; RV32I-NEXT: call __gesf2 ; RV32I-NEXT: slti a0, a0, 0 ; RV32I-NEXT: addi s2, a0, -1 ; RV32I-NEXT: mv a0, s0 ; RV32I-NEXT: call __fixunssfdi -; RV32I-NEXT: and a0, s2, a0 -; RV32I-NEXT: or a0, s1, a0 -; RV32I-NEXT: and a1, s2, a1 -; RV32I-NEXT: or a1, s1, a1 -; RV32I-NEXT: lw ra, 12(sp) # 4-byte Folded Reload -; RV32I-NEXT: lw s0, 8(sp) # 4-byte Folded Reload -; RV32I-NEXT: lw s1, 4(sp) # 4-byte Folded Reload -; RV32I-NEXT: lw s2, 0(sp) # 4-byte Folded Reload -; RV32I-NEXT: addi sp, sp, 16 +; RV32I-NEXT: mv s1, a1 +; RV32I-NEXT: and s3, s2, a0 +; RV32I-NEXT: lui a1, 391168 +; RV32I-NEXT: addi a1, a1, -1 +; RV32I-NEXT: mv a0, s0 +; RV32I-NEXT: call __gtsf2 +; RV32I-NEXT: sgtz a0, a0 +; RV32I-NEXT: neg a1, a0 +; RV32I-NEXT: or a0, a1, s3 +; RV32I-NEXT: and a2, s2, s1 +; RV32I-NEXT: or a1, a1, a2 +; RV32I-NEXT: lw ra, 28(sp) # 4-byte Folded Reload +; RV32I-NEXT: lw s0, 24(sp) # 4-byte Folded Reload +; RV32I-NEXT: lw s1, 20(sp) # 4-byte Folded Reload +; RV32I-NEXT: lw s2, 16(sp) # 4-byte Folded Reload +; RV32I-NEXT: lw s3, 12(sp) # 4-byte Folded Reload +; RV32I-NEXT: addi sp, sp, 32 ; RV32I-NEXT: ret ; ; RV64I-LABEL: fcvt_lu_s_sat: @@ -2089,26 +2091,24 @@ define zeroext i32 @fcvt_wu_s_sat_zext(float %a) nounwind { ; RV32I-NEXT: sw ra, 12(sp) # 4-byte Folded Spill ; RV32I-NEXT: sw s0, 8(sp) # 4-byte Folded Spill ; RV32I-NEXT: sw s1, 4(sp) # 4-byte Folded Spill -; RV32I-NEXT: sw s2, 0(sp) # 4-byte Folded Spill ; RV32I-NEXT: mv s0, a0 -; RV32I-NEXT: lui a1, 325632 -; RV32I-NEXT: addi a1, a1, -1 -; RV32I-NEXT: call __gtsf2 -; RV32I-NEXT: sgtz a0, a0 -; RV32I-NEXT: neg s1, a0 -; RV32I-NEXT: mv a0, s0 ; RV32I-NEXT: li a1, 0 ; RV32I-NEXT: call __gesf2 ; RV32I-NEXT: slti a0, a0, 0 -; RV32I-NEXT: addi s2, a0, -1 +; RV32I-NEXT: addi s1, a0, -1 ; RV32I-NEXT: mv a0, s0 ; RV32I-NEXT: call __fixunssfsi -; RV32I-NEXT: and a0, s2, a0 -; RV32I-NEXT: or a0, s1, a0 +; RV32I-NEXT: and s1, s1, a0 +; RV32I-NEXT: lui a1, 325632 +; RV32I-NEXT: addi a1, a1, -1 +; RV32I-NEXT: mv a0, s0 +; RV32I-NEXT: call __gtsf2 +; RV32I-NEXT: sgtz a0, a0 +; RV32I-NEXT: neg a0, a0 +; RV32I-NEXT: or a0, a0, s1 ; RV32I-NEXT: lw ra, 12(sp) # 4-byte Folded Reload ; RV32I-NEXT: lw s0, 8(sp) # 4-byte Folded Reload ; RV32I-NEXT: lw s1, 4(sp) # 4-byte Folded Reload -; RV32I-NEXT: lw s2, 0(sp) # 4-byte Folded Reload ; RV32I-NEXT: addi sp, sp, 16 ; RV32I-NEXT: ret ; diff --git a/llvm/test/CodeGen/RISCV/float-round-conv-sat.ll b/llvm/test/CodeGen/RISCV/float-round-conv-sat.ll index 4f747c278da03c16d44a343e7a43e4e669dc0183..5e99c7eb9056282b18ec7bb8e14da746cc10b8c0 100644 --- a/llvm/test/CodeGen/RISCV/float-round-conv-sat.ll +++ b/llvm/test/CodeGen/RISCV/float-round-conv-sat.ll @@ -37,8 +37,7 @@ define i64 @test_floor_si64(float %x) nounwind { ; RV32IF-NEXT: addi sp, sp, -16 ; RV32IF-NEXT: sw ra, 12(sp) # 4-byte Folded Spill ; RV32IF-NEXT: sw s0, 8(sp) # 4-byte Folded Spill -; RV32IF-NEXT: sw s1, 4(sp) # 4-byte Folded Spill -; RV32IF-NEXT: fsw fs0, 0(sp) # 4-byte Folded Spill +; RV32IF-NEXT: fsw fs0, 4(sp) # 4-byte Folded Spill ; RV32IF-NEXT: fmv.s fs0, fa0 ; RV32IF-NEXT: lui a0, 307200 ; RV32IF-NEXT: fmv.w.x fa5, a0 @@ -53,33 +52,32 @@ define i64 @test_floor_si64(float %x) nounwind { ; RV32IF-NEXT: lui a0, 913408 ; RV32IF-NEXT: fmv.w.x fa5, a0 ; RV32IF-NEXT: fle.s s0, fa5, fs0 -; RV32IF-NEXT: neg s1, s0 ; RV32IF-NEXT: fmv.s fa0, fs0 ; RV32IF-NEXT: call __fixsfdi -; RV32IF-NEXT: lui a2, %hi(.LCPI1_0) -; RV32IF-NEXT: flw fa5, %lo(.LCPI1_0)(a2) -; RV32IF-NEXT: and a0, s1, a0 -; RV32IF-NEXT: flt.s a3, fa5, fs0 -; RV32IF-NEXT: neg a2, a3 -; RV32IF-NEXT: or a0, a2, a0 -; RV32IF-NEXT: feq.s a2, fs0, fs0 -; RV32IF-NEXT: neg a2, a2 -; RV32IF-NEXT: lui a5, 524288 ; RV32IF-NEXT: lui a4, 524288 +; RV32IF-NEXT: lui a2, 524288 ; RV32IF-NEXT: beqz s0, .LBB1_4 ; RV32IF-NEXT: # %bb.3: -; RV32IF-NEXT: mv a4, a1 +; RV32IF-NEXT: mv a2, a1 ; RV32IF-NEXT: .LBB1_4: -; RV32IF-NEXT: and a0, a2, a0 +; RV32IF-NEXT: lui a1, %hi(.LCPI1_0) +; RV32IF-NEXT: flw fa5, %lo(.LCPI1_0)(a1) +; RV32IF-NEXT: flt.s a3, fa5, fs0 ; RV32IF-NEXT: beqz a3, .LBB1_6 ; RV32IF-NEXT: # %bb.5: -; RV32IF-NEXT: addi a4, a5, -1 +; RV32IF-NEXT: addi a2, a4, -1 ; RV32IF-NEXT: .LBB1_6: -; RV32IF-NEXT: and a1, a2, a4 +; RV32IF-NEXT: feq.s a1, fs0, fs0 +; RV32IF-NEXT: neg a4, a1 +; RV32IF-NEXT: and a1, a4, a2 +; RV32IF-NEXT: neg a2, s0 +; RV32IF-NEXT: and a0, a2, a0 +; RV32IF-NEXT: neg a2, a3 +; RV32IF-NEXT: or a0, a2, a0 +; RV32IF-NEXT: and a0, a4, a0 ; RV32IF-NEXT: lw ra, 12(sp) # 4-byte Folded Reload ; RV32IF-NEXT: lw s0, 8(sp) # 4-byte Folded Reload -; RV32IF-NEXT: lw s1, 4(sp) # 4-byte Folded Reload -; RV32IF-NEXT: flw fs0, 0(sp) # 4-byte Folded Reload +; RV32IF-NEXT: flw fs0, 4(sp) # 4-byte Folded Reload ; RV32IF-NEXT: addi sp, sp, 16 ; RV32IF-NEXT: ret ; @@ -117,23 +115,23 @@ define i64 @test_floor_si64(float %x) nounwind { ; RV32IZFINX-NEXT: lui a2, %hi(.LCPI1_0) ; RV32IZFINX-NEXT: lw a2, %lo(.LCPI1_0)(a2) ; RV32IZFINX-NEXT: and a0, s2, a0 -; RV32IZFINX-NEXT: flt.s a3, a2, s0 -; RV32IZFINX-NEXT: neg a2, a3 +; RV32IZFINX-NEXT: flt.s a4, a2, s0 +; RV32IZFINX-NEXT: neg a2, a4 ; RV32IZFINX-NEXT: or a0, a2, a0 ; RV32IZFINX-NEXT: feq.s a2, s0, s0 ; RV32IZFINX-NEXT: neg a2, a2 ; RV32IZFINX-NEXT: lui a5, 524288 -; RV32IZFINX-NEXT: lui a4, 524288 +; RV32IZFINX-NEXT: lui a3, 524288 ; RV32IZFINX-NEXT: beqz s1, .LBB1_4 ; RV32IZFINX-NEXT: # %bb.3: -; RV32IZFINX-NEXT: mv a4, a1 +; RV32IZFINX-NEXT: mv a3, a1 ; RV32IZFINX-NEXT: .LBB1_4: ; RV32IZFINX-NEXT: and a0, a2, a0 -; RV32IZFINX-NEXT: beqz a3, .LBB1_6 +; RV32IZFINX-NEXT: beqz a4, .LBB1_6 ; RV32IZFINX-NEXT: # %bb.5: -; RV32IZFINX-NEXT: addi a4, a5, -1 +; RV32IZFINX-NEXT: addi a3, a5, -1 ; RV32IZFINX-NEXT: .LBB1_6: -; RV32IZFINX-NEXT: and a1, a2, a4 +; RV32IZFINX-NEXT: and a1, a2, a3 ; RV32IZFINX-NEXT: lw ra, 12(sp) # 4-byte Folded Reload ; RV32IZFINX-NEXT: lw s0, 8(sp) # 4-byte Folded Reload ; RV32IZFINX-NEXT: lw s1, 4(sp) # 4-byte Folded Reload @@ -299,8 +297,7 @@ define i64 @test_ceil_si64(float %x) nounwind { ; RV32IF-NEXT: addi sp, sp, -16 ; RV32IF-NEXT: sw ra, 12(sp) # 4-byte Folded Spill ; RV32IF-NEXT: sw s0, 8(sp) # 4-byte Folded Spill -; RV32IF-NEXT: sw s1, 4(sp) # 4-byte Folded Spill -; RV32IF-NEXT: fsw fs0, 0(sp) # 4-byte Folded Spill +; RV32IF-NEXT: fsw fs0, 4(sp) # 4-byte Folded Spill ; RV32IF-NEXT: fmv.s fs0, fa0 ; RV32IF-NEXT: lui a0, 307200 ; RV32IF-NEXT: fmv.w.x fa5, a0 @@ -315,33 +312,32 @@ define i64 @test_ceil_si64(float %x) nounwind { ; RV32IF-NEXT: lui a0, 913408 ; RV32IF-NEXT: fmv.w.x fa5, a0 ; RV32IF-NEXT: fle.s s0, fa5, fs0 -; RV32IF-NEXT: neg s1, s0 ; RV32IF-NEXT: fmv.s fa0, fs0 ; RV32IF-NEXT: call __fixsfdi -; RV32IF-NEXT: lui a2, %hi(.LCPI5_0) -; RV32IF-NEXT: flw fa5, %lo(.LCPI5_0)(a2) -; RV32IF-NEXT: and a0, s1, a0 -; RV32IF-NEXT: flt.s a3, fa5, fs0 -; RV32IF-NEXT: neg a2, a3 -; RV32IF-NEXT: or a0, a2, a0 -; RV32IF-NEXT: feq.s a2, fs0, fs0 -; RV32IF-NEXT: neg a2, a2 -; RV32IF-NEXT: lui a5, 524288 ; RV32IF-NEXT: lui a4, 524288 +; RV32IF-NEXT: lui a2, 524288 ; RV32IF-NEXT: beqz s0, .LBB5_4 ; RV32IF-NEXT: # %bb.3: -; RV32IF-NEXT: mv a4, a1 +; RV32IF-NEXT: mv a2, a1 ; RV32IF-NEXT: .LBB5_4: -; RV32IF-NEXT: and a0, a2, a0 +; RV32IF-NEXT: lui a1, %hi(.LCPI5_0) +; RV32IF-NEXT: flw fa5, %lo(.LCPI5_0)(a1) +; RV32IF-NEXT: flt.s a3, fa5, fs0 ; RV32IF-NEXT: beqz a3, .LBB5_6 ; RV32IF-NEXT: # %bb.5: -; RV32IF-NEXT: addi a4, a5, -1 +; RV32IF-NEXT: addi a2, a4, -1 ; RV32IF-NEXT: .LBB5_6: -; RV32IF-NEXT: and a1, a2, a4 +; RV32IF-NEXT: feq.s a1, fs0, fs0 +; RV32IF-NEXT: neg a4, a1 +; RV32IF-NEXT: and a1, a4, a2 +; RV32IF-NEXT: neg a2, s0 +; RV32IF-NEXT: and a0, a2, a0 +; RV32IF-NEXT: neg a2, a3 +; RV32IF-NEXT: or a0, a2, a0 +; RV32IF-NEXT: and a0, a4, a0 ; RV32IF-NEXT: lw ra, 12(sp) # 4-byte Folded Reload ; RV32IF-NEXT: lw s0, 8(sp) # 4-byte Folded Reload -; RV32IF-NEXT: lw s1, 4(sp) # 4-byte Folded Reload -; RV32IF-NEXT: flw fs0, 0(sp) # 4-byte Folded Reload +; RV32IF-NEXT: flw fs0, 4(sp) # 4-byte Folded Reload ; RV32IF-NEXT: addi sp, sp, 16 ; RV32IF-NEXT: ret ; @@ -379,23 +375,23 @@ define i64 @test_ceil_si64(float %x) nounwind { ; RV32IZFINX-NEXT: lui a2, %hi(.LCPI5_0) ; RV32IZFINX-NEXT: lw a2, %lo(.LCPI5_0)(a2) ; RV32IZFINX-NEXT: and a0, s2, a0 -; RV32IZFINX-NEXT: flt.s a3, a2, s0 -; RV32IZFINX-NEXT: neg a2, a3 +; RV32IZFINX-NEXT: flt.s a4, a2, s0 +; RV32IZFINX-NEXT: neg a2, a4 ; RV32IZFINX-NEXT: or a0, a2, a0 ; RV32IZFINX-NEXT: feq.s a2, s0, s0 ; RV32IZFINX-NEXT: neg a2, a2 ; RV32IZFINX-NEXT: lui a5, 524288 -; RV32IZFINX-NEXT: lui a4, 524288 +; RV32IZFINX-NEXT: lui a3, 524288 ; RV32IZFINX-NEXT: beqz s1, .LBB5_4 ; RV32IZFINX-NEXT: # %bb.3: -; RV32IZFINX-NEXT: mv a4, a1 +; RV32IZFINX-NEXT: mv a3, a1 ; RV32IZFINX-NEXT: .LBB5_4: ; RV32IZFINX-NEXT: and a0, a2, a0 -; RV32IZFINX-NEXT: beqz a3, .LBB5_6 +; RV32IZFINX-NEXT: beqz a4, .LBB5_6 ; RV32IZFINX-NEXT: # %bb.5: -; RV32IZFINX-NEXT: addi a4, a5, -1 +; RV32IZFINX-NEXT: addi a3, a5, -1 ; RV32IZFINX-NEXT: .LBB5_6: -; RV32IZFINX-NEXT: and a1, a2, a4 +; RV32IZFINX-NEXT: and a1, a2, a3 ; RV32IZFINX-NEXT: lw ra, 12(sp) # 4-byte Folded Reload ; RV32IZFINX-NEXT: lw s0, 8(sp) # 4-byte Folded Reload ; RV32IZFINX-NEXT: lw s1, 4(sp) # 4-byte Folded Reload @@ -561,8 +557,7 @@ define i64 @test_trunc_si64(float %x) nounwind { ; RV32IF-NEXT: addi sp, sp, -16 ; RV32IF-NEXT: sw ra, 12(sp) # 4-byte Folded Spill ; RV32IF-NEXT: sw s0, 8(sp) # 4-byte Folded Spill -; RV32IF-NEXT: sw s1, 4(sp) # 4-byte Folded Spill -; RV32IF-NEXT: fsw fs0, 0(sp) # 4-byte Folded Spill +; RV32IF-NEXT: fsw fs0, 4(sp) # 4-byte Folded Spill ; RV32IF-NEXT: fmv.s fs0, fa0 ; RV32IF-NEXT: lui a0, 307200 ; RV32IF-NEXT: fmv.w.x fa5, a0 @@ -577,33 +572,32 @@ define i64 @test_trunc_si64(float %x) nounwind { ; RV32IF-NEXT: lui a0, 913408 ; RV32IF-NEXT: fmv.w.x fa5, a0 ; RV32IF-NEXT: fle.s s0, fa5, fs0 -; RV32IF-NEXT: neg s1, s0 ; RV32IF-NEXT: fmv.s fa0, fs0 ; RV32IF-NEXT: call __fixsfdi -; RV32IF-NEXT: lui a2, %hi(.LCPI9_0) -; RV32IF-NEXT: flw fa5, %lo(.LCPI9_0)(a2) -; RV32IF-NEXT: and a0, s1, a0 -; RV32IF-NEXT: flt.s a3, fa5, fs0 -; RV32IF-NEXT: neg a2, a3 -; RV32IF-NEXT: or a0, a2, a0 -; RV32IF-NEXT: feq.s a2, fs0, fs0 -; RV32IF-NEXT: neg a2, a2 -; RV32IF-NEXT: lui a5, 524288 ; RV32IF-NEXT: lui a4, 524288 +; RV32IF-NEXT: lui a2, 524288 ; RV32IF-NEXT: beqz s0, .LBB9_4 ; RV32IF-NEXT: # %bb.3: -; RV32IF-NEXT: mv a4, a1 +; RV32IF-NEXT: mv a2, a1 ; RV32IF-NEXT: .LBB9_4: -; RV32IF-NEXT: and a0, a2, a0 +; RV32IF-NEXT: lui a1, %hi(.LCPI9_0) +; RV32IF-NEXT: flw fa5, %lo(.LCPI9_0)(a1) +; RV32IF-NEXT: flt.s a3, fa5, fs0 ; RV32IF-NEXT: beqz a3, .LBB9_6 ; RV32IF-NEXT: # %bb.5: -; RV32IF-NEXT: addi a4, a5, -1 +; RV32IF-NEXT: addi a2, a4, -1 ; RV32IF-NEXT: .LBB9_6: -; RV32IF-NEXT: and a1, a2, a4 +; RV32IF-NEXT: feq.s a1, fs0, fs0 +; RV32IF-NEXT: neg a4, a1 +; RV32IF-NEXT: and a1, a4, a2 +; RV32IF-NEXT: neg a2, s0 +; RV32IF-NEXT: and a0, a2, a0 +; RV32IF-NEXT: neg a2, a3 +; RV32IF-NEXT: or a0, a2, a0 +; RV32IF-NEXT: and a0, a4, a0 ; RV32IF-NEXT: lw ra, 12(sp) # 4-byte Folded Reload ; RV32IF-NEXT: lw s0, 8(sp) # 4-byte Folded Reload -; RV32IF-NEXT: lw s1, 4(sp) # 4-byte Folded Reload -; RV32IF-NEXT: flw fs0, 0(sp) # 4-byte Folded Reload +; RV32IF-NEXT: flw fs0, 4(sp) # 4-byte Folded Reload ; RV32IF-NEXT: addi sp, sp, 16 ; RV32IF-NEXT: ret ; @@ -641,23 +635,23 @@ define i64 @test_trunc_si64(float %x) nounwind { ; RV32IZFINX-NEXT: lui a2, %hi(.LCPI9_0) ; RV32IZFINX-NEXT: lw a2, %lo(.LCPI9_0)(a2) ; RV32IZFINX-NEXT: and a0, s2, a0 -; RV32IZFINX-NEXT: flt.s a3, a2, s0 -; RV32IZFINX-NEXT: neg a2, a3 +; RV32IZFINX-NEXT: flt.s a4, a2, s0 +; RV32IZFINX-NEXT: neg a2, a4 ; RV32IZFINX-NEXT: or a0, a2, a0 ; RV32IZFINX-NEXT: feq.s a2, s0, s0 ; RV32IZFINX-NEXT: neg a2, a2 ; RV32IZFINX-NEXT: lui a5, 524288 -; RV32IZFINX-NEXT: lui a4, 524288 +; RV32IZFINX-NEXT: lui a3, 524288 ; RV32IZFINX-NEXT: beqz s1, .LBB9_4 ; RV32IZFINX-NEXT: # %bb.3: -; RV32IZFINX-NEXT: mv a4, a1 +; RV32IZFINX-NEXT: mv a3, a1 ; RV32IZFINX-NEXT: .LBB9_4: ; RV32IZFINX-NEXT: and a0, a2, a0 -; RV32IZFINX-NEXT: beqz a3, .LBB9_6 +; RV32IZFINX-NEXT: beqz a4, .LBB9_6 ; RV32IZFINX-NEXT: # %bb.5: -; RV32IZFINX-NEXT: addi a4, a5, -1 +; RV32IZFINX-NEXT: addi a3, a5, -1 ; RV32IZFINX-NEXT: .LBB9_6: -; RV32IZFINX-NEXT: and a1, a2, a4 +; RV32IZFINX-NEXT: and a1, a2, a3 ; RV32IZFINX-NEXT: lw ra, 12(sp) # 4-byte Folded Reload ; RV32IZFINX-NEXT: lw s0, 8(sp) # 4-byte Folded Reload ; RV32IZFINX-NEXT: lw s1, 4(sp) # 4-byte Folded Reload @@ -823,8 +817,7 @@ define i64 @test_round_si64(float %x) nounwind { ; RV32IF-NEXT: addi sp, sp, -16 ; RV32IF-NEXT: sw ra, 12(sp) # 4-byte Folded Spill ; RV32IF-NEXT: sw s0, 8(sp) # 4-byte Folded Spill -; RV32IF-NEXT: sw s1, 4(sp) # 4-byte Folded Spill -; RV32IF-NEXT: fsw fs0, 0(sp) # 4-byte Folded Spill +; RV32IF-NEXT: fsw fs0, 4(sp) # 4-byte Folded Spill ; RV32IF-NEXT: fmv.s fs0, fa0 ; RV32IF-NEXT: lui a0, 307200 ; RV32IF-NEXT: fmv.w.x fa5, a0 @@ -839,33 +832,32 @@ define i64 @test_round_si64(float %x) nounwind { ; RV32IF-NEXT: lui a0, 913408 ; RV32IF-NEXT: fmv.w.x fa5, a0 ; RV32IF-NEXT: fle.s s0, fa5, fs0 -; RV32IF-NEXT: neg s1, s0 ; RV32IF-NEXT: fmv.s fa0, fs0 ; RV32IF-NEXT: call __fixsfdi -; RV32IF-NEXT: lui a2, %hi(.LCPI13_0) -; RV32IF-NEXT: flw fa5, %lo(.LCPI13_0)(a2) -; RV32IF-NEXT: and a0, s1, a0 -; RV32IF-NEXT: flt.s a3, fa5, fs0 -; RV32IF-NEXT: neg a2, a3 -; RV32IF-NEXT: or a0, a2, a0 -; RV32IF-NEXT: feq.s a2, fs0, fs0 -; RV32IF-NEXT: neg a2, a2 -; RV32IF-NEXT: lui a5, 524288 ; RV32IF-NEXT: lui a4, 524288 +; RV32IF-NEXT: lui a2, 524288 ; RV32IF-NEXT: beqz s0, .LBB13_4 ; RV32IF-NEXT: # %bb.3: -; RV32IF-NEXT: mv a4, a1 +; RV32IF-NEXT: mv a2, a1 ; RV32IF-NEXT: .LBB13_4: -; RV32IF-NEXT: and a0, a2, a0 +; RV32IF-NEXT: lui a1, %hi(.LCPI13_0) +; RV32IF-NEXT: flw fa5, %lo(.LCPI13_0)(a1) +; RV32IF-NEXT: flt.s a3, fa5, fs0 ; RV32IF-NEXT: beqz a3, .LBB13_6 ; RV32IF-NEXT: # %bb.5: -; RV32IF-NEXT: addi a4, a5, -1 +; RV32IF-NEXT: addi a2, a4, -1 ; RV32IF-NEXT: .LBB13_6: -; RV32IF-NEXT: and a1, a2, a4 +; RV32IF-NEXT: feq.s a1, fs0, fs0 +; RV32IF-NEXT: neg a4, a1 +; RV32IF-NEXT: and a1, a4, a2 +; RV32IF-NEXT: neg a2, s0 +; RV32IF-NEXT: and a0, a2, a0 +; RV32IF-NEXT: neg a2, a3 +; RV32IF-NEXT: or a0, a2, a0 +; RV32IF-NEXT: and a0, a4, a0 ; RV32IF-NEXT: lw ra, 12(sp) # 4-byte Folded Reload ; RV32IF-NEXT: lw s0, 8(sp) # 4-byte Folded Reload -; RV32IF-NEXT: lw s1, 4(sp) # 4-byte Folded Reload -; RV32IF-NEXT: flw fs0, 0(sp) # 4-byte Folded Reload +; RV32IF-NEXT: flw fs0, 4(sp) # 4-byte Folded Reload ; RV32IF-NEXT: addi sp, sp, 16 ; RV32IF-NEXT: ret ; @@ -903,23 +895,23 @@ define i64 @test_round_si64(float %x) nounwind { ; RV32IZFINX-NEXT: lui a2, %hi(.LCPI13_0) ; RV32IZFINX-NEXT: lw a2, %lo(.LCPI13_0)(a2) ; RV32IZFINX-NEXT: and a0, s2, a0 -; RV32IZFINX-NEXT: flt.s a3, a2, s0 -; RV32IZFINX-NEXT: neg a2, a3 +; RV32IZFINX-NEXT: flt.s a4, a2, s0 +; RV32IZFINX-NEXT: neg a2, a4 ; RV32IZFINX-NEXT: or a0, a2, a0 ; RV32IZFINX-NEXT: feq.s a2, s0, s0 ; RV32IZFINX-NEXT: neg a2, a2 ; RV32IZFINX-NEXT: lui a5, 524288 -; RV32IZFINX-NEXT: lui a4, 524288 +; RV32IZFINX-NEXT: lui a3, 524288 ; RV32IZFINX-NEXT: beqz s1, .LBB13_4 ; RV32IZFINX-NEXT: # %bb.3: -; RV32IZFINX-NEXT: mv a4, a1 +; RV32IZFINX-NEXT: mv a3, a1 ; RV32IZFINX-NEXT: .LBB13_4: ; RV32IZFINX-NEXT: and a0, a2, a0 -; RV32IZFINX-NEXT: beqz a3, .LBB13_6 +; RV32IZFINX-NEXT: beqz a4, .LBB13_6 ; RV32IZFINX-NEXT: # %bb.5: -; RV32IZFINX-NEXT: addi a4, a5, -1 +; RV32IZFINX-NEXT: addi a3, a5, -1 ; RV32IZFINX-NEXT: .LBB13_6: -; RV32IZFINX-NEXT: and a1, a2, a4 +; RV32IZFINX-NEXT: and a1, a2, a3 ; RV32IZFINX-NEXT: lw ra, 12(sp) # 4-byte Folded Reload ; RV32IZFINX-NEXT: lw s0, 8(sp) # 4-byte Folded Reload ; RV32IZFINX-NEXT: lw s1, 4(sp) # 4-byte Folded Reload @@ -1085,8 +1077,7 @@ define i64 @test_roundeven_si64(float %x) nounwind { ; RV32IF-NEXT: addi sp, sp, -16 ; RV32IF-NEXT: sw ra, 12(sp) # 4-byte Folded Spill ; RV32IF-NEXT: sw s0, 8(sp) # 4-byte Folded Spill -; RV32IF-NEXT: sw s1, 4(sp) # 4-byte Folded Spill -; RV32IF-NEXT: fsw fs0, 0(sp) # 4-byte Folded Spill +; RV32IF-NEXT: fsw fs0, 4(sp) # 4-byte Folded Spill ; RV32IF-NEXT: fmv.s fs0, fa0 ; RV32IF-NEXT: lui a0, 307200 ; RV32IF-NEXT: fmv.w.x fa5, a0 @@ -1101,33 +1092,32 @@ define i64 @test_roundeven_si64(float %x) nounwind { ; RV32IF-NEXT: lui a0, 913408 ; RV32IF-NEXT: fmv.w.x fa5, a0 ; RV32IF-NEXT: fle.s s0, fa5, fs0 -; RV32IF-NEXT: neg s1, s0 ; RV32IF-NEXT: fmv.s fa0, fs0 ; RV32IF-NEXT: call __fixsfdi -; RV32IF-NEXT: lui a2, %hi(.LCPI17_0) -; RV32IF-NEXT: flw fa5, %lo(.LCPI17_0)(a2) -; RV32IF-NEXT: and a0, s1, a0 -; RV32IF-NEXT: flt.s a3, fa5, fs0 -; RV32IF-NEXT: neg a2, a3 -; RV32IF-NEXT: or a0, a2, a0 -; RV32IF-NEXT: feq.s a2, fs0, fs0 -; RV32IF-NEXT: neg a2, a2 -; RV32IF-NEXT: lui a5, 524288 ; RV32IF-NEXT: lui a4, 524288 +; RV32IF-NEXT: lui a2, 524288 ; RV32IF-NEXT: beqz s0, .LBB17_4 ; RV32IF-NEXT: # %bb.3: -; RV32IF-NEXT: mv a4, a1 +; RV32IF-NEXT: mv a2, a1 ; RV32IF-NEXT: .LBB17_4: -; RV32IF-NEXT: and a0, a2, a0 +; RV32IF-NEXT: lui a1, %hi(.LCPI17_0) +; RV32IF-NEXT: flw fa5, %lo(.LCPI17_0)(a1) +; RV32IF-NEXT: flt.s a3, fa5, fs0 ; RV32IF-NEXT: beqz a3, .LBB17_6 ; RV32IF-NEXT: # %bb.5: -; RV32IF-NEXT: addi a4, a5, -1 +; RV32IF-NEXT: addi a2, a4, -1 ; RV32IF-NEXT: .LBB17_6: -; RV32IF-NEXT: and a1, a2, a4 +; RV32IF-NEXT: feq.s a1, fs0, fs0 +; RV32IF-NEXT: neg a4, a1 +; RV32IF-NEXT: and a1, a4, a2 +; RV32IF-NEXT: neg a2, s0 +; RV32IF-NEXT: and a0, a2, a0 +; RV32IF-NEXT: neg a2, a3 +; RV32IF-NEXT: or a0, a2, a0 +; RV32IF-NEXT: and a0, a4, a0 ; RV32IF-NEXT: lw ra, 12(sp) # 4-byte Folded Reload ; RV32IF-NEXT: lw s0, 8(sp) # 4-byte Folded Reload -; RV32IF-NEXT: lw s1, 4(sp) # 4-byte Folded Reload -; RV32IF-NEXT: flw fs0, 0(sp) # 4-byte Folded Reload +; RV32IF-NEXT: flw fs0, 4(sp) # 4-byte Folded Reload ; RV32IF-NEXT: addi sp, sp, 16 ; RV32IF-NEXT: ret ; @@ -1165,23 +1155,23 @@ define i64 @test_roundeven_si64(float %x) nounwind { ; RV32IZFINX-NEXT: lui a2, %hi(.LCPI17_0) ; RV32IZFINX-NEXT: lw a2, %lo(.LCPI17_0)(a2) ; RV32IZFINX-NEXT: and a0, s2, a0 -; RV32IZFINX-NEXT: flt.s a3, a2, s0 -; RV32IZFINX-NEXT: neg a2, a3 +; RV32IZFINX-NEXT: flt.s a4, a2, s0 +; RV32IZFINX-NEXT: neg a2, a4 ; RV32IZFINX-NEXT: or a0, a2, a0 ; RV32IZFINX-NEXT: feq.s a2, s0, s0 ; RV32IZFINX-NEXT: neg a2, a2 ; RV32IZFINX-NEXT: lui a5, 524288 -; RV32IZFINX-NEXT: lui a4, 524288 +; RV32IZFINX-NEXT: lui a3, 524288 ; RV32IZFINX-NEXT: beqz s1, .LBB17_4 ; RV32IZFINX-NEXT: # %bb.3: -; RV32IZFINX-NEXT: mv a4, a1 +; RV32IZFINX-NEXT: mv a3, a1 ; RV32IZFINX-NEXT: .LBB17_4: ; RV32IZFINX-NEXT: and a0, a2, a0 -; RV32IZFINX-NEXT: beqz a3, .LBB17_6 +; RV32IZFINX-NEXT: beqz a4, .LBB17_6 ; RV32IZFINX-NEXT: # %bb.5: -; RV32IZFINX-NEXT: addi a4, a5, -1 +; RV32IZFINX-NEXT: addi a3, a5, -1 ; RV32IZFINX-NEXT: .LBB17_6: -; RV32IZFINX-NEXT: and a1, a2, a4 +; RV32IZFINX-NEXT: and a1, a2, a3 ; RV32IZFINX-NEXT: lw ra, 12(sp) # 4-byte Folded Reload ; RV32IZFINX-NEXT: lw s0, 8(sp) # 4-byte Folded Reload ; RV32IZFINX-NEXT: lw s1, 4(sp) # 4-byte Folded Reload @@ -1347,8 +1337,7 @@ define i64 @test_rint_si64(float %x) nounwind { ; RV32IF-NEXT: addi sp, sp, -16 ; RV32IF-NEXT: sw ra, 12(sp) # 4-byte Folded Spill ; RV32IF-NEXT: sw s0, 8(sp) # 4-byte Folded Spill -; RV32IF-NEXT: sw s1, 4(sp) # 4-byte Folded Spill -; RV32IF-NEXT: fsw fs0, 0(sp) # 4-byte Folded Spill +; RV32IF-NEXT: fsw fs0, 4(sp) # 4-byte Folded Spill ; RV32IF-NEXT: fmv.s fs0, fa0 ; RV32IF-NEXT: lui a0, 307200 ; RV32IF-NEXT: fmv.w.x fa5, a0 @@ -1363,33 +1352,32 @@ define i64 @test_rint_si64(float %x) nounwind { ; RV32IF-NEXT: lui a0, 913408 ; RV32IF-NEXT: fmv.w.x fa5, a0 ; RV32IF-NEXT: fle.s s0, fa5, fs0 -; RV32IF-NEXT: neg s1, s0 ; RV32IF-NEXT: fmv.s fa0, fs0 ; RV32IF-NEXT: call __fixsfdi -; RV32IF-NEXT: lui a2, %hi(.LCPI21_0) -; RV32IF-NEXT: flw fa5, %lo(.LCPI21_0)(a2) -; RV32IF-NEXT: and a0, s1, a0 -; RV32IF-NEXT: flt.s a3, fa5, fs0 -; RV32IF-NEXT: neg a2, a3 -; RV32IF-NEXT: or a0, a2, a0 -; RV32IF-NEXT: feq.s a2, fs0, fs0 -; RV32IF-NEXT: neg a2, a2 -; RV32IF-NEXT: lui a5, 524288 ; RV32IF-NEXT: lui a4, 524288 +; RV32IF-NEXT: lui a2, 524288 ; RV32IF-NEXT: beqz s0, .LBB21_4 ; RV32IF-NEXT: # %bb.3: -; RV32IF-NEXT: mv a4, a1 +; RV32IF-NEXT: mv a2, a1 ; RV32IF-NEXT: .LBB21_4: -; RV32IF-NEXT: and a0, a2, a0 +; RV32IF-NEXT: lui a1, %hi(.LCPI21_0) +; RV32IF-NEXT: flw fa5, %lo(.LCPI21_0)(a1) +; RV32IF-NEXT: flt.s a3, fa5, fs0 ; RV32IF-NEXT: beqz a3, .LBB21_6 ; RV32IF-NEXT: # %bb.5: -; RV32IF-NEXT: addi a4, a5, -1 +; RV32IF-NEXT: addi a2, a4, -1 ; RV32IF-NEXT: .LBB21_6: -; RV32IF-NEXT: and a1, a2, a4 +; RV32IF-NEXT: feq.s a1, fs0, fs0 +; RV32IF-NEXT: neg a4, a1 +; RV32IF-NEXT: and a1, a4, a2 +; RV32IF-NEXT: neg a2, s0 +; RV32IF-NEXT: and a0, a2, a0 +; RV32IF-NEXT: neg a2, a3 +; RV32IF-NEXT: or a0, a2, a0 +; RV32IF-NEXT: and a0, a4, a0 ; RV32IF-NEXT: lw ra, 12(sp) # 4-byte Folded Reload ; RV32IF-NEXT: lw s0, 8(sp) # 4-byte Folded Reload -; RV32IF-NEXT: lw s1, 4(sp) # 4-byte Folded Reload -; RV32IF-NEXT: flw fs0, 0(sp) # 4-byte Folded Reload +; RV32IF-NEXT: flw fs0, 4(sp) # 4-byte Folded Reload ; RV32IF-NEXT: addi sp, sp, 16 ; RV32IF-NEXT: ret ; @@ -1427,23 +1415,23 @@ define i64 @test_rint_si64(float %x) nounwind { ; RV32IZFINX-NEXT: lui a2, %hi(.LCPI21_0) ; RV32IZFINX-NEXT: lw a2, %lo(.LCPI21_0)(a2) ; RV32IZFINX-NEXT: and a0, s2, a0 -; RV32IZFINX-NEXT: flt.s a3, a2, s0 -; RV32IZFINX-NEXT: neg a2, a3 +; RV32IZFINX-NEXT: flt.s a4, a2, s0 +; RV32IZFINX-NEXT: neg a2, a4 ; RV32IZFINX-NEXT: or a0, a2, a0 ; RV32IZFINX-NEXT: feq.s a2, s0, s0 ; RV32IZFINX-NEXT: neg a2, a2 ; RV32IZFINX-NEXT: lui a5, 524288 -; RV32IZFINX-NEXT: lui a4, 524288 +; RV32IZFINX-NEXT: lui a3, 524288 ; RV32IZFINX-NEXT: beqz s1, .LBB21_4 ; RV32IZFINX-NEXT: # %bb.3: -; RV32IZFINX-NEXT: mv a4, a1 +; RV32IZFINX-NEXT: mv a3, a1 ; RV32IZFINX-NEXT: .LBB21_4: ; RV32IZFINX-NEXT: and a0, a2, a0 -; RV32IZFINX-NEXT: beqz a3, .LBB21_6 +; RV32IZFINX-NEXT: beqz a4, .LBB21_6 ; RV32IZFINX-NEXT: # %bb.5: -; RV32IZFINX-NEXT: addi a4, a5, -1 +; RV32IZFINX-NEXT: addi a3, a5, -1 ; RV32IZFINX-NEXT: .LBB21_6: -; RV32IZFINX-NEXT: and a1, a2, a4 +; RV32IZFINX-NEXT: and a1, a2, a3 ; RV32IZFINX-NEXT: lw ra, 12(sp) # 4-byte Folded Reload ; RV32IZFINX-NEXT: lw s0, 8(sp) # 4-byte Folded Reload ; RV32IZFINX-NEXT: lw s1, 4(sp) # 4-byte Folded Reload diff --git a/llvm/test/CodeGen/RISCV/forced-atomics.ll b/llvm/test/CodeGen/RISCV/forced-atomics.ll index c303690aadfff8c16c871ab07cda04e78bef06a9..f6a53a9d76dd3561562d4b097b9585446d52d7cb 100644 --- a/llvm/test/CodeGen/RISCV/forced-atomics.ll +++ b/llvm/test/CodeGen/RISCV/forced-atomics.ll @@ -3567,8 +3567,8 @@ define i64 @rmw64_umax_seq_cst(ptr %p) nounwind { ; RV32-NEXT: # in Loop: Header=BB51_2 Depth=1 ; RV32-NEXT: neg a3, a0 ; RV32-NEXT: and a3, a3, a1 -; RV32-NEXT: sw a1, 4(sp) ; RV32-NEXT: sw a4, 0(sp) +; RV32-NEXT: sw a1, 4(sp) ; RV32-NEXT: mv a1, sp ; RV32-NEXT: li a4, 5 ; RV32-NEXT: li a5, 5 @@ -3659,8 +3659,8 @@ define i64 @rmw64_umin_seq_cst(ptr %p) nounwind { ; RV32-NEXT: # in Loop: Header=BB52_2 Depth=1 ; RV32-NEXT: neg a3, a0 ; RV32-NEXT: and a3, a3, a1 -; RV32-NEXT: sw a1, 4(sp) ; RV32-NEXT: sw a4, 0(sp) +; RV32-NEXT: sw a1, 4(sp) ; RV32-NEXT: mv a1, sp ; RV32-NEXT: li a4, 5 ; RV32-NEXT: li a5, 5 diff --git a/llvm/test/CodeGen/RISCV/fpclamptosat.ll b/llvm/test/CodeGen/RISCV/fpclamptosat.ll index 06ab813faf0253b1f00d76cf6fd3dec60423ad30..deb5a6d4013d49439d78df57446961bdd37166b3 100644 --- a/llvm/test/CodeGen/RISCV/fpclamptosat.ll +++ b/llvm/test/CodeGen/RISCV/fpclamptosat.ll @@ -114,8 +114,8 @@ define i32 @utest_f64i32(double %x) { ; RV32IF-NEXT: sw ra, 12(sp) # 4-byte Folded Spill ; RV32IF-NEXT: .cfi_offset ra, -4 ; RV32IF-NEXT: call __fixunsdfdi -; RV32IF-NEXT: seqz a1, a1 ; RV32IF-NEXT: sltiu a2, a0, -1 +; RV32IF-NEXT: seqz a1, a1 ; RV32IF-NEXT: and a1, a1, a2 ; RV32IF-NEXT: addi a1, a1, -1 ; RV32IF-NEXT: or a0, a1, a0 @@ -429,8 +429,8 @@ define i32 @utesth_f16i32(half %x) { ; RV32-NEXT: .cfi_offset ra, -4 ; RV32-NEXT: call __extendhfsf2 ; RV32-NEXT: call __fixunssfdi -; RV32-NEXT: seqz a1, a1 ; RV32-NEXT: sltiu a2, a0, -1 +; RV32-NEXT: seqz a1, a1 ; RV32-NEXT: and a1, a1, a2 ; RV32-NEXT: addi a1, a1, -1 ; RV32-NEXT: or a0, a1, a0 diff --git a/llvm/test/CodeGen/RISCV/half-convert.ll b/llvm/test/CodeGen/RISCV/half-convert.ll index 277749c75bbbf194768cb1fa220af37224d00943..31fb6e2ee9c840986fe8312f52a474c27146204f 100644 --- a/llvm/test/CodeGen/RISCV/half-convert.ll +++ b/llvm/test/CodeGen/RISCV/half-convert.ll @@ -2145,47 +2145,41 @@ define i64 @fcvt_l_h(half %a) nounwind { define i64 @fcvt_l_h_sat(half %a) nounwind { ; RV32IZFH-LABEL: fcvt_l_h_sat: ; RV32IZFH: # %bb.0: # %start -; RV32IZFH-NEXT: addi sp, sp, -32 -; RV32IZFH-NEXT: sw ra, 28(sp) # 4-byte Folded Spill -; RV32IZFH-NEXT: sw s0, 24(sp) # 4-byte Folded Spill -; RV32IZFH-NEXT: sw s1, 20(sp) # 4-byte Folded Spill -; RV32IZFH-NEXT: sw s2, 16(sp) # 4-byte Folded Spill -; RV32IZFH-NEXT: sw s3, 12(sp) # 4-byte Folded Spill -; RV32IZFH-NEXT: fsw fs0, 8(sp) # 4-byte Folded Spill -; RV32IZFH-NEXT: lui a0, %hi(.LCPI10_0) -; RV32IZFH-NEXT: flw fa5, %lo(.LCPI10_0)(a0) +; RV32IZFH-NEXT: addi sp, sp, -16 +; RV32IZFH-NEXT: sw ra, 12(sp) # 4-byte Folded Spill +; RV32IZFH-NEXT: sw s0, 8(sp) # 4-byte Folded Spill +; RV32IZFH-NEXT: fsw fs0, 4(sp) # 4-byte Folded Spill ; RV32IZFH-NEXT: fcvt.s.h fs0, fa0 -; RV32IZFH-NEXT: flt.s s0, fa5, fs0 -; RV32IZFH-NEXT: neg s1, s0 ; RV32IZFH-NEXT: lui a0, 913408 ; RV32IZFH-NEXT: fmv.w.x fa5, a0 -; RV32IZFH-NEXT: fle.s s2, fa5, fs0 -; RV32IZFH-NEXT: neg s3, s2 +; RV32IZFH-NEXT: fle.s s0, fa5, fs0 ; RV32IZFH-NEXT: fmv.s fa0, fs0 ; RV32IZFH-NEXT: call __fixsfdi -; RV32IZFH-NEXT: and a0, s3, a0 -; RV32IZFH-NEXT: or a0, s1, a0 -; RV32IZFH-NEXT: feq.s a2, fs0, fs0 -; RV32IZFH-NEXT: neg a2, a2 ; RV32IZFH-NEXT: lui a4, 524288 -; RV32IZFH-NEXT: lui a3, 524288 -; RV32IZFH-NEXT: beqz s2, .LBB10_2 +; RV32IZFH-NEXT: lui a2, 524288 +; RV32IZFH-NEXT: beqz s0, .LBB10_2 ; RV32IZFH-NEXT: # %bb.1: # %start -; RV32IZFH-NEXT: mv a3, a1 +; RV32IZFH-NEXT: mv a2, a1 ; RV32IZFH-NEXT: .LBB10_2: # %start -; RV32IZFH-NEXT: and a0, a2, a0 -; RV32IZFH-NEXT: beqz s0, .LBB10_4 +; RV32IZFH-NEXT: lui a1, %hi(.LCPI10_0) +; RV32IZFH-NEXT: flw fa5, %lo(.LCPI10_0)(a1) +; RV32IZFH-NEXT: flt.s a3, fa5, fs0 +; RV32IZFH-NEXT: beqz a3, .LBB10_4 ; RV32IZFH-NEXT: # %bb.3: -; RV32IZFH-NEXT: addi a3, a4, -1 +; RV32IZFH-NEXT: addi a2, a4, -1 ; RV32IZFH-NEXT: .LBB10_4: # %start -; RV32IZFH-NEXT: and a1, a2, a3 -; RV32IZFH-NEXT: lw ra, 28(sp) # 4-byte Folded Reload -; RV32IZFH-NEXT: lw s0, 24(sp) # 4-byte Folded Reload -; RV32IZFH-NEXT: lw s1, 20(sp) # 4-byte Folded Reload -; RV32IZFH-NEXT: lw s2, 16(sp) # 4-byte Folded Reload -; RV32IZFH-NEXT: lw s3, 12(sp) # 4-byte Folded Reload -; RV32IZFH-NEXT: flw fs0, 8(sp) # 4-byte Folded Reload -; RV32IZFH-NEXT: addi sp, sp, 32 +; RV32IZFH-NEXT: feq.s a1, fs0, fs0 +; RV32IZFH-NEXT: neg a4, a1 +; RV32IZFH-NEXT: and a1, a4, a2 +; RV32IZFH-NEXT: neg a2, a3 +; RV32IZFH-NEXT: neg a3, s0 +; RV32IZFH-NEXT: and a0, a3, a0 +; RV32IZFH-NEXT: or a0, a2, a0 +; RV32IZFH-NEXT: and a0, a4, a0 +; RV32IZFH-NEXT: lw ra, 12(sp) # 4-byte Folded Reload +; RV32IZFH-NEXT: lw s0, 8(sp) # 4-byte Folded Reload +; RV32IZFH-NEXT: flw fs0, 4(sp) # 4-byte Folded Reload +; RV32IZFH-NEXT: addi sp, sp, 16 ; RV32IZFH-NEXT: ret ; ; RV64IZFH-LABEL: fcvt_l_h_sat: @@ -2199,47 +2193,41 @@ define i64 @fcvt_l_h_sat(half %a) nounwind { ; ; RV32IDZFH-LABEL: fcvt_l_h_sat: ; RV32IDZFH: # %bb.0: # %start -; RV32IDZFH-NEXT: addi sp, sp, -32 -; RV32IDZFH-NEXT: sw ra, 28(sp) # 4-byte Folded Spill -; RV32IDZFH-NEXT: sw s0, 24(sp) # 4-byte Folded Spill -; RV32IDZFH-NEXT: sw s1, 20(sp) # 4-byte Folded Spill -; RV32IDZFH-NEXT: sw s2, 16(sp) # 4-byte Folded Spill -; RV32IDZFH-NEXT: sw s3, 12(sp) # 4-byte Folded Spill +; RV32IDZFH-NEXT: addi sp, sp, -16 +; RV32IDZFH-NEXT: sw ra, 12(sp) # 4-byte Folded Spill +; RV32IDZFH-NEXT: sw s0, 8(sp) # 4-byte Folded Spill ; RV32IDZFH-NEXT: fsd fs0, 0(sp) # 8-byte Folded Spill -; RV32IDZFH-NEXT: lui a0, %hi(.LCPI10_0) -; RV32IDZFH-NEXT: flw fa5, %lo(.LCPI10_0)(a0) ; RV32IDZFH-NEXT: fcvt.s.h fs0, fa0 -; RV32IDZFH-NEXT: flt.s s0, fa5, fs0 -; RV32IDZFH-NEXT: neg s1, s0 ; RV32IDZFH-NEXT: lui a0, 913408 ; RV32IDZFH-NEXT: fmv.w.x fa5, a0 -; RV32IDZFH-NEXT: fle.s s2, fa5, fs0 -; RV32IDZFH-NEXT: neg s3, s2 +; RV32IDZFH-NEXT: fle.s s0, fa5, fs0 ; RV32IDZFH-NEXT: fmv.s fa0, fs0 ; RV32IDZFH-NEXT: call __fixsfdi -; RV32IDZFH-NEXT: and a0, s3, a0 -; RV32IDZFH-NEXT: or a0, s1, a0 -; RV32IDZFH-NEXT: feq.s a2, fs0, fs0 -; RV32IDZFH-NEXT: neg a2, a2 ; RV32IDZFH-NEXT: lui a4, 524288 -; RV32IDZFH-NEXT: lui a3, 524288 -; RV32IDZFH-NEXT: beqz s2, .LBB10_2 +; RV32IDZFH-NEXT: lui a2, 524288 +; RV32IDZFH-NEXT: beqz s0, .LBB10_2 ; RV32IDZFH-NEXT: # %bb.1: # %start -; RV32IDZFH-NEXT: mv a3, a1 +; RV32IDZFH-NEXT: mv a2, a1 ; RV32IDZFH-NEXT: .LBB10_2: # %start -; RV32IDZFH-NEXT: and a0, a2, a0 -; RV32IDZFH-NEXT: beqz s0, .LBB10_4 +; RV32IDZFH-NEXT: lui a1, %hi(.LCPI10_0) +; RV32IDZFH-NEXT: flw fa5, %lo(.LCPI10_0)(a1) +; RV32IDZFH-NEXT: flt.s a3, fa5, fs0 +; RV32IDZFH-NEXT: beqz a3, .LBB10_4 ; RV32IDZFH-NEXT: # %bb.3: -; RV32IDZFH-NEXT: addi a3, a4, -1 +; RV32IDZFH-NEXT: addi a2, a4, -1 ; RV32IDZFH-NEXT: .LBB10_4: # %start -; RV32IDZFH-NEXT: and a1, a2, a3 -; RV32IDZFH-NEXT: lw ra, 28(sp) # 4-byte Folded Reload -; RV32IDZFH-NEXT: lw s0, 24(sp) # 4-byte Folded Reload -; RV32IDZFH-NEXT: lw s1, 20(sp) # 4-byte Folded Reload -; RV32IDZFH-NEXT: lw s2, 16(sp) # 4-byte Folded Reload -; RV32IDZFH-NEXT: lw s3, 12(sp) # 4-byte Folded Reload +; RV32IDZFH-NEXT: feq.s a1, fs0, fs0 +; RV32IDZFH-NEXT: neg a4, a1 +; RV32IDZFH-NEXT: and a1, a4, a2 +; RV32IDZFH-NEXT: neg a2, a3 +; RV32IDZFH-NEXT: neg a3, s0 +; RV32IDZFH-NEXT: and a0, a3, a0 +; RV32IDZFH-NEXT: or a0, a2, a0 +; RV32IDZFH-NEXT: and a0, a4, a0 +; RV32IDZFH-NEXT: lw ra, 12(sp) # 4-byte Folded Reload +; RV32IDZFH-NEXT: lw s0, 8(sp) # 4-byte Folded Reload ; RV32IDZFH-NEXT: fld fs0, 0(sp) # 8-byte Folded Reload -; RV32IDZFH-NEXT: addi sp, sp, 32 +; RV32IDZFH-NEXT: addi sp, sp, 16 ; RV32IDZFH-NEXT: ret ; ; RV64IDZFH-LABEL: fcvt_l_h_sat: @@ -2515,47 +2503,41 @@ define i64 @fcvt_l_h_sat(half %a) nounwind { ; ; RV32ID-LABEL: fcvt_l_h_sat: ; RV32ID: # %bb.0: # %start -; RV32ID-NEXT: addi sp, sp, -32 -; RV32ID-NEXT: sw ra, 28(sp) # 4-byte Folded Spill -; RV32ID-NEXT: sw s0, 24(sp) # 4-byte Folded Spill -; RV32ID-NEXT: sw s1, 20(sp) # 4-byte Folded Spill -; RV32ID-NEXT: sw s2, 16(sp) # 4-byte Folded Spill -; RV32ID-NEXT: sw s3, 12(sp) # 4-byte Folded Spill +; RV32ID-NEXT: addi sp, sp, -16 +; RV32ID-NEXT: sw ra, 12(sp) # 4-byte Folded Spill +; RV32ID-NEXT: sw s0, 8(sp) # 4-byte Folded Spill ; RV32ID-NEXT: fsd fs0, 0(sp) # 8-byte Folded Spill ; RV32ID-NEXT: call __extendhfsf2 -; RV32ID-NEXT: lui a0, %hi(.LCPI10_0) -; RV32ID-NEXT: flw fa5, %lo(.LCPI10_0)(a0) ; RV32ID-NEXT: fmv.s fs0, fa0 -; RV32ID-NEXT: flt.s s0, fa5, fa0 -; RV32ID-NEXT: neg s1, s0 ; RV32ID-NEXT: lui a0, 913408 ; RV32ID-NEXT: fmv.w.x fa5, a0 -; RV32ID-NEXT: fle.s s2, fa5, fa0 -; RV32ID-NEXT: neg s3, s2 +; RV32ID-NEXT: fle.s s0, fa5, fa0 ; RV32ID-NEXT: call __fixsfdi -; RV32ID-NEXT: and a0, s3, a0 -; RV32ID-NEXT: or a0, s1, a0 -; RV32ID-NEXT: feq.s a2, fs0, fs0 -; RV32ID-NEXT: neg a2, a2 ; RV32ID-NEXT: lui a4, 524288 -; RV32ID-NEXT: lui a3, 524288 -; RV32ID-NEXT: beqz s2, .LBB10_2 +; RV32ID-NEXT: lui a2, 524288 +; RV32ID-NEXT: beqz s0, .LBB10_2 ; RV32ID-NEXT: # %bb.1: # %start -; RV32ID-NEXT: mv a3, a1 +; RV32ID-NEXT: mv a2, a1 ; RV32ID-NEXT: .LBB10_2: # %start -; RV32ID-NEXT: and a0, a2, a0 -; RV32ID-NEXT: beqz s0, .LBB10_4 +; RV32ID-NEXT: lui a1, %hi(.LCPI10_0) +; RV32ID-NEXT: flw fa5, %lo(.LCPI10_0)(a1) +; RV32ID-NEXT: flt.s a3, fa5, fs0 +; RV32ID-NEXT: beqz a3, .LBB10_4 ; RV32ID-NEXT: # %bb.3: -; RV32ID-NEXT: addi a3, a4, -1 +; RV32ID-NEXT: addi a2, a4, -1 ; RV32ID-NEXT: .LBB10_4: # %start -; RV32ID-NEXT: and a1, a2, a3 -; RV32ID-NEXT: lw ra, 28(sp) # 4-byte Folded Reload -; RV32ID-NEXT: lw s0, 24(sp) # 4-byte Folded Reload -; RV32ID-NEXT: lw s1, 20(sp) # 4-byte Folded Reload -; RV32ID-NEXT: lw s2, 16(sp) # 4-byte Folded Reload -; RV32ID-NEXT: lw s3, 12(sp) # 4-byte Folded Reload +; RV32ID-NEXT: feq.s a1, fs0, fs0 +; RV32ID-NEXT: neg a4, a1 +; RV32ID-NEXT: and a1, a4, a2 +; RV32ID-NEXT: neg a2, s0 +; RV32ID-NEXT: and a0, a2, a0 +; RV32ID-NEXT: neg a2, a3 +; RV32ID-NEXT: or a0, a2, a0 +; RV32ID-NEXT: and a0, a4, a0 +; RV32ID-NEXT: lw ra, 12(sp) # 4-byte Folded Reload +; RV32ID-NEXT: lw s0, 8(sp) # 4-byte Folded Reload ; RV32ID-NEXT: fld fs0, 0(sp) # 8-byte Folded Reload -; RV32ID-NEXT: addi sp, sp, 32 +; RV32ID-NEXT: addi sp, sp, 16 ; RV32ID-NEXT: ret ; ; RV64ID-LABEL: fcvt_l_h_sat: @@ -2574,47 +2556,41 @@ define i64 @fcvt_l_h_sat(half %a) nounwind { ; ; RV32IFZFHMIN-LABEL: fcvt_l_h_sat: ; RV32IFZFHMIN: # %bb.0: # %start -; RV32IFZFHMIN-NEXT: addi sp, sp, -32 -; RV32IFZFHMIN-NEXT: sw ra, 28(sp) # 4-byte Folded Spill -; RV32IFZFHMIN-NEXT: sw s0, 24(sp) # 4-byte Folded Spill -; RV32IFZFHMIN-NEXT: sw s1, 20(sp) # 4-byte Folded Spill -; RV32IFZFHMIN-NEXT: sw s2, 16(sp) # 4-byte Folded Spill -; RV32IFZFHMIN-NEXT: sw s3, 12(sp) # 4-byte Folded Spill -; RV32IFZFHMIN-NEXT: fsw fs0, 8(sp) # 4-byte Folded Spill -; RV32IFZFHMIN-NEXT: lui a0, %hi(.LCPI10_0) -; RV32IFZFHMIN-NEXT: flw fa5, %lo(.LCPI10_0)(a0) +; RV32IFZFHMIN-NEXT: addi sp, sp, -16 +; RV32IFZFHMIN-NEXT: sw ra, 12(sp) # 4-byte Folded Spill +; RV32IFZFHMIN-NEXT: sw s0, 8(sp) # 4-byte Folded Spill +; RV32IFZFHMIN-NEXT: fsw fs0, 4(sp) # 4-byte Folded Spill ; RV32IFZFHMIN-NEXT: fcvt.s.h fs0, fa0 -; RV32IFZFHMIN-NEXT: flt.s s0, fa5, fs0 -; RV32IFZFHMIN-NEXT: neg s1, s0 ; RV32IFZFHMIN-NEXT: lui a0, 913408 ; RV32IFZFHMIN-NEXT: fmv.w.x fa5, a0 -; RV32IFZFHMIN-NEXT: fle.s s2, fa5, fs0 -; RV32IFZFHMIN-NEXT: neg s3, s2 +; RV32IFZFHMIN-NEXT: fle.s s0, fa5, fs0 ; RV32IFZFHMIN-NEXT: fmv.s fa0, fs0 ; RV32IFZFHMIN-NEXT: call __fixsfdi -; RV32IFZFHMIN-NEXT: and a0, s3, a0 -; RV32IFZFHMIN-NEXT: or a0, s1, a0 -; RV32IFZFHMIN-NEXT: feq.s a2, fs0, fs0 -; RV32IFZFHMIN-NEXT: neg a2, a2 ; RV32IFZFHMIN-NEXT: lui a4, 524288 -; RV32IFZFHMIN-NEXT: lui a3, 524288 -; RV32IFZFHMIN-NEXT: beqz s2, .LBB10_2 +; RV32IFZFHMIN-NEXT: lui a2, 524288 +; RV32IFZFHMIN-NEXT: beqz s0, .LBB10_2 ; RV32IFZFHMIN-NEXT: # %bb.1: # %start -; RV32IFZFHMIN-NEXT: mv a3, a1 +; RV32IFZFHMIN-NEXT: mv a2, a1 ; RV32IFZFHMIN-NEXT: .LBB10_2: # %start -; RV32IFZFHMIN-NEXT: and a0, a2, a0 -; RV32IFZFHMIN-NEXT: beqz s0, .LBB10_4 +; RV32IFZFHMIN-NEXT: lui a1, %hi(.LCPI10_0) +; RV32IFZFHMIN-NEXT: flw fa5, %lo(.LCPI10_0)(a1) +; RV32IFZFHMIN-NEXT: flt.s a3, fa5, fs0 +; RV32IFZFHMIN-NEXT: beqz a3, .LBB10_4 ; RV32IFZFHMIN-NEXT: # %bb.3: -; RV32IFZFHMIN-NEXT: addi a3, a4, -1 +; RV32IFZFHMIN-NEXT: addi a2, a4, -1 ; RV32IFZFHMIN-NEXT: .LBB10_4: # %start -; RV32IFZFHMIN-NEXT: and a1, a2, a3 -; RV32IFZFHMIN-NEXT: lw ra, 28(sp) # 4-byte Folded Reload -; RV32IFZFHMIN-NEXT: lw s0, 24(sp) # 4-byte Folded Reload -; RV32IFZFHMIN-NEXT: lw s1, 20(sp) # 4-byte Folded Reload -; RV32IFZFHMIN-NEXT: lw s2, 16(sp) # 4-byte Folded Reload -; RV32IFZFHMIN-NEXT: lw s3, 12(sp) # 4-byte Folded Reload -; RV32IFZFHMIN-NEXT: flw fs0, 8(sp) # 4-byte Folded Reload -; RV32IFZFHMIN-NEXT: addi sp, sp, 32 +; RV32IFZFHMIN-NEXT: feq.s a1, fs0, fs0 +; RV32IFZFHMIN-NEXT: neg a4, a1 +; RV32IFZFHMIN-NEXT: and a1, a4, a2 +; RV32IFZFHMIN-NEXT: neg a2, a3 +; RV32IFZFHMIN-NEXT: neg a3, s0 +; RV32IFZFHMIN-NEXT: and a0, a3, a0 +; RV32IFZFHMIN-NEXT: or a0, a2, a0 +; RV32IFZFHMIN-NEXT: and a0, a4, a0 +; RV32IFZFHMIN-NEXT: lw ra, 12(sp) # 4-byte Folded Reload +; RV32IFZFHMIN-NEXT: lw s0, 8(sp) # 4-byte Folded Reload +; RV32IFZFHMIN-NEXT: flw fs0, 4(sp) # 4-byte Folded Reload +; RV32IFZFHMIN-NEXT: addi sp, sp, 16 ; RV32IFZFHMIN-NEXT: ret ; ; CHECK64-IZFHMIN-LABEL: fcvt_l_h_sat: @@ -2629,47 +2605,41 @@ define i64 @fcvt_l_h_sat(half %a) nounwind { ; ; RV32IDZFHMIN-LABEL: fcvt_l_h_sat: ; RV32IDZFHMIN: # %bb.0: # %start -; RV32IDZFHMIN-NEXT: addi sp, sp, -32 -; RV32IDZFHMIN-NEXT: sw ra, 28(sp) # 4-byte Folded Spill -; RV32IDZFHMIN-NEXT: sw s0, 24(sp) # 4-byte Folded Spill -; RV32IDZFHMIN-NEXT: sw s1, 20(sp) # 4-byte Folded Spill -; RV32IDZFHMIN-NEXT: sw s2, 16(sp) # 4-byte Folded Spill -; RV32IDZFHMIN-NEXT: sw s3, 12(sp) # 4-byte Folded Spill +; RV32IDZFHMIN-NEXT: addi sp, sp, -16 +; RV32IDZFHMIN-NEXT: sw ra, 12(sp) # 4-byte Folded Spill +; RV32IDZFHMIN-NEXT: sw s0, 8(sp) # 4-byte Folded Spill ; RV32IDZFHMIN-NEXT: fsd fs0, 0(sp) # 8-byte Folded Spill -; RV32IDZFHMIN-NEXT: lui a0, %hi(.LCPI10_0) -; RV32IDZFHMIN-NEXT: flw fa5, %lo(.LCPI10_0)(a0) ; RV32IDZFHMIN-NEXT: fcvt.s.h fs0, fa0 -; RV32IDZFHMIN-NEXT: flt.s s0, fa5, fs0 -; RV32IDZFHMIN-NEXT: neg s1, s0 ; RV32IDZFHMIN-NEXT: lui a0, 913408 ; RV32IDZFHMIN-NEXT: fmv.w.x fa5, a0 -; RV32IDZFHMIN-NEXT: fle.s s2, fa5, fs0 -; RV32IDZFHMIN-NEXT: neg s3, s2 +; RV32IDZFHMIN-NEXT: fle.s s0, fa5, fs0 ; RV32IDZFHMIN-NEXT: fmv.s fa0, fs0 ; RV32IDZFHMIN-NEXT: call __fixsfdi -; RV32IDZFHMIN-NEXT: and a0, s3, a0 -; RV32IDZFHMIN-NEXT: or a0, s1, a0 -; RV32IDZFHMIN-NEXT: feq.s a2, fs0, fs0 -; RV32IDZFHMIN-NEXT: neg a2, a2 ; RV32IDZFHMIN-NEXT: lui a4, 524288 -; RV32IDZFHMIN-NEXT: lui a3, 524288 -; RV32IDZFHMIN-NEXT: beqz s2, .LBB10_2 +; RV32IDZFHMIN-NEXT: lui a2, 524288 +; RV32IDZFHMIN-NEXT: beqz s0, .LBB10_2 ; RV32IDZFHMIN-NEXT: # %bb.1: # %start -; RV32IDZFHMIN-NEXT: mv a3, a1 +; RV32IDZFHMIN-NEXT: mv a2, a1 ; RV32IDZFHMIN-NEXT: .LBB10_2: # %start -; RV32IDZFHMIN-NEXT: and a0, a2, a0 -; RV32IDZFHMIN-NEXT: beqz s0, .LBB10_4 +; RV32IDZFHMIN-NEXT: lui a1, %hi(.LCPI10_0) +; RV32IDZFHMIN-NEXT: flw fa5, %lo(.LCPI10_0)(a1) +; RV32IDZFHMIN-NEXT: flt.s a3, fa5, fs0 +; RV32IDZFHMIN-NEXT: beqz a3, .LBB10_4 ; RV32IDZFHMIN-NEXT: # %bb.3: -; RV32IDZFHMIN-NEXT: addi a3, a4, -1 +; RV32IDZFHMIN-NEXT: addi a2, a4, -1 ; RV32IDZFHMIN-NEXT: .LBB10_4: # %start -; RV32IDZFHMIN-NEXT: and a1, a2, a3 -; RV32IDZFHMIN-NEXT: lw ra, 28(sp) # 4-byte Folded Reload -; RV32IDZFHMIN-NEXT: lw s0, 24(sp) # 4-byte Folded Reload -; RV32IDZFHMIN-NEXT: lw s1, 20(sp) # 4-byte Folded Reload -; RV32IDZFHMIN-NEXT: lw s2, 16(sp) # 4-byte Folded Reload -; RV32IDZFHMIN-NEXT: lw s3, 12(sp) # 4-byte Folded Reload +; RV32IDZFHMIN-NEXT: feq.s a1, fs0, fs0 +; RV32IDZFHMIN-NEXT: neg a4, a1 +; RV32IDZFHMIN-NEXT: and a1, a4, a2 +; RV32IDZFHMIN-NEXT: neg a2, a3 +; RV32IDZFHMIN-NEXT: neg a3, s0 +; RV32IDZFHMIN-NEXT: and a0, a3, a0 +; RV32IDZFHMIN-NEXT: or a0, a2, a0 +; RV32IDZFHMIN-NEXT: and a0, a4, a0 +; RV32IDZFHMIN-NEXT: lw ra, 12(sp) # 4-byte Folded Reload +; RV32IDZFHMIN-NEXT: lw s0, 8(sp) # 4-byte Folded Reload ; RV32IDZFHMIN-NEXT: fld fs0, 0(sp) # 8-byte Folded Reload -; RV32IDZFHMIN-NEXT: addi sp, sp, 32 +; RV32IDZFHMIN-NEXT: addi sp, sp, 16 ; RV32IDZFHMIN-NEXT: ret ; ; CHECK32-IZHINXMIN-LABEL: fcvt_l_h_sat: diff --git a/llvm/test/CodeGen/RISCV/half-round-conv-sat.ll b/llvm/test/CodeGen/RISCV/half-round-conv-sat.ll index 9c95210bfa7c01cb2b98880d18c2d8f2f45f075e..04a8a66f44598f46795c068c7302f652fcd450ce 100644 --- a/llvm/test/CodeGen/RISCV/half-round-conv-sat.ll +++ b/llvm/test/CodeGen/RISCV/half-round-conv-sat.ll @@ -108,40 +108,38 @@ define i64 @test_floor_si64(half %x) nounwind { ; RV32IZFH-NEXT: addi sp, sp, -16 ; RV32IZFH-NEXT: sw ra, 12(sp) # 4-byte Folded Spill ; RV32IZFH-NEXT: sw s0, 8(sp) # 4-byte Folded Spill -; RV32IZFH-NEXT: sw s1, 4(sp) # 4-byte Folded Spill -; RV32IZFH-NEXT: fsw fs0, 0(sp) # 4-byte Folded Spill +; RV32IZFH-NEXT: fsw fs0, 4(sp) # 4-byte Folded Spill ; RV32IZFH-NEXT: fcvt.s.h fs0, fa0 ; RV32IZFH-NEXT: lui a0, 913408 ; RV32IZFH-NEXT: fmv.w.x fa5, a0 ; RV32IZFH-NEXT: fle.s s0, fa5, fs0 -; RV32IZFH-NEXT: neg s1, s0 ; RV32IZFH-NEXT: fmv.s fa0, fs0 ; RV32IZFH-NEXT: call __fixsfdi -; RV32IZFH-NEXT: lui a2, %hi(.LCPI1_1) -; RV32IZFH-NEXT: flw fa5, %lo(.LCPI1_1)(a2) -; RV32IZFH-NEXT: and a0, s1, a0 -; RV32IZFH-NEXT: flt.s a3, fa5, fs0 -; RV32IZFH-NEXT: neg a2, a3 -; RV32IZFH-NEXT: or a0, a2, a0 -; RV32IZFH-NEXT: feq.s a2, fs0, fs0 -; RV32IZFH-NEXT: neg a2, a2 -; RV32IZFH-NEXT: lui a5, 524288 ; RV32IZFH-NEXT: lui a4, 524288 +; RV32IZFH-NEXT: lui a2, 524288 ; RV32IZFH-NEXT: beqz s0, .LBB1_4 ; RV32IZFH-NEXT: # %bb.3: -; RV32IZFH-NEXT: mv a4, a1 +; RV32IZFH-NEXT: mv a2, a1 ; RV32IZFH-NEXT: .LBB1_4: +; RV32IZFH-NEXT: lui a1, %hi(.LCPI1_1) +; RV32IZFH-NEXT: flw fa5, %lo(.LCPI1_1)(a1) +; RV32IZFH-NEXT: flt.s a3, fa5, fs0 +; RV32IZFH-NEXT: beqz a3, .LBB1_6 +; RV32IZFH-NEXT: # %bb.5: +; RV32IZFH-NEXT: addi a2, a4, -1 +; RV32IZFH-NEXT: .LBB1_6: +; RV32IZFH-NEXT: feq.s a1, fs0, fs0 +; RV32IZFH-NEXT: neg a4, a1 +; RV32IZFH-NEXT: and a1, a4, a2 +; RV32IZFH-NEXT: neg a2, s0 ; RV32IZFH-NEXT: and a0, a2, a0 +; RV32IZFH-NEXT: neg a2, a3 +; RV32IZFH-NEXT: or a0, a2, a0 +; RV32IZFH-NEXT: and a0, a4, a0 ; RV32IZFH-NEXT: lw ra, 12(sp) # 4-byte Folded Reload ; RV32IZFH-NEXT: lw s0, 8(sp) # 4-byte Folded Reload -; RV32IZFH-NEXT: lw s1, 4(sp) # 4-byte Folded Reload -; RV32IZFH-NEXT: flw fs0, 0(sp) # 4-byte Folded Reload +; RV32IZFH-NEXT: flw fs0, 4(sp) # 4-byte Folded Reload ; RV32IZFH-NEXT: addi sp, sp, 16 -; RV32IZFH-NEXT: beqz a3, .LBB1_6 -; RV32IZFH-NEXT: # %bb.5: -; RV32IZFH-NEXT: addi a4, a5, -1 -; RV32IZFH-NEXT: .LBB1_6: -; RV32IZFH-NEXT: and a1, a2, a4 ; RV32IZFH-NEXT: ret ; ; RV64IZFH-LABEL: test_floor_si64: @@ -179,16 +177,16 @@ define i64 @test_floor_si64(half %x) nounwind { ; RV32IZHINX-NEXT: lui a2, %hi(.LCPI1_1) ; RV32IZHINX-NEXT: lw a2, %lo(.LCPI1_1)(a2) ; RV32IZHINX-NEXT: and a0, s2, a0 -; RV32IZHINX-NEXT: flt.s a3, a2, s0 -; RV32IZHINX-NEXT: neg a2, a3 +; RV32IZHINX-NEXT: flt.s a4, a2, s0 +; RV32IZHINX-NEXT: neg a2, a4 ; RV32IZHINX-NEXT: or a0, a2, a0 ; RV32IZHINX-NEXT: feq.s a2, s0, s0 ; RV32IZHINX-NEXT: neg a2, a2 ; RV32IZHINX-NEXT: lui a5, 524288 -; RV32IZHINX-NEXT: lui a4, 524288 +; RV32IZHINX-NEXT: lui a3, 524288 ; RV32IZHINX-NEXT: beqz s1, .LBB1_4 ; RV32IZHINX-NEXT: # %bb.3: -; RV32IZHINX-NEXT: mv a4, a1 +; RV32IZHINX-NEXT: mv a3, a1 ; RV32IZHINX-NEXT: .LBB1_4: ; RV32IZHINX-NEXT: and a0, a2, a0 ; RV32IZHINX-NEXT: lw ra, 12(sp) # 4-byte Folded Reload @@ -196,11 +194,11 @@ define i64 @test_floor_si64(half %x) nounwind { ; RV32IZHINX-NEXT: lw s1, 4(sp) # 4-byte Folded Reload ; RV32IZHINX-NEXT: lw s2, 0(sp) # 4-byte Folded Reload ; RV32IZHINX-NEXT: addi sp, sp, 16 -; RV32IZHINX-NEXT: beqz a3, .LBB1_6 +; RV32IZHINX-NEXT: beqz a4, .LBB1_6 ; RV32IZHINX-NEXT: # %bb.5: -; RV32IZHINX-NEXT: addi a4, a5, -1 +; RV32IZHINX-NEXT: addi a3, a5, -1 ; RV32IZHINX-NEXT: .LBB1_6: -; RV32IZHINX-NEXT: and a1, a2, a4 +; RV32IZHINX-NEXT: and a1, a2, a3 ; RV32IZHINX-NEXT: ret ; ; RV64IZHINX-LABEL: test_floor_si64: @@ -238,41 +236,39 @@ define i64 @test_floor_si64(half %x) nounwind { ; RV32IZFHMIN-NEXT: addi sp, sp, -16 ; RV32IZFHMIN-NEXT: sw ra, 12(sp) # 4-byte Folded Spill ; RV32IZFHMIN-NEXT: sw s0, 8(sp) # 4-byte Folded Spill -; RV32IZFHMIN-NEXT: sw s1, 4(sp) # 4-byte Folded Spill -; RV32IZFHMIN-NEXT: fsw fs0, 0(sp) # 4-byte Folded Spill +; RV32IZFHMIN-NEXT: fsw fs0, 4(sp) # 4-byte Folded Spill ; RV32IZFHMIN-NEXT: fcvt.h.s fa5, fa5 ; RV32IZFHMIN-NEXT: fcvt.s.h fs0, fa5 ; RV32IZFHMIN-NEXT: lui a0, 913408 ; RV32IZFHMIN-NEXT: fmv.w.x fa5, a0 ; RV32IZFHMIN-NEXT: fle.s s0, fa5, fs0 -; RV32IZFHMIN-NEXT: neg s1, s0 ; RV32IZFHMIN-NEXT: fmv.s fa0, fs0 ; RV32IZFHMIN-NEXT: call __fixsfdi -; RV32IZFHMIN-NEXT: lui a2, %hi(.LCPI1_0) -; RV32IZFHMIN-NEXT: flw fa5, %lo(.LCPI1_0)(a2) -; RV32IZFHMIN-NEXT: and a0, s1, a0 -; RV32IZFHMIN-NEXT: flt.s a3, fa5, fs0 -; RV32IZFHMIN-NEXT: neg a2, a3 -; RV32IZFHMIN-NEXT: or a0, a2, a0 -; RV32IZFHMIN-NEXT: feq.s a2, fs0, fs0 -; RV32IZFHMIN-NEXT: neg a2, a2 -; RV32IZFHMIN-NEXT: lui a5, 524288 ; RV32IZFHMIN-NEXT: lui a4, 524288 +; RV32IZFHMIN-NEXT: lui a2, 524288 ; RV32IZFHMIN-NEXT: beqz s0, .LBB1_4 ; RV32IZFHMIN-NEXT: # %bb.3: -; RV32IZFHMIN-NEXT: mv a4, a1 +; RV32IZFHMIN-NEXT: mv a2, a1 ; RV32IZFHMIN-NEXT: .LBB1_4: +; RV32IZFHMIN-NEXT: lui a1, %hi(.LCPI1_0) +; RV32IZFHMIN-NEXT: flw fa5, %lo(.LCPI1_0)(a1) +; RV32IZFHMIN-NEXT: flt.s a3, fa5, fs0 +; RV32IZFHMIN-NEXT: beqz a3, .LBB1_6 +; RV32IZFHMIN-NEXT: # %bb.5: +; RV32IZFHMIN-NEXT: addi a2, a4, -1 +; RV32IZFHMIN-NEXT: .LBB1_6: +; RV32IZFHMIN-NEXT: feq.s a1, fs0, fs0 +; RV32IZFHMIN-NEXT: neg a4, a1 +; RV32IZFHMIN-NEXT: and a1, a4, a2 +; RV32IZFHMIN-NEXT: neg a2, s0 ; RV32IZFHMIN-NEXT: and a0, a2, a0 +; RV32IZFHMIN-NEXT: neg a2, a3 +; RV32IZFHMIN-NEXT: or a0, a2, a0 +; RV32IZFHMIN-NEXT: and a0, a4, a0 ; RV32IZFHMIN-NEXT: lw ra, 12(sp) # 4-byte Folded Reload ; RV32IZFHMIN-NEXT: lw s0, 8(sp) # 4-byte Folded Reload -; RV32IZFHMIN-NEXT: lw s1, 4(sp) # 4-byte Folded Reload -; RV32IZFHMIN-NEXT: flw fs0, 0(sp) # 4-byte Folded Reload +; RV32IZFHMIN-NEXT: flw fs0, 4(sp) # 4-byte Folded Reload ; RV32IZFHMIN-NEXT: addi sp, sp, 16 -; RV32IZFHMIN-NEXT: beqz a3, .LBB1_6 -; RV32IZFHMIN-NEXT: # %bb.5: -; RV32IZFHMIN-NEXT: addi a4, a5, -1 -; RV32IZFHMIN-NEXT: .LBB1_6: -; RV32IZFHMIN-NEXT: and a1, a2, a4 ; RV32IZFHMIN-NEXT: ret ; ; RV64IZFHMIN-LABEL: test_floor_si64: @@ -324,16 +320,16 @@ define i64 @test_floor_si64(half %x) nounwind { ; RV32IZHINXMIN-NEXT: lui a2, %hi(.LCPI1_0) ; RV32IZHINXMIN-NEXT: lw a2, %lo(.LCPI1_0)(a2) ; RV32IZHINXMIN-NEXT: and a0, s2, a0 -; RV32IZHINXMIN-NEXT: flt.s a3, a2, s0 -; RV32IZHINXMIN-NEXT: neg a2, a3 +; RV32IZHINXMIN-NEXT: flt.s a4, a2, s0 +; RV32IZHINXMIN-NEXT: neg a2, a4 ; RV32IZHINXMIN-NEXT: or a0, a2, a0 ; RV32IZHINXMIN-NEXT: feq.s a2, s0, s0 ; RV32IZHINXMIN-NEXT: neg a2, a2 ; RV32IZHINXMIN-NEXT: lui a5, 524288 -; RV32IZHINXMIN-NEXT: lui a4, 524288 +; RV32IZHINXMIN-NEXT: lui a3, 524288 ; RV32IZHINXMIN-NEXT: beqz s1, .LBB1_4 ; RV32IZHINXMIN-NEXT: # %bb.3: -; RV32IZHINXMIN-NEXT: mv a4, a1 +; RV32IZHINXMIN-NEXT: mv a3, a1 ; RV32IZHINXMIN-NEXT: .LBB1_4: ; RV32IZHINXMIN-NEXT: and a0, a2, a0 ; RV32IZHINXMIN-NEXT: lw ra, 12(sp) # 4-byte Folded Reload @@ -341,11 +337,11 @@ define i64 @test_floor_si64(half %x) nounwind { ; RV32IZHINXMIN-NEXT: lw s1, 4(sp) # 4-byte Folded Reload ; RV32IZHINXMIN-NEXT: lw s2, 0(sp) # 4-byte Folded Reload ; RV32IZHINXMIN-NEXT: addi sp, sp, 16 -; RV32IZHINXMIN-NEXT: beqz a3, .LBB1_6 +; RV32IZHINXMIN-NEXT: beqz a4, .LBB1_6 ; RV32IZHINXMIN-NEXT: # %bb.5: -; RV32IZHINXMIN-NEXT: addi a4, a5, -1 +; RV32IZHINXMIN-NEXT: addi a3, a5, -1 ; RV32IZHINXMIN-NEXT: .LBB1_6: -; RV32IZHINXMIN-NEXT: and a1, a2, a4 +; RV32IZHINXMIN-NEXT: and a1, a2, a3 ; RV32IZHINXMIN-NEXT: ret ; ; RV64IZHINXMIN-LABEL: test_floor_si64: @@ -824,40 +820,38 @@ define i64 @test_ceil_si64(half %x) nounwind { ; RV32IZFH-NEXT: addi sp, sp, -16 ; RV32IZFH-NEXT: sw ra, 12(sp) # 4-byte Folded Spill ; RV32IZFH-NEXT: sw s0, 8(sp) # 4-byte Folded Spill -; RV32IZFH-NEXT: sw s1, 4(sp) # 4-byte Folded Spill -; RV32IZFH-NEXT: fsw fs0, 0(sp) # 4-byte Folded Spill +; RV32IZFH-NEXT: fsw fs0, 4(sp) # 4-byte Folded Spill ; RV32IZFH-NEXT: fcvt.s.h fs0, fa0 ; RV32IZFH-NEXT: lui a0, 913408 ; RV32IZFH-NEXT: fmv.w.x fa5, a0 ; RV32IZFH-NEXT: fle.s s0, fa5, fs0 -; RV32IZFH-NEXT: neg s1, s0 ; RV32IZFH-NEXT: fmv.s fa0, fs0 ; RV32IZFH-NEXT: call __fixsfdi -; RV32IZFH-NEXT: lui a2, %hi(.LCPI5_1) -; RV32IZFH-NEXT: flw fa5, %lo(.LCPI5_1)(a2) -; RV32IZFH-NEXT: and a0, s1, a0 -; RV32IZFH-NEXT: flt.s a3, fa5, fs0 -; RV32IZFH-NEXT: neg a2, a3 -; RV32IZFH-NEXT: or a0, a2, a0 -; RV32IZFH-NEXT: feq.s a2, fs0, fs0 -; RV32IZFH-NEXT: neg a2, a2 -; RV32IZFH-NEXT: lui a5, 524288 ; RV32IZFH-NEXT: lui a4, 524288 +; RV32IZFH-NEXT: lui a2, 524288 ; RV32IZFH-NEXT: beqz s0, .LBB5_4 ; RV32IZFH-NEXT: # %bb.3: -; RV32IZFH-NEXT: mv a4, a1 +; RV32IZFH-NEXT: mv a2, a1 ; RV32IZFH-NEXT: .LBB5_4: +; RV32IZFH-NEXT: lui a1, %hi(.LCPI5_1) +; RV32IZFH-NEXT: flw fa5, %lo(.LCPI5_1)(a1) +; RV32IZFH-NEXT: flt.s a3, fa5, fs0 +; RV32IZFH-NEXT: beqz a3, .LBB5_6 +; RV32IZFH-NEXT: # %bb.5: +; RV32IZFH-NEXT: addi a2, a4, -1 +; RV32IZFH-NEXT: .LBB5_6: +; RV32IZFH-NEXT: feq.s a1, fs0, fs0 +; RV32IZFH-NEXT: neg a4, a1 +; RV32IZFH-NEXT: and a1, a4, a2 +; RV32IZFH-NEXT: neg a2, s0 ; RV32IZFH-NEXT: and a0, a2, a0 +; RV32IZFH-NEXT: neg a2, a3 +; RV32IZFH-NEXT: or a0, a2, a0 +; RV32IZFH-NEXT: and a0, a4, a0 ; RV32IZFH-NEXT: lw ra, 12(sp) # 4-byte Folded Reload ; RV32IZFH-NEXT: lw s0, 8(sp) # 4-byte Folded Reload -; RV32IZFH-NEXT: lw s1, 4(sp) # 4-byte Folded Reload -; RV32IZFH-NEXT: flw fs0, 0(sp) # 4-byte Folded Reload +; RV32IZFH-NEXT: flw fs0, 4(sp) # 4-byte Folded Reload ; RV32IZFH-NEXT: addi sp, sp, 16 -; RV32IZFH-NEXT: beqz a3, .LBB5_6 -; RV32IZFH-NEXT: # %bb.5: -; RV32IZFH-NEXT: addi a4, a5, -1 -; RV32IZFH-NEXT: .LBB5_6: -; RV32IZFH-NEXT: and a1, a2, a4 ; RV32IZFH-NEXT: ret ; ; RV64IZFH-LABEL: test_ceil_si64: @@ -895,16 +889,16 @@ define i64 @test_ceil_si64(half %x) nounwind { ; RV32IZHINX-NEXT: lui a2, %hi(.LCPI5_1) ; RV32IZHINX-NEXT: lw a2, %lo(.LCPI5_1)(a2) ; RV32IZHINX-NEXT: and a0, s2, a0 -; RV32IZHINX-NEXT: flt.s a3, a2, s0 -; RV32IZHINX-NEXT: neg a2, a3 +; RV32IZHINX-NEXT: flt.s a4, a2, s0 +; RV32IZHINX-NEXT: neg a2, a4 ; RV32IZHINX-NEXT: or a0, a2, a0 ; RV32IZHINX-NEXT: feq.s a2, s0, s0 ; RV32IZHINX-NEXT: neg a2, a2 ; RV32IZHINX-NEXT: lui a5, 524288 -; RV32IZHINX-NEXT: lui a4, 524288 +; RV32IZHINX-NEXT: lui a3, 524288 ; RV32IZHINX-NEXT: beqz s1, .LBB5_4 ; RV32IZHINX-NEXT: # %bb.3: -; RV32IZHINX-NEXT: mv a4, a1 +; RV32IZHINX-NEXT: mv a3, a1 ; RV32IZHINX-NEXT: .LBB5_4: ; RV32IZHINX-NEXT: and a0, a2, a0 ; RV32IZHINX-NEXT: lw ra, 12(sp) # 4-byte Folded Reload @@ -912,11 +906,11 @@ define i64 @test_ceil_si64(half %x) nounwind { ; RV32IZHINX-NEXT: lw s1, 4(sp) # 4-byte Folded Reload ; RV32IZHINX-NEXT: lw s2, 0(sp) # 4-byte Folded Reload ; RV32IZHINX-NEXT: addi sp, sp, 16 -; RV32IZHINX-NEXT: beqz a3, .LBB5_6 +; RV32IZHINX-NEXT: beqz a4, .LBB5_6 ; RV32IZHINX-NEXT: # %bb.5: -; RV32IZHINX-NEXT: addi a4, a5, -1 +; RV32IZHINX-NEXT: addi a3, a5, -1 ; RV32IZHINX-NEXT: .LBB5_6: -; RV32IZHINX-NEXT: and a1, a2, a4 +; RV32IZHINX-NEXT: and a1, a2, a3 ; RV32IZHINX-NEXT: ret ; ; RV64IZHINX-LABEL: test_ceil_si64: @@ -954,41 +948,39 @@ define i64 @test_ceil_si64(half %x) nounwind { ; RV32IZFHMIN-NEXT: addi sp, sp, -16 ; RV32IZFHMIN-NEXT: sw ra, 12(sp) # 4-byte Folded Spill ; RV32IZFHMIN-NEXT: sw s0, 8(sp) # 4-byte Folded Spill -; RV32IZFHMIN-NEXT: sw s1, 4(sp) # 4-byte Folded Spill -; RV32IZFHMIN-NEXT: fsw fs0, 0(sp) # 4-byte Folded Spill +; RV32IZFHMIN-NEXT: fsw fs0, 4(sp) # 4-byte Folded Spill ; RV32IZFHMIN-NEXT: fcvt.h.s fa5, fa5 ; RV32IZFHMIN-NEXT: fcvt.s.h fs0, fa5 ; RV32IZFHMIN-NEXT: lui a0, 913408 ; RV32IZFHMIN-NEXT: fmv.w.x fa5, a0 ; RV32IZFHMIN-NEXT: fle.s s0, fa5, fs0 -; RV32IZFHMIN-NEXT: neg s1, s0 ; RV32IZFHMIN-NEXT: fmv.s fa0, fs0 ; RV32IZFHMIN-NEXT: call __fixsfdi -; RV32IZFHMIN-NEXT: lui a2, %hi(.LCPI5_0) -; RV32IZFHMIN-NEXT: flw fa5, %lo(.LCPI5_0)(a2) -; RV32IZFHMIN-NEXT: and a0, s1, a0 -; RV32IZFHMIN-NEXT: flt.s a3, fa5, fs0 -; RV32IZFHMIN-NEXT: neg a2, a3 -; RV32IZFHMIN-NEXT: or a0, a2, a0 -; RV32IZFHMIN-NEXT: feq.s a2, fs0, fs0 -; RV32IZFHMIN-NEXT: neg a2, a2 -; RV32IZFHMIN-NEXT: lui a5, 524288 ; RV32IZFHMIN-NEXT: lui a4, 524288 +; RV32IZFHMIN-NEXT: lui a2, 524288 ; RV32IZFHMIN-NEXT: beqz s0, .LBB5_4 ; RV32IZFHMIN-NEXT: # %bb.3: -; RV32IZFHMIN-NEXT: mv a4, a1 +; RV32IZFHMIN-NEXT: mv a2, a1 ; RV32IZFHMIN-NEXT: .LBB5_4: +; RV32IZFHMIN-NEXT: lui a1, %hi(.LCPI5_0) +; RV32IZFHMIN-NEXT: flw fa5, %lo(.LCPI5_0)(a1) +; RV32IZFHMIN-NEXT: flt.s a3, fa5, fs0 +; RV32IZFHMIN-NEXT: beqz a3, .LBB5_6 +; RV32IZFHMIN-NEXT: # %bb.5: +; RV32IZFHMIN-NEXT: addi a2, a4, -1 +; RV32IZFHMIN-NEXT: .LBB5_6: +; RV32IZFHMIN-NEXT: feq.s a1, fs0, fs0 +; RV32IZFHMIN-NEXT: neg a4, a1 +; RV32IZFHMIN-NEXT: and a1, a4, a2 +; RV32IZFHMIN-NEXT: neg a2, s0 ; RV32IZFHMIN-NEXT: and a0, a2, a0 +; RV32IZFHMIN-NEXT: neg a2, a3 +; RV32IZFHMIN-NEXT: or a0, a2, a0 +; RV32IZFHMIN-NEXT: and a0, a4, a0 ; RV32IZFHMIN-NEXT: lw ra, 12(sp) # 4-byte Folded Reload ; RV32IZFHMIN-NEXT: lw s0, 8(sp) # 4-byte Folded Reload -; RV32IZFHMIN-NEXT: lw s1, 4(sp) # 4-byte Folded Reload -; RV32IZFHMIN-NEXT: flw fs0, 0(sp) # 4-byte Folded Reload +; RV32IZFHMIN-NEXT: flw fs0, 4(sp) # 4-byte Folded Reload ; RV32IZFHMIN-NEXT: addi sp, sp, 16 -; RV32IZFHMIN-NEXT: beqz a3, .LBB5_6 -; RV32IZFHMIN-NEXT: # %bb.5: -; RV32IZFHMIN-NEXT: addi a4, a5, -1 -; RV32IZFHMIN-NEXT: .LBB5_6: -; RV32IZFHMIN-NEXT: and a1, a2, a4 ; RV32IZFHMIN-NEXT: ret ; ; RV64IZFHMIN-LABEL: test_ceil_si64: @@ -1040,16 +1032,16 @@ define i64 @test_ceil_si64(half %x) nounwind { ; RV32IZHINXMIN-NEXT: lui a2, %hi(.LCPI5_0) ; RV32IZHINXMIN-NEXT: lw a2, %lo(.LCPI5_0)(a2) ; RV32IZHINXMIN-NEXT: and a0, s2, a0 -; RV32IZHINXMIN-NEXT: flt.s a3, a2, s0 -; RV32IZHINXMIN-NEXT: neg a2, a3 +; RV32IZHINXMIN-NEXT: flt.s a4, a2, s0 +; RV32IZHINXMIN-NEXT: neg a2, a4 ; RV32IZHINXMIN-NEXT: or a0, a2, a0 ; RV32IZHINXMIN-NEXT: feq.s a2, s0, s0 ; RV32IZHINXMIN-NEXT: neg a2, a2 ; RV32IZHINXMIN-NEXT: lui a5, 524288 -; RV32IZHINXMIN-NEXT: lui a4, 524288 +; RV32IZHINXMIN-NEXT: lui a3, 524288 ; RV32IZHINXMIN-NEXT: beqz s1, .LBB5_4 ; RV32IZHINXMIN-NEXT: # %bb.3: -; RV32IZHINXMIN-NEXT: mv a4, a1 +; RV32IZHINXMIN-NEXT: mv a3, a1 ; RV32IZHINXMIN-NEXT: .LBB5_4: ; RV32IZHINXMIN-NEXT: and a0, a2, a0 ; RV32IZHINXMIN-NEXT: lw ra, 12(sp) # 4-byte Folded Reload @@ -1057,11 +1049,11 @@ define i64 @test_ceil_si64(half %x) nounwind { ; RV32IZHINXMIN-NEXT: lw s1, 4(sp) # 4-byte Folded Reload ; RV32IZHINXMIN-NEXT: lw s2, 0(sp) # 4-byte Folded Reload ; RV32IZHINXMIN-NEXT: addi sp, sp, 16 -; RV32IZHINXMIN-NEXT: beqz a3, .LBB5_6 +; RV32IZHINXMIN-NEXT: beqz a4, .LBB5_6 ; RV32IZHINXMIN-NEXT: # %bb.5: -; RV32IZHINXMIN-NEXT: addi a4, a5, -1 +; RV32IZHINXMIN-NEXT: addi a3, a5, -1 ; RV32IZHINXMIN-NEXT: .LBB5_6: -; RV32IZHINXMIN-NEXT: and a1, a2, a4 +; RV32IZHINXMIN-NEXT: and a1, a2, a3 ; RV32IZHINXMIN-NEXT: ret ; ; RV64IZHINXMIN-LABEL: test_ceil_si64: @@ -1540,40 +1532,38 @@ define i64 @test_trunc_si64(half %x) nounwind { ; RV32IZFH-NEXT: addi sp, sp, -16 ; RV32IZFH-NEXT: sw ra, 12(sp) # 4-byte Folded Spill ; RV32IZFH-NEXT: sw s0, 8(sp) # 4-byte Folded Spill -; RV32IZFH-NEXT: sw s1, 4(sp) # 4-byte Folded Spill -; RV32IZFH-NEXT: fsw fs0, 0(sp) # 4-byte Folded Spill +; RV32IZFH-NEXT: fsw fs0, 4(sp) # 4-byte Folded Spill ; RV32IZFH-NEXT: fcvt.s.h fs0, fa0 ; RV32IZFH-NEXT: lui a0, 913408 ; RV32IZFH-NEXT: fmv.w.x fa5, a0 ; RV32IZFH-NEXT: fle.s s0, fa5, fs0 -; RV32IZFH-NEXT: neg s1, s0 ; RV32IZFH-NEXT: fmv.s fa0, fs0 ; RV32IZFH-NEXT: call __fixsfdi -; RV32IZFH-NEXT: lui a2, %hi(.LCPI9_1) -; RV32IZFH-NEXT: flw fa5, %lo(.LCPI9_1)(a2) -; RV32IZFH-NEXT: and a0, s1, a0 -; RV32IZFH-NEXT: flt.s a3, fa5, fs0 -; RV32IZFH-NEXT: neg a2, a3 -; RV32IZFH-NEXT: or a0, a2, a0 -; RV32IZFH-NEXT: feq.s a2, fs0, fs0 -; RV32IZFH-NEXT: neg a2, a2 -; RV32IZFH-NEXT: lui a5, 524288 ; RV32IZFH-NEXT: lui a4, 524288 +; RV32IZFH-NEXT: lui a2, 524288 ; RV32IZFH-NEXT: beqz s0, .LBB9_4 ; RV32IZFH-NEXT: # %bb.3: -; RV32IZFH-NEXT: mv a4, a1 +; RV32IZFH-NEXT: mv a2, a1 ; RV32IZFH-NEXT: .LBB9_4: +; RV32IZFH-NEXT: lui a1, %hi(.LCPI9_1) +; RV32IZFH-NEXT: flw fa5, %lo(.LCPI9_1)(a1) +; RV32IZFH-NEXT: flt.s a3, fa5, fs0 +; RV32IZFH-NEXT: beqz a3, .LBB9_6 +; RV32IZFH-NEXT: # %bb.5: +; RV32IZFH-NEXT: addi a2, a4, -1 +; RV32IZFH-NEXT: .LBB9_6: +; RV32IZFH-NEXT: feq.s a1, fs0, fs0 +; RV32IZFH-NEXT: neg a4, a1 +; RV32IZFH-NEXT: and a1, a4, a2 +; RV32IZFH-NEXT: neg a2, s0 ; RV32IZFH-NEXT: and a0, a2, a0 +; RV32IZFH-NEXT: neg a2, a3 +; RV32IZFH-NEXT: or a0, a2, a0 +; RV32IZFH-NEXT: and a0, a4, a0 ; RV32IZFH-NEXT: lw ra, 12(sp) # 4-byte Folded Reload ; RV32IZFH-NEXT: lw s0, 8(sp) # 4-byte Folded Reload -; RV32IZFH-NEXT: lw s1, 4(sp) # 4-byte Folded Reload -; RV32IZFH-NEXT: flw fs0, 0(sp) # 4-byte Folded Reload +; RV32IZFH-NEXT: flw fs0, 4(sp) # 4-byte Folded Reload ; RV32IZFH-NEXT: addi sp, sp, 16 -; RV32IZFH-NEXT: beqz a3, .LBB9_6 -; RV32IZFH-NEXT: # %bb.5: -; RV32IZFH-NEXT: addi a4, a5, -1 -; RV32IZFH-NEXT: .LBB9_6: -; RV32IZFH-NEXT: and a1, a2, a4 ; RV32IZFH-NEXT: ret ; ; RV64IZFH-LABEL: test_trunc_si64: @@ -1611,16 +1601,16 @@ define i64 @test_trunc_si64(half %x) nounwind { ; RV32IZHINX-NEXT: lui a2, %hi(.LCPI9_1) ; RV32IZHINX-NEXT: lw a2, %lo(.LCPI9_1)(a2) ; RV32IZHINX-NEXT: and a0, s2, a0 -; RV32IZHINX-NEXT: flt.s a3, a2, s0 -; RV32IZHINX-NEXT: neg a2, a3 +; RV32IZHINX-NEXT: flt.s a4, a2, s0 +; RV32IZHINX-NEXT: neg a2, a4 ; RV32IZHINX-NEXT: or a0, a2, a0 ; RV32IZHINX-NEXT: feq.s a2, s0, s0 ; RV32IZHINX-NEXT: neg a2, a2 ; RV32IZHINX-NEXT: lui a5, 524288 -; RV32IZHINX-NEXT: lui a4, 524288 +; RV32IZHINX-NEXT: lui a3, 524288 ; RV32IZHINX-NEXT: beqz s1, .LBB9_4 ; RV32IZHINX-NEXT: # %bb.3: -; RV32IZHINX-NEXT: mv a4, a1 +; RV32IZHINX-NEXT: mv a3, a1 ; RV32IZHINX-NEXT: .LBB9_4: ; RV32IZHINX-NEXT: and a0, a2, a0 ; RV32IZHINX-NEXT: lw ra, 12(sp) # 4-byte Folded Reload @@ -1628,11 +1618,11 @@ define i64 @test_trunc_si64(half %x) nounwind { ; RV32IZHINX-NEXT: lw s1, 4(sp) # 4-byte Folded Reload ; RV32IZHINX-NEXT: lw s2, 0(sp) # 4-byte Folded Reload ; RV32IZHINX-NEXT: addi sp, sp, 16 -; RV32IZHINX-NEXT: beqz a3, .LBB9_6 +; RV32IZHINX-NEXT: beqz a4, .LBB9_6 ; RV32IZHINX-NEXT: # %bb.5: -; RV32IZHINX-NEXT: addi a4, a5, -1 +; RV32IZHINX-NEXT: addi a3, a5, -1 ; RV32IZHINX-NEXT: .LBB9_6: -; RV32IZHINX-NEXT: and a1, a2, a4 +; RV32IZHINX-NEXT: and a1, a2, a3 ; RV32IZHINX-NEXT: ret ; ; RV64IZHINX-LABEL: test_trunc_si64: @@ -1670,41 +1660,39 @@ define i64 @test_trunc_si64(half %x) nounwind { ; RV32IZFHMIN-NEXT: addi sp, sp, -16 ; RV32IZFHMIN-NEXT: sw ra, 12(sp) # 4-byte Folded Spill ; RV32IZFHMIN-NEXT: sw s0, 8(sp) # 4-byte Folded Spill -; RV32IZFHMIN-NEXT: sw s1, 4(sp) # 4-byte Folded Spill -; RV32IZFHMIN-NEXT: fsw fs0, 0(sp) # 4-byte Folded Spill +; RV32IZFHMIN-NEXT: fsw fs0, 4(sp) # 4-byte Folded Spill ; RV32IZFHMIN-NEXT: fcvt.h.s fa5, fa5 ; RV32IZFHMIN-NEXT: fcvt.s.h fs0, fa5 ; RV32IZFHMIN-NEXT: lui a0, 913408 ; RV32IZFHMIN-NEXT: fmv.w.x fa5, a0 ; RV32IZFHMIN-NEXT: fle.s s0, fa5, fs0 -; RV32IZFHMIN-NEXT: neg s1, s0 ; RV32IZFHMIN-NEXT: fmv.s fa0, fs0 ; RV32IZFHMIN-NEXT: call __fixsfdi -; RV32IZFHMIN-NEXT: lui a2, %hi(.LCPI9_0) -; RV32IZFHMIN-NEXT: flw fa5, %lo(.LCPI9_0)(a2) -; RV32IZFHMIN-NEXT: and a0, s1, a0 -; RV32IZFHMIN-NEXT: flt.s a3, fa5, fs0 -; RV32IZFHMIN-NEXT: neg a2, a3 -; RV32IZFHMIN-NEXT: or a0, a2, a0 -; RV32IZFHMIN-NEXT: feq.s a2, fs0, fs0 -; RV32IZFHMIN-NEXT: neg a2, a2 -; RV32IZFHMIN-NEXT: lui a5, 524288 ; RV32IZFHMIN-NEXT: lui a4, 524288 +; RV32IZFHMIN-NEXT: lui a2, 524288 ; RV32IZFHMIN-NEXT: beqz s0, .LBB9_4 ; RV32IZFHMIN-NEXT: # %bb.3: -; RV32IZFHMIN-NEXT: mv a4, a1 +; RV32IZFHMIN-NEXT: mv a2, a1 ; RV32IZFHMIN-NEXT: .LBB9_4: +; RV32IZFHMIN-NEXT: lui a1, %hi(.LCPI9_0) +; RV32IZFHMIN-NEXT: flw fa5, %lo(.LCPI9_0)(a1) +; RV32IZFHMIN-NEXT: flt.s a3, fa5, fs0 +; RV32IZFHMIN-NEXT: beqz a3, .LBB9_6 +; RV32IZFHMIN-NEXT: # %bb.5: +; RV32IZFHMIN-NEXT: addi a2, a4, -1 +; RV32IZFHMIN-NEXT: .LBB9_6: +; RV32IZFHMIN-NEXT: feq.s a1, fs0, fs0 +; RV32IZFHMIN-NEXT: neg a4, a1 +; RV32IZFHMIN-NEXT: and a1, a4, a2 +; RV32IZFHMIN-NEXT: neg a2, s0 ; RV32IZFHMIN-NEXT: and a0, a2, a0 +; RV32IZFHMIN-NEXT: neg a2, a3 +; RV32IZFHMIN-NEXT: or a0, a2, a0 +; RV32IZFHMIN-NEXT: and a0, a4, a0 ; RV32IZFHMIN-NEXT: lw ra, 12(sp) # 4-byte Folded Reload ; RV32IZFHMIN-NEXT: lw s0, 8(sp) # 4-byte Folded Reload -; RV32IZFHMIN-NEXT: lw s1, 4(sp) # 4-byte Folded Reload -; RV32IZFHMIN-NEXT: flw fs0, 0(sp) # 4-byte Folded Reload +; RV32IZFHMIN-NEXT: flw fs0, 4(sp) # 4-byte Folded Reload ; RV32IZFHMIN-NEXT: addi sp, sp, 16 -; RV32IZFHMIN-NEXT: beqz a3, .LBB9_6 -; RV32IZFHMIN-NEXT: # %bb.5: -; RV32IZFHMIN-NEXT: addi a4, a5, -1 -; RV32IZFHMIN-NEXT: .LBB9_6: -; RV32IZFHMIN-NEXT: and a1, a2, a4 ; RV32IZFHMIN-NEXT: ret ; ; RV64IZFHMIN-LABEL: test_trunc_si64: @@ -1756,16 +1744,16 @@ define i64 @test_trunc_si64(half %x) nounwind { ; RV32IZHINXMIN-NEXT: lui a2, %hi(.LCPI9_0) ; RV32IZHINXMIN-NEXT: lw a2, %lo(.LCPI9_0)(a2) ; RV32IZHINXMIN-NEXT: and a0, s2, a0 -; RV32IZHINXMIN-NEXT: flt.s a3, a2, s0 -; RV32IZHINXMIN-NEXT: neg a2, a3 +; RV32IZHINXMIN-NEXT: flt.s a4, a2, s0 +; RV32IZHINXMIN-NEXT: neg a2, a4 ; RV32IZHINXMIN-NEXT: or a0, a2, a0 ; RV32IZHINXMIN-NEXT: feq.s a2, s0, s0 ; RV32IZHINXMIN-NEXT: neg a2, a2 ; RV32IZHINXMIN-NEXT: lui a5, 524288 -; RV32IZHINXMIN-NEXT: lui a4, 524288 +; RV32IZHINXMIN-NEXT: lui a3, 524288 ; RV32IZHINXMIN-NEXT: beqz s1, .LBB9_4 ; RV32IZHINXMIN-NEXT: # %bb.3: -; RV32IZHINXMIN-NEXT: mv a4, a1 +; RV32IZHINXMIN-NEXT: mv a3, a1 ; RV32IZHINXMIN-NEXT: .LBB9_4: ; RV32IZHINXMIN-NEXT: and a0, a2, a0 ; RV32IZHINXMIN-NEXT: lw ra, 12(sp) # 4-byte Folded Reload @@ -1773,11 +1761,11 @@ define i64 @test_trunc_si64(half %x) nounwind { ; RV32IZHINXMIN-NEXT: lw s1, 4(sp) # 4-byte Folded Reload ; RV32IZHINXMIN-NEXT: lw s2, 0(sp) # 4-byte Folded Reload ; RV32IZHINXMIN-NEXT: addi sp, sp, 16 -; RV32IZHINXMIN-NEXT: beqz a3, .LBB9_6 +; RV32IZHINXMIN-NEXT: beqz a4, .LBB9_6 ; RV32IZHINXMIN-NEXT: # %bb.5: -; RV32IZHINXMIN-NEXT: addi a4, a5, -1 +; RV32IZHINXMIN-NEXT: addi a3, a5, -1 ; RV32IZHINXMIN-NEXT: .LBB9_6: -; RV32IZHINXMIN-NEXT: and a1, a2, a4 +; RV32IZHINXMIN-NEXT: and a1, a2, a3 ; RV32IZHINXMIN-NEXT: ret ; ; RV64IZHINXMIN-LABEL: test_trunc_si64: @@ -2256,40 +2244,38 @@ define i64 @test_round_si64(half %x) nounwind { ; RV32IZFH-NEXT: addi sp, sp, -16 ; RV32IZFH-NEXT: sw ra, 12(sp) # 4-byte Folded Spill ; RV32IZFH-NEXT: sw s0, 8(sp) # 4-byte Folded Spill -; RV32IZFH-NEXT: sw s1, 4(sp) # 4-byte Folded Spill -; RV32IZFH-NEXT: fsw fs0, 0(sp) # 4-byte Folded Spill +; RV32IZFH-NEXT: fsw fs0, 4(sp) # 4-byte Folded Spill ; RV32IZFH-NEXT: fcvt.s.h fs0, fa0 ; RV32IZFH-NEXT: lui a0, 913408 ; RV32IZFH-NEXT: fmv.w.x fa5, a0 ; RV32IZFH-NEXT: fle.s s0, fa5, fs0 -; RV32IZFH-NEXT: neg s1, s0 ; RV32IZFH-NEXT: fmv.s fa0, fs0 ; RV32IZFH-NEXT: call __fixsfdi -; RV32IZFH-NEXT: lui a2, %hi(.LCPI13_1) -; RV32IZFH-NEXT: flw fa5, %lo(.LCPI13_1)(a2) -; RV32IZFH-NEXT: and a0, s1, a0 -; RV32IZFH-NEXT: flt.s a3, fa5, fs0 -; RV32IZFH-NEXT: neg a2, a3 -; RV32IZFH-NEXT: or a0, a2, a0 -; RV32IZFH-NEXT: feq.s a2, fs0, fs0 -; RV32IZFH-NEXT: neg a2, a2 -; RV32IZFH-NEXT: lui a5, 524288 ; RV32IZFH-NEXT: lui a4, 524288 +; RV32IZFH-NEXT: lui a2, 524288 ; RV32IZFH-NEXT: beqz s0, .LBB13_4 ; RV32IZFH-NEXT: # %bb.3: -; RV32IZFH-NEXT: mv a4, a1 +; RV32IZFH-NEXT: mv a2, a1 ; RV32IZFH-NEXT: .LBB13_4: +; RV32IZFH-NEXT: lui a1, %hi(.LCPI13_1) +; RV32IZFH-NEXT: flw fa5, %lo(.LCPI13_1)(a1) +; RV32IZFH-NEXT: flt.s a3, fa5, fs0 +; RV32IZFH-NEXT: beqz a3, .LBB13_6 +; RV32IZFH-NEXT: # %bb.5: +; RV32IZFH-NEXT: addi a2, a4, -1 +; RV32IZFH-NEXT: .LBB13_6: +; RV32IZFH-NEXT: feq.s a1, fs0, fs0 +; RV32IZFH-NEXT: neg a4, a1 +; RV32IZFH-NEXT: and a1, a4, a2 +; RV32IZFH-NEXT: neg a2, s0 ; RV32IZFH-NEXT: and a0, a2, a0 +; RV32IZFH-NEXT: neg a2, a3 +; RV32IZFH-NEXT: or a0, a2, a0 +; RV32IZFH-NEXT: and a0, a4, a0 ; RV32IZFH-NEXT: lw ra, 12(sp) # 4-byte Folded Reload ; RV32IZFH-NEXT: lw s0, 8(sp) # 4-byte Folded Reload -; RV32IZFH-NEXT: lw s1, 4(sp) # 4-byte Folded Reload -; RV32IZFH-NEXT: flw fs0, 0(sp) # 4-byte Folded Reload +; RV32IZFH-NEXT: flw fs0, 4(sp) # 4-byte Folded Reload ; RV32IZFH-NEXT: addi sp, sp, 16 -; RV32IZFH-NEXT: beqz a3, .LBB13_6 -; RV32IZFH-NEXT: # %bb.5: -; RV32IZFH-NEXT: addi a4, a5, -1 -; RV32IZFH-NEXT: .LBB13_6: -; RV32IZFH-NEXT: and a1, a2, a4 ; RV32IZFH-NEXT: ret ; ; RV64IZFH-LABEL: test_round_si64: @@ -2327,16 +2313,16 @@ define i64 @test_round_si64(half %x) nounwind { ; RV32IZHINX-NEXT: lui a2, %hi(.LCPI13_1) ; RV32IZHINX-NEXT: lw a2, %lo(.LCPI13_1)(a2) ; RV32IZHINX-NEXT: and a0, s2, a0 -; RV32IZHINX-NEXT: flt.s a3, a2, s0 -; RV32IZHINX-NEXT: neg a2, a3 +; RV32IZHINX-NEXT: flt.s a4, a2, s0 +; RV32IZHINX-NEXT: neg a2, a4 ; RV32IZHINX-NEXT: or a0, a2, a0 ; RV32IZHINX-NEXT: feq.s a2, s0, s0 ; RV32IZHINX-NEXT: neg a2, a2 ; RV32IZHINX-NEXT: lui a5, 524288 -; RV32IZHINX-NEXT: lui a4, 524288 +; RV32IZHINX-NEXT: lui a3, 524288 ; RV32IZHINX-NEXT: beqz s1, .LBB13_4 ; RV32IZHINX-NEXT: # %bb.3: -; RV32IZHINX-NEXT: mv a4, a1 +; RV32IZHINX-NEXT: mv a3, a1 ; RV32IZHINX-NEXT: .LBB13_4: ; RV32IZHINX-NEXT: and a0, a2, a0 ; RV32IZHINX-NEXT: lw ra, 12(sp) # 4-byte Folded Reload @@ -2344,11 +2330,11 @@ define i64 @test_round_si64(half %x) nounwind { ; RV32IZHINX-NEXT: lw s1, 4(sp) # 4-byte Folded Reload ; RV32IZHINX-NEXT: lw s2, 0(sp) # 4-byte Folded Reload ; RV32IZHINX-NEXT: addi sp, sp, 16 -; RV32IZHINX-NEXT: beqz a3, .LBB13_6 +; RV32IZHINX-NEXT: beqz a4, .LBB13_6 ; RV32IZHINX-NEXT: # %bb.5: -; RV32IZHINX-NEXT: addi a4, a5, -1 +; RV32IZHINX-NEXT: addi a3, a5, -1 ; RV32IZHINX-NEXT: .LBB13_6: -; RV32IZHINX-NEXT: and a1, a2, a4 +; RV32IZHINX-NEXT: and a1, a2, a3 ; RV32IZHINX-NEXT: ret ; ; RV64IZHINX-LABEL: test_round_si64: @@ -2386,41 +2372,39 @@ define i64 @test_round_si64(half %x) nounwind { ; RV32IZFHMIN-NEXT: addi sp, sp, -16 ; RV32IZFHMIN-NEXT: sw ra, 12(sp) # 4-byte Folded Spill ; RV32IZFHMIN-NEXT: sw s0, 8(sp) # 4-byte Folded Spill -; RV32IZFHMIN-NEXT: sw s1, 4(sp) # 4-byte Folded Spill -; RV32IZFHMIN-NEXT: fsw fs0, 0(sp) # 4-byte Folded Spill +; RV32IZFHMIN-NEXT: fsw fs0, 4(sp) # 4-byte Folded Spill ; RV32IZFHMIN-NEXT: fcvt.h.s fa5, fa5 ; RV32IZFHMIN-NEXT: fcvt.s.h fs0, fa5 ; RV32IZFHMIN-NEXT: lui a0, 913408 ; RV32IZFHMIN-NEXT: fmv.w.x fa5, a0 ; RV32IZFHMIN-NEXT: fle.s s0, fa5, fs0 -; RV32IZFHMIN-NEXT: neg s1, s0 ; RV32IZFHMIN-NEXT: fmv.s fa0, fs0 ; RV32IZFHMIN-NEXT: call __fixsfdi -; RV32IZFHMIN-NEXT: lui a2, %hi(.LCPI13_0) -; RV32IZFHMIN-NEXT: flw fa5, %lo(.LCPI13_0)(a2) -; RV32IZFHMIN-NEXT: and a0, s1, a0 -; RV32IZFHMIN-NEXT: flt.s a3, fa5, fs0 -; RV32IZFHMIN-NEXT: neg a2, a3 -; RV32IZFHMIN-NEXT: or a0, a2, a0 -; RV32IZFHMIN-NEXT: feq.s a2, fs0, fs0 -; RV32IZFHMIN-NEXT: neg a2, a2 -; RV32IZFHMIN-NEXT: lui a5, 524288 ; RV32IZFHMIN-NEXT: lui a4, 524288 +; RV32IZFHMIN-NEXT: lui a2, 524288 ; RV32IZFHMIN-NEXT: beqz s0, .LBB13_4 ; RV32IZFHMIN-NEXT: # %bb.3: -; RV32IZFHMIN-NEXT: mv a4, a1 +; RV32IZFHMIN-NEXT: mv a2, a1 ; RV32IZFHMIN-NEXT: .LBB13_4: +; RV32IZFHMIN-NEXT: lui a1, %hi(.LCPI13_0) +; RV32IZFHMIN-NEXT: flw fa5, %lo(.LCPI13_0)(a1) +; RV32IZFHMIN-NEXT: flt.s a3, fa5, fs0 +; RV32IZFHMIN-NEXT: beqz a3, .LBB13_6 +; RV32IZFHMIN-NEXT: # %bb.5: +; RV32IZFHMIN-NEXT: addi a2, a4, -1 +; RV32IZFHMIN-NEXT: .LBB13_6: +; RV32IZFHMIN-NEXT: feq.s a1, fs0, fs0 +; RV32IZFHMIN-NEXT: neg a4, a1 +; RV32IZFHMIN-NEXT: and a1, a4, a2 +; RV32IZFHMIN-NEXT: neg a2, s0 ; RV32IZFHMIN-NEXT: and a0, a2, a0 +; RV32IZFHMIN-NEXT: neg a2, a3 +; RV32IZFHMIN-NEXT: or a0, a2, a0 +; RV32IZFHMIN-NEXT: and a0, a4, a0 ; RV32IZFHMIN-NEXT: lw ra, 12(sp) # 4-byte Folded Reload ; RV32IZFHMIN-NEXT: lw s0, 8(sp) # 4-byte Folded Reload -; RV32IZFHMIN-NEXT: lw s1, 4(sp) # 4-byte Folded Reload -; RV32IZFHMIN-NEXT: flw fs0, 0(sp) # 4-byte Folded Reload +; RV32IZFHMIN-NEXT: flw fs0, 4(sp) # 4-byte Folded Reload ; RV32IZFHMIN-NEXT: addi sp, sp, 16 -; RV32IZFHMIN-NEXT: beqz a3, .LBB13_6 -; RV32IZFHMIN-NEXT: # %bb.5: -; RV32IZFHMIN-NEXT: addi a4, a5, -1 -; RV32IZFHMIN-NEXT: .LBB13_6: -; RV32IZFHMIN-NEXT: and a1, a2, a4 ; RV32IZFHMIN-NEXT: ret ; ; RV64IZFHMIN-LABEL: test_round_si64: @@ -2472,16 +2456,16 @@ define i64 @test_round_si64(half %x) nounwind { ; RV32IZHINXMIN-NEXT: lui a2, %hi(.LCPI13_0) ; RV32IZHINXMIN-NEXT: lw a2, %lo(.LCPI13_0)(a2) ; RV32IZHINXMIN-NEXT: and a0, s2, a0 -; RV32IZHINXMIN-NEXT: flt.s a3, a2, s0 -; RV32IZHINXMIN-NEXT: neg a2, a3 +; RV32IZHINXMIN-NEXT: flt.s a4, a2, s0 +; RV32IZHINXMIN-NEXT: neg a2, a4 ; RV32IZHINXMIN-NEXT: or a0, a2, a0 ; RV32IZHINXMIN-NEXT: feq.s a2, s0, s0 ; RV32IZHINXMIN-NEXT: neg a2, a2 ; RV32IZHINXMIN-NEXT: lui a5, 524288 -; RV32IZHINXMIN-NEXT: lui a4, 524288 +; RV32IZHINXMIN-NEXT: lui a3, 524288 ; RV32IZHINXMIN-NEXT: beqz s1, .LBB13_4 ; RV32IZHINXMIN-NEXT: # %bb.3: -; RV32IZHINXMIN-NEXT: mv a4, a1 +; RV32IZHINXMIN-NEXT: mv a3, a1 ; RV32IZHINXMIN-NEXT: .LBB13_4: ; RV32IZHINXMIN-NEXT: and a0, a2, a0 ; RV32IZHINXMIN-NEXT: lw ra, 12(sp) # 4-byte Folded Reload @@ -2489,11 +2473,11 @@ define i64 @test_round_si64(half %x) nounwind { ; RV32IZHINXMIN-NEXT: lw s1, 4(sp) # 4-byte Folded Reload ; RV32IZHINXMIN-NEXT: lw s2, 0(sp) # 4-byte Folded Reload ; RV32IZHINXMIN-NEXT: addi sp, sp, 16 -; RV32IZHINXMIN-NEXT: beqz a3, .LBB13_6 +; RV32IZHINXMIN-NEXT: beqz a4, .LBB13_6 ; RV32IZHINXMIN-NEXT: # %bb.5: -; RV32IZHINXMIN-NEXT: addi a4, a5, -1 +; RV32IZHINXMIN-NEXT: addi a3, a5, -1 ; RV32IZHINXMIN-NEXT: .LBB13_6: -; RV32IZHINXMIN-NEXT: and a1, a2, a4 +; RV32IZHINXMIN-NEXT: and a1, a2, a3 ; RV32IZHINXMIN-NEXT: ret ; ; RV64IZHINXMIN-LABEL: test_round_si64: @@ -2972,40 +2956,38 @@ define i64 @test_roundeven_si64(half %x) nounwind { ; RV32IZFH-NEXT: addi sp, sp, -16 ; RV32IZFH-NEXT: sw ra, 12(sp) # 4-byte Folded Spill ; RV32IZFH-NEXT: sw s0, 8(sp) # 4-byte Folded Spill -; RV32IZFH-NEXT: sw s1, 4(sp) # 4-byte Folded Spill -; RV32IZFH-NEXT: fsw fs0, 0(sp) # 4-byte Folded Spill +; RV32IZFH-NEXT: fsw fs0, 4(sp) # 4-byte Folded Spill ; RV32IZFH-NEXT: fcvt.s.h fs0, fa0 ; RV32IZFH-NEXT: lui a0, 913408 ; RV32IZFH-NEXT: fmv.w.x fa5, a0 ; RV32IZFH-NEXT: fle.s s0, fa5, fs0 -; RV32IZFH-NEXT: neg s1, s0 ; RV32IZFH-NEXT: fmv.s fa0, fs0 ; RV32IZFH-NEXT: call __fixsfdi -; RV32IZFH-NEXT: lui a2, %hi(.LCPI17_1) -; RV32IZFH-NEXT: flw fa5, %lo(.LCPI17_1)(a2) -; RV32IZFH-NEXT: and a0, s1, a0 -; RV32IZFH-NEXT: flt.s a3, fa5, fs0 -; RV32IZFH-NEXT: neg a2, a3 -; RV32IZFH-NEXT: or a0, a2, a0 -; RV32IZFH-NEXT: feq.s a2, fs0, fs0 -; RV32IZFH-NEXT: neg a2, a2 -; RV32IZFH-NEXT: lui a5, 524288 ; RV32IZFH-NEXT: lui a4, 524288 +; RV32IZFH-NEXT: lui a2, 524288 ; RV32IZFH-NEXT: beqz s0, .LBB17_4 ; RV32IZFH-NEXT: # %bb.3: -; RV32IZFH-NEXT: mv a4, a1 +; RV32IZFH-NEXT: mv a2, a1 ; RV32IZFH-NEXT: .LBB17_4: +; RV32IZFH-NEXT: lui a1, %hi(.LCPI17_1) +; RV32IZFH-NEXT: flw fa5, %lo(.LCPI17_1)(a1) +; RV32IZFH-NEXT: flt.s a3, fa5, fs0 +; RV32IZFH-NEXT: beqz a3, .LBB17_6 +; RV32IZFH-NEXT: # %bb.5: +; RV32IZFH-NEXT: addi a2, a4, -1 +; RV32IZFH-NEXT: .LBB17_6: +; RV32IZFH-NEXT: feq.s a1, fs0, fs0 +; RV32IZFH-NEXT: neg a4, a1 +; RV32IZFH-NEXT: and a1, a4, a2 +; RV32IZFH-NEXT: neg a2, s0 ; RV32IZFH-NEXT: and a0, a2, a0 +; RV32IZFH-NEXT: neg a2, a3 +; RV32IZFH-NEXT: or a0, a2, a0 +; RV32IZFH-NEXT: and a0, a4, a0 ; RV32IZFH-NEXT: lw ra, 12(sp) # 4-byte Folded Reload ; RV32IZFH-NEXT: lw s0, 8(sp) # 4-byte Folded Reload -; RV32IZFH-NEXT: lw s1, 4(sp) # 4-byte Folded Reload -; RV32IZFH-NEXT: flw fs0, 0(sp) # 4-byte Folded Reload +; RV32IZFH-NEXT: flw fs0, 4(sp) # 4-byte Folded Reload ; RV32IZFH-NEXT: addi sp, sp, 16 -; RV32IZFH-NEXT: beqz a3, .LBB17_6 -; RV32IZFH-NEXT: # %bb.5: -; RV32IZFH-NEXT: addi a4, a5, -1 -; RV32IZFH-NEXT: .LBB17_6: -; RV32IZFH-NEXT: and a1, a2, a4 ; RV32IZFH-NEXT: ret ; ; RV64IZFH-LABEL: test_roundeven_si64: @@ -3043,16 +3025,16 @@ define i64 @test_roundeven_si64(half %x) nounwind { ; RV32IZHINX-NEXT: lui a2, %hi(.LCPI17_1) ; RV32IZHINX-NEXT: lw a2, %lo(.LCPI17_1)(a2) ; RV32IZHINX-NEXT: and a0, s2, a0 -; RV32IZHINX-NEXT: flt.s a3, a2, s0 -; RV32IZHINX-NEXT: neg a2, a3 +; RV32IZHINX-NEXT: flt.s a4, a2, s0 +; RV32IZHINX-NEXT: neg a2, a4 ; RV32IZHINX-NEXT: or a0, a2, a0 ; RV32IZHINX-NEXT: feq.s a2, s0, s0 ; RV32IZHINX-NEXT: neg a2, a2 ; RV32IZHINX-NEXT: lui a5, 524288 -; RV32IZHINX-NEXT: lui a4, 524288 +; RV32IZHINX-NEXT: lui a3, 524288 ; RV32IZHINX-NEXT: beqz s1, .LBB17_4 ; RV32IZHINX-NEXT: # %bb.3: -; RV32IZHINX-NEXT: mv a4, a1 +; RV32IZHINX-NEXT: mv a3, a1 ; RV32IZHINX-NEXT: .LBB17_4: ; RV32IZHINX-NEXT: and a0, a2, a0 ; RV32IZHINX-NEXT: lw ra, 12(sp) # 4-byte Folded Reload @@ -3060,11 +3042,11 @@ define i64 @test_roundeven_si64(half %x) nounwind { ; RV32IZHINX-NEXT: lw s1, 4(sp) # 4-byte Folded Reload ; RV32IZHINX-NEXT: lw s2, 0(sp) # 4-byte Folded Reload ; RV32IZHINX-NEXT: addi sp, sp, 16 -; RV32IZHINX-NEXT: beqz a3, .LBB17_6 +; RV32IZHINX-NEXT: beqz a4, .LBB17_6 ; RV32IZHINX-NEXT: # %bb.5: -; RV32IZHINX-NEXT: addi a4, a5, -1 +; RV32IZHINX-NEXT: addi a3, a5, -1 ; RV32IZHINX-NEXT: .LBB17_6: -; RV32IZHINX-NEXT: and a1, a2, a4 +; RV32IZHINX-NEXT: and a1, a2, a3 ; RV32IZHINX-NEXT: ret ; ; RV64IZHINX-LABEL: test_roundeven_si64: @@ -3102,41 +3084,39 @@ define i64 @test_roundeven_si64(half %x) nounwind { ; RV32IZFHMIN-NEXT: addi sp, sp, -16 ; RV32IZFHMIN-NEXT: sw ra, 12(sp) # 4-byte Folded Spill ; RV32IZFHMIN-NEXT: sw s0, 8(sp) # 4-byte Folded Spill -; RV32IZFHMIN-NEXT: sw s1, 4(sp) # 4-byte Folded Spill -; RV32IZFHMIN-NEXT: fsw fs0, 0(sp) # 4-byte Folded Spill +; RV32IZFHMIN-NEXT: fsw fs0, 4(sp) # 4-byte Folded Spill ; RV32IZFHMIN-NEXT: fcvt.h.s fa5, fa5 ; RV32IZFHMIN-NEXT: fcvt.s.h fs0, fa5 ; RV32IZFHMIN-NEXT: lui a0, 913408 ; RV32IZFHMIN-NEXT: fmv.w.x fa5, a0 ; RV32IZFHMIN-NEXT: fle.s s0, fa5, fs0 -; RV32IZFHMIN-NEXT: neg s1, s0 ; RV32IZFHMIN-NEXT: fmv.s fa0, fs0 ; RV32IZFHMIN-NEXT: call __fixsfdi -; RV32IZFHMIN-NEXT: lui a2, %hi(.LCPI17_0) -; RV32IZFHMIN-NEXT: flw fa5, %lo(.LCPI17_0)(a2) -; RV32IZFHMIN-NEXT: and a0, s1, a0 -; RV32IZFHMIN-NEXT: flt.s a3, fa5, fs0 -; RV32IZFHMIN-NEXT: neg a2, a3 -; RV32IZFHMIN-NEXT: or a0, a2, a0 -; RV32IZFHMIN-NEXT: feq.s a2, fs0, fs0 -; RV32IZFHMIN-NEXT: neg a2, a2 -; RV32IZFHMIN-NEXT: lui a5, 524288 ; RV32IZFHMIN-NEXT: lui a4, 524288 +; RV32IZFHMIN-NEXT: lui a2, 524288 ; RV32IZFHMIN-NEXT: beqz s0, .LBB17_4 ; RV32IZFHMIN-NEXT: # %bb.3: -; RV32IZFHMIN-NEXT: mv a4, a1 +; RV32IZFHMIN-NEXT: mv a2, a1 ; RV32IZFHMIN-NEXT: .LBB17_4: +; RV32IZFHMIN-NEXT: lui a1, %hi(.LCPI17_0) +; RV32IZFHMIN-NEXT: flw fa5, %lo(.LCPI17_0)(a1) +; RV32IZFHMIN-NEXT: flt.s a3, fa5, fs0 +; RV32IZFHMIN-NEXT: beqz a3, .LBB17_6 +; RV32IZFHMIN-NEXT: # %bb.5: +; RV32IZFHMIN-NEXT: addi a2, a4, -1 +; RV32IZFHMIN-NEXT: .LBB17_6: +; RV32IZFHMIN-NEXT: feq.s a1, fs0, fs0 +; RV32IZFHMIN-NEXT: neg a4, a1 +; RV32IZFHMIN-NEXT: and a1, a4, a2 +; RV32IZFHMIN-NEXT: neg a2, s0 ; RV32IZFHMIN-NEXT: and a0, a2, a0 +; RV32IZFHMIN-NEXT: neg a2, a3 +; RV32IZFHMIN-NEXT: or a0, a2, a0 +; RV32IZFHMIN-NEXT: and a0, a4, a0 ; RV32IZFHMIN-NEXT: lw ra, 12(sp) # 4-byte Folded Reload ; RV32IZFHMIN-NEXT: lw s0, 8(sp) # 4-byte Folded Reload -; RV32IZFHMIN-NEXT: lw s1, 4(sp) # 4-byte Folded Reload -; RV32IZFHMIN-NEXT: flw fs0, 0(sp) # 4-byte Folded Reload +; RV32IZFHMIN-NEXT: flw fs0, 4(sp) # 4-byte Folded Reload ; RV32IZFHMIN-NEXT: addi sp, sp, 16 -; RV32IZFHMIN-NEXT: beqz a3, .LBB17_6 -; RV32IZFHMIN-NEXT: # %bb.5: -; RV32IZFHMIN-NEXT: addi a4, a5, -1 -; RV32IZFHMIN-NEXT: .LBB17_6: -; RV32IZFHMIN-NEXT: and a1, a2, a4 ; RV32IZFHMIN-NEXT: ret ; ; RV64IZFHMIN-LABEL: test_roundeven_si64: @@ -3188,16 +3168,16 @@ define i64 @test_roundeven_si64(half %x) nounwind { ; RV32IZHINXMIN-NEXT: lui a2, %hi(.LCPI17_0) ; RV32IZHINXMIN-NEXT: lw a2, %lo(.LCPI17_0)(a2) ; RV32IZHINXMIN-NEXT: and a0, s2, a0 -; RV32IZHINXMIN-NEXT: flt.s a3, a2, s0 -; RV32IZHINXMIN-NEXT: neg a2, a3 +; RV32IZHINXMIN-NEXT: flt.s a4, a2, s0 +; RV32IZHINXMIN-NEXT: neg a2, a4 ; RV32IZHINXMIN-NEXT: or a0, a2, a0 ; RV32IZHINXMIN-NEXT: feq.s a2, s0, s0 ; RV32IZHINXMIN-NEXT: neg a2, a2 ; RV32IZHINXMIN-NEXT: lui a5, 524288 -; RV32IZHINXMIN-NEXT: lui a4, 524288 +; RV32IZHINXMIN-NEXT: lui a3, 524288 ; RV32IZHINXMIN-NEXT: beqz s1, .LBB17_4 ; RV32IZHINXMIN-NEXT: # %bb.3: -; RV32IZHINXMIN-NEXT: mv a4, a1 +; RV32IZHINXMIN-NEXT: mv a3, a1 ; RV32IZHINXMIN-NEXT: .LBB17_4: ; RV32IZHINXMIN-NEXT: and a0, a2, a0 ; RV32IZHINXMIN-NEXT: lw ra, 12(sp) # 4-byte Folded Reload @@ -3205,11 +3185,11 @@ define i64 @test_roundeven_si64(half %x) nounwind { ; RV32IZHINXMIN-NEXT: lw s1, 4(sp) # 4-byte Folded Reload ; RV32IZHINXMIN-NEXT: lw s2, 0(sp) # 4-byte Folded Reload ; RV32IZHINXMIN-NEXT: addi sp, sp, 16 -; RV32IZHINXMIN-NEXT: beqz a3, .LBB17_6 +; RV32IZHINXMIN-NEXT: beqz a4, .LBB17_6 ; RV32IZHINXMIN-NEXT: # %bb.5: -; RV32IZHINXMIN-NEXT: addi a4, a5, -1 +; RV32IZHINXMIN-NEXT: addi a3, a5, -1 ; RV32IZHINXMIN-NEXT: .LBB17_6: -; RV32IZHINXMIN-NEXT: and a1, a2, a4 +; RV32IZHINXMIN-NEXT: and a1, a2, a3 ; RV32IZHINXMIN-NEXT: ret ; ; RV64IZHINXMIN-LABEL: test_roundeven_si64: @@ -3688,40 +3668,38 @@ define i64 @test_rint_si64(half %x) nounwind { ; RV32IZFH-NEXT: addi sp, sp, -16 ; RV32IZFH-NEXT: sw ra, 12(sp) # 4-byte Folded Spill ; RV32IZFH-NEXT: sw s0, 8(sp) # 4-byte Folded Spill -; RV32IZFH-NEXT: sw s1, 4(sp) # 4-byte Folded Spill -; RV32IZFH-NEXT: fsw fs0, 0(sp) # 4-byte Folded Spill +; RV32IZFH-NEXT: fsw fs0, 4(sp) # 4-byte Folded Spill ; RV32IZFH-NEXT: fcvt.s.h fs0, fa0 ; RV32IZFH-NEXT: lui a0, 913408 ; RV32IZFH-NEXT: fmv.w.x fa5, a0 ; RV32IZFH-NEXT: fle.s s0, fa5, fs0 -; RV32IZFH-NEXT: neg s1, s0 ; RV32IZFH-NEXT: fmv.s fa0, fs0 ; RV32IZFH-NEXT: call __fixsfdi -; RV32IZFH-NEXT: lui a2, %hi(.LCPI21_1) -; RV32IZFH-NEXT: flw fa5, %lo(.LCPI21_1)(a2) -; RV32IZFH-NEXT: and a0, s1, a0 -; RV32IZFH-NEXT: flt.s a3, fa5, fs0 -; RV32IZFH-NEXT: neg a2, a3 -; RV32IZFH-NEXT: or a0, a2, a0 -; RV32IZFH-NEXT: feq.s a2, fs0, fs0 -; RV32IZFH-NEXT: neg a2, a2 -; RV32IZFH-NEXT: lui a5, 524288 ; RV32IZFH-NEXT: lui a4, 524288 +; RV32IZFH-NEXT: lui a2, 524288 ; RV32IZFH-NEXT: beqz s0, .LBB21_4 ; RV32IZFH-NEXT: # %bb.3: -; RV32IZFH-NEXT: mv a4, a1 +; RV32IZFH-NEXT: mv a2, a1 ; RV32IZFH-NEXT: .LBB21_4: +; RV32IZFH-NEXT: lui a1, %hi(.LCPI21_1) +; RV32IZFH-NEXT: flw fa5, %lo(.LCPI21_1)(a1) +; RV32IZFH-NEXT: flt.s a3, fa5, fs0 +; RV32IZFH-NEXT: beqz a3, .LBB21_6 +; RV32IZFH-NEXT: # %bb.5: +; RV32IZFH-NEXT: addi a2, a4, -1 +; RV32IZFH-NEXT: .LBB21_6: +; RV32IZFH-NEXT: feq.s a1, fs0, fs0 +; RV32IZFH-NEXT: neg a4, a1 +; RV32IZFH-NEXT: and a1, a4, a2 +; RV32IZFH-NEXT: neg a2, s0 ; RV32IZFH-NEXT: and a0, a2, a0 +; RV32IZFH-NEXT: neg a2, a3 +; RV32IZFH-NEXT: or a0, a2, a0 +; RV32IZFH-NEXT: and a0, a4, a0 ; RV32IZFH-NEXT: lw ra, 12(sp) # 4-byte Folded Reload ; RV32IZFH-NEXT: lw s0, 8(sp) # 4-byte Folded Reload -; RV32IZFH-NEXT: lw s1, 4(sp) # 4-byte Folded Reload -; RV32IZFH-NEXT: flw fs0, 0(sp) # 4-byte Folded Reload +; RV32IZFH-NEXT: flw fs0, 4(sp) # 4-byte Folded Reload ; RV32IZFH-NEXT: addi sp, sp, 16 -; RV32IZFH-NEXT: beqz a3, .LBB21_6 -; RV32IZFH-NEXT: # %bb.5: -; RV32IZFH-NEXT: addi a4, a5, -1 -; RV32IZFH-NEXT: .LBB21_6: -; RV32IZFH-NEXT: and a1, a2, a4 ; RV32IZFH-NEXT: ret ; ; RV64IZFH-LABEL: test_rint_si64: @@ -3759,16 +3737,16 @@ define i64 @test_rint_si64(half %x) nounwind { ; RV32IZHINX-NEXT: lui a2, %hi(.LCPI21_1) ; RV32IZHINX-NEXT: lw a2, %lo(.LCPI21_1)(a2) ; RV32IZHINX-NEXT: and a0, s2, a0 -; RV32IZHINX-NEXT: flt.s a3, a2, s0 -; RV32IZHINX-NEXT: neg a2, a3 +; RV32IZHINX-NEXT: flt.s a4, a2, s0 +; RV32IZHINX-NEXT: neg a2, a4 ; RV32IZHINX-NEXT: or a0, a2, a0 ; RV32IZHINX-NEXT: feq.s a2, s0, s0 ; RV32IZHINX-NEXT: neg a2, a2 ; RV32IZHINX-NEXT: lui a5, 524288 -; RV32IZHINX-NEXT: lui a4, 524288 +; RV32IZHINX-NEXT: lui a3, 524288 ; RV32IZHINX-NEXT: beqz s1, .LBB21_4 ; RV32IZHINX-NEXT: # %bb.3: -; RV32IZHINX-NEXT: mv a4, a1 +; RV32IZHINX-NEXT: mv a3, a1 ; RV32IZHINX-NEXT: .LBB21_4: ; RV32IZHINX-NEXT: and a0, a2, a0 ; RV32IZHINX-NEXT: lw ra, 12(sp) # 4-byte Folded Reload @@ -3776,11 +3754,11 @@ define i64 @test_rint_si64(half %x) nounwind { ; RV32IZHINX-NEXT: lw s1, 4(sp) # 4-byte Folded Reload ; RV32IZHINX-NEXT: lw s2, 0(sp) # 4-byte Folded Reload ; RV32IZHINX-NEXT: addi sp, sp, 16 -; RV32IZHINX-NEXT: beqz a3, .LBB21_6 +; RV32IZHINX-NEXT: beqz a4, .LBB21_6 ; RV32IZHINX-NEXT: # %bb.5: -; RV32IZHINX-NEXT: addi a4, a5, -1 +; RV32IZHINX-NEXT: addi a3, a5, -1 ; RV32IZHINX-NEXT: .LBB21_6: -; RV32IZHINX-NEXT: and a1, a2, a4 +; RV32IZHINX-NEXT: and a1, a2, a3 ; RV32IZHINX-NEXT: ret ; ; RV64IZHINX-LABEL: test_rint_si64: @@ -3818,41 +3796,39 @@ define i64 @test_rint_si64(half %x) nounwind { ; RV32IZFHMIN-NEXT: addi sp, sp, -16 ; RV32IZFHMIN-NEXT: sw ra, 12(sp) # 4-byte Folded Spill ; RV32IZFHMIN-NEXT: sw s0, 8(sp) # 4-byte Folded Spill -; RV32IZFHMIN-NEXT: sw s1, 4(sp) # 4-byte Folded Spill -; RV32IZFHMIN-NEXT: fsw fs0, 0(sp) # 4-byte Folded Spill +; RV32IZFHMIN-NEXT: fsw fs0, 4(sp) # 4-byte Folded Spill ; RV32IZFHMIN-NEXT: fcvt.h.s fa5, fa5 ; RV32IZFHMIN-NEXT: fcvt.s.h fs0, fa5 ; RV32IZFHMIN-NEXT: lui a0, 913408 ; RV32IZFHMIN-NEXT: fmv.w.x fa5, a0 ; RV32IZFHMIN-NEXT: fle.s s0, fa5, fs0 -; RV32IZFHMIN-NEXT: neg s1, s0 ; RV32IZFHMIN-NEXT: fmv.s fa0, fs0 ; RV32IZFHMIN-NEXT: call __fixsfdi -; RV32IZFHMIN-NEXT: lui a2, %hi(.LCPI21_0) -; RV32IZFHMIN-NEXT: flw fa5, %lo(.LCPI21_0)(a2) -; RV32IZFHMIN-NEXT: and a0, s1, a0 -; RV32IZFHMIN-NEXT: flt.s a3, fa5, fs0 -; RV32IZFHMIN-NEXT: neg a2, a3 -; RV32IZFHMIN-NEXT: or a0, a2, a0 -; RV32IZFHMIN-NEXT: feq.s a2, fs0, fs0 -; RV32IZFHMIN-NEXT: neg a2, a2 -; RV32IZFHMIN-NEXT: lui a5, 524288 ; RV32IZFHMIN-NEXT: lui a4, 524288 +; RV32IZFHMIN-NEXT: lui a2, 524288 ; RV32IZFHMIN-NEXT: beqz s0, .LBB21_4 ; RV32IZFHMIN-NEXT: # %bb.3: -; RV32IZFHMIN-NEXT: mv a4, a1 +; RV32IZFHMIN-NEXT: mv a2, a1 ; RV32IZFHMIN-NEXT: .LBB21_4: +; RV32IZFHMIN-NEXT: lui a1, %hi(.LCPI21_0) +; RV32IZFHMIN-NEXT: flw fa5, %lo(.LCPI21_0)(a1) +; RV32IZFHMIN-NEXT: flt.s a3, fa5, fs0 +; RV32IZFHMIN-NEXT: beqz a3, .LBB21_6 +; RV32IZFHMIN-NEXT: # %bb.5: +; RV32IZFHMIN-NEXT: addi a2, a4, -1 +; RV32IZFHMIN-NEXT: .LBB21_6: +; RV32IZFHMIN-NEXT: feq.s a1, fs0, fs0 +; RV32IZFHMIN-NEXT: neg a4, a1 +; RV32IZFHMIN-NEXT: and a1, a4, a2 +; RV32IZFHMIN-NEXT: neg a2, s0 ; RV32IZFHMIN-NEXT: and a0, a2, a0 +; RV32IZFHMIN-NEXT: neg a2, a3 +; RV32IZFHMIN-NEXT: or a0, a2, a0 +; RV32IZFHMIN-NEXT: and a0, a4, a0 ; RV32IZFHMIN-NEXT: lw ra, 12(sp) # 4-byte Folded Reload ; RV32IZFHMIN-NEXT: lw s0, 8(sp) # 4-byte Folded Reload -; RV32IZFHMIN-NEXT: lw s1, 4(sp) # 4-byte Folded Reload -; RV32IZFHMIN-NEXT: flw fs0, 0(sp) # 4-byte Folded Reload +; RV32IZFHMIN-NEXT: flw fs0, 4(sp) # 4-byte Folded Reload ; RV32IZFHMIN-NEXT: addi sp, sp, 16 -; RV32IZFHMIN-NEXT: beqz a3, .LBB21_6 -; RV32IZFHMIN-NEXT: # %bb.5: -; RV32IZFHMIN-NEXT: addi a4, a5, -1 -; RV32IZFHMIN-NEXT: .LBB21_6: -; RV32IZFHMIN-NEXT: and a1, a2, a4 ; RV32IZFHMIN-NEXT: ret ; ; RV64IZFHMIN-LABEL: test_rint_si64: @@ -3904,16 +3880,16 @@ define i64 @test_rint_si64(half %x) nounwind { ; RV32IZHINXMIN-NEXT: lui a2, %hi(.LCPI21_0) ; RV32IZHINXMIN-NEXT: lw a2, %lo(.LCPI21_0)(a2) ; RV32IZHINXMIN-NEXT: and a0, s2, a0 -; RV32IZHINXMIN-NEXT: flt.s a3, a2, s0 -; RV32IZHINXMIN-NEXT: neg a2, a3 +; RV32IZHINXMIN-NEXT: flt.s a4, a2, s0 +; RV32IZHINXMIN-NEXT: neg a2, a4 ; RV32IZHINXMIN-NEXT: or a0, a2, a0 ; RV32IZHINXMIN-NEXT: feq.s a2, s0, s0 ; RV32IZHINXMIN-NEXT: neg a2, a2 ; RV32IZHINXMIN-NEXT: lui a5, 524288 -; RV32IZHINXMIN-NEXT: lui a4, 524288 +; RV32IZHINXMIN-NEXT: lui a3, 524288 ; RV32IZHINXMIN-NEXT: beqz s1, .LBB21_4 ; RV32IZHINXMIN-NEXT: # %bb.3: -; RV32IZHINXMIN-NEXT: mv a4, a1 +; RV32IZHINXMIN-NEXT: mv a3, a1 ; RV32IZHINXMIN-NEXT: .LBB21_4: ; RV32IZHINXMIN-NEXT: and a0, a2, a0 ; RV32IZHINXMIN-NEXT: lw ra, 12(sp) # 4-byte Folded Reload @@ -3921,11 +3897,11 @@ define i64 @test_rint_si64(half %x) nounwind { ; RV32IZHINXMIN-NEXT: lw s1, 4(sp) # 4-byte Folded Reload ; RV32IZHINXMIN-NEXT: lw s2, 0(sp) # 4-byte Folded Reload ; RV32IZHINXMIN-NEXT: addi sp, sp, 16 -; RV32IZHINXMIN-NEXT: beqz a3, .LBB21_6 +; RV32IZHINXMIN-NEXT: beqz a4, .LBB21_6 ; RV32IZHINXMIN-NEXT: # %bb.5: -; RV32IZHINXMIN-NEXT: addi a4, a5, -1 +; RV32IZHINXMIN-NEXT: addi a3, a5, -1 ; RV32IZHINXMIN-NEXT: .LBB21_6: -; RV32IZHINXMIN-NEXT: and a1, a2, a4 +; RV32IZHINXMIN-NEXT: and a1, a2, a3 ; RV32IZHINXMIN-NEXT: ret ; ; RV64IZHINXMIN-LABEL: test_rint_si64: diff --git a/llvm/test/CodeGen/RISCV/iabs.ll b/llvm/test/CodeGen/RISCV/iabs.ll index 98c886333d69a0315e024066de3ac80e747cce22..a0c85ab4dca7f7c8e506e1ceeae4a82ac9535fbc 100644 --- a/llvm/test/CodeGen/RISCV/iabs.ll +++ b/llvm/test/CodeGen/RISCV/iabs.ll @@ -630,8 +630,8 @@ define void @zext16_abs8(i8 %x, ptr %p) { ; RV32I-LABEL: zext16_abs8: ; RV32I: # %bb.0: ; RV32I-NEXT: slli a0, a0, 24 -; RV32I-NEXT: srai a0, a0, 24 ; RV32I-NEXT: srai a2, a0, 31 +; RV32I-NEXT: srai a0, a0, 24 ; RV32I-NEXT: xor a0, a0, a2 ; RV32I-NEXT: sub a0, a0, a2 ; RV32I-NEXT: sh a0, 0(a1) @@ -648,8 +648,8 @@ define void @zext16_abs8(i8 %x, ptr %p) { ; RV64I-LABEL: zext16_abs8: ; RV64I: # %bb.0: ; RV64I-NEXT: slli a0, a0, 56 -; RV64I-NEXT: srai a0, a0, 56 ; RV64I-NEXT: srai a2, a0, 63 +; RV64I-NEXT: srai a0, a0, 56 ; RV64I-NEXT: xor a0, a0, a2 ; RV64I-NEXT: subw a0, a0, a2 ; RV64I-NEXT: sh a0, 0(a1) diff --git a/llvm/test/CodeGen/RISCV/pr84653_pr85190.ll b/llvm/test/CodeGen/RISCV/pr84653_pr85190.ll new file mode 100644 index 0000000000000000000000000000000000000000..3fa494e1a57ddc8e023ceafc06aec937daedc4a9 --- /dev/null +++ b/llvm/test/CodeGen/RISCV/pr84653_pr85190.ll @@ -0,0 +1,95 @@ +; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py UTC_ARGS: --version 4 +; RUN: llc < %s -mtriple=riscv64 | FileCheck %s --check-prefixes=CHECK-NOZBB +; RUN: llc < %s -mtriple=riscv64 -mattr=+zbb | FileCheck %s --check-prefixes=CHECK-ZBB + +; This test case miscompiled for ZBB (DAGCombiner turned a SELECT into a more +; poisonous AND operation). +define i1 @pr84653(i32 %x) { +; CHECK-NOZBB-LABEL: pr84653: +; CHECK-NOZBB: # %bb.0: +; CHECK-NOZBB-NEXT: sext.w a1, a0 +; CHECK-NOZBB-NEXT: sgtz a2, a1 +; CHECK-NOZBB-NEXT: lui a3, 524288 +; CHECK-NOZBB-NEXT: addi a3, a3, -1 +; CHECK-NOZBB-NEXT: xor a0, a0, a3 +; CHECK-NOZBB-NEXT: sext.w a0, a0 +; CHECK-NOZBB-NEXT: slt a0, a0, a1 +; CHECK-NOZBB-NEXT: and a0, a2, a0 +; CHECK-NOZBB-NEXT: ret +; +; CHECK-ZBB-LABEL: pr84653: +; CHECK-ZBB: # %bb.0: +; CHECK-ZBB-NEXT: sext.w a1, a0 +; CHECK-ZBB-NEXT: lui a2, 524288 +; CHECK-ZBB-NEXT: addi a2, a2, -1 +; CHECK-ZBB-NEXT: xor a0, a0, a2 +; CHECK-ZBB-NEXT: sext.w a0, a0 +; CHECK-ZBB-NEXT: max a0, a0, zero +; CHECK-ZBB-NEXT: slt a0, a0, a1 +; CHECK-ZBB-NEXT: ret + %cmp1 = icmp sgt i32 %x, 0 + %sub = sub nsw i32 2147483647, %x ; 0x7fffffff + %cmp2 = icmp sgt i32 %x, %sub + %r = select i1 %cmp1, i1 %cmp2, i1 false + ret i1 %r +} + +; This test case miscompiled for ZBB (DAGCombiner turned a SELECT into a more +; poisonous AND operation). +define i1 @pr85190(i64 %a) { +; CHECK-NOZBB-LABEL: pr85190: +; CHECK-NOZBB: # %bb.0: +; CHECK-NOZBB-NEXT: ori a1, a0, 7 +; CHECK-NOZBB-NEXT: slti a2, a0, 0 +; CHECK-NOZBB-NEXT: li a3, -1 +; CHECK-NOZBB-NEXT: slli a3, a3, 63 +; CHECK-NOZBB-NEXT: sub a3, a3, a1 +; CHECK-NOZBB-NEXT: slt a0, a0, a3 +; CHECK-NOZBB-NEXT: and a0, a2, a0 +; CHECK-NOZBB-NEXT: ret +; +; CHECK-ZBB-LABEL: pr85190: +; CHECK-ZBB: # %bb.0: +; CHECK-ZBB-NEXT: ori a1, a0, 7 +; CHECK-ZBB-NEXT: li a2, -1 +; CHECK-ZBB-NEXT: slli a2, a2, 63 +; CHECK-ZBB-NEXT: sub a2, a2, a1 +; CHECK-ZBB-NEXT: slt a0, a0, a2 +; CHECK-ZBB-NEXT: ret + %or = or i64 %a, 7 + %cmp1 = icmp slt i64 %a, 0 + %sub = sub nsw i64 -9223372036854775808, %or ; 0x8000000000000000 + %cmp2 = icmp sgt i64 %sub, %a + %res = select i1 %cmp1, i1 %cmp2, i1 false + ret i1 %res +} + +define i1 @select_to_or(i32 %x) { +; CHECK-NOZBB-LABEL: select_to_or: +; CHECK-NOZBB: # %bb.0: +; CHECK-NOZBB-NEXT: sext.w a1, a0 +; CHECK-NOZBB-NEXT: sgtz a2, a1 +; CHECK-NOZBB-NEXT: lui a3, 524288 +; CHECK-NOZBB-NEXT: addi a3, a3, -1 +; CHECK-NOZBB-NEXT: xor a0, a0, a3 +; CHECK-NOZBB-NEXT: sext.w a0, a0 +; CHECK-NOZBB-NEXT: slt a0, a0, a1 +; CHECK-NOZBB-NEXT: or a0, a2, a0 +; CHECK-NOZBB-NEXT: ret +; +; CHECK-ZBB-LABEL: select_to_or: +; CHECK-ZBB: # %bb.0: +; CHECK-ZBB-NEXT: sext.w a1, a0 +; CHECK-ZBB-NEXT: lui a2, 524288 +; CHECK-ZBB-NEXT: addi a2, a2, -1 +; CHECK-ZBB-NEXT: xor a0, a0, a2 +; CHECK-ZBB-NEXT: sext.w a0, a0 +; CHECK-ZBB-NEXT: min a0, a0, zero +; CHECK-ZBB-NEXT: slt a0, a0, a1 +; CHECK-ZBB-NEXT: ret + %cmp1 = icmp sgt i32 %x, 0 + %sub = sub nsw i32 2147483647, %x ; 0x7fffffff + %cmp2 = icmp sgt i32 %x, %sub + %r = select i1 %cmp1, i1 true, i1 %cmp2 + ret i1 %r +} diff --git a/llvm/test/CodeGen/RISCV/pr89833.ll b/llvm/test/CodeGen/RISCV/pr89833.ll new file mode 100644 index 0000000000000000000000000000000000000000..54a985040e758ad960c302ef72b590ae8481ec2c --- /dev/null +++ b/llvm/test/CodeGen/RISCV/pr89833.ll @@ -0,0 +1,16 @@ +; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py +; RUN: llc < %s -mtriple=riscv64 -mattr=+v | FileCheck %s + +declare void @llvm.riscv.masked.strided.store.nxv16i8.p0.i64(, ptr, i64, ) + +define void @test( %value, %mask) { +; CHECK-LABEL: test: +; CHECK: # %bb.0: +; CHECK-NEXT: vsetvli a0, zero, e8, m2, ta, ma +; CHECK-NEXT: vnsrl.wi v12, v8, 0 +; CHECK-NEXT: vse8.v v12, (zero), v0.t +; CHECK-NEXT: ret + %trunc = trunc %value to + call void @llvm.riscv.masked.strided.store.nxv16i8.p0.i64( %trunc, ptr null, i64 1, %mask) + ret void +} diff --git a/llvm/test/CodeGen/RISCV/rv32zba.ll b/llvm/test/CodeGen/RISCV/rv32zba.ll index a78f823d318418dbae1e2b6b416f0f38374583a9..2a72c1288f65cc5a75817ab21551b3cfef580109 100644 --- a/llvm/test/CodeGen/RISCV/rv32zba.ll +++ b/llvm/test/CodeGen/RISCV/rv32zba.ll @@ -407,8 +407,8 @@ define i32 @mul25(i32 %a) { ; ; RV32ZBA-LABEL: mul25: ; RV32ZBA: # %bb.0: -; RV32ZBA-NEXT: sh1add a1, a0, a0 -; RV32ZBA-NEXT: sh3add a0, a1, a0 +; RV32ZBA-NEXT: sh2add a0, a0, a0 +; RV32ZBA-NEXT: sh2add a0, a0, a0 ; RV32ZBA-NEXT: ret %c = mul i32 %a, 25 ret i32 %c @@ -455,8 +455,8 @@ define i32 @mul27(i32 %a) { ; ; RV32ZBA-LABEL: mul27: ; RV32ZBA: # %bb.0: -; RV32ZBA-NEXT: sh3add a0, a0, a0 ; RV32ZBA-NEXT: sh1add a0, a0, a0 +; RV32ZBA-NEXT: sh3add a0, a0, a0 ; RV32ZBA-NEXT: ret %c = mul i32 %a, 27 ret i32 %c @@ -471,8 +471,8 @@ define i32 @mul45(i32 %a) { ; ; RV32ZBA-LABEL: mul45: ; RV32ZBA: # %bb.0: -; RV32ZBA-NEXT: sh3add a0, a0, a0 ; RV32ZBA-NEXT: sh2add a0, a0, a0 +; RV32ZBA-NEXT: sh3add a0, a0, a0 ; RV32ZBA-NEXT: ret %c = mul i32 %a, 45 ret i32 %c diff --git a/llvm/test/CodeGen/RISCV/rv64-legal-i32/rv64zba.ll b/llvm/test/CodeGen/RISCV/rv64-legal-i32/rv64zba.ll index ee9b73ca82f2130ca351bb0784b656a5f8621b9c..c3ae40124ba04b44082e3ca518b0f2a69eb7eac3 100644 --- a/llvm/test/CodeGen/RISCV/rv64-legal-i32/rv64zba.ll +++ b/llvm/test/CodeGen/RISCV/rv64-legal-i32/rv64zba.ll @@ -634,7 +634,6 @@ define i64 @zext_mul288(i32 signext %a) { } ; We can't use slli.uw becaues the shift amount is more than 31. -; FIXME: The zext.w is unneeded. define i64 @zext_mul12884901888(i32 signext %a) { ; RV64I-LABEL: zext_mul12884901888: ; RV64I: # %bb.0: @@ -647,7 +646,6 @@ define i64 @zext_mul12884901888(i32 signext %a) { ; ; RV64ZBA-LABEL: zext_mul12884901888: ; RV64ZBA: # %bb.0: -; RV64ZBA-NEXT: andi a0, a0, -1 ; RV64ZBA-NEXT: sh1add a0, a0, a0 ; RV64ZBA-NEXT: slli a0, a0, 32 ; RV64ZBA-NEXT: ret @@ -657,7 +655,6 @@ define i64 @zext_mul12884901888(i32 signext %a) { } ; We can't use slli.uw becaues the shift amount is more than 31. -; FIXME: The zext.w is unneeded. define i64 @zext_mul21474836480(i32 signext %a) { ; RV64I-LABEL: zext_mul21474836480: ; RV64I: # %bb.0: @@ -670,7 +667,6 @@ define i64 @zext_mul21474836480(i32 signext %a) { ; ; RV64ZBA-LABEL: zext_mul21474836480: ; RV64ZBA: # %bb.0: -; RV64ZBA-NEXT: andi a0, a0, -1 ; RV64ZBA-NEXT: sh2add a0, a0, a0 ; RV64ZBA-NEXT: slli a0, a0, 32 ; RV64ZBA-NEXT: ret @@ -680,7 +676,6 @@ define i64 @zext_mul21474836480(i32 signext %a) { } ; We can't use slli.uw becaues the shift amount is more than 31. -; FIXME: The zext.w is unneeded. define i64 @zext_mul38654705664(i32 signext %a) { ; RV64I-LABEL: zext_mul38654705664: ; RV64I: # %bb.0: @@ -693,7 +688,6 @@ define i64 @zext_mul38654705664(i32 signext %a) { ; ; RV64ZBA-LABEL: zext_mul38654705664: ; RV64ZBA: # %bb.0: -; RV64ZBA-NEXT: andi a0, a0, -1 ; RV64ZBA-NEXT: sh3add a0, a0, a0 ; RV64ZBA-NEXT: slli a0, a0, 32 ; RV64ZBA-NEXT: ret @@ -963,8 +957,8 @@ define i64 @mul25(i64 %a) { ; ; RV64ZBA-LABEL: mul25: ; RV64ZBA: # %bb.0: -; RV64ZBA-NEXT: sh1add a1, a0, a0 -; RV64ZBA-NEXT: sh3add a0, a1, a0 +; RV64ZBA-NEXT: sh2add a0, a0, a0 +; RV64ZBA-NEXT: sh2add a0, a0, a0 ; RV64ZBA-NEXT: ret %c = mul i64 %a, 25 ret i64 %c @@ -1011,8 +1005,8 @@ define i64 @mul27(i64 %a) { ; ; RV64ZBA-LABEL: mul27: ; RV64ZBA: # %bb.0: -; RV64ZBA-NEXT: sh3add a0, a0, a0 ; RV64ZBA-NEXT: sh1add a0, a0, a0 +; RV64ZBA-NEXT: sh3add a0, a0, a0 ; RV64ZBA-NEXT: ret %c = mul i64 %a, 27 ret i64 %c @@ -1027,8 +1021,8 @@ define i64 @mul45(i64 %a) { ; ; RV64ZBA-LABEL: mul45: ; RV64ZBA: # %bb.0: -; RV64ZBA-NEXT: sh3add a0, a0, a0 ; RV64ZBA-NEXT: sh2add a0, a0, a0 +; RV64ZBA-NEXT: sh3add a0, a0, a0 ; RV64ZBA-NEXT: ret %c = mul i64 %a, 45 ret i64 %c diff --git a/llvm/test/CodeGen/RISCV/rv64-legal-i32/rv64zbb-zbkb.ll b/llvm/test/CodeGen/RISCV/rv64-legal-i32/rv64zbb-zbkb.ll index 39a5b9b0f3676c36cf9c1635f116ea6188001b28..c98ad4592a6620b36cf4156ba09bddfe12f3289c 100644 --- a/llvm/test/CodeGen/RISCV/rv64-legal-i32/rv64zbb-zbkb.ll +++ b/llvm/test/CodeGen/RISCV/rv64-legal-i32/rv64zbb-zbkb.ll @@ -102,11 +102,10 @@ declare i32 @llvm.fshl.i32(i32, i32, i32) define signext i32 @rol_i32(i32 signext %a, i32 signext %b) nounwind { ; RV64I-LABEL: rol_i32: ; RV64I: # %bb.0: -; RV64I-NEXT: andi a2, a1, -1 -; RV64I-NEXT: sllw a1, a0, a1 -; RV64I-NEXT: negw a2, a2 -; RV64I-NEXT: srlw a0, a0, a2 -; RV64I-NEXT: or a0, a1, a0 +; RV64I-NEXT: sllw a2, a0, a1 +; RV64I-NEXT: negw a1, a1 +; RV64I-NEXT: srlw a0, a0, a1 +; RV64I-NEXT: or a0, a2, a0 ; RV64I-NEXT: ret ; ; RV64ZBB-ZBKB-LABEL: rol_i32: @@ -121,11 +120,10 @@ define signext i32 @rol_i32(i32 signext %a, i32 signext %b) nounwind { define void @rol_i32_nosext(i32 signext %a, i32 signext %b, ptr %x) nounwind { ; RV64I-LABEL: rol_i32_nosext: ; RV64I: # %bb.0: -; RV64I-NEXT: andi a3, a1, -1 -; RV64I-NEXT: sllw a1, a0, a1 -; RV64I-NEXT: negw a3, a3 -; RV64I-NEXT: srlw a0, a0, a3 -; RV64I-NEXT: or a0, a1, a0 +; RV64I-NEXT: sllw a3, a0, a1 +; RV64I-NEXT: negw a1, a1 +; RV64I-NEXT: srlw a0, a0, a1 +; RV64I-NEXT: or a0, a3, a0 ; RV64I-NEXT: sw a0, 0(a2) ; RV64I-NEXT: ret ; @@ -142,12 +140,11 @@ define void @rol_i32_nosext(i32 signext %a, i32 signext %b, ptr %x) nounwind { define signext i32 @rol_i32_neg_constant_rhs(i32 signext %a) nounwind { ; RV64I-LABEL: rol_i32_neg_constant_rhs: ; RV64I: # %bb.0: -; RV64I-NEXT: andi a1, a0, -1 -; RV64I-NEXT: li a2, -2 -; RV64I-NEXT: sllw a0, a2, a0 -; RV64I-NEXT: negw a1, a1 -; RV64I-NEXT: srlw a1, a2, a1 -; RV64I-NEXT: or a0, a0, a1 +; RV64I-NEXT: li a1, -2 +; RV64I-NEXT: sllw a2, a1, a0 +; RV64I-NEXT: negw a0, a0 +; RV64I-NEXT: srlw a0, a1, a0 +; RV64I-NEXT: or a0, a2, a0 ; RV64I-NEXT: ret ; ; RV64ZBB-ZBKB-LABEL: rol_i32_neg_constant_rhs: @@ -183,11 +180,10 @@ declare i32 @llvm.fshr.i32(i32, i32, i32) define signext i32 @ror_i32(i32 signext %a, i32 signext %b) nounwind { ; RV64I-LABEL: ror_i32: ; RV64I: # %bb.0: -; RV64I-NEXT: andi a2, a1, -1 -; RV64I-NEXT: srlw a1, a0, a1 -; RV64I-NEXT: negw a2, a2 -; RV64I-NEXT: sllw a0, a0, a2 -; RV64I-NEXT: or a0, a1, a0 +; RV64I-NEXT: srlw a2, a0, a1 +; RV64I-NEXT: negw a1, a1 +; RV64I-NEXT: sllw a0, a0, a1 +; RV64I-NEXT: or a0, a2, a0 ; RV64I-NEXT: ret ; ; RV64ZBB-ZBKB-LABEL: ror_i32: @@ -202,11 +198,10 @@ define signext i32 @ror_i32(i32 signext %a, i32 signext %b) nounwind { define void @ror_i32_nosext(i32 signext %a, i32 signext %b, ptr %x) nounwind { ; RV64I-LABEL: ror_i32_nosext: ; RV64I: # %bb.0: -; RV64I-NEXT: andi a3, a1, -1 -; RV64I-NEXT: srlw a1, a0, a1 -; RV64I-NEXT: negw a3, a3 -; RV64I-NEXT: sllw a0, a0, a3 -; RV64I-NEXT: or a0, a1, a0 +; RV64I-NEXT: srlw a3, a0, a1 +; RV64I-NEXT: negw a1, a1 +; RV64I-NEXT: sllw a0, a0, a1 +; RV64I-NEXT: or a0, a3, a0 ; RV64I-NEXT: sw a0, 0(a2) ; RV64I-NEXT: ret ; @@ -223,12 +218,11 @@ define void @ror_i32_nosext(i32 signext %a, i32 signext %b, ptr %x) nounwind { define signext i32 @ror_i32_neg_constant_rhs(i32 signext %a) nounwind { ; RV64I-LABEL: ror_i32_neg_constant_rhs: ; RV64I: # %bb.0: -; RV64I-NEXT: andi a1, a0, -1 -; RV64I-NEXT: li a2, -2 -; RV64I-NEXT: srlw a0, a2, a0 -; RV64I-NEXT: negw a1, a1 -; RV64I-NEXT: sllw a1, a2, a1 -; RV64I-NEXT: or a0, a0, a1 +; RV64I-NEXT: li a1, -2 +; RV64I-NEXT: srlw a2, a1, a0 +; RV64I-NEXT: negw a0, a0 +; RV64I-NEXT: sllw a0, a1, a0 +; RV64I-NEXT: or a0, a2, a0 ; RV64I-NEXT: ret ; ; RV64ZBB-ZBKB-LABEL: ror_i32_neg_constant_rhs: diff --git a/llvm/test/CodeGen/RISCV/rv64-legal-i32/xaluo.ll b/llvm/test/CodeGen/RISCV/rv64-legal-i32/xaluo.ll index 3c1b76818781a188756deb7f6691d0d85ccad91d..1c794a1bd1684d8d691bd9adc3fbbeaf2dfa0498 100644 --- a/llvm/test/CodeGen/RISCV/rv64-legal-i32/xaluo.ll +++ b/llvm/test/CodeGen/RISCV/rv64-legal-i32/xaluo.ll @@ -731,12 +731,13 @@ define zeroext i1 @smulo2.i64(i64 %v1, ptr %res) { ; RV64ZBA-LABEL: smulo2.i64: ; RV64ZBA: # %bb.0: # %entry ; RV64ZBA-NEXT: li a2, 13 -; RV64ZBA-NEXT: mulh a3, a0, a2 -; RV64ZBA-NEXT: mul a2, a0, a2 -; RV64ZBA-NEXT: srai a0, a2, 63 -; RV64ZBA-NEXT: xor a0, a3, a0 +; RV64ZBA-NEXT: mulh a2, a0, a2 +; RV64ZBA-NEXT: sh1add a3, a0, a0 +; RV64ZBA-NEXT: sh2add a3, a3, a0 +; RV64ZBA-NEXT: srai a0, a3, 63 +; RV64ZBA-NEXT: xor a0, a2, a0 ; RV64ZBA-NEXT: snez a0, a0 -; RV64ZBA-NEXT: sd a2, 0(a1) +; RV64ZBA-NEXT: sd a3, 0(a1) ; RV64ZBA-NEXT: ret ; ; RV64ZICOND-LABEL: smulo2.i64: @@ -809,9 +810,9 @@ define zeroext i1 @umulo2.i32(i32 signext %v1, ptr %res) { ; ; RV64ZBA-LABEL: umulo2.i32: ; RV64ZBA: # %bb.0: # %entry -; RV64ZBA-NEXT: zext.w a0, a0 -; RV64ZBA-NEXT: sh1add a2, a0, a0 -; RV64ZBA-NEXT: sh2add a2, a2, a0 +; RV64ZBA-NEXT: zext.w a2, a0 +; RV64ZBA-NEXT: sh1add.uw a0, a0, a2 +; RV64ZBA-NEXT: sh2add a2, a0, a2 ; RV64ZBA-NEXT: srli a0, a2, 32 ; RV64ZBA-NEXT: snez a0, a0 ; RV64ZBA-NEXT: sw a2, 0(a1) @@ -925,10 +926,11 @@ define zeroext i1 @umulo2.i64(i64 %v1, ptr %res) { ; ; RV64ZBA-LABEL: umulo2.i64: ; RV64ZBA: # %bb.0: # %entry -; RV64ZBA-NEXT: li a3, 13 -; RV64ZBA-NEXT: mulhu a2, a0, a3 +; RV64ZBA-NEXT: li a2, 13 +; RV64ZBA-NEXT: mulhu a2, a0, a2 ; RV64ZBA-NEXT: snez a2, a2 -; RV64ZBA-NEXT: mul a0, a0, a3 +; RV64ZBA-NEXT: sh1add a3, a0, a0 +; RV64ZBA-NEXT: sh2add a0, a3, a0 ; RV64ZBA-NEXT: sd a0, 0(a1) ; RV64ZBA-NEXT: mv a0, a2 ; RV64ZBA-NEXT: ret diff --git a/llvm/test/CodeGen/RISCV/rv64i-demanded-bits.ll b/llvm/test/CodeGen/RISCV/rv64i-demanded-bits.ll index 6a441e2b9f67fb1add5e4a77bb5b3fafd20573fd..b8c43289bdfed21a9b3f5297418a4c3536c347e8 100644 --- a/llvm/test/CodeGen/RISCV/rv64i-demanded-bits.ll +++ b/llvm/test/CodeGen/RISCV/rv64i-demanded-bits.ll @@ -192,3 +192,17 @@ entry: %or = or i32 %and, 255 ret i32 %or } + +define i64 @and_allones(i32 signext %x) { +; CHECK-LABEL: and_allones: +; CHECK: # %bb.0: # %entry +; CHECK-NEXT: addi a0, a0, -1 +; CHECK-NEXT: li a1, 1 +; CHECK-NEXT: sll a0, a1, a0 +; CHECK-NEXT: ret +entry: + %y = zext i32 %x to i64 + %shamt = add nsw i64 %y, -1 + %ret = shl i64 1, %shamt + ret i64 %ret +} diff --git a/llvm/test/CodeGen/RISCV/rv64xtheadba.ll b/llvm/test/CodeGen/RISCV/rv64xtheadba.ll index 46e474a2d1edea8af928499d3323ff4084df95d5..7754128370d66a5b363df252a483d1e11ed175b0 100644 --- a/llvm/test/CodeGen/RISCV/rv64xtheadba.ll +++ b/llvm/test/CodeGen/RISCV/rv64xtheadba.ll @@ -389,8 +389,8 @@ define i64 @mul27(i64 %a) { ; ; RV64XTHEADBA-LABEL: mul27: ; RV64XTHEADBA: # %bb.0: -; RV64XTHEADBA-NEXT: th.addsl a0, a0, a0, 3 ; RV64XTHEADBA-NEXT: th.addsl a0, a0, a0, 1 +; RV64XTHEADBA-NEXT: th.addsl a0, a0, a0, 3 ; RV64XTHEADBA-NEXT: ret %c = mul i64 %a, 27 ret i64 %c @@ -405,8 +405,8 @@ define i64 @mul45(i64 %a) { ; ; RV64XTHEADBA-LABEL: mul45: ; RV64XTHEADBA: # %bb.0: -; RV64XTHEADBA-NEXT: th.addsl a0, a0, a0, 3 ; RV64XTHEADBA-NEXT: th.addsl a0, a0, a0, 2 +; RV64XTHEADBA-NEXT: th.addsl a0, a0, a0, 3 ; RV64XTHEADBA-NEXT: ret %c = mul i64 %a, 45 ret i64 %c diff --git a/llvm/test/CodeGen/RISCV/rv64zba.ll b/llvm/test/CodeGen/RISCV/rv64zba.ll index ccb23fc2bbfa36c8ddf0121677fd5ec073160b55..817e2b7d0bd9937da490f2c3dcaf3751d805dc7b 100644 --- a/llvm/test/CodeGen/RISCV/rv64zba.ll +++ b/llvm/test/CodeGen/RISCV/rv64zba.ll @@ -4,7 +4,9 @@ ; RUN: llc -mtriple=riscv64 -mattr=+m,+zba -verify-machineinstrs < %s \ ; RUN: | FileCheck %s -check-prefixes=CHECK,RV64ZBA,RV64ZBANOZBB ; RUN: llc -mtriple=riscv64 -mattr=+m,+zba,+zbb -verify-machineinstrs < %s \ -; RUN: | FileCheck %s -check-prefixes=CHECK,RV64ZBA,RV64ZBAZBB +; RUN: | FileCheck %s -check-prefixes=CHECK,RV64ZBA,RV64ZBAZBB,RV64ZBAZBBNOZBS +; RUN: llc -mtriple=riscv64 -mattr=+m,+zba,+zbb,+zbs -verify-machineinstrs < %s \ +; RUN: | FileCheck %s -check-prefixes=CHECK,RV64ZBA,RV64ZBAZBB,RV64ZBAZBBZBS define i64 @slliuw(i64 %a) nounwind { ; RV64I-LABEL: slliuw: @@ -641,31 +643,52 @@ define i64 @mul96(i64 %a) { } define i64 @mul119(i64 %a) { -; CHECK-LABEL: mul119: -; CHECK: # %bb.0: -; CHECK-NEXT: li a1, 119 -; CHECK-NEXT: mul a0, a0, a1 -; CHECK-NEXT: ret +; RV64I-LABEL: mul119: +; RV64I: # %bb.0: +; RV64I-NEXT: li a1, 119 +; RV64I-NEXT: mul a0, a0, a1 +; RV64I-NEXT: ret +; +; RV64ZBA-LABEL: mul119: +; RV64ZBA: # %bb.0: +; RV64ZBA-NEXT: sh3add a1, a0, a0 +; RV64ZBA-NEXT: slli a0, a0, 7 +; RV64ZBA-NEXT: sub a0, a0, a1 +; RV64ZBA-NEXT: ret %c = mul i64 %a, 119 ret i64 %c } define i64 @mul123(i64 %a) { -; CHECK-LABEL: mul123: -; CHECK: # %bb.0: -; CHECK-NEXT: li a1, 123 -; CHECK-NEXT: mul a0, a0, a1 -; CHECK-NEXT: ret +; RV64I-LABEL: mul123: +; RV64I: # %bb.0: +; RV64I-NEXT: li a1, 123 +; RV64I-NEXT: mul a0, a0, a1 +; RV64I-NEXT: ret +; +; RV64ZBA-LABEL: mul123: +; RV64ZBA: # %bb.0: +; RV64ZBA-NEXT: sh2add a1, a0, a0 +; RV64ZBA-NEXT: slli a0, a0, 7 +; RV64ZBA-NEXT: sub a0, a0, a1 +; RV64ZBA-NEXT: ret %c = mul i64 %a, 123 ret i64 %c } define i64 @mul125(i64 %a) { -; CHECK-LABEL: mul125: -; CHECK: # %bb.0: -; CHECK-NEXT: li a1, 125 -; CHECK-NEXT: mul a0, a0, a1 -; CHECK-NEXT: ret +; RV64I-LABEL: mul125: +; RV64I: # %bb.0: +; RV64I-NEXT: li a1, 125 +; RV64I-NEXT: mul a0, a0, a1 +; RV64I-NEXT: ret +; +; RV64ZBA-LABEL: mul125: +; RV64ZBA: # %bb.0: +; RV64ZBA-NEXT: sh1add a1, a0, a0 +; RV64ZBA-NEXT: slli a0, a0, 7 +; RV64ZBA-NEXT: sub a0, a0, a1 +; RV64ZBA-NEXT: ret %c = mul i64 %a, 125 ret i64 %c } @@ -753,6 +776,25 @@ define i64 @mul288(i64 %a) { ret i64 %c } +define i64 @zext_mul68(i32 signext %a) { +; RV64I-LABEL: zext_mul68: +; RV64I: # %bb.0: +; RV64I-NEXT: li a1, 17 +; RV64I-NEXT: slli a1, a1, 34 +; RV64I-NEXT: slli a0, a0, 32 +; RV64I-NEXT: mulhu a0, a0, a1 +; RV64I-NEXT: ret +; +; RV64ZBA-LABEL: zext_mul68: +; RV64ZBA: # %bb.0: +; RV64ZBA-NEXT: slli.uw a1, a0, 6 +; RV64ZBA-NEXT: sh2add.uw a0, a0, a1 +; RV64ZBA-NEXT: ret + %b = zext i32 %a to i64 + %c = mul i64 %b, 68 + ret i64 %c +} + define i64 @zext_mul96(i32 signext %a) { ; RV64I-LABEL: zext_mul96: ; RV64I: # %bb.0: @@ -811,7 +853,6 @@ define i64 @zext_mul288(i32 signext %a) { } ; We can't use slli.uw becaues the shift amount is more than 31. -; FIXME: The zext.w is unneeded. define i64 @zext_mul12884901888(i32 signext %a) { ; RV64I-LABEL: zext_mul12884901888: ; RV64I: # %bb.0: @@ -824,7 +865,6 @@ define i64 @zext_mul12884901888(i32 signext %a) { ; ; RV64ZBA-LABEL: zext_mul12884901888: ; RV64ZBA: # %bb.0: -; RV64ZBA-NEXT: andi a0, a0, -1 ; RV64ZBA-NEXT: sh1add a0, a0, a0 ; RV64ZBA-NEXT: slli a0, a0, 32 ; RV64ZBA-NEXT: ret @@ -834,7 +874,6 @@ define i64 @zext_mul12884901888(i32 signext %a) { } ; We can't use slli.uw becaues the shift amount is more than 31. -; FIXME: The zext.w is unneeded. define i64 @zext_mul21474836480(i32 signext %a) { ; RV64I-LABEL: zext_mul21474836480: ; RV64I: # %bb.0: @@ -847,7 +886,6 @@ define i64 @zext_mul21474836480(i32 signext %a) { ; ; RV64ZBA-LABEL: zext_mul21474836480: ; RV64ZBA: # %bb.0: -; RV64ZBA-NEXT: andi a0, a0, -1 ; RV64ZBA-NEXT: sh2add a0, a0, a0 ; RV64ZBA-NEXT: slli a0, a0, 32 ; RV64ZBA-NEXT: ret @@ -857,7 +895,6 @@ define i64 @zext_mul21474836480(i32 signext %a) { } ; We can't use slli.uw becaues the shift amount is more than 31. -; FIXME: The zext.w is unneeded. define i64 @zext_mul38654705664(i32 signext %a) { ; RV64I-LABEL: zext_mul38654705664: ; RV64I: # %bb.0: @@ -870,7 +907,6 @@ define i64 @zext_mul38654705664(i32 signext %a) { ; ; RV64ZBA-LABEL: zext_mul38654705664: ; RV64ZBA: # %bb.0: -; RV64ZBA-NEXT: andi a0, a0, -1 ; RV64ZBA-NEXT: sh3add a0, a0, a0 ; RV64ZBA-NEXT: slli a0, a0, 32 ; RV64ZBA-NEXT: ret @@ -1140,8 +1176,8 @@ define i64 @mul25(i64 %a) { ; ; RV64ZBA-LABEL: mul25: ; RV64ZBA: # %bb.0: -; RV64ZBA-NEXT: sh1add a1, a0, a0 -; RV64ZBA-NEXT: sh3add a0, a1, a0 +; RV64ZBA-NEXT: sh2add a0, a0, a0 +; RV64ZBA-NEXT: sh2add a0, a0, a0 ; RV64ZBA-NEXT: ret %c = mul i64 %a, 25 ret i64 %c @@ -1188,8 +1224,8 @@ define i64 @mul27(i64 %a) { ; ; RV64ZBA-LABEL: mul27: ; RV64ZBA: # %bb.0: -; RV64ZBA-NEXT: sh3add a0, a0, a0 ; RV64ZBA-NEXT: sh1add a0, a0, a0 +; RV64ZBA-NEXT: sh3add a0, a0, a0 ; RV64ZBA-NEXT: ret %c = mul i64 %a, 27 ret i64 %c @@ -1204,8 +1240,8 @@ define i64 @mul45(i64 %a) { ; ; RV64ZBA-LABEL: mul45: ; RV64ZBA: # %bb.0: -; RV64ZBA-NEXT: sh3add a0, a0, a0 ; RV64ZBA-NEXT: sh2add a0, a0, a0 +; RV64ZBA-NEXT: sh3add a0, a0, a0 ; RV64ZBA-NEXT: ret %c = mul i64 %a, 45 ret i64 %c @@ -2699,3 +2735,121 @@ define i64 @mul_neg8(i64 %a) { %c = mul i64 %a, -8 ret i64 %c } + +define i64 @bext_mul12(i32 %1, i32 %2) { +; RV64I-LABEL: bext_mul12: +; RV64I: # %bb.0: # %entry +; RV64I-NEXT: srlw a0, a0, a1 +; RV64I-NEXT: andi a0, a0, 1 +; RV64I-NEXT: li a1, 12 +; RV64I-NEXT: mul a0, a0, a1 +; RV64I-NEXT: ret +; +; RV64ZBANOZBB-LABEL: bext_mul12: +; RV64ZBANOZBB: # %bb.0: # %entry +; RV64ZBANOZBB-NEXT: srlw a0, a0, a1 +; RV64ZBANOZBB-NEXT: andi a0, a0, 1 +; RV64ZBANOZBB-NEXT: sh1add a0, a0, a0 +; RV64ZBANOZBB-NEXT: slli a0, a0, 2 +; RV64ZBANOZBB-NEXT: ret +; +; RV64ZBAZBBNOZBS-LABEL: bext_mul12: +; RV64ZBAZBBNOZBS: # %bb.0: # %entry +; RV64ZBAZBBNOZBS-NEXT: srlw a0, a0, a1 +; RV64ZBAZBBNOZBS-NEXT: andi a0, a0, 1 +; RV64ZBAZBBNOZBS-NEXT: sh1add a0, a0, a0 +; RV64ZBAZBBNOZBS-NEXT: slli a0, a0, 2 +; RV64ZBAZBBNOZBS-NEXT: ret +; +; RV64ZBAZBBZBS-LABEL: bext_mul12: +; RV64ZBAZBBZBS: # %bb.0: # %entry +; RV64ZBAZBBZBS-NEXT: bext a0, a0, a1 +; RV64ZBAZBBZBS-NEXT: sh1add a0, a0, a0 +; RV64ZBAZBBZBS-NEXT: slli a0, a0, 2 +; RV64ZBAZBBZBS-NEXT: ret +entry: + %3 = lshr i32 %1, %2 + %4 = and i32 %3, 1 + %5 = zext nneg i32 %4 to i64 + %6 = mul i64 %5, 12 + ret i64 %6 +} + +define i64 @bext_mul45(i32 %1, i32 %2) { +; RV64I-LABEL: bext_mul45: +; RV64I: # %bb.0: # %entry +; RV64I-NEXT: srlw a0, a0, a1 +; RV64I-NEXT: andi a0, a0, 1 +; RV64I-NEXT: li a1, 45 +; RV64I-NEXT: mul a0, a0, a1 +; RV64I-NEXT: ret +; +; RV64ZBANOZBB-LABEL: bext_mul45: +; RV64ZBANOZBB: # %bb.0: # %entry +; RV64ZBANOZBB-NEXT: srlw a0, a0, a1 +; RV64ZBANOZBB-NEXT: andi a0, a0, 1 +; RV64ZBANOZBB-NEXT: sh2add a0, a0, a0 +; RV64ZBANOZBB-NEXT: sh3add a0, a0, a0 +; RV64ZBANOZBB-NEXT: ret +; +; RV64ZBAZBBNOZBS-LABEL: bext_mul45: +; RV64ZBAZBBNOZBS: # %bb.0: # %entry +; RV64ZBAZBBNOZBS-NEXT: srlw a0, a0, a1 +; RV64ZBAZBBNOZBS-NEXT: andi a0, a0, 1 +; RV64ZBAZBBNOZBS-NEXT: sh2add a0, a0, a0 +; RV64ZBAZBBNOZBS-NEXT: sh3add a0, a0, a0 +; RV64ZBAZBBNOZBS-NEXT: ret +; +; RV64ZBAZBBZBS-LABEL: bext_mul45: +; RV64ZBAZBBZBS: # %bb.0: # %entry +; RV64ZBAZBBZBS-NEXT: bext a0, a0, a1 +; RV64ZBAZBBZBS-NEXT: sh2add a0, a0, a0 +; RV64ZBAZBBZBS-NEXT: sh3add a0, a0, a0 +; RV64ZBAZBBZBS-NEXT: ret +entry: + %3 = lshr i32 %1, %2 + %4 = and i32 %3, 1 + %5 = zext nneg i32 %4 to i64 + %6 = mul i64 %5, 45 + ret i64 %6 +} + +define i64 @bext_mul132(i32 %1, i32 %2) { +; RV64I-LABEL: bext_mul132: +; RV64I: # %bb.0: # %entry +; RV64I-NEXT: srlw a0, a0, a1 +; RV64I-NEXT: andi a0, a0, 1 +; RV64I-NEXT: li a1, 132 +; RV64I-NEXT: mul a0, a0, a1 +; RV64I-NEXT: ret +; +; RV64ZBANOZBB-LABEL: bext_mul132: +; RV64ZBANOZBB: # %bb.0: # %entry +; RV64ZBANOZBB-NEXT: srlw a0, a0, a1 +; RV64ZBANOZBB-NEXT: andi a0, a0, 1 +; RV64ZBANOZBB-NEXT: slli a1, a0, 7 +; RV64ZBANOZBB-NEXT: sh2add a0, a0, a1 +; RV64ZBANOZBB-NEXT: ret +; +; RV64ZBAZBBNOZBS-LABEL: bext_mul132: +; RV64ZBAZBBNOZBS: # %bb.0: # %entry +; RV64ZBAZBBNOZBS-NEXT: srlw a0, a0, a1 +; RV64ZBAZBBNOZBS-NEXT: andi a0, a0, 1 +; RV64ZBAZBBNOZBS-NEXT: slli a1, a0, 7 +; RV64ZBAZBBNOZBS-NEXT: sh2add a0, a0, a1 +; RV64ZBAZBBNOZBS-NEXT: ret +; +; RV64ZBAZBBZBS-LABEL: bext_mul132: +; RV64ZBAZBBZBS: # %bb.0: # %entry +; RV64ZBAZBBZBS-NEXT: bext a0, a0, a1 +; RV64ZBAZBBZBS-NEXT: slli a1, a0, 7 +; RV64ZBAZBBZBS-NEXT: sh2add a0, a0, a1 +; RV64ZBAZBBZBS-NEXT: ret +entry: + %3 = lshr i32 %1, %2 + %4 = and i32 %3, 1 + %5 = zext nneg i32 %4 to i64 + %6 = mul i64 %5, 132 + ret i64 %6 +} + diff --git a/llvm/test/CodeGen/RISCV/rvv/commutable.ll b/llvm/test/CodeGen/RISCV/rvv/commutable.ll new file mode 100644 index 0000000000000000000000000000000000000000..b59df3b743cd52febac3abc8fb75c02b4478ea8f --- /dev/null +++ b/llvm/test/CodeGen/RISCV/rvv/commutable.ll @@ -0,0 +1,651 @@ +; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py +; RUN: sed 's/iXLen/i32/g' %s | llc -mtriple=riscv32 -mattr=+f,+d,+zvfh,+v \ +; RUN: -verify-machineinstrs | FileCheck %s +; RUN: sed 's/iXLen/i64/g' %s | llc -mtriple=riscv64 -mattr=+f,+d,+zvfh,+v \ +; RUN: -verify-machineinstrs | FileCheck %s + +; vadd.vv +declare @llvm.riscv.vadd.nxv1i64.nxv1i64(, , , iXLen); +define @commutable_vadd_vv( %0, %1, iXLen %2) nounwind { +; CHECK-LABEL: commutable_vadd_vv: +; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, ma +; CHECK-NEXT: vadd.vv v8, v8, v9 +; CHECK-NEXT: vsetvli a0, zero, e64, m1, ta, ma +; CHECK-NEXT: vadd.vv v8, v8, v8 +; CHECK-NEXT: ret +entry: + %a = call @llvm.riscv.vadd.nxv1i64.nxv1i64( undef, %0, %1, iXLen %2) + %b = call @llvm.riscv.vadd.nxv1i64.nxv1i64( undef, %1, %0, iXLen %2) + %ret = add %a, %b + ret %ret +} + +declare @llvm.riscv.vadd.mask.nxv1i64.nxv1i64(, , , , iXLen, iXLen); +define @commutable_vadd_vv_masked( %0, %1, %mask, iXLen %2) { +; CHECK-LABEL: commutable_vadd_vv_masked: +; CHECK: # %bb.0: +; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, ma +; CHECK-NEXT: vadd.vv v10, v8, v9, v0.t +; CHECK-NEXT: vadd.vv v8, v8, v9, v0.t +; CHECK-NEXT: vsetvli a0, zero, e64, m1, ta, ma +; CHECK-NEXT: vadd.vv v8, v10, v8 +; CHECK-NEXT: ret + %a = call @llvm.riscv.vadd.mask.nxv1i64.nxv1i64( undef, %0, %1, %mask, iXLen %2, iXLen 1) + %b = call @llvm.riscv.vadd.mask.nxv1i64.nxv1i64( undef, %1, %0, %mask, iXLen %2, iXLen 1) + %ret = add %a, %b + ret %ret +} + +; vand.vv +declare @llvm.riscv.vand.nxv1i64.nxv1i64(, , , iXLen); +define @commutable_vand_vv( %0, %1, iXLen %2) nounwind { +; CHECK-LABEL: commutable_vand_vv: +; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, ma +; CHECK-NEXT: vand.vv v8, v8, v9 +; CHECK-NEXT: vsetvli a0, zero, e64, m1, ta, ma +; CHECK-NEXT: vadd.vv v8, v8, v8 +; CHECK-NEXT: ret +entry: + %a = call @llvm.riscv.vand.nxv1i64.nxv1i64( undef, %0, %1, iXLen %2) + %b = call @llvm.riscv.vand.nxv1i64.nxv1i64( undef, %1, %0, iXLen %2) + %ret = add %a, %b + ret %ret +} + +declare @llvm.riscv.vand.mask.nxv1i64.nxv1i64(, , , , iXLen, iXLen); +define @commutable_vand_vv_masked( %0, %1, %mask, iXLen %2) { +; CHECK-LABEL: commutable_vand_vv_masked: +; CHECK: # %bb.0: +; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, ma +; CHECK-NEXT: vand.vv v10, v8, v9, v0.t +; CHECK-NEXT: vand.vv v8, v8, v9, v0.t +; CHECK-NEXT: vsetvli a0, zero, e64, m1, ta, ma +; CHECK-NEXT: vadd.vv v8, v10, v8 +; CHECK-NEXT: ret + %a = call @llvm.riscv.vand.mask.nxv1i64.nxv1i64( undef, %0, %1, %mask, iXLen %2, iXLen 1) + %b = call @llvm.riscv.vand.mask.nxv1i64.nxv1i64( undef, %1, %0, %mask, iXLen %2, iXLen 1) + %ret = add %a, %b + ret %ret +} + +; vor.vv +declare @llvm.riscv.vor.nxv1i64.nxv1i64(, , , iXLen); +define @commutable_vor_vv( %0, %1, iXLen %2) nounwind { +; CHECK-LABEL: commutable_vor_vv: +; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, ma +; CHECK-NEXT: vor.vv v8, v8, v9 +; CHECK-NEXT: vsetvli a0, zero, e64, m1, ta, ma +; CHECK-NEXT: vadd.vv v8, v8, v8 +; CHECK-NEXT: ret +entry: + %a = call @llvm.riscv.vor.nxv1i64.nxv1i64( undef, %0, %1, iXLen %2) + %b = call @llvm.riscv.vor.nxv1i64.nxv1i64( undef, %1, %0, iXLen %2) + %ret = add %a, %b + ret %ret +} + +declare @llvm.riscv.vor.mask.nxv1i64.nxv1i64(, , , , iXLen, iXLen); +define @commutable_vor_vv_masked( %0, %1, %mask, iXLen %2) { +; CHECK-LABEL: commutable_vor_vv_masked: +; CHECK: # %bb.0: +; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, ma +; CHECK-NEXT: vor.vv v10, v8, v9, v0.t +; CHECK-NEXT: vor.vv v8, v8, v9, v0.t +; CHECK-NEXT: vsetvli a0, zero, e64, m1, ta, ma +; CHECK-NEXT: vadd.vv v8, v10, v8 +; CHECK-NEXT: ret + %a = call @llvm.riscv.vor.mask.nxv1i64.nxv1i64( undef, %0, %1, %mask, iXLen %2, iXLen 1) + %b = call @llvm.riscv.vor.mask.nxv1i64.nxv1i64( undef, %1, %0, %mask, iXLen %2, iXLen 1) + %ret = add %a, %b + ret %ret +} + +; vxor.vv +declare @llvm.riscv.vxor.nxv1i64.nxv1i64(, , , iXLen); +define @commutable_vxor_vv( %0, %1, iXLen %2) nounwind { +; CHECK-LABEL: commutable_vxor_vv: +; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, ma +; CHECK-NEXT: vxor.vv v8, v8, v9 +; CHECK-NEXT: vsetvli a0, zero, e64, m1, ta, ma +; CHECK-NEXT: vadd.vv v8, v8, v8 +; CHECK-NEXT: ret +entry: + %a = call @llvm.riscv.vxor.nxv1i64.nxv1i64( undef, %0, %1, iXLen %2) + %b = call @llvm.riscv.vxor.nxv1i64.nxv1i64( undef, %1, %0, iXLen %2) + %ret = add %a, %b + ret %ret +} + +declare @llvm.riscv.vxor.mask.nxv1i64.nxv1i64(, , , , iXLen, iXLen); +define @commutable_vxor_vv_masked( %0, %1, %mask, iXLen %2) { +; CHECK-LABEL: commutable_vxor_vv_masked: +; CHECK: # %bb.0: +; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, ma +; CHECK-NEXT: vxor.vv v10, v8, v9, v0.t +; CHECK-NEXT: vxor.vv v8, v8, v9, v0.t +; CHECK-NEXT: vsetvli a0, zero, e64, m1, ta, ma +; CHECK-NEXT: vadd.vv v8, v10, v8 +; CHECK-NEXT: ret + %a = call @llvm.riscv.vxor.mask.nxv1i64.nxv1i64( undef, %0, %1, %mask, iXLen %2, iXLen 1) + %b = call @llvm.riscv.vxor.mask.nxv1i64.nxv1i64( undef, %1, %0, %mask, iXLen %2, iXLen 1) + %ret = add %a, %b + ret %ret +} + +; vmseq.vv +declare @llvm.riscv.vmseq.nxv1i64(, , iXLen); +define @commutable_vmseq_vv( %0, %1, iXLen %2) nounwind { +; CHECK-LABEL: commutable_vmseq_vv: +; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, ma +; CHECK-NEXT: vmseq.vv v8, v8, v9 +; CHECK-NEXT: vsetvli a0, zero, e8, mf8, ta, ma +; CHECK-NEXT: vmxor.mm v0, v8, v8 +; CHECK-NEXT: ret +entry: + %a = call @llvm.riscv.vmseq.nxv1i64( %0, %1, iXLen %2) + %b = call @llvm.riscv.vmseq.nxv1i64( %1, %0, iXLen %2) + %ret = add %a, %b + ret %ret +} + +declare @llvm.riscv.vmseq.mask.nxv1i64(, , , , iXLen); +define @commutable_vmseq_vv_masked( %0, %1, %mask, iXLen %2) { +; CHECK-LABEL: commutable_vmseq_vv_masked: +; CHECK: # %bb.0: +; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, ma +; CHECK-NEXT: vmseq.vv v10, v8, v9, v0.t +; CHECK-NEXT: vmseq.vv v8, v8, v9, v0.t +; CHECK-NEXT: vsetvli a0, zero, e8, mf8, ta, ma +; CHECK-NEXT: vmxor.mm v0, v10, v8 +; CHECK-NEXT: ret + %a = call @llvm.riscv.vmseq.mask.nxv1i64( undef, %0, %1, %mask, iXLen %2) + %b = call @llvm.riscv.vmseq.mask.nxv1i64( undef, %1, %0, %mask, iXLen %2) + %ret = add %a, %b + ret %ret +} + +; vmsne.vv +declare @llvm.riscv.vmsne.nxv1i64(, , iXLen); +define @commutable_vmsne_vv( %0, %1, iXLen %2) nounwind { +; CHECK-LABEL: commutable_vmsne_vv: +; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, ma +; CHECK-NEXT: vmsne.vv v8, v8, v9 +; CHECK-NEXT: vsetvli a0, zero, e8, mf8, ta, ma +; CHECK-NEXT: vmxor.mm v0, v8, v8 +; CHECK-NEXT: ret +entry: + %a = call @llvm.riscv.vmsne.nxv1i64( %0, %1, iXLen %2) + %b = call @llvm.riscv.vmsne.nxv1i64( %1, %0, iXLen %2) + %ret = add %a, %b + ret %ret +} + +declare @llvm.riscv.vmsne.mask.nxv1i64(, , , , iXLen); +define @commutable_vmsne_vv_masked( %0, %1, %mask, iXLen %2) { +; CHECK-LABEL: commutable_vmsne_vv_masked: +; CHECK: # %bb.0: +; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, ma +; CHECK-NEXT: vmsne.vv v10, v8, v9, v0.t +; CHECK-NEXT: vmsne.vv v8, v8, v9, v0.t +; CHECK-NEXT: vsetvli a0, zero, e8, mf8, ta, ma +; CHECK-NEXT: vmxor.mm v0, v10, v8 +; CHECK-NEXT: ret + %a = call @llvm.riscv.vmsne.mask.nxv1i64( undef, %0, %1, %mask, iXLen %2) + %b = call @llvm.riscv.vmsne.mask.nxv1i64( undef, %1, %0, %mask, iXLen %2) + %ret = add %a, %b + ret %ret +} + +; vmin.vv +declare @llvm.riscv.vmin.nxv1i64.nxv1i64(, , , iXLen); +define @commutable_vmin_vv( %0, %1, iXLen %2) nounwind { +; CHECK-LABEL: commutable_vmin_vv: +; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, ma +; CHECK-NEXT: vmin.vv v8, v8, v9 +; CHECK-NEXT: vsetvli a0, zero, e64, m1, ta, ma +; CHECK-NEXT: vadd.vv v8, v8, v8 +; CHECK-NEXT: ret +entry: + %a = call @llvm.riscv.vmin.nxv1i64.nxv1i64( undef, %0, %1, iXLen %2) + %b = call @llvm.riscv.vmin.nxv1i64.nxv1i64( undef, %1, %0, iXLen %2) + %ret = add %a, %b + ret %ret +} + +declare @llvm.riscv.vmin.mask.nxv1i64.nxv1i64(, , , , iXLen, iXLen); +define @commutable_vmin_vv_masked( %0, %1, %mask, iXLen %2) { +; CHECK-LABEL: commutable_vmin_vv_masked: +; CHECK: # %bb.0: +; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, ma +; CHECK-NEXT: vmin.vv v10, v8, v9, v0.t +; CHECK-NEXT: vmin.vv v8, v8, v9, v0.t +; CHECK-NEXT: vsetvli a0, zero, e64, m1, ta, ma +; CHECK-NEXT: vadd.vv v8, v10, v8 +; CHECK-NEXT: ret + %a = call @llvm.riscv.vmin.mask.nxv1i64.nxv1i64( undef, %0, %1, %mask, iXLen %2, iXLen 1) + %b = call @llvm.riscv.vmin.mask.nxv1i64.nxv1i64( undef, %1, %0, %mask, iXLen %2, iXLen 1) + %ret = add %a, %b + ret %ret +} + +; vminu.vv +declare @llvm.riscv.vminu.nxv1i64.nxv1i64(, , , iXLen); +define @commutable_vminu_vv( %0, %1, iXLen %2) nounwind { +; CHECK-LABEL: commutable_vminu_vv: +; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, ma +; CHECK-NEXT: vminu.vv v8, v8, v9 +; CHECK-NEXT: vsetvli a0, zero, e64, m1, ta, ma +; CHECK-NEXT: vadd.vv v8, v8, v8 +; CHECK-NEXT: ret +entry: + %a = call @llvm.riscv.vminu.nxv1i64.nxv1i64( undef, %0, %1, iXLen %2) + %b = call @llvm.riscv.vminu.nxv1i64.nxv1i64( undef, %1, %0, iXLen %2) + %ret = add %a, %b + ret %ret +} + +declare @llvm.riscv.vminu.mask.nxv1i64.nxv1i64(, , , , iXLen, iXLen); +define @commutable_vminu_vv_masked( %0, %1, %mask, iXLen %2) { +; CHECK-LABEL: commutable_vminu_vv_masked: +; CHECK: # %bb.0: +; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, ma +; CHECK-NEXT: vminu.vv v10, v8, v9, v0.t +; CHECK-NEXT: vminu.vv v8, v8, v9, v0.t +; CHECK-NEXT: vsetvli a0, zero, e64, m1, ta, ma +; CHECK-NEXT: vadd.vv v8, v10, v8 +; CHECK-NEXT: ret + %a = call @llvm.riscv.vminu.mask.nxv1i64.nxv1i64( undef, %0, %1, %mask, iXLen %2, iXLen 1) + %b = call @llvm.riscv.vminu.mask.nxv1i64.nxv1i64( undef, %1, %0, %mask, iXLen %2, iXLen 1) + %ret = add %a, %b + ret %ret +} + +; vmax.vv +declare @llvm.riscv.vmax.nxv1i64.nxv1i64(, , , iXLen); +define @commutable_vmax_vv( %0, %1, iXLen %2) nounwind { +; CHECK-LABEL: commutable_vmax_vv: +; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, ma +; CHECK-NEXT: vmax.vv v8, v8, v9 +; CHECK-NEXT: vsetvli a0, zero, e64, m1, ta, ma +; CHECK-NEXT: vadd.vv v8, v8, v8 +; CHECK-NEXT: ret +entry: + %a = call @llvm.riscv.vmax.nxv1i64.nxv1i64( undef, %0, %1, iXLen %2) + %b = call @llvm.riscv.vmax.nxv1i64.nxv1i64( undef, %1, %0, iXLen %2) + %ret = add %a, %b + ret %ret +} + +declare @llvm.riscv.vmax.mask.nxv1i64.nxv1i64(, , , , iXLen, iXLen); +define @commutable_vmax_vv_masked( %0, %1, %mask, iXLen %2) { +; CHECK-LABEL: commutable_vmax_vv_masked: +; CHECK: # %bb.0: +; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, ma +; CHECK-NEXT: vmax.vv v10, v8, v9, v0.t +; CHECK-NEXT: vmax.vv v8, v8, v9, v0.t +; CHECK-NEXT: vsetvli a0, zero, e64, m1, ta, ma +; CHECK-NEXT: vadd.vv v8, v10, v8 +; CHECK-NEXT: ret + %a = call @llvm.riscv.vmax.mask.nxv1i64.nxv1i64( undef, %0, %1, %mask, iXLen %2, iXLen 1) + %b = call @llvm.riscv.vmax.mask.nxv1i64.nxv1i64( undef, %1, %0, %mask, iXLen %2, iXLen 1) + %ret = add %a, %b + ret %ret +} + +; vmaxu.vv +declare @llvm.riscv.vmaxu.nxv1i64.nxv1i64(, , , iXLen); +define @commutable_vmaxu_vv( %0, %1, iXLen %2) nounwind { +; CHECK-LABEL: commutable_vmaxu_vv: +; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, ma +; CHECK-NEXT: vmaxu.vv v8, v8, v9 +; CHECK-NEXT: vsetvli a0, zero, e64, m1, ta, ma +; CHECK-NEXT: vadd.vv v8, v8, v8 +; CHECK-NEXT: ret +entry: + %a = call @llvm.riscv.vmaxu.nxv1i64.nxv1i64( undef, %0, %1, iXLen %2) + %b = call @llvm.riscv.vmaxu.nxv1i64.nxv1i64( undef, %1, %0, iXLen %2) + %ret = add %a, %b + ret %ret +} + +declare @llvm.riscv.vmaxu.mask.nxv1i64.nxv1i64(, , , , iXLen, iXLen); +define @commutable_vmaxu_vv_masked( %0, %1, %mask, iXLen %2) { +; CHECK-LABEL: commutable_vmaxu_vv_masked: +; CHECK: # %bb.0: +; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, ma +; CHECK-NEXT: vmaxu.vv v10, v8, v9, v0.t +; CHECK-NEXT: vmaxu.vv v8, v8, v9, v0.t +; CHECK-NEXT: vsetvli a0, zero, e64, m1, ta, ma +; CHECK-NEXT: vadd.vv v8, v10, v8 +; CHECK-NEXT: ret + %a = call @llvm.riscv.vmaxu.mask.nxv1i64.nxv1i64( undef, %0, %1, %mask, iXLen %2, iXLen 1) + %b = call @llvm.riscv.vmaxu.mask.nxv1i64.nxv1i64( undef, %1, %0, %mask, iXLen %2, iXLen 1) + %ret = add %a, %b + ret %ret +} + +; vmul.vv +declare @llvm.riscv.vmul.nxv1i64.nxv1i64(, , , iXLen); +define @commutable_vmul_vv( %0, %1, iXLen %2) nounwind { +; CHECK-LABEL: commutable_vmul_vv: +; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, ma +; CHECK-NEXT: vmul.vv v8, v8, v9 +; CHECK-NEXT: vsetvli a0, zero, e64, m1, ta, ma +; CHECK-NEXT: vadd.vv v8, v8, v8 +; CHECK-NEXT: ret +entry: + %a = call @llvm.riscv.vmul.nxv1i64.nxv1i64( undef, %0, %1, iXLen %2) + %b = call @llvm.riscv.vmul.nxv1i64.nxv1i64( undef, %1, %0, iXLen %2) + %ret = add %a, %b + ret %ret +} + +declare @llvm.riscv.vmul.mask.nxv1i64.nxv1i64(, , , , iXLen, iXLen); +define @commutable_vmul_vv_masked( %0, %1, %mask, iXLen %2) { +; CHECK-LABEL: commutable_vmul_vv_masked: +; CHECK: # %bb.0: +; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, ma +; CHECK-NEXT: vmul.vv v10, v8, v9, v0.t +; CHECK-NEXT: vmul.vv v8, v8, v9, v0.t +; CHECK-NEXT: vsetvli a0, zero, e64, m1, ta, ma +; CHECK-NEXT: vadd.vv v8, v10, v8 +; CHECK-NEXT: ret + %a = call @llvm.riscv.vmul.mask.nxv1i64.nxv1i64( undef, %0, %1, %mask, iXLen %2, iXLen 1) + %b = call @llvm.riscv.vmul.mask.nxv1i64.nxv1i64( undef, %1, %0, %mask, iXLen %2, iXLen 1) + %ret = add %a, %b + ret %ret +} + +; vmulh.vv +declare @llvm.riscv.vmulh.nxv1i64.nxv1i64(, , , iXLen); +define @commutable_vmulh_vv( %0, %1, iXLen %2) nounwind { +; CHECK-LABEL: commutable_vmulh_vv: +; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, ma +; CHECK-NEXT: vmulh.vv v8, v8, v9 +; CHECK-NEXT: vsetvli a0, zero, e64, m1, ta, ma +; CHECK-NEXT: vadd.vv v8, v8, v8 +; CHECK-NEXT: ret +entry: + %a = call @llvm.riscv.vmulh.nxv1i64.nxv1i64( undef, %0, %1, iXLen %2) + %b = call @llvm.riscv.vmulh.nxv1i64.nxv1i64( undef, %1, %0, iXLen %2) + %ret = add %a, %b + ret %ret +} + +declare @llvm.riscv.vmulh.mask.nxv1i64.nxv1i64(, , , , iXLen, iXLen); +define @commutable_vmulh_vv_masked( %0, %1, %mask, iXLen %2) { +; CHECK-LABEL: commutable_vmulh_vv_masked: +; CHECK: # %bb.0: +; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, ma +; CHECK-NEXT: vmulh.vv v10, v8, v9, v0.t +; CHECK-NEXT: vmulh.vv v8, v8, v9, v0.t +; CHECK-NEXT: vsetvli a0, zero, e64, m1, ta, ma +; CHECK-NEXT: vadd.vv v8, v10, v8 +; CHECK-NEXT: ret + %a = call @llvm.riscv.vmulh.mask.nxv1i64.nxv1i64( undef, %0, %1, %mask, iXLen %2, iXLen 1) + %b = call @llvm.riscv.vmulh.mask.nxv1i64.nxv1i64( undef, %1, %0, %mask, iXLen %2, iXLen 1) + %ret = add %a, %b + ret %ret +} + +; vmulhu.vv +declare @llvm.riscv.vmulhu.nxv1i64.nxv1i64(, , , iXLen); +define @commutable_vmulhu_vv( %0, %1, iXLen %2) nounwind { +; CHECK-LABEL: commutable_vmulhu_vv: +; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, ma +; CHECK-NEXT: vmulhu.vv v8, v8, v9 +; CHECK-NEXT: vsetvli a0, zero, e64, m1, ta, ma +; CHECK-NEXT: vadd.vv v8, v8, v8 +; CHECK-NEXT: ret +entry: + %a = call @llvm.riscv.vmulhu.nxv1i64.nxv1i64( undef, %0, %1, iXLen %2) + %b = call @llvm.riscv.vmulhu.nxv1i64.nxv1i64( undef, %1, %0, iXLen %2) + %ret = add %a, %b + ret %ret +} + +declare @llvm.riscv.vmulhu.mask.nxv1i64.nxv1i64(, , , , iXLen, iXLen); +define @commutable_vmulhu_vv_masked( %0, %1, %mask, iXLen %2) { +; CHECK-LABEL: commutable_vmulhu_vv_masked: +; CHECK: # %bb.0: +; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, ma +; CHECK-NEXT: vmulhu.vv v10, v8, v9, v0.t +; CHECK-NEXT: vmulhu.vv v8, v8, v9, v0.t +; CHECK-NEXT: vsetvli a0, zero, e64, m1, ta, ma +; CHECK-NEXT: vadd.vv v8, v10, v8 +; CHECK-NEXT: ret + %a = call @llvm.riscv.vmulhu.mask.nxv1i64.nxv1i64( undef, %0, %1, %mask, iXLen %2, iXLen 1) + %b = call @llvm.riscv.vmulhu.mask.nxv1i64.nxv1i64( undef, %1, %0, %mask, iXLen %2, iXLen 1) + %ret = add %a, %b + ret %ret +} + +; vwadd.vv +declare @llvm.riscv.vwadd.nxv1i64.nxv1i32.nxv1i32(, , , iXLen); +define @commutable_vwadd_vv( %0, %1, iXLen %2) nounwind { +; CHECK-LABEL: commutable_vwadd_vv: +; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vsetvli zero, a0, e32, mf2, ta, ma +; CHECK-NEXT: vwadd.vv v10, v8, v9 +; CHECK-NEXT: vsetvli a0, zero, e64, m1, ta, ma +; CHECK-NEXT: vadd.vv v8, v10, v10 +; CHECK-NEXT: ret +entry: + %a = call @llvm.riscv.vwadd.nxv1i64.nxv1i32.nxv1i32( undef, %0, %1, iXLen %2) + %b = call @llvm.riscv.vwadd.nxv1i64.nxv1i32.nxv1i32( undef, %1, %0, iXLen %2) + %ret = add %a, %b + ret %ret +} + +declare @llvm.riscv.vwadd.mask.nxv1i64.nxv1i32.nxv1i32(, , , , iXLen, iXLen); +define @commutable_vwadd_vv_masked( %0, %1, %mask, iXLen %2) { +; CHECK-LABEL: commutable_vwadd_vv_masked: +; CHECK: # %bb.0: +; CHECK-NEXT: vsetvli zero, a0, e32, mf2, ta, ma +; CHECK-NEXT: vwadd.vv v10, v8, v9, v0.t +; CHECK-NEXT: vwadd.vv v11, v8, v9, v0.t +; CHECK-NEXT: vsetvli a0, zero, e64, m1, ta, ma +; CHECK-NEXT: vadd.vv v8, v10, v11 +; CHECK-NEXT: ret + %a = call @llvm.riscv.vwadd.mask.nxv1i64.nxv1i32.nxv1i32( undef, %0, %1, %mask, iXLen %2, iXLen 1) + %b = call @llvm.riscv.vwadd.mask.nxv1i64.nxv1i32.nxv1i32( undef, %1, %0, %mask, iXLen %2, iXLen 1) + %ret = add %a, %b + ret %ret +} + +; vwaddu.vv +declare @llvm.riscv.vwaddu.nxv1i64.nxv1i32.nxv1i32(, , , iXLen); +define @commutable_vwaddu_vv( %0, %1, iXLen %2) nounwind { +; CHECK-LABEL: commutable_vwaddu_vv: +; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vsetvli zero, a0, e32, mf2, ta, ma +; CHECK-NEXT: vwaddu.vv v10, v8, v9 +; CHECK-NEXT: vsetvli a0, zero, e64, m1, ta, ma +; CHECK-NEXT: vadd.vv v8, v10, v10 +; CHECK-NEXT: ret +entry: + %a = call @llvm.riscv.vwaddu.nxv1i64.nxv1i32.nxv1i32( undef, %0, %1, iXLen %2) + %b = call @llvm.riscv.vwaddu.nxv1i64.nxv1i32.nxv1i32( undef, %1, %0, iXLen %2) + %ret = add %a, %b + ret %ret +} + +declare @llvm.riscv.vwaddu.mask.nxv1i64.nxv1i32.nxv1i32(, , , , iXLen, iXLen); +define @commutable_vwaddu_vv_masked( %0, %1, %mask, iXLen %2) { +; CHECK-LABEL: commutable_vwaddu_vv_masked: +; CHECK: # %bb.0: +; CHECK-NEXT: vsetvli zero, a0, e32, mf2, ta, ma +; CHECK-NEXT: vwaddu.vv v10, v8, v9, v0.t +; CHECK-NEXT: vwaddu.vv v11, v8, v9, v0.t +; CHECK-NEXT: vsetvli a0, zero, e64, m1, ta, ma +; CHECK-NEXT: vadd.vv v8, v10, v11 +; CHECK-NEXT: ret + %a = call @llvm.riscv.vwaddu.mask.nxv1i64.nxv1i32.nxv1i32( undef, %0, %1, %mask, iXLen %2, iXLen 1) + %b = call @llvm.riscv.vwaddu.mask.nxv1i64.nxv1i32.nxv1i32( undef, %1, %0, %mask, iXLen %2, iXLen 1) + %ret = add %a, %b + ret %ret +} + +; vwmul.vv +declare @llvm.riscv.vwmul.nxv1i64.nxv1i32.nxv1i32(, , , iXLen); +define @commutable_vwmul_vv( %0, %1, iXLen %2) nounwind { +; CHECK-LABEL: commutable_vwmul_vv: +; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vsetvli zero, a0, e32, mf2, ta, ma +; CHECK-NEXT: vwmul.vv v10, v8, v9 +; CHECK-NEXT: vsetvli a0, zero, e64, m1, ta, ma +; CHECK-NEXT: vadd.vv v8, v10, v10 +; CHECK-NEXT: ret +entry: + %a = call @llvm.riscv.vwmul.nxv1i64.nxv1i32.nxv1i32( undef, %0, %1, iXLen %2) + %b = call @llvm.riscv.vwmul.nxv1i64.nxv1i32.nxv1i32( undef, %1, %0, iXLen %2) + %ret = add %a, %b + ret %ret +} + +declare @llvm.riscv.vwmul.mask.nxv1i64.nxv1i32.nxv1i32(, , , , iXLen, iXLen); +define @commutable_vwmul_vv_masked( %0, %1, %mask, iXLen %2) { +; CHECK-LABEL: commutable_vwmul_vv_masked: +; CHECK: # %bb.0: +; CHECK-NEXT: vsetvli zero, a0, e32, mf2, ta, ma +; CHECK-NEXT: vwmul.vv v10, v8, v9, v0.t +; CHECK-NEXT: vwmul.vv v11, v8, v9, v0.t +; CHECK-NEXT: vsetvli a0, zero, e64, m1, ta, ma +; CHECK-NEXT: vadd.vv v8, v10, v11 +; CHECK-NEXT: ret + %a = call @llvm.riscv.vwmul.mask.nxv1i64.nxv1i32.nxv1i32( undef, %0, %1, %mask, iXLen %2, iXLen 1) + %b = call @llvm.riscv.vwmul.mask.nxv1i64.nxv1i32.nxv1i32( undef, %1, %0, %mask, iXLen %2, iXLen 1) + %ret = add %a, %b + ret %ret +} + +; vwmulu.vv +declare @llvm.riscv.vwmulu.nxv1i64.nxv1i32.nxv1i32(, , , iXLen); +define @commutable_vwmulu_vv( %0, %1, iXLen %2) nounwind { +; CHECK-LABEL: commutable_vwmulu_vv: +; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vsetvli zero, a0, e32, mf2, ta, ma +; CHECK-NEXT: vwmulu.vv v10, v8, v9 +; CHECK-NEXT: vsetvli a0, zero, e64, m1, ta, ma +; CHECK-NEXT: vadd.vv v8, v10, v10 +; CHECK-NEXT: ret +entry: + %a = call @llvm.riscv.vwmulu.nxv1i64.nxv1i32.nxv1i32( undef, %0, %1, iXLen %2) + %b = call @llvm.riscv.vwmulu.nxv1i64.nxv1i32.nxv1i32( undef, %1, %0, iXLen %2) + %ret = add %a, %b + ret %ret +} + +declare @llvm.riscv.vwmulu.mask.nxv1i64.nxv1i32.nxv1i32(, , , , iXLen, iXLen); +define @commutable_vwmulu_vv_masked( %0, %1, %mask, iXLen %2) { +; CHECK-LABEL: commutable_vwmulu_vv_masked: +; CHECK: # %bb.0: +; CHECK-NEXT: vsetvli zero, a0, e32, mf2, ta, ma +; CHECK-NEXT: vwmulu.vv v10, v8, v9, v0.t +; CHECK-NEXT: vwmulu.vv v11, v8, v9, v0.t +; CHECK-NEXT: vsetvli a0, zero, e64, m1, ta, ma +; CHECK-NEXT: vadd.vv v8, v10, v11 +; CHECK-NEXT: ret + %a = call @llvm.riscv.vwmulu.mask.nxv1i64.nxv1i32.nxv1i32( undef, %0, %1, %mask, iXLen %2, iXLen 1) + %b = call @llvm.riscv.vwmulu.mask.nxv1i64.nxv1i32.nxv1i32( undef, %1, %0, %mask, iXLen %2, iXLen 1) + %ret = add %a, %b + ret %ret +} + +; vwmacc.vv +declare @llvm.riscv.vwmacc.nxv1i64.nxv1i32(, , , iXLen, iXLen); +define @commutable_vwmacc_vv( %0, %1, iXLen %2) nounwind { +; CHECK-LABEL: commutable_vwmacc_vv: +; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vsetvli zero, a0, e32, mf2, ta, ma +; CHECK-NEXT: vwmacc.vv v10, v8, v9 +; CHECK-NEXT: vsetvli a0, zero, e64, m1, ta, ma +; CHECK-NEXT: vadd.vv v8, v10, v10 +; CHECK-NEXT: ret +entry: + %a = call @llvm.riscv.vwmacc.nxv1i64.nxv1i32( undef, %0, %1, iXLen %2, iXLen 1) + %b = call @llvm.riscv.vwmacc.nxv1i64.nxv1i32( undef, %1, %0, iXLen %2, iXLen 1) + %ret = add %a, %b + ret %ret +} + +declare @llvm.riscv.vwmacc.mask.nxv1i64.nxv1i32(, , , , iXLen, iXLen); +define @commutable_vwmacc_vv_masked( %0, %1, %mask, iXLen %2) { +; CHECK-LABEL: commutable_vwmacc_vv_masked: +; CHECK: # %bb.0: +; CHECK-NEXT: vsetvli zero, a0, e32, mf2, ta, ma +; CHECK-NEXT: vwmacc.vv v10, v8, v9, v0.t +; CHECK-NEXT: vwmacc.vv v11, v9, v8, v0.t +; CHECK-NEXT: vsetvli a0, zero, e64, m1, ta, ma +; CHECK-NEXT: vadd.vv v8, v10, v11 +; CHECK-NEXT: ret + %a = call @llvm.riscv.vwmacc.mask.nxv1i64.nxv1i32( undef, %0, %1, %mask, iXLen %2, iXLen 1) + %b = call @llvm.riscv.vwmacc.mask.nxv1i64.nxv1i32( undef, %1, %0, %mask, iXLen %2, iXLen 1) + %ret = add %a, %b + ret %ret +} + +; vwmaccu.vv +declare @llvm.riscv.vwmaccu.nxv1i64.nxv1i32(, , , iXLen, iXLen); +define @commutable_vwmaccu_vv( %0, %1, iXLen %2) nounwind { +; CHECK-LABEL: commutable_vwmaccu_vv: +; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vsetvli zero, a0, e32, mf2, ta, ma +; CHECK-NEXT: vwmaccu.vv v10, v8, v9 +; CHECK-NEXT: vsetvli a0, zero, e64, m1, ta, ma +; CHECK-NEXT: vadd.vv v8, v10, v10 +; CHECK-NEXT: ret +entry: + %a = call @llvm.riscv.vwmaccu.nxv1i64.nxv1i32( undef, %0, %1, iXLen %2, iXLen 1) + %b = call @llvm.riscv.vwmaccu.nxv1i64.nxv1i32( undef, %1, %0, iXLen %2, iXLen 1) + %ret = add %a, %b + ret %ret +} + +declare @llvm.riscv.vwmaccu.mask.nxv1i64.nxv1i32(, , , , iXLen, iXLen); +define @commutable_vwmaccu_vv_masked( %0, %1, %mask, iXLen %2) { +; CHECK-LABEL: commutable_vwmaccu_vv_masked: +; CHECK: # %bb.0: +; CHECK-NEXT: vsetvli zero, a0, e32, mf2, ta, ma +; CHECK-NEXT: vwmaccu.vv v10, v8, v9, v0.t +; CHECK-NEXT: vwmaccu.vv v11, v9, v8, v0.t +; CHECK-NEXT: vsetvli a0, zero, e64, m1, ta, ma +; CHECK-NEXT: vadd.vv v8, v10, v11 +; CHECK-NEXT: ret + %a = call @llvm.riscv.vwmaccu.mask.nxv1i64.nxv1i32( undef, %0, %1, %mask, iXLen %2, iXLen 1) + %b = call @llvm.riscv.vwmaccu.mask.nxv1i64.nxv1i32( undef, %1, %0, %mask, iXLen %2, iXLen 1) + %ret = add %a, %b + ret %ret +} + +; vadc.vvm +declare @llvm.riscv.vadc.nxv1i64.nxv1i64(, , , , iXLen); +define @commutable_vadc_vv( %0, %1, %mask, iXLen %2) nounwind { +; CHECK-LABEL: commutable_vadc_vv: +; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, ma +; CHECK-NEXT: vadc.vvm v10, v8, v9, v0 +; CHECK-NEXT: vadc.vvm v8, v8, v9, v0 +; CHECK-NEXT: vsetvli a0, zero, e64, m1, ta, ma +; CHECK-NEXT: vadd.vv v8, v10, v8 +; CHECK-NEXT: ret +entry: + %a = call @llvm.riscv.vadc.nxv1i64.nxv1i64( undef, %0, %1, %mask, iXLen %2) + %b = call @llvm.riscv.vadc.nxv1i64.nxv1i64( undef, %1, %0, %mask, iXLen %2) + %ret = add %a, %b + ret %ret +} + diff --git a/llvm/test/CodeGen/RISCV/rvv/fixed-vectors-fp-buildvec.ll b/llvm/test/CodeGen/RISCV/rvv/fixed-vectors-fp-buildvec.ll index 8e214e40547832d49e151e6b5ee82dcba12803c6..9e83efd351953921358bb78ae9f38ed87b46ae8f 100644 --- a/llvm/test/CodeGen/RISCV/rvv/fixed-vectors-fp-buildvec.ll +++ b/llvm/test/CodeGen/RISCV/rvv/fixed-vectors-fp-buildvec.ll @@ -1407,8 +1407,8 @@ define <8 x float> @buildvec_v8f32_zvl256(float %e0, float %e1, float %e2, float ; CHECK-NEXT: vfmv.v.f v8, fa4 ; CHECK-NEXT: vfslide1down.vf v8, v8, fa5 ; CHECK-NEXT: vfslide1down.vf v8, v8, fa6 -; CHECK-NEXT: vmv.v.i v0, 15 ; CHECK-NEXT: vfslide1down.vf v8, v8, fa7 +; CHECK-NEXT: vmv.v.i v0, 15 ; CHECK-NEXT: vslidedown.vi v8, v9, 4, v0.t ; CHECK-NEXT: ret %v0 = insertelement <8 x float> poison, float %e0, i64 0 @@ -1458,8 +1458,8 @@ define <8 x double> @buildvec_v8f64_zvl512(double %e0, double %e1, double %e2, d ; CHECK-NEXT: vfmv.v.f v8, fa4 ; CHECK-NEXT: vfslide1down.vf v8, v8, fa5 ; CHECK-NEXT: vfslide1down.vf v8, v8, fa6 -; CHECK-NEXT: vmv.v.i v0, 15 ; CHECK-NEXT: vfslide1down.vf v8, v8, fa7 +; CHECK-NEXT: vmv.v.i v0, 15 ; CHECK-NEXT: vslidedown.vi v8, v9, 4, v0.t ; CHECK-NEXT: ret %v0 = insertelement <8 x double> poison, double %e0, i64 0 diff --git a/llvm/test/CodeGen/RISCV/rvv/fixed-vectors-fp-interleave.ll b/llvm/test/CodeGen/RISCV/rvv/fixed-vectors-fp-interleave.ll index 6bfd0ac932672f51793b7b64eca7b46f0122eafd..ed152e64a91ef49dd2661d803d01e12f1b9be750 100644 --- a/llvm/test/CodeGen/RISCV/rvv/fixed-vectors-fp-interleave.ll +++ b/llvm/test/CodeGen/RISCV/rvv/fixed-vectors-fp-interleave.ll @@ -57,8 +57,8 @@ define <4 x double> @interleave_v2f64(<2 x double> %x, <2 x double> %y) { ; RV32-V512-NEXT: vid.v v10 ; RV32-V512-NEXT: vsrl.vi v11, v10, 1 ; RV32-V512-NEXT: vsetvli zero, zero, e64, m1, ta, mu -; RV32-V512-NEXT: vmv.v.i v0, 10 ; RV32-V512-NEXT: vrgatherei16.vv v10, v8, v11 +; RV32-V512-NEXT: vmv.v.i v0, 10 ; RV32-V512-NEXT: vrgatherei16.vv v10, v9, v11, v0.t ; RV32-V512-NEXT: vmv.v.v v8, v10 ; RV32-V512-NEXT: ret @@ -68,8 +68,8 @@ define <4 x double> @interleave_v2f64(<2 x double> %x, <2 x double> %y) { ; RV64-V512-NEXT: vsetivli zero, 4, e64, m1, ta, mu ; RV64-V512-NEXT: vid.v v10 ; RV64-V512-NEXT: vsrl.vi v11, v10, 1 -; RV64-V512-NEXT: vmv.v.i v0, 10 ; RV64-V512-NEXT: vrgather.vv v10, v8, v11 +; RV64-V512-NEXT: vmv.v.i v0, 10 ; RV64-V512-NEXT: vrgather.vv v10, v9, v11, v0.t ; RV64-V512-NEXT: vmv.v.v v8, v10 ; RV64-V512-NEXT: ret diff --git a/llvm/test/CodeGen/RISCV/rvv/fixed-vectors-fp2i-sat.ll b/llvm/test/CodeGen/RISCV/rvv/fixed-vectors-fp2i-sat.ll index 85b849045e8ceecdcf7f000d162ee2b97cd8dd67..a8e4af2d7368e885d234890aac3e41eee5ccdfde 100644 --- a/llvm/test/CodeGen/RISCV/rvv/fixed-vectors-fp2i-sat.ll +++ b/llvm/test/CodeGen/RISCV/rvv/fixed-vectors-fp2i-sat.ll @@ -395,8 +395,8 @@ define void @fp2si_v8f64_v8i8(ptr %x, ptr %y) { ; RV32-NEXT: fmin.d fa5, fa5, fa4 ; RV32-NEXT: fcvt.w.d a2, fa5, rtz ; RV32-NEXT: and a0, a0, a2 -; RV32-NEXT: vmv.v.i v0, 15 ; RV32-NEXT: vslide1down.vx v9, v9, a0 +; RV32-NEXT: vmv.v.i v0, 15 ; RV32-NEXT: vslidedown.vi v9, v8, 4, v0.t ; RV32-NEXT: vse8.v v9, (a1) ; RV32-NEXT: addi sp, s0, -128 @@ -496,8 +496,8 @@ define void @fp2si_v8f64_v8i8(ptr %x, ptr %y) { ; RV64-NEXT: fmin.d fa5, fa5, fa4 ; RV64-NEXT: fcvt.l.d a2, fa5, rtz ; RV64-NEXT: and a0, a0, a2 -; RV64-NEXT: vmv.v.i v0, 15 ; RV64-NEXT: vslide1down.vx v9, v9, a0 +; RV64-NEXT: vmv.v.i v0, 15 ; RV64-NEXT: vslidedown.vi v9, v8, 4, v0.t ; RV64-NEXT: vse8.v v9, (a1) ; RV64-NEXT: addi sp, s0, -128 @@ -580,8 +580,8 @@ define void @fp2ui_v8f64_v8i8(ptr %x, ptr %y) { ; RV32-NEXT: fmax.d fa4, fa4, fa3 ; RV32-NEXT: fmin.d fa5, fa4, fa5 ; RV32-NEXT: fcvt.wu.d a0, fa5, rtz -; RV32-NEXT: vmv.v.i v0, 15 ; RV32-NEXT: vslide1down.vx v9, v9, a0 +; RV32-NEXT: vmv.v.i v0, 15 ; RV32-NEXT: vslidedown.vi v9, v8, 4, v0.t ; RV32-NEXT: vse8.v v9, (a1) ; RV32-NEXT: addi sp, s0, -128 @@ -656,8 +656,8 @@ define void @fp2ui_v8f64_v8i8(ptr %x, ptr %y) { ; RV64-NEXT: fmax.d fa4, fa4, fa3 ; RV64-NEXT: fmin.d fa5, fa4, fa5 ; RV64-NEXT: fcvt.lu.d a0, fa5, rtz -; RV64-NEXT: vmv.v.i v0, 15 ; RV64-NEXT: vslide1down.vx v9, v9, a0 +; RV64-NEXT: vmv.v.i v0, 15 ; RV64-NEXT: vslidedown.vi v9, v8, 4, v0.t ; RV64-NEXT: vse8.v v9, (a1) ; RV64-NEXT: addi sp, s0, -128 diff --git a/llvm/test/CodeGen/RISCV/rvv/fixed-vectors-int-interleave.ll b/llvm/test/CodeGen/RISCV/rvv/fixed-vectors-int-interleave.ll index 6da83644413bc2e9e7932ab20d853351edf6119d..40ff8b50d99d8d58f512dd09b5a41b70d3444209 100644 --- a/llvm/test/CodeGen/RISCV/rvv/fixed-vectors-int-interleave.ll +++ b/llvm/test/CodeGen/RISCV/rvv/fixed-vectors-int-interleave.ll @@ -70,8 +70,8 @@ define <4 x i64> @interleave_v2i64(<2 x i64> %x, <2 x i64> %y) { ; RV32-V512-NEXT: vid.v v10 ; RV32-V512-NEXT: vsrl.vi v11, v10, 1 ; RV32-V512-NEXT: vsetvli zero, zero, e64, m1, ta, mu -; RV32-V512-NEXT: vmv.v.i v0, 10 ; RV32-V512-NEXT: vrgatherei16.vv v10, v8, v11 +; RV32-V512-NEXT: vmv.v.i v0, 10 ; RV32-V512-NEXT: vrgatherei16.vv v10, v9, v11, v0.t ; RV32-V512-NEXT: vmv.v.v v8, v10 ; RV32-V512-NEXT: ret @@ -81,8 +81,8 @@ define <4 x i64> @interleave_v2i64(<2 x i64> %x, <2 x i64> %y) { ; RV64-V512-NEXT: vsetivli zero, 4, e64, m1, ta, mu ; RV64-V512-NEXT: vid.v v10 ; RV64-V512-NEXT: vsrl.vi v11, v10, 1 -; RV64-V512-NEXT: vmv.v.i v0, 10 ; RV64-V512-NEXT: vrgather.vv v10, v8, v11 +; RV64-V512-NEXT: vmv.v.i v0, 10 ; RV64-V512-NEXT: vrgather.vv v10, v9, v11, v0.t ; RV64-V512-NEXT: vmv.v.v v8, v10 ; RV64-V512-NEXT: ret @@ -195,8 +195,8 @@ define <4 x i32> @interleave_v4i32_offset_1(<4 x i32> %x, <4 x i32> %y) { ; V128-NEXT: vsetivli zero, 4, e32, m1, ta, mu ; V128-NEXT: vid.v v8 ; V128-NEXT: vsrl.vi v8, v8, 1 -; V128-NEXT: vmv.v.i v0, 10 ; V128-NEXT: vadd.vi v8, v8, 1 +; V128-NEXT: vmv.v.i v0, 10 ; V128-NEXT: vrgather.vv v10, v9, v8, v0.t ; V128-NEXT: vmv.v.v v8, v10 ; V128-NEXT: ret @@ -210,8 +210,8 @@ define <4 x i32> @interleave_v4i32_offset_1(<4 x i32> %x, <4 x i32> %y) { ; V512-NEXT: vsetivli zero, 4, e32, mf2, ta, mu ; V512-NEXT: vid.v v8 ; V512-NEXT: vsrl.vi v8, v8, 1 -; V512-NEXT: vmv.v.i v0, 10 ; V512-NEXT: vadd.vi v8, v8, 1 +; V512-NEXT: vmv.v.i v0, 10 ; V512-NEXT: vrgather.vv v10, v9, v8, v0.t ; V512-NEXT: vmv1r.v v8, v10 ; V512-NEXT: ret diff --git a/llvm/test/CodeGen/RISCV/rvv/fixed-vectors-int-shuffles.ll b/llvm/test/CodeGen/RISCV/rvv/fixed-vectors-int-shuffles.ll index 0e8d9cf030669064fe98cfc913deee35fc60915c..58af6ac246d1619e1ae8c1e0923f73f216e920f6 100644 --- a/llvm/test/CodeGen/RISCV/rvv/fixed-vectors-int-shuffles.ll +++ b/llvm/test/CodeGen/RISCV/rvv/fixed-vectors-int-shuffles.ll @@ -89,8 +89,8 @@ define <4 x i16> @vrgather_shuffle_vv_v4i16(<4 x i16> %x, <4 x i16> %y) { ; CHECK-NEXT: addi a0, a0, %lo(.LCPI6_0) ; CHECK-NEXT: vsetivli zero, 4, e16, mf2, ta, mu ; CHECK-NEXT: vle16.v v11, (a0) -; CHECK-NEXT: vmv.v.i v0, 8 ; CHECK-NEXT: vrgather.vv v10, v8, v11 +; CHECK-NEXT: vmv.v.i v0, 8 ; CHECK-NEXT: vrgather.vi v10, v9, 1, v0.t ; CHECK-NEXT: vmv1r.v v8, v10 ; CHECK-NEXT: ret @@ -162,16 +162,16 @@ define <8 x i64> @vrgather_shuffle_vv_v8i64(<8 x i64> %x, <8 x i64> %y) { ; RV32: # %bb.0: ; RV32-NEXT: vsetivli zero, 8, e16, m1, ta, ma ; RV32-NEXT: vmv.v.i v16, 2 -; RV32-NEXT: li a0, 5 -; RV32-NEXT: vslide1down.vx v20, v16, a0 ; RV32-NEXT: lui a0, %hi(.LCPI11_0) ; RV32-NEXT: addi a0, a0, %lo(.LCPI11_0) -; RV32-NEXT: vle16.v v21, (a0) +; RV32-NEXT: vle16.v v20, (a0) +; RV32-NEXT: li a0, 5 +; RV32-NEXT: vslide1down.vx v21, v16, a0 ; RV32-NEXT: vsetvli zero, zero, e64, m4, ta, mu +; RV32-NEXT: vrgatherei16.vv v16, v8, v20 ; RV32-NEXT: li a0, 164 ; RV32-NEXT: vmv.s.x v0, a0 -; RV32-NEXT: vrgatherei16.vv v16, v8, v21 -; RV32-NEXT: vrgatherei16.vv v16, v12, v20, v0.t +; RV32-NEXT: vrgatherei16.vv v16, v12, v21, v0.t ; RV32-NEXT: vmv.v.v v8, v16 ; RV32-NEXT: ret ; @@ -210,13 +210,13 @@ define <8 x i64> @vrgather_shuffle_xv_v8i64(<8 x i64> %x) { ; RV32-NEXT: vsetivli zero, 8, e64, m4, ta, mu ; RV32-NEXT: vle16.v v16, (a0) ; RV32-NEXT: vmv.v.i v20, -1 +; RV32-NEXT: vrgatherei16.vv v12, v20, v16 ; RV32-NEXT: lui a0, %hi(.LCPI12_1) ; RV32-NEXT: addi a0, a0, %lo(.LCPI12_1) -; RV32-NEXT: vle16.v v17, (a0) +; RV32-NEXT: vle16.v v16, (a0) ; RV32-NEXT: li a0, 113 ; RV32-NEXT: vmv.s.x v0, a0 -; RV32-NEXT: vrgatherei16.vv v12, v20, v16 -; RV32-NEXT: vrgatherei16.vv v12, v8, v17, v0.t +; RV32-NEXT: vrgatherei16.vv v12, v8, v16, v0.t ; RV32-NEXT: vmv.v.v v8, v12 ; RV32-NEXT: ret ; @@ -368,9 +368,9 @@ define <8 x i8> @splat_ve2_we0(<8 x i8> %v, <8 x i8> %w) { ; CHECK-LABEL: splat_ve2_we0: ; CHECK: # %bb.0: ; CHECK-NEXT: vsetivli zero, 8, e8, mf2, ta, mu +; CHECK-NEXT: vrgather.vi v10, v8, 2 ; CHECK-NEXT: li a0, 66 ; CHECK-NEXT: vmv.s.x v0, a0 -; CHECK-NEXT: vrgather.vi v10, v8, 2 ; CHECK-NEXT: vrgather.vi v10, v9, 0, v0.t ; CHECK-NEXT: vmv1r.v v8, v10 ; CHECK-NEXT: ret @@ -387,9 +387,9 @@ define <8 x i8> @splat_ve2_we0_ins_i0ve4(<8 x i8> %v, <8 x i8> %w) { ; CHECK-NEXT: vsetvli zero, zero, e8, mf2, tu, ma ; CHECK-NEXT: vmv.s.x v11, a0 ; CHECK-NEXT: vsetvli zero, zero, e8, mf2, ta, mu +; CHECK-NEXT: vrgather.vv v10, v8, v11 ; CHECK-NEXT: li a0, 66 ; CHECK-NEXT: vmv.s.x v0, a0 -; CHECK-NEXT: vrgather.vv v10, v8, v11 ; CHECK-NEXT: vrgather.vi v10, v9, 0, v0.t ; CHECK-NEXT: vmv1r.v v8, v10 ; CHECK-NEXT: ret @@ -422,9 +422,9 @@ define <8 x i8> @splat_ve2_we0_ins_i2ve4(<8 x i8> %v, <8 x i8> %w) { ; CHECK-NEXT: vsetivli zero, 2, e32, mf2, ta, ma ; CHECK-NEXT: vmv.v.x v11, a0 ; CHECK-NEXT: vsetivli zero, 8, e8, mf2, ta, mu +; CHECK-NEXT: vrgather.vv v10, v8, v11 ; CHECK-NEXT: li a0, 66 ; CHECK-NEXT: vmv.s.x v0, a0 -; CHECK-NEXT: vrgather.vv v10, v8, v11 ; CHECK-NEXT: vrgather.vi v10, v9, 0, v0.t ; CHECK-NEXT: vmv1r.v v8, v10 ; CHECK-NEXT: ret @@ -441,9 +441,9 @@ define <8 x i8> @splat_ve2_we0_ins_i2we4(<8 x i8> %v, <8 x i8> %w) { ; CHECK-NEXT: vsetivli zero, 3, e8, mf2, tu, ma ; CHECK-NEXT: vslideup.vi v11, v10, 2 ; CHECK-NEXT: vsetivli zero, 8, e8, mf2, ta, mu +; CHECK-NEXT: vrgather.vi v10, v8, 2 ; CHECK-NEXT: li a0, 70 ; CHECK-NEXT: vmv.s.x v0, a0 -; CHECK-NEXT: vrgather.vi v10, v8, 2 ; CHECK-NEXT: vrgather.vv v10, v9, v11, v0.t ; CHECK-NEXT: vmv1r.v v8, v10 ; CHECK-NEXT: ret @@ -464,9 +464,9 @@ define <8 x i8> @splat_ve2_we0_ins_i2ve4_i5we6(<8 x i8> %v, <8 x i8> %w) { ; CHECK-NEXT: vsetivli zero, 2, e32, mf2, ta, ma ; CHECK-NEXT: vmv.v.x v12, a0 ; CHECK-NEXT: vsetivli zero, 8, e8, mf2, ta, mu +; CHECK-NEXT: vrgather.vv v10, v8, v12 ; CHECK-NEXT: li a0, 98 ; CHECK-NEXT: vmv.s.x v0, a0 -; CHECK-NEXT: vrgather.vv v10, v8, v12 ; CHECK-NEXT: vrgather.vv v10, v9, v11, v0.t ; CHECK-NEXT: vmv1r.v v8, v10 ; CHECK-NEXT: ret @@ -681,9 +681,9 @@ define <8 x i8> @merge_non_contiguous_slideup_slidedown(<8 x i8> %v, <8 x i8> %w ; CHECK-LABEL: merge_non_contiguous_slideup_slidedown: ; CHECK: # %bb.0: ; CHECK-NEXT: vsetivli zero, 8, e8, mf2, ta, mu +; CHECK-NEXT: vslidedown.vi v8, v8, 2 ; CHECK-NEXT: li a0, 234 ; CHECK-NEXT: vmv.s.x v0, a0 -; CHECK-NEXT: vslidedown.vi v8, v8, 2 ; CHECK-NEXT: vslideup.vi v8, v9, 1, v0.t ; CHECK-NEXT: ret %res = shufflevector <8 x i8> %v, <8 x i8> %w, <8 x i32> @@ -695,12 +695,12 @@ define <8 x i8> @unmergable(<8 x i8> %v, <8 x i8> %w) { ; CHECK-LABEL: unmergable: ; CHECK: # %bb.0: ; CHECK-NEXT: vsetivli zero, 8, e8, mf2, ta, mu +; CHECK-NEXT: vslidedown.vi v8, v8, 2 ; CHECK-NEXT: lui a0, %hi(.LCPI46_0) ; CHECK-NEXT: addi a0, a0, %lo(.LCPI46_0) ; CHECK-NEXT: vle8.v v10, (a0) ; CHECK-NEXT: li a0, 234 ; CHECK-NEXT: vmv.s.x v0, a0 -; CHECK-NEXT: vslidedown.vi v8, v8, 2 ; CHECK-NEXT: vrgather.vv v8, v9, v10, v0.t ; CHECK-NEXT: ret %res = shufflevector <8 x i8> %v, <8 x i8> %w, <8 x i32> diff --git a/llvm/test/CodeGen/RISCV/rvv/fixed-vectors-interleaved-access.ll b/llvm/test/CodeGen/RISCV/rvv/fixed-vectors-interleaved-access.ll index f98cb343a2ab429bc6c2ba485f7eac464950f946..99364264de8293b2aac7a74474749334765b18e8 100644 --- a/llvm/test/CodeGen/RISCV/rvv/fixed-vectors-interleaved-access.ll +++ b/llvm/test/CodeGen/RISCV/rvv/fixed-vectors-interleaved-access.ll @@ -159,16 +159,17 @@ define {<8 x i64>, <8 x i64>, <8 x i64>, <8 x i64>, <8 x i64>, <8 x i64>} @load_ ; RV32-NEXT: addi sp, sp, -16 ; RV32-NEXT: .cfi_def_cfa_offset 16 ; RV32-NEXT: csrr a2, vlenb -; RV32-NEXT: li a3, 56 +; RV32-NEXT: li a3, 54 ; RV32-NEXT: mul a2, a2, a3 ; RV32-NEXT: sub sp, sp, a2 -; RV32-NEXT: .cfi_escape 0x0f, 0x0d, 0x72, 0x00, 0x11, 0x10, 0x22, 0x11, 0x38, 0x92, 0xa2, 0x38, 0x00, 0x1e, 0x22 # sp + 16 + 56 * vlenb +; RV32-NEXT: .cfi_escape 0x0f, 0x0d, 0x72, 0x00, 0x11, 0x10, 0x22, 0x11, 0x36, 0x92, 0xa2, 0x38, 0x00, 0x1e, 0x22 # sp + 16 + 54 * vlenb ; RV32-NEXT: addi a3, a1, 256 ; RV32-NEXT: li a2, 32 ; RV32-NEXT: vsetvli zero, a2, e32, m8, ta, ma ; RV32-NEXT: vle32.v v16, (a3) ; RV32-NEXT: csrr a3, vlenb -; RV32-NEXT: slli a3, a3, 5 +; RV32-NEXT: li a4, 21 +; RV32-NEXT: mul a3, a3, a4 ; RV32-NEXT: add a3, sp, a3 ; RV32-NEXT: addi a3, a3, 16 ; RV32-NEXT: vs8r.v v16, (a3) # Unknown-size Folded Spill @@ -176,31 +177,30 @@ define {<8 x i64>, <8 x i64>, <8 x i64>, <8 x i64>, <8 x i64>, <8 x i64>} @load_ ; RV32-NEXT: vsetivli zero, 16, e32, m4, ta, ma ; RV32-NEXT: vslideup.vi v8, v16, 4 ; RV32-NEXT: csrr a4, vlenb -; RV32-NEXT: slli a4, a4, 4 +; RV32-NEXT: slli a5, a4, 3 +; RV32-NEXT: add a4, a5, a4 ; RV32-NEXT: add a4, sp, a4 ; RV32-NEXT: addi a4, a4, 16 ; RV32-NEXT: vs4r.v v8, (a4) # Unknown-size Folded Spill ; RV32-NEXT: lui a4, 12 -; RV32-NEXT: vmv.s.x v3, a4 +; RV32-NEXT: vmv.s.x v0, a4 +; RV32-NEXT: csrr a4, vlenb +; RV32-NEXT: add a4, sp, a4 +; RV32-NEXT: addi a4, a4, 16 +; RV32-NEXT: vs1r.v v0, (a4) # Unknown-size Folded Spill ; RV32-NEXT: vsetivli zero, 16, e32, m8, ta, ma ; RV32-NEXT: vslidedown.vi v16, v16, 16 ; RV32-NEXT: csrr a4, vlenb -; RV32-NEXT: li a5, 24 +; RV32-NEXT: li a5, 37 ; RV32-NEXT: mul a4, a4, a5 ; RV32-NEXT: add a4, sp, a4 ; RV32-NEXT: addi a4, a4, 16 ; RV32-NEXT: vs8r.v v16, (a4) # Unknown-size Folded Spill ; RV32-NEXT: vsetivli zero, 16, e32, m4, ta, mu -; RV32-NEXT: vmv1r.v v0, v3 -; RV32-NEXT: csrr a4, vlenb -; RV32-NEXT: slli a4, a4, 2 -; RV32-NEXT: add a4, sp, a4 -; RV32-NEXT: addi a4, a4, 16 -; RV32-NEXT: vs1r.v v3, (a4) # Unknown-size Folded Spill ; RV32-NEXT: vslideup.vi v8, v16, 10, v0.t ; RV32-NEXT: csrr a4, vlenb -; RV32-NEXT: li a5, 20 -; RV32-NEXT: mul a4, a4, a5 +; RV32-NEXT: slli a5, a4, 4 +; RV32-NEXT: add a4, a5, a4 ; RV32-NEXT: add a4, sp, a4 ; RV32-NEXT: addi a4, a4, 16 ; RV32-NEXT: vs4r.v v8, (a4) # Unknown-size Folded Spill @@ -209,71 +209,82 @@ define {<8 x i64>, <8 x i64>, <8 x i64>, <8 x i64>, <8 x i64>, <8 x i64>} @load_ ; RV32-NEXT: vsetvli zero, a2, e32, m8, ta, mu ; RV32-NEXT: vle16.v v8, (a4) ; RV32-NEXT: csrr a4, vlenb -; RV32-NEXT: slli a4, a4, 3 +; RV32-NEXT: li a5, 13 +; RV32-NEXT: mul a4, a4, a5 ; RV32-NEXT: add a4, sp, a4 ; RV32-NEXT: addi a4, a4, 16 ; RV32-NEXT: vs4r.v v8, (a4) # Unknown-size Folded Spill -; RV32-NEXT: lui a4, %hi(.LCPI6_1) -; RV32-NEXT: addi a4, a4, %lo(.LCPI6_1) -; RV32-NEXT: lui a5, 1 -; RV32-NEXT: vle16.v v8, (a4) -; RV32-NEXT: addi a4, sp, 16 -; RV32-NEXT: vs4r.v v8, (a4) # Unknown-size Folded Spill -; RV32-NEXT: vle32.v v16, (a1) +; RV32-NEXT: vle32.v v24, (a1) ; RV32-NEXT: csrr a1, vlenb -; RV32-NEXT: li a4, 40 +; RV32-NEXT: li a4, 45 ; RV32-NEXT: mul a1, a1, a4 ; RV32-NEXT: add a1, sp, a1 ; RV32-NEXT: addi a1, a1, 16 -; RV32-NEXT: vs8r.v v16, (a1) # Unknown-size Folded Spill -; RV32-NEXT: vle32.v v24, (a3) +; RV32-NEXT: vs8r.v v24, (a1) # Unknown-size Folded Spill +; RV32-NEXT: lui a1, %hi(.LCPI6_1) +; RV32-NEXT: addi a1, a1, %lo(.LCPI6_1) +; RV32-NEXT: lui a4, 1 +; RV32-NEXT: addi a4, a4, -64 +; RV32-NEXT: vle16.v v8, (a1) ; RV32-NEXT: csrr a1, vlenb -; RV32-NEXT: li a3, 48 -; RV32-NEXT: mul a1, a1, a3 +; RV32-NEXT: slli a5, a1, 2 +; RV32-NEXT: add a1, a5, a1 ; RV32-NEXT: add a1, sp, a1 ; RV32-NEXT: addi a1, a1, 16 -; RV32-NEXT: vs8r.v v24, (a1) # Unknown-size Folded Spill -; RV32-NEXT: addi a1, a5, -64 -; RV32-NEXT: vmv.s.x v0, a1 +; RV32-NEXT: vs4r.v v8, (a1) # Unknown-size Folded Spill +; RV32-NEXT: vle32.v v16, (a3) ; RV32-NEXT: csrr a1, vlenb -; RV32-NEXT: li a3, 12 +; RV32-NEXT: li a3, 29 ; RV32-NEXT: mul a1, a1, a3 ; RV32-NEXT: add a1, sp, a1 ; RV32-NEXT: addi a1, a1, 16 -; RV32-NEXT: vs1r.v v0, (a1) # Unknown-size Folded Spill +; RV32-NEXT: vs8r.v v16, (a1) # Unknown-size Folded Spill +; RV32-NEXT: vmv.s.x v2, a4 ; RV32-NEXT: csrr a1, vlenb -; RV32-NEXT: slli a1, a1, 3 +; RV32-NEXT: li a3, 13 +; RV32-NEXT: mul a1, a1, a3 ; RV32-NEXT: add a1, sp, a1 ; RV32-NEXT: addi a1, a1, 16 ; RV32-NEXT: vl4r.v v4, (a1) # Unknown-size Folded Reload -; RV32-NEXT: vrgatherei16.vv v8, v16, v4 -; RV32-NEXT: addi a1, sp, 16 -; RV32-NEXT: vl4r.v v16, (a1) # Unknown-size Folded Reload -; RV32-NEXT: vrgatherei16.vv v8, v24, v16, v0.t +; RV32-NEXT: vrgatherei16.vv v8, v24, v4 +; RV32-NEXT: vmv1r.v v0, v2 +; RV32-NEXT: csrr a1, vlenb +; RV32-NEXT: slli a3, a1, 2 +; RV32-NEXT: add a1, a3, a1 +; RV32-NEXT: add a1, sp, a1 +; RV32-NEXT: addi a1, a1, 16 +; RV32-NEXT: vl4r.v v24, (a1) # Unknown-size Folded Reload +; RV32-NEXT: vrgatherei16.vv v8, v16, v24, v0.t ; RV32-NEXT: vsetivli zero, 12, e32, m4, tu, ma ; RV32-NEXT: csrr a1, vlenb -; RV32-NEXT: li a3, 20 -; RV32-NEXT: mul a1, a1, a3 +; RV32-NEXT: slli a3, a1, 4 +; RV32-NEXT: add a1, a3, a1 ; RV32-NEXT: add a1, sp, a1 ; RV32-NEXT: addi a1, a1, 16 ; RV32-NEXT: vl4r.v v12, (a1) # Unknown-size Folded Reload ; RV32-NEXT: vmv.v.v v12, v8 ; RV32-NEXT: csrr a1, vlenb -; RV32-NEXT: li a3, 20 -; RV32-NEXT: mul a1, a1, a3 +; RV32-NEXT: slli a3, a1, 4 +; RV32-NEXT: add a1, a3, a1 ; RV32-NEXT: add a1, sp, a1 ; RV32-NEXT: addi a1, a1, 16 ; RV32-NEXT: vs4r.v v12, (a1) # Unknown-size Folded Spill ; RV32-NEXT: vsetivli zero, 16, e32, m4, ta, mu ; RV32-NEXT: csrr a1, vlenb -; RV32-NEXT: slli a1, a1, 5 +; RV32-NEXT: li a3, 21 +; RV32-NEXT: mul a1, a1, a3 ; RV32-NEXT: add a1, sp, a1 ; RV32-NEXT: addi a1, a1, 16 -; RV32-NEXT: vl8r.v v16, (a1) # Unknown-size Folded Reload +; RV32-NEXT: vl8r.v v8, (a1) # Unknown-size Folded Reload +; RV32-NEXT: vmv4r.v v16, v8 ; RV32-NEXT: vslideup.vi v8, v16, 2 +; RV32-NEXT: csrr a1, vlenb +; RV32-NEXT: add a1, sp, a1 +; RV32-NEXT: addi a1, a1, 16 +; RV32-NEXT: vl1r.v v3, (a1) # Unknown-size Folded Reload ; RV32-NEXT: vmv1r.v v0, v3 ; RV32-NEXT: csrr a1, vlenb -; RV32-NEXT: li a3, 24 +; RV32-NEXT: li a3, 37 ; RV32-NEXT: mul a1, a1, a3 ; RV32-NEXT: add a1, sp, a1 ; RV32-NEXT: addi a1, a1, 16 @@ -283,36 +294,45 @@ define {<8 x i64>, <8 x i64>, <8 x i64>, <8 x i64>, <8 x i64>, <8 x i64>} @load_ ; RV32-NEXT: lui a1, %hi(.LCPI6_2) ; RV32-NEXT: addi a1, a1, %lo(.LCPI6_2) ; RV32-NEXT: vsetvli zero, a2, e32, m8, ta, mu -; RV32-NEXT: lui a3, %hi(.LCPI6_3) -; RV32-NEXT: addi a3, a3, %lo(.LCPI6_3) -; RV32-NEXT: vle16.v v24, (a1) -; RV32-NEXT: vle16.v v8, (a3) +; RV32-NEXT: vle16.v v8, (a1) +; RV32-NEXT: csrr a1, vlenb +; RV32-NEXT: li a3, 13 +; RV32-NEXT: mul a1, a1, a3 +; RV32-NEXT: add a1, sp, a1 +; RV32-NEXT: addi a1, a1, 16 +; RV32-NEXT: vs4r.v v8, (a1) # Unknown-size Folded Spill +; RV32-NEXT: lui a1, %hi(.LCPI6_3) +; RV32-NEXT: addi a1, a1, %lo(.LCPI6_3) +; RV32-NEXT: vle16.v v8, (a1) ; RV32-NEXT: csrr a1, vlenb -; RV32-NEXT: slli a1, a1, 3 +; RV32-NEXT: slli a3, a1, 2 +; RV32-NEXT: add a1, a3, a1 ; RV32-NEXT: add a1, sp, a1 ; RV32-NEXT: addi a1, a1, 16 ; RV32-NEXT: vs4r.v v8, (a1) # Unknown-size Folded Spill ; RV32-NEXT: csrr a1, vlenb -; RV32-NEXT: li a3, 40 +; RV32-NEXT: li a3, 45 ; RV32-NEXT: mul a1, a1, a3 ; RV32-NEXT: add a1, sp, a1 ; RV32-NEXT: addi a1, a1, 16 -; RV32-NEXT: vl8r.v v0, (a1) # Unknown-size Folded Reload -; RV32-NEXT: vrgatherei16.vv v8, v0, v24 +; RV32-NEXT: vl8r.v v24, (a1) # Unknown-size Folded Reload ; RV32-NEXT: csrr a1, vlenb -; RV32-NEXT: li a3, 12 +; RV32-NEXT: li a3, 13 ; RV32-NEXT: mul a1, a1, a3 ; RV32-NEXT: add a1, sp, a1 ; RV32-NEXT: addi a1, a1, 16 -; RV32-NEXT: vl1r.v v0, (a1) # Unknown-size Folded Reload +; RV32-NEXT: vl4r.v v4, (a1) # Unknown-size Folded Reload +; RV32-NEXT: vrgatherei16.vv v8, v24, v4 +; RV32-NEXT: vmv1r.v v0, v2 ; RV32-NEXT: csrr a1, vlenb -; RV32-NEXT: li a3, 48 +; RV32-NEXT: li a3, 29 ; RV32-NEXT: mul a1, a1, a3 ; RV32-NEXT: add a1, sp, a1 ; RV32-NEXT: addi a1, a1, 16 ; RV32-NEXT: vl8r.v v24, (a1) # Unknown-size Folded Reload ; RV32-NEXT: csrr a1, vlenb -; RV32-NEXT: slli a1, a1, 3 +; RV32-NEXT: slli a3, a1, 2 +; RV32-NEXT: add a1, a3, a1 ; RV32-NEXT: add a1, sp, a1 ; RV32-NEXT: addi a1, a1, 16 ; RV32-NEXT: vl4r.v v4, (a1) # Unknown-size Folded Reload @@ -320,8 +340,8 @@ define {<8 x i64>, <8 x i64>, <8 x i64>, <8 x i64>, <8 x i64>, <8 x i64>} @load_ ; RV32-NEXT: vsetivli zero, 12, e32, m4, tu, ma ; RV32-NEXT: vmv.v.v v20, v8 ; RV32-NEXT: csrr a1, vlenb -; RV32-NEXT: li a3, 12 -; RV32-NEXT: mul a1, a1, a3 +; RV32-NEXT: slli a3, a1, 2 +; RV32-NEXT: add a1, a3, a1 ; RV32-NEXT: add a1, sp, a1 ; RV32-NEXT: addi a1, a1, 16 ; RV32-NEXT: vs4r.v v20, (a1) # Unknown-size Folded Spill @@ -330,171 +350,178 @@ define {<8 x i64>, <8 x i64>, <8 x i64>, <8 x i64>, <8 x i64>, <8 x i64>} @load_ ; RV32-NEXT: vsetivli zero, 16, e32, m4, ta, mu ; RV32-NEXT: vle16.v v8, (a1) ; RV32-NEXT: csrr a1, vlenb -; RV32-NEXT: slli a1, a1, 5 +; RV32-NEXT: li a3, 21 +; RV32-NEXT: mul a1, a1, a3 ; RV32-NEXT: add a1, sp, a1 ; RV32-NEXT: addi a1, a1, 16 ; RV32-NEXT: vl8r.v v24, (a1) # Unknown-size Folded Reload ; RV32-NEXT: vrgatherei16.vv v12, v24, v8 +; RV32-NEXT: vmv1r.v v0, v3 +; RV32-NEXT: vslideup.vi v12, v16, 6, v0.t ; RV32-NEXT: csrr a1, vlenb -; RV32-NEXT: slli a1, a1, 2 +; RV32-NEXT: li a3, 13 +; RV32-NEXT: mul a1, a1, a3 ; RV32-NEXT: add a1, sp, a1 ; RV32-NEXT: addi a1, a1, 16 -; RV32-NEXT: vl1r.v v3, (a1) # Unknown-size Folded Reload -; RV32-NEXT: vmv1r.v v0, v3 -; RV32-NEXT: vslideup.vi v12, v16, 6, v0.t -; RV32-NEXT: vmv.v.v v4, v12 +; RV32-NEXT: vs4r.v v12, (a1) # Unknown-size Folded Spill ; RV32-NEXT: lui a1, %hi(.LCPI6_5) ; RV32-NEXT: addi a1, a1, %lo(.LCPI6_5) ; RV32-NEXT: vsetvli zero, a2, e32, m8, ta, mu -; RV32-NEXT: lui a3, %hi(.LCPI6_6) -; RV32-NEXT: addi a3, a3, %lo(.LCPI6_6) ; RV32-NEXT: vle16.v v24, (a1) -; RV32-NEXT: vle16.v v8, (a3) -; RV32-NEXT: csrr a1, vlenb -; RV32-NEXT: slli a1, a1, 3 -; RV32-NEXT: add a1, sp, a1 -; RV32-NEXT: addi a1, a1, 16 -; RV32-NEXT: vs4r.v v8, (a1) # Unknown-size Folded Spill -; RV32-NEXT: li a1, 960 -; RV32-NEXT: vmv.s.x v2, a1 +; RV32-NEXT: lui a1, %hi(.LCPI6_6) +; RV32-NEXT: addi a1, a1, %lo(.LCPI6_6) +; RV32-NEXT: li a3, 960 +; RV32-NEXT: vle16.v v4, (a1) +; RV32-NEXT: vmv.s.x v0, a3 +; RV32-NEXT: addi a1, sp, 16 +; RV32-NEXT: vs1r.v v0, (a1) # Unknown-size Folded Spill ; RV32-NEXT: csrr a1, vlenb -; RV32-NEXT: li a3, 40 +; RV32-NEXT: li a3, 45 ; RV32-NEXT: mul a1, a1, a3 ; RV32-NEXT: add a1, sp, a1 ; RV32-NEXT: addi a1, a1, 16 ; RV32-NEXT: vl8r.v v16, (a1) # Unknown-size Folded Reload ; RV32-NEXT: vrgatherei16.vv v8, v16, v24 -; RV32-NEXT: vmv1r.v v0, v2 ; RV32-NEXT: csrr a1, vlenb -; RV32-NEXT: li a3, 48 +; RV32-NEXT: li a3, 29 ; RV32-NEXT: mul a1, a1, a3 ; RV32-NEXT: add a1, sp, a1 ; RV32-NEXT: addi a1, a1, 16 ; RV32-NEXT: vl8r.v v24, (a1) # Unknown-size Folded Reload +; RV32-NEXT: vrgatherei16.vv v8, v24, v4, v0.t +; RV32-NEXT: vsetivli zero, 10, e32, m4, tu, ma ; RV32-NEXT: csrr a1, vlenb -; RV32-NEXT: slli a1, a1, 3 +; RV32-NEXT: li a3, 13 +; RV32-NEXT: mul a1, a1, a3 ; RV32-NEXT: add a1, sp, a1 ; RV32-NEXT: addi a1, a1, 16 -; RV32-NEXT: vl4r.v v16, (a1) # Unknown-size Folded Reload -; RV32-NEXT: vrgatherei16.vv v8, v24, v16, v0.t -; RV32-NEXT: vsetivli zero, 10, e32, m4, tu, ma -; RV32-NEXT: vmv.v.v v4, v8 +; RV32-NEXT: vl4r.v v12, (a1) # Unknown-size Folded Reload +; RV32-NEXT: vmv.v.v v12, v8 ; RV32-NEXT: csrr a1, vlenb -; RV32-NEXT: slli a1, a1, 3 +; RV32-NEXT: li a3, 13 +; RV32-NEXT: mul a1, a1, a3 ; RV32-NEXT: add a1, sp, a1 ; RV32-NEXT: addi a1, a1, 16 -; RV32-NEXT: vs4r.v v4, (a1) # Unknown-size Folded Spill +; RV32-NEXT: vs4r.v v12, (a1) # Unknown-size Folded Spill ; RV32-NEXT: lui a1, %hi(.LCPI6_7) ; RV32-NEXT: addi a1, a1, %lo(.LCPI6_7) ; RV32-NEXT: vsetivli zero, 16, e32, m4, ta, mu ; RV32-NEXT: vle16.v v8, (a1) ; RV32-NEXT: csrr a1, vlenb -; RV32-NEXT: slli a1, a1, 5 +; RV32-NEXT: li a3, 21 +; RV32-NEXT: mul a1, a1, a3 ; RV32-NEXT: add a1, sp, a1 ; RV32-NEXT: addi a1, a1, 16 -; RV32-NEXT: vl8r.v v24, (a1) # Unknown-size Folded Reload -; RV32-NEXT: vrgatherei16.vv v28, v24, v8 +; RV32-NEXT: vl8r.v v16, (a1) # Unknown-size Folded Reload +; RV32-NEXT: vrgatherei16.vv v4, v16, v8 ; RV32-NEXT: vmv1r.v v0, v3 ; RV32-NEXT: csrr a1, vlenb -; RV32-NEXT: li a3, 24 +; RV32-NEXT: li a3, 37 ; RV32-NEXT: mul a1, a1, a3 ; RV32-NEXT: add a1, sp, a1 ; RV32-NEXT: addi a1, a1, 16 ; RV32-NEXT: vl8r.v v8, (a1) # Unknown-size Folded Reload -; RV32-NEXT: vslideup.vi v28, v8, 4, v0.t -; RV32-NEXT: vmv.v.v v4, v28 +; RV32-NEXT: vslideup.vi v4, v8, 4, v0.t ; RV32-NEXT: lui a1, %hi(.LCPI6_8) ; RV32-NEXT: addi a1, a1, %lo(.LCPI6_8) ; RV32-NEXT: vsetvli zero, a2, e32, m8, ta, mu -; RV32-NEXT: lui a3, %hi(.LCPI6_9) -; RV32-NEXT: addi a3, a3, %lo(.LCPI6_9) -; RV32-NEXT: vle16.v v28, (a1) -; RV32-NEXT: vle16.v v24, (a3) +; RV32-NEXT: vle16.v v0, (a1) +; RV32-NEXT: lui a1, %hi(.LCPI6_9) +; RV32-NEXT: addi a1, a1, %lo(.LCPI6_9) +; RV32-NEXT: vle16.v v8, (a1) ; RV32-NEXT: csrr a1, vlenb -; RV32-NEXT: li a3, 40 -; RV32-NEXT: mul a1, a1, a3 ; RV32-NEXT: add a1, sp, a1 ; RV32-NEXT: addi a1, a1, 16 -; RV32-NEXT: vl8r.v v16, (a1) # Unknown-size Folded Reload -; RV32-NEXT: vrgatherei16.vv v8, v16, v28 -; RV32-NEXT: vmv1r.v v0, v2 +; RV32-NEXT: vs4r.v v8, (a1) # Unknown-size Folded Spill ; RV32-NEXT: csrr a1, vlenb -; RV32-NEXT: li a3, 48 +; RV32-NEXT: li a3, 45 ; RV32-NEXT: mul a1, a1, a3 ; RV32-NEXT: add a1, sp, a1 ; RV32-NEXT: addi a1, a1, 16 ; RV32-NEXT: vl8r.v v16, (a1) # Unknown-size Folded Reload -; RV32-NEXT: vrgatherei16.vv v8, v16, v24, v0.t +; RV32-NEXT: vrgatherei16.vv v8, v16, v0 +; RV32-NEXT: addi a1, sp, 16 +; RV32-NEXT: vl1r.v v0, (a1) # Unknown-size Folded Reload +; RV32-NEXT: csrr a1, vlenb +; RV32-NEXT: add a1, sp, a1 +; RV32-NEXT: addi a1, a1, 16 +; RV32-NEXT: vl4r.v v16, (a1) # Unknown-size Folded Reload +; RV32-NEXT: vrgatherei16.vv v8, v24, v16, v0.t ; RV32-NEXT: vsetivli zero, 10, e32, m4, tu, ma ; RV32-NEXT: vmv.v.v v4, v8 ; RV32-NEXT: csrr a1, vlenb -; RV32-NEXT: slli a1, a1, 2 ; RV32-NEXT: add a1, sp, a1 ; RV32-NEXT: addi a1, a1, 16 ; RV32-NEXT: vs4r.v v4, (a1) # Unknown-size Folded Spill ; RV32-NEXT: vsetivli zero, 16, e32, m4, ta, mu -; RV32-NEXT: lui a1, %hi(.LCPI6_10) -; RV32-NEXT: addi a1, a1, %lo(.LCPI6_10) -; RV32-NEXT: vle16.v v4, (a1) -; RV32-NEXT: lui a1, 15 -; RV32-NEXT: vmv.s.x v6, a1 ; RV32-NEXT: csrr a1, vlenb -; RV32-NEXT: slli a1, a1, 5 +; RV32-NEXT: li a3, 21 +; RV32-NEXT: mul a1, a1, a3 ; RV32-NEXT: add a1, sp, a1 ; RV32-NEXT: addi a1, a1, 16 -; RV32-NEXT: vl8r.v v24, (a1) # Unknown-size Folded Reload -; RV32-NEXT: vslideup.vi v28, v24, 6 -; RV32-NEXT: vmv1r.v v0, v6 +; RV32-NEXT: vl8r.v v8, (a1) # Unknown-size Folded Reload +; RV32-NEXT: vslideup.vi v12, v8, 6 +; RV32-NEXT: lui a1, %hi(.LCPI6_10) +; RV32-NEXT: addi a1, a1, %lo(.LCPI6_10) +; RV32-NEXT: vle16.v v8, (a1) +; RV32-NEXT: lui a1, 15 +; RV32-NEXT: vmv.s.x v24, a1 +; RV32-NEXT: vmv1r.v v0, v24 ; RV32-NEXT: csrr a1, vlenb -; RV32-NEXT: li a3, 24 +; RV32-NEXT: li a3, 37 ; RV32-NEXT: mul a1, a1, a3 ; RV32-NEXT: add a1, sp, a1 ; RV32-NEXT: addi a1, a1, 16 -; RV32-NEXT: vl8r.v v8, (a1) # Unknown-size Folded Reload -; RV32-NEXT: vrgatherei16.vv v28, v8, v4, v0.t +; RV32-NEXT: vl8r.v v16, (a1) # Unknown-size Folded Reload +; RV32-NEXT: vrgatherei16.vv v12, v16, v8, v0.t +; RV32-NEXT: vmv.v.v v28, v12 ; RV32-NEXT: lui a1, %hi(.LCPI6_11) ; RV32-NEXT: addi a1, a1, %lo(.LCPI6_11) ; RV32-NEXT: vsetvli zero, a2, e32, m8, ta, mu -; RV32-NEXT: lui a3, %hi(.LCPI6_12) -; RV32-NEXT: addi a3, a3, %lo(.LCPI6_12) ; RV32-NEXT: vle16.v v0, (a1) -; RV32-NEXT: vle16.v v24, (a3) -; RV32-NEXT: li a1, 1008 -; RV32-NEXT: vmv.s.x v7, a1 -; RV32-NEXT: csrr a1, vlenb -; RV32-NEXT: slli a1, a1, 5 -; RV32-NEXT: add a1, sp, a1 -; RV32-NEXT: addi a1, a1, 16 -; RV32-NEXT: vs1r.v v7, (a1) # Unknown-size Folded Spill +; RV32-NEXT: lui a1, %hi(.LCPI6_12) +; RV32-NEXT: addi a1, a1, %lo(.LCPI6_12) +; RV32-NEXT: li a3, 1008 +; RV32-NEXT: vle16.v v4, (a1) +; RV32-NEXT: vmv.s.x v25, a3 +; RV32-NEXT: addi a1, sp, 16 +; RV32-NEXT: vs1r.v v25, (a1) # Unknown-size Folded Spill ; RV32-NEXT: csrr a1, vlenb -; RV32-NEXT: li a3, 40 +; RV32-NEXT: li a3, 45 ; RV32-NEXT: mul a1, a1, a3 ; RV32-NEXT: add a1, sp, a1 ; RV32-NEXT: addi a1, a1, 16 ; RV32-NEXT: vl8r.v v16, (a1) # Unknown-size Folded Reload ; RV32-NEXT: vrgatherei16.vv v8, v16, v0 -; RV32-NEXT: vmv1r.v v0, v7 +; RV32-NEXT: vmv1r.v v0, v25 ; RV32-NEXT: csrr a1, vlenb -; RV32-NEXT: li a3, 48 +; RV32-NEXT: li a3, 29 ; RV32-NEXT: mul a1, a1, a3 ; RV32-NEXT: add a1, sp, a1 ; RV32-NEXT: addi a1, a1, 16 ; RV32-NEXT: vl8r.v v16, (a1) # Unknown-size Folded Reload -; RV32-NEXT: vrgatherei16.vv v8, v16, v24, v0.t +; RV32-NEXT: vrgatherei16.vv v8, v16, v4, v0.t ; RV32-NEXT: vsetivli zero, 10, e32, m4, tu, ma ; RV32-NEXT: vmv.v.v v28, v8 +; RV32-NEXT: csrr a1, vlenb +; RV32-NEXT: li a3, 21 +; RV32-NEXT: mul a1, a1, a3 +; RV32-NEXT: add a1, sp, a1 +; RV32-NEXT: addi a1, a1, 16 +; RV32-NEXT: vs4r.v v28, (a1) # Unknown-size Folded Spill ; RV32-NEXT: lui a1, %hi(.LCPI6_13) ; RV32-NEXT: addi a1, a1, %lo(.LCPI6_13) ; RV32-NEXT: vsetivli zero, 16, e32, m4, ta, mu ; RV32-NEXT: vle16.v v8, (a1) -; RV32-NEXT: vmv1r.v v0, v6 +; RV32-NEXT: vmv1r.v v0, v24 ; RV32-NEXT: csrr a1, vlenb -; RV32-NEXT: slli a1, a1, 4 +; RV32-NEXT: slli a3, a1, 3 +; RV32-NEXT: add a1, a3, a1 ; RV32-NEXT: add a1, sp, a1 ; RV32-NEXT: addi a1, a1, 16 ; RV32-NEXT: vl4r.v v24, (a1) # Unknown-size Folded Reload ; RV32-NEXT: csrr a1, vlenb -; RV32-NEXT: li a3, 24 +; RV32-NEXT: li a3, 37 ; RV32-NEXT: mul a1, a1, a3 ; RV32-NEXT: add a1, sp, a1 ; RV32-NEXT: addi a1, a1, 16 @@ -503,79 +530,70 @@ define {<8 x i64>, <8 x i64>, <8 x i64>, <8 x i64>, <8 x i64>, <8 x i64>} @load_ ; RV32-NEXT: lui a1, %hi(.LCPI6_14) ; RV32-NEXT: addi a1, a1, %lo(.LCPI6_14) ; RV32-NEXT: vsetvli zero, a2, e32, m8, ta, mu -; RV32-NEXT: lui a2, %hi(.LCPI6_15) -; RV32-NEXT: addi a2, a2, %lo(.LCPI6_15) ; RV32-NEXT: vle16.v v16, (a1) -; RV32-NEXT: vle16.v v8, (a2) -; RV32-NEXT: csrr a1, vlenb -; RV32-NEXT: li a2, 24 -; RV32-NEXT: mul a1, a1, a2 -; RV32-NEXT: add a1, sp, a1 -; RV32-NEXT: addi a1, a1, 16 -; RV32-NEXT: vs4r.v v8, (a1) # Unknown-size Folded Spill +; RV32-NEXT: lui a1, %hi(.LCPI6_15) +; RV32-NEXT: addi a1, a1, %lo(.LCPI6_15) +; RV32-NEXT: vle16.v v28, (a1) ; RV32-NEXT: csrr a1, vlenb -; RV32-NEXT: li a2, 40 +; RV32-NEXT: li a2, 45 ; RV32-NEXT: mul a1, a1, a2 ; RV32-NEXT: add a1, sp, a1 ; RV32-NEXT: addi a1, a1, 16 ; RV32-NEXT: vl8r.v v0, (a1) # Unknown-size Folded Reload ; RV32-NEXT: vrgatherei16.vv v8, v0, v16 -; RV32-NEXT: csrr a1, vlenb -; RV32-NEXT: slli a1, a1, 5 -; RV32-NEXT: add a1, sp, a1 -; RV32-NEXT: addi a1, a1, 16 +; RV32-NEXT: addi a1, sp, 16 ; RV32-NEXT: vl1r.v v0, (a1) # Unknown-size Folded Reload ; RV32-NEXT: csrr a1, vlenb -; RV32-NEXT: li a2, 48 +; RV32-NEXT: li a2, 29 ; RV32-NEXT: mul a1, a1, a2 ; RV32-NEXT: add a1, sp, a1 ; RV32-NEXT: addi a1, a1, 16 ; RV32-NEXT: vl8r.v v16, (a1) # Unknown-size Folded Reload -; RV32-NEXT: csrr a1, vlenb -; RV32-NEXT: li a2, 24 -; RV32-NEXT: mul a1, a1, a2 -; RV32-NEXT: add a1, sp, a1 -; RV32-NEXT: addi a1, a1, 16 -; RV32-NEXT: vl4r.v v4, (a1) # Unknown-size Folded Reload -; RV32-NEXT: vrgatherei16.vv v8, v16, v4, v0.t +; RV32-NEXT: vrgatherei16.vv v8, v16, v28, v0.t ; RV32-NEXT: vsetivli zero, 10, e32, m4, tu, ma ; RV32-NEXT: vmv.v.v v24, v8 ; RV32-NEXT: addi a1, a0, 320 ; RV32-NEXT: vsetivli zero, 16, e32, m4, ta, ma ; RV32-NEXT: vse32.v v24, (a1) ; RV32-NEXT: addi a1, a0, 256 -; RV32-NEXT: vse32.v v28, (a1) +; RV32-NEXT: csrr a2, vlenb +; RV32-NEXT: li a3, 21 +; RV32-NEXT: mul a2, a2, a3 +; RV32-NEXT: add a2, sp, a2 +; RV32-NEXT: addi a2, a2, 16 +; RV32-NEXT: vl4r.v v8, (a2) # Unknown-size Folded Reload +; RV32-NEXT: vse32.v v8, (a1) ; RV32-NEXT: addi a1, a0, 192 ; RV32-NEXT: csrr a2, vlenb -; RV32-NEXT: slli a2, a2, 2 ; RV32-NEXT: add a2, sp, a2 ; RV32-NEXT: addi a2, a2, 16 ; RV32-NEXT: vl4r.v v8, (a2) # Unknown-size Folded Reload ; RV32-NEXT: vse32.v v8, (a1) ; RV32-NEXT: addi a1, a0, 128 ; RV32-NEXT: csrr a2, vlenb -; RV32-NEXT: slli a2, a2, 3 +; RV32-NEXT: li a3, 13 +; RV32-NEXT: mul a2, a2, a3 ; RV32-NEXT: add a2, sp, a2 ; RV32-NEXT: addi a2, a2, 16 ; RV32-NEXT: vl4r.v v8, (a2) # Unknown-size Folded Reload ; RV32-NEXT: vse32.v v8, (a1) ; RV32-NEXT: addi a1, a0, 64 ; RV32-NEXT: csrr a2, vlenb -; RV32-NEXT: li a3, 12 -; RV32-NEXT: mul a2, a2, a3 +; RV32-NEXT: slli a3, a2, 2 +; RV32-NEXT: add a2, a3, a2 ; RV32-NEXT: add a2, sp, a2 ; RV32-NEXT: addi a2, a2, 16 ; RV32-NEXT: vl4r.v v8, (a2) # Unknown-size Folded Reload ; RV32-NEXT: vse32.v v8, (a1) ; RV32-NEXT: csrr a1, vlenb -; RV32-NEXT: li a2, 20 -; RV32-NEXT: mul a1, a1, a2 +; RV32-NEXT: slli a2, a1, 4 +; RV32-NEXT: add a1, a2, a1 ; RV32-NEXT: add a1, sp, a1 ; RV32-NEXT: addi a1, a1, 16 ; RV32-NEXT: vl4r.v v8, (a1) # Unknown-size Folded Reload ; RV32-NEXT: vse32.v v8, (a0) ; RV32-NEXT: csrr a0, vlenb -; RV32-NEXT: li a1, 56 +; RV32-NEXT: li a1, 54 ; RV32-NEXT: mul a0, a0, a1 ; RV32-NEXT: add sp, sp, a0 ; RV32-NEXT: addi sp, sp, 16 @@ -586,320 +604,324 @@ define {<8 x i64>, <8 x i64>, <8 x i64>, <8 x i64>, <8 x i64>, <8 x i64>} @load_ ; RV64-NEXT: addi sp, sp, -16 ; RV64-NEXT: .cfi_def_cfa_offset 16 ; RV64-NEXT: csrr a2, vlenb -; RV64-NEXT: li a3, 52 +; RV64-NEXT: li a3, 56 ; RV64-NEXT: mul a2, a2, a3 ; RV64-NEXT: sub sp, sp, a2 -; RV64-NEXT: .cfi_escape 0x0f, 0x0d, 0x72, 0x00, 0x11, 0x10, 0x22, 0x11, 0x34, 0x92, 0xa2, 0x38, 0x00, 0x1e, 0x22 # sp + 16 + 52 * vlenb +; RV64-NEXT: .cfi_escape 0x0f, 0x0d, 0x72, 0x00, 0x11, 0x10, 0x22, 0x11, 0x38, 0x92, 0xa2, 0x38, 0x00, 0x1e, 0x22 # sp + 16 + 56 * vlenb ; RV64-NEXT: vsetivli zero, 16, e64, m8, ta, ma ; RV64-NEXT: addi a2, a1, 256 ; RV64-NEXT: vle64.v v16, (a2) ; RV64-NEXT: csrr a2, vlenb -; RV64-NEXT: li a3, 27 -; RV64-NEXT: mul a2, a2, a3 +; RV64-NEXT: slli a2, a2, 5 ; RV64-NEXT: add a2, sp, a2 ; RV64-NEXT: addi a2, a2, 16 ; RV64-NEXT: vs8r.v v16, (a2) # Unknown-size Folded Spill ; RV64-NEXT: addi a2, a1, 128 ; RV64-NEXT: vle64.v v8, (a2) ; RV64-NEXT: csrr a2, vlenb -; RV64-NEXT: li a3, 35 +; RV64-NEXT: li a3, 40 ; RV64-NEXT: mul a2, a2, a3 ; RV64-NEXT: add a2, sp, a2 ; RV64-NEXT: addi a2, a2, 16 ; RV64-NEXT: vs8r.v v8, (a2) # Unknown-size Folded Spill -; RV64-NEXT: vle64.v v8, (a1) -; RV64-NEXT: csrr a1, vlenb -; RV64-NEXT: li a2, 43 -; RV64-NEXT: mul a1, a1, a2 -; RV64-NEXT: add a1, sp, a1 -; RV64-NEXT: addi a1, a1, 16 -; RV64-NEXT: vs8r.v v8, (a1) # Unknown-size Folded Spill +; RV64-NEXT: vle64.v v24, (a1) ; RV64-NEXT: vsetivli zero, 8, e64, m4, ta, ma ; RV64-NEXT: vrgather.vi v8, v16, 4 ; RV64-NEXT: li a1, 128 -; RV64-NEXT: vmv.s.x v0, a1 +; RV64-NEXT: vmv.s.x v4, a1 ; RV64-NEXT: vsetivli zero, 8, e64, m8, ta, ma -; RV64-NEXT: vslidedown.vi v24, v16, 8 -; RV64-NEXT: vsetivli zero, 8, e64, m4, ta, mu -; RV64-NEXT: vmv1r.v v28, v0 +; RV64-NEXT: vslidedown.vi v16, v16, 8 ; RV64-NEXT: csrr a1, vlenb -; RV64-NEXT: slli a2, a1, 1 -; RV64-NEXT: add a1, a2, a1 +; RV64-NEXT: li a2, 24 +; RV64-NEXT: mul a1, a1, a2 ; RV64-NEXT: add a1, sp, a1 ; RV64-NEXT: addi a1, a1, 16 -; RV64-NEXT: vs1r.v v0, (a1) # Unknown-size Folded Spill -; RV64-NEXT: vrgather.vi v8, v24, 2, v0.t +; RV64-NEXT: vs8r.v v16, (a1) # Unknown-size Folded Spill +; RV64-NEXT: vsetivli zero, 8, e64, m4, ta, mu +; RV64-NEXT: vmv1r.v v0, v4 ; RV64-NEXT: csrr a1, vlenb -; RV64-NEXT: li a2, 19 +; RV64-NEXT: li a2, 20 ; RV64-NEXT: mul a1, a1, a2 ; RV64-NEXT: add a1, sp, a1 ; RV64-NEXT: addi a1, a1, 16 -; RV64-NEXT: vs8r.v v24, (a1) # Unknown-size Folded Spill -; RV64-NEXT: vmv.v.v v4, v8 +; RV64-NEXT: vs1r.v v4, (a1) # Unknown-size Folded Spill +; RV64-NEXT: vrgather.vi v8, v16, 2, v0.t +; RV64-NEXT: vmv.v.v v20, v8 ; RV64-NEXT: vsetivli zero, 16, e16, m2, ta, ma ; RV64-NEXT: li a1, 6 ; RV64-NEXT: vid.v v8 -; RV64-NEXT: vmul.vx v2, v8, a1 +; RV64-NEXT: vmul.vx v6, v8, a1 ; RV64-NEXT: vsetvli zero, zero, e64, m8, ta, ma +; RV64-NEXT: vrgatherei16.vv v8, v24, v6 ; RV64-NEXT: csrr a1, vlenb -; RV64-NEXT: li a2, 43 +; RV64-NEXT: li a2, 48 ; RV64-NEXT: mul a1, a1, a2 ; RV64-NEXT: add a1, sp, a1 ; RV64-NEXT: addi a1, a1, 16 -; RV64-NEXT: vl8r.v v16, (a1) # Unknown-size Folded Reload -; RV64-NEXT: vrgatherei16.vv v8, v16, v2 +; RV64-NEXT: vs8r.v v24, (a1) # Unknown-size Folded Spill ; RV64-NEXT: vsetvli zero, zero, e16, m2, ta, ma ; RV64-NEXT: li a1, 56 -; RV64-NEXT: vmv.s.x v1, a1 -; RV64-NEXT: vadd.vi v30, v2, -16 +; RV64-NEXT: vmv.s.x v5, a1 +; RV64-NEXT: vadd.vi v16, v6, -16 ; RV64-NEXT: vsetvli zero, zero, e64, m8, ta, mu -; RV64-NEXT: vmv1r.v v0, v1 +; RV64-NEXT: vmv1r.v v0, v5 ; RV64-NEXT: csrr a1, vlenb -; RV64-NEXT: li a2, 35 +; RV64-NEXT: li a2, 40 ; RV64-NEXT: mul a1, a1, a2 ; RV64-NEXT: add a1, sp, a1 ; RV64-NEXT: addi a1, a1, 16 -; RV64-NEXT: vl8r.v v16, (a1) # Unknown-size Folded Reload -; RV64-NEXT: vrgatherei16.vv v8, v16, v30, v0.t +; RV64-NEXT: vl8r.v v24, (a1) # Unknown-size Folded Reload +; RV64-NEXT: vrgatherei16.vv v8, v24, v16, v0.t ; RV64-NEXT: vsetivli zero, 6, e64, m4, tu, ma -; RV64-NEXT: vmv.v.v v4, v8 +; RV64-NEXT: vmv.v.v v20, v8 ; RV64-NEXT: csrr a1, vlenb -; RV64-NEXT: slli a2, a1, 4 -; RV64-NEXT: sub a1, a2, a1 +; RV64-NEXT: slli a1, a1, 4 ; RV64-NEXT: add a1, sp, a1 ; RV64-NEXT: addi a1, a1, 16 -; RV64-NEXT: vs4r.v v4, (a1) # Unknown-size Folded Spill +; RV64-NEXT: vs4r.v v20, (a1) # Unknown-size Folded Spill ; RV64-NEXT: vsetivli zero, 8, e64, m4, ta, mu ; RV64-NEXT: csrr a1, vlenb -; RV64-NEXT: li a2, 27 -; RV64-NEXT: mul a1, a1, a2 +; RV64-NEXT: slli a1, a1, 5 ; RV64-NEXT: add a1, sp, a1 ; RV64-NEXT: addi a1, a1, 16 ; RV64-NEXT: vl8r.v v16, (a1) # Unknown-size Folded Reload -; RV64-NEXT: vrgather.vi v4, v16, 5 -; RV64-NEXT: vmv1r.v v0, v28 -; RV64-NEXT: vrgather.vi v4, v24, 3, v0.t -; RV64-NEXT: vsetivli zero, 16, e16, m2, ta, ma -; RV64-NEXT: addi a1, sp, 16 -; RV64-NEXT: vs2r.v v2, (a1) # Unknown-size Folded Spill -; RV64-NEXT: vadd.vi v16, v2, 1 -; RV64-NEXT: vsetvli zero, zero, e64, m8, ta, ma +; RV64-NEXT: vrgather.vi v24, v16, 5 +; RV64-NEXT: vmv1r.v v0, v4 ; RV64-NEXT: csrr a1, vlenb -; RV64-NEXT: li a2, 43 +; RV64-NEXT: li a2, 24 ; RV64-NEXT: mul a1, a1, a2 ; RV64-NEXT: add a1, sp, a1 ; RV64-NEXT: addi a1, a1, 16 -; RV64-NEXT: vl8r.v v24, (a1) # Unknown-size Folded Reload -; RV64-NEXT: vrgatherei16.vv v8, v24, v16 -; RV64-NEXT: vsetvli zero, zero, e16, m2, ta, ma -; RV64-NEXT: vadd.vi v16, v2, -15 +; RV64-NEXT: vl8r.v v16, (a1) # Unknown-size Folded Reload +; RV64-NEXT: vrgather.vi v24, v16, 3, v0.t +; RV64-NEXT: vsetivli zero, 16, e16, m2, ta, ma +; RV64-NEXT: vadd.vi v28, v6, 1 +; RV64-NEXT: vsetvli zero, zero, e64, m8, ta, ma ; RV64-NEXT: csrr a1, vlenb -; RV64-NEXT: li a2, 11 +; RV64-NEXT: li a2, 48 ; RV64-NEXT: mul a1, a1, a2 ; RV64-NEXT: add a1, sp, a1 ; RV64-NEXT: addi a1, a1, 16 -; RV64-NEXT: vs2r.v v16, (a1) # Unknown-size Folded Spill +; RV64-NEXT: vl8r.v v16, (a1) # Unknown-size Folded Reload +; RV64-NEXT: vrgatherei16.vv v8, v16, v28 +; RV64-NEXT: vsetvli zero, zero, e16, m2, ta, ma +; RV64-NEXT: vadd.vi v28, v6, -15 ; RV64-NEXT: vsetvli zero, zero, e64, m8, ta, mu -; RV64-NEXT: vmv1r.v v0, v1 +; RV64-NEXT: vmv1r.v v0, v5 ; RV64-NEXT: csrr a1, vlenb -; RV64-NEXT: li a2, 35 +; RV64-NEXT: li a2, 40 ; RV64-NEXT: mul a1, a1, a2 ; RV64-NEXT: add a1, sp, a1 ; RV64-NEXT: addi a1, a1, 16 ; RV64-NEXT: vl8r.v v16, (a1) # Unknown-size Folded Reload +; RV64-NEXT: vrgatherei16.vv v8, v16, v28, v0.t +; RV64-NEXT: vsetivli zero, 6, e64, m4, tu, ma +; RV64-NEXT: vmv.v.v v24, v8 ; RV64-NEXT: csrr a1, vlenb -; RV64-NEXT: li a2, 11 +; RV64-NEXT: li a2, 12 ; RV64-NEXT: mul a1, a1, a2 ; RV64-NEXT: add a1, sp, a1 ; RV64-NEXT: addi a1, a1, 16 -; RV64-NEXT: vl2r.v v2, (a1) # Unknown-size Folded Reload -; RV64-NEXT: vrgatherei16.vv v8, v16, v2, v0.t -; RV64-NEXT: vsetivli zero, 6, e64, m4, tu, ma -; RV64-NEXT: vmv.v.v v4, v8 +; RV64-NEXT: vs4r.v v24, (a1) # Unknown-size Folded Spill +; RV64-NEXT: vsetivli zero, 16, e16, m2, ta, ma +; RV64-NEXT: vmv2r.v v26, v6 +; RV64-NEXT: vadd.vi v24, v6, 2 +; RV64-NEXT: vsetvli zero, zero, e64, m8, ta, ma ; RV64-NEXT: csrr a1, vlenb -; RV64-NEXT: li a2, 11 +; RV64-NEXT: li a2, 48 ; RV64-NEXT: mul a1, a1, a2 ; RV64-NEXT: add a1, sp, a1 ; RV64-NEXT: addi a1, a1, 16 -; RV64-NEXT: vs4r.v v4, (a1) # Unknown-size Folded Spill -; RV64-NEXT: vsetivli zero, 16, e16, m2, ta, ma -; RV64-NEXT: addi a1, sp, 16 -; RV64-NEXT: vl2r.v v2, (a1) # Unknown-size Folded Reload -; RV64-NEXT: vadd.vi v6, v2, 2 -; RV64-NEXT: vsetvli zero, zero, e64, m8, ta, ma -; RV64-NEXT: vrgatherei16.vv v8, v24, v6 +; RV64-NEXT: vl8r.v v0, (a1) # Unknown-size Folded Reload +; RV64-NEXT: vrgatherei16.vv v8, v0, v24 ; RV64-NEXT: vsetvli zero, zero, e16, m2, ta, ma ; RV64-NEXT: li a1, 24 -; RV64-NEXT: vmv.s.x v7, a1 -; RV64-NEXT: vadd.vi v26, v2, -14 +; RV64-NEXT: vmv.s.x v0, a1 +; RV64-NEXT: csrr a1, vlenb +; RV64-NEXT: slli a1, a1, 1 +; RV64-NEXT: add a1, sp, a1 +; RV64-NEXT: addi a1, a1, 16 +; RV64-NEXT: vs1r.v v0, (a1) # Unknown-size Folded Spill +; RV64-NEXT: vadd.vi v24, v26, -14 +; RV64-NEXT: vmv2r.v v6, v26 ; RV64-NEXT: vsetvli zero, zero, e64, m8, ta, mu -; RV64-NEXT: vmv1r.v v0, v7 -; RV64-NEXT: vrgatherei16.vv v8, v16, v26, v0.t +; RV64-NEXT: vrgatherei16.vv v8, v16, v24, v0.t ; RV64-NEXT: vsetivli zero, 4, e32, m1, ta, ma ; RV64-NEXT: vmv.v.i v12, 6 ; RV64-NEXT: vsetivli zero, 8, e64, m4, ta, mu ; RV64-NEXT: csrr a1, vlenb -; RV64-NEXT: li a2, 27 -; RV64-NEXT: mul a1, a1, a2 +; RV64-NEXT: slli a1, a1, 5 ; RV64-NEXT: add a1, sp, a1 ; RV64-NEXT: addi a1, a1, 16 ; RV64-NEXT: vl8r.v v24, (a1) # Unknown-size Folded Reload -; RV64-NEXT: vrgatherei16.vv v16, v24, v12 +; RV64-NEXT: vrgatherei16.vv v20, v24, v12 ; RV64-NEXT: csrr a1, vlenb -; RV64-NEXT: slli a2, a1, 1 -; RV64-NEXT: add a1, a2, a1 +; RV64-NEXT: li a2, 20 +; RV64-NEXT: mul a1, a1, a2 ; RV64-NEXT: add a1, sp, a1 ; RV64-NEXT: addi a1, a1, 16 -; RV64-NEXT: vl1r.v v6, (a1) # Unknown-size Folded Reload -; RV64-NEXT: vmv1r.v v0, v6 +; RV64-NEXT: vl1r.v v0, (a1) # Unknown-size Folded Reload ; RV64-NEXT: csrr a1, vlenb -; RV64-NEXT: li a2, 19 +; RV64-NEXT: li a2, 24 ; RV64-NEXT: mul a1, a1, a2 ; RV64-NEXT: add a1, sp, a1 ; RV64-NEXT: addi a1, a1, 16 ; RV64-NEXT: vl8r.v v24, (a1) # Unknown-size Folded Reload -; RV64-NEXT: vrgather.vi v16, v24, 4, v0.t +; RV64-NEXT: vrgather.vi v20, v24, 4, v0.t ; RV64-NEXT: vsetivli zero, 5, e64, m4, tu, ma -; RV64-NEXT: vmv.v.v v16, v8 +; RV64-NEXT: vmv.v.v v20, v8 ; RV64-NEXT: csrr a1, vlenb -; RV64-NEXT: slli a2, a1, 3 -; RV64-NEXT: sub a1, a2, a1 +; RV64-NEXT: slli a1, a1, 3 ; RV64-NEXT: add a1, sp, a1 ; RV64-NEXT: addi a1, a1, 16 -; RV64-NEXT: vs4r.v v16, (a1) # Unknown-size Folded Spill +; RV64-NEXT: vs4r.v v20, (a1) # Unknown-size Folded Spill ; RV64-NEXT: vsetivli zero, 16, e16, m2, ta, ma -; RV64-NEXT: vadd.vi v28, v2, 3 +; RV64-NEXT: vmv2r.v v10, v6 +; RV64-NEXT: csrr a1, vlenb +; RV64-NEXT: li a2, 6 +; RV64-NEXT: mul a1, a1, a2 +; RV64-NEXT: add a1, sp, a1 +; RV64-NEXT: addi a1, a1, 16 +; RV64-NEXT: vs2r.v v6, (a1) # Unknown-size Folded Spill +; RV64-NEXT: vadd.vi v8, v6, 3 ; RV64-NEXT: vsetvli zero, zero, e64, m8, ta, ma ; RV64-NEXT: csrr a1, vlenb -; RV64-NEXT: li a2, 43 +; RV64-NEXT: li a2, 48 ; RV64-NEXT: mul a1, a1, a2 ; RV64-NEXT: add a1, sp, a1 ; RV64-NEXT: addi a1, a1, 16 -; RV64-NEXT: vl8r.v v16, (a1) # Unknown-size Folded Reload -; RV64-NEXT: vrgatherei16.vv v8, v16, v28 +; RV64-NEXT: vl8r.v v0, (a1) # Unknown-size Folded Reload +; RV64-NEXT: vrgatherei16.vv v16, v0, v8 ; RV64-NEXT: vsetvli zero, zero, e16, m2, ta, ma -; RV64-NEXT: vadd.vi v28, v2, -13 +; RV64-NEXT: vadd.vi v28, v10, -13 ; RV64-NEXT: vsetvli zero, zero, e64, m8, ta, mu -; RV64-NEXT: vmv1r.v v0, v7 ; RV64-NEXT: csrr a1, vlenb -; RV64-NEXT: li a2, 35 +; RV64-NEXT: slli a1, a1, 1 +; RV64-NEXT: add a1, sp, a1 +; RV64-NEXT: addi a1, a1, 16 +; RV64-NEXT: vl1r.v v0, (a1) # Unknown-size Folded Reload +; RV64-NEXT: csrr a1, vlenb +; RV64-NEXT: li a2, 40 ; RV64-NEXT: mul a1, a1, a2 ; RV64-NEXT: add a1, sp, a1 ; RV64-NEXT: addi a1, a1, 16 -; RV64-NEXT: vl8r.v v16, (a1) # Unknown-size Folded Reload -; RV64-NEXT: vrgatherei16.vv v8, v16, v28, v0.t +; RV64-NEXT: vl8r.v v8, (a1) # Unknown-size Folded Reload +; RV64-NEXT: vrgatherei16.vv v16, v8, v28, v0.t ; RV64-NEXT: lui a1, 16 ; RV64-NEXT: addi a1, a1, 7 ; RV64-NEXT: vsetivli zero, 4, e32, m1, ta, ma ; RV64-NEXT: vmv.v.x v12, a1 ; RV64-NEXT: vsetivli zero, 8, e64, m4, ta, mu ; RV64-NEXT: csrr a1, vlenb -; RV64-NEXT: li a2, 27 -; RV64-NEXT: mul a1, a1, a2 +; RV64-NEXT: slli a1, a1, 5 ; RV64-NEXT: add a1, sp, a1 ; RV64-NEXT: addi a1, a1, 16 -; RV64-NEXT: vl8r.v v24, (a1) # Unknown-size Folded Reload -; RV64-NEXT: vrgatherei16.vv v16, v24, v12 -; RV64-NEXT: vmv1r.v v0, v6 +; RV64-NEXT: vl8r.v v0, (a1) # Unknown-size Folded Reload +; RV64-NEXT: vmv4r.v v8, v0 +; RV64-NEXT: vrgatherei16.vv v20, v0, v12 ; RV64-NEXT: csrr a1, vlenb -; RV64-NEXT: li a2, 19 +; RV64-NEXT: li a2, 20 ; RV64-NEXT: mul a1, a1, a2 ; RV64-NEXT: add a1, sp, a1 ; RV64-NEXT: addi a1, a1, 16 -; RV64-NEXT: vl8r.v v24, (a1) # Unknown-size Folded Reload -; RV64-NEXT: vrgather.vi v16, v24, 5, v0.t +; RV64-NEXT: vl1r.v v0, (a1) # Unknown-size Folded Reload +; RV64-NEXT: vrgather.vi v20, v24, 5, v0.t ; RV64-NEXT: vsetivli zero, 5, e64, m4, tu, ma -; RV64-NEXT: vmv.v.v v16, v8 +; RV64-NEXT: vmv.v.v v20, v16 ; RV64-NEXT: csrr a1, vlenb -; RV64-NEXT: slli a2, a1, 1 -; RV64-NEXT: add a1, a2, a1 +; RV64-NEXT: li a2, 20 +; RV64-NEXT: mul a1, a1, a2 ; RV64-NEXT: add a1, sp, a1 ; RV64-NEXT: addi a1, a1, 16 -; RV64-NEXT: vs4r.v v16, (a1) # Unknown-size Folded Spill +; RV64-NEXT: vs4r.v v20, (a1) # Unknown-size Folded Spill ; RV64-NEXT: lui a1, 96 ; RV64-NEXT: vsetivli zero, 4, e32, m1, ta, ma -; RV64-NEXT: vmv.v.x v8, a1 +; RV64-NEXT: vmv.v.x v12, a1 ; RV64-NEXT: vsetivli zero, 8, e64, m4, ta, mu ; RV64-NEXT: li a1, 192 ; RV64-NEXT: vmv.s.x v0, a1 ; RV64-NEXT: csrr a1, vlenb -; RV64-NEXT: slli a1, a1, 1 ; RV64-NEXT: add a1, sp, a1 ; RV64-NEXT: addi a1, a1, 16 ; RV64-NEXT: vs1r.v v0, (a1) # Unknown-size Folded Spill +; RV64-NEXT: vrgather.vi v28, v8, 2 +; RV64-NEXT: vrgatherei16.vv v28, v24, v12, v0.t +; RV64-NEXT: vsetivli zero, 16, e16, m2, ta, ma ; RV64-NEXT: csrr a1, vlenb -; RV64-NEXT: li a2, 27 +; RV64-NEXT: li a2, 6 ; RV64-NEXT: mul a1, a1, a2 ; RV64-NEXT: add a1, sp, a1 ; RV64-NEXT: addi a1, a1, 16 -; RV64-NEXT: vl8r.v v16, (a1) # Unknown-size Folded Reload -; RV64-NEXT: vrgather.vi v4, v16, 2 -; RV64-NEXT: vrgatherei16.vv v4, v24, v8, v0.t -; RV64-NEXT: vsetivli zero, 16, e16, m2, ta, ma -; RV64-NEXT: vadd.vi v16, v2, 4 +; RV64-NEXT: vl2r.v v24, (a1) # Unknown-size Folded Reload +; RV64-NEXT: vadd.vi v16, v24, 4 ; RV64-NEXT: vsetvli zero, zero, e64, m8, ta, ma ; RV64-NEXT: csrr a1, vlenb -; RV64-NEXT: li a2, 43 +; RV64-NEXT: li a2, 48 ; RV64-NEXT: mul a1, a1, a2 ; RV64-NEXT: add a1, sp, a1 ; RV64-NEXT: addi a1, a1, 16 -; RV64-NEXT: vl8r.v v24, (a1) # Unknown-size Folded Reload -; RV64-NEXT: vrgatherei16.vv v8, v24, v16 +; RV64-NEXT: vl8r.v v0, (a1) # Unknown-size Folded Reload +; RV64-NEXT: vrgatherei16.vv v8, v0, v16 ; RV64-NEXT: vsetvli zero, zero, e16, m2, ta, ma ; RV64-NEXT: li a1, 28 -; RV64-NEXT: vmv.s.x v1, a1 -; RV64-NEXT: vadd.vi v16, v2, -12 +; RV64-NEXT: vmv.s.x v0, a1 +; RV64-NEXT: addi a1, sp, 16 +; RV64-NEXT: vs1r.v v0, (a1) # Unknown-size Folded Spill +; RV64-NEXT: vadd.vi v26, v24, -12 ; RV64-NEXT: vsetvli zero, zero, e64, m8, ta, mu -; RV64-NEXT: vmv1r.v v0, v1 ; RV64-NEXT: csrr a1, vlenb -; RV64-NEXT: li a2, 35 +; RV64-NEXT: li a2, 40 ; RV64-NEXT: mul a1, a1, a2 ; RV64-NEXT: add a1, sp, a1 ; RV64-NEXT: addi a1, a1, 16 -; RV64-NEXT: vl8r.v v24, (a1) # Unknown-size Folded Reload -; RV64-NEXT: vrgatherei16.vv v8, v24, v16, v0.t +; RV64-NEXT: vl8r.v v16, (a1) # Unknown-size Folded Reload +; RV64-NEXT: vrgatherei16.vv v8, v16, v26, v0.t ; RV64-NEXT: vsetivli zero, 5, e64, m4, tu, ma -; RV64-NEXT: vmv.v.v v4, v8 +; RV64-NEXT: vmv.v.v v28, v8 +; RV64-NEXT: csrr a1, vlenb +; RV64-NEXT: slli a1, a1, 1 +; RV64-NEXT: add a1, sp, a1 +; RV64-NEXT: addi a1, a1, 16 +; RV64-NEXT: vs4r.v v28, (a1) # Unknown-size Folded Spill ; RV64-NEXT: lui a1, 112 ; RV64-NEXT: addi a1, a1, 1 ; RV64-NEXT: vsetivli zero, 4, e32, m1, ta, ma ; RV64-NEXT: vmv.v.x v12, a1 ; RV64-NEXT: vsetivli zero, 8, e64, m4, ta, mu ; RV64-NEXT: csrr a1, vlenb -; RV64-NEXT: li a2, 27 -; RV64-NEXT: mul a1, a1, a2 +; RV64-NEXT: slli a1, a1, 5 ; RV64-NEXT: add a1, sp, a1 ; RV64-NEXT: addi a1, a1, 16 ; RV64-NEXT: vl8r.v v16, (a1) # Unknown-size Folded Reload ; RV64-NEXT: vrgather.vi v8, v16, 3 ; RV64-NEXT: csrr a1, vlenb -; RV64-NEXT: slli a1, a1, 1 ; RV64-NEXT: add a1, sp, a1 ; RV64-NEXT: addi a1, a1, 16 ; RV64-NEXT: vl1r.v v0, (a1) # Unknown-size Folded Reload ; RV64-NEXT: csrr a1, vlenb -; RV64-NEXT: li a2, 19 +; RV64-NEXT: li a2, 24 ; RV64-NEXT: mul a1, a1, a2 ; RV64-NEXT: add a1, sp, a1 ; RV64-NEXT: addi a1, a1, 16 ; RV64-NEXT: vl8r.v v16, (a1) # Unknown-size Folded Reload ; RV64-NEXT: vrgatherei16.vv v8, v16, v12, v0.t ; RV64-NEXT: vsetivli zero, 16, e16, m2, ta, ma -; RV64-NEXT: vadd.vi v12, v2, 5 +; RV64-NEXT: vadd.vi v12, v24, 5 ; RV64-NEXT: vsetvli zero, zero, e64, m8, ta, ma ; RV64-NEXT: csrr a1, vlenb -; RV64-NEXT: li a2, 43 +; RV64-NEXT: li a2, 48 ; RV64-NEXT: mul a1, a1, a2 ; RV64-NEXT: add a1, sp, a1 ; RV64-NEXT: addi a1, a1, 16 -; RV64-NEXT: vl8r.v v24, (a1) # Unknown-size Folded Reload -; RV64-NEXT: vrgatherei16.vv v16, v24, v12 +; RV64-NEXT: vl8r.v v0, (a1) # Unknown-size Folded Reload +; RV64-NEXT: vrgatherei16.vv v16, v0, v12 ; RV64-NEXT: vsetvli zero, zero, e16, m2, ta, ma -; RV64-NEXT: vadd.vi v12, v2, -11 +; RV64-NEXT: vadd.vi v12, v24, -11 ; RV64-NEXT: vsetvli zero, zero, e64, m8, ta, mu -; RV64-NEXT: vmv1r.v v0, v1 +; RV64-NEXT: addi a1, sp, 16 +; RV64-NEXT: vl1r.v v0, (a1) # Unknown-size Folded Reload ; RV64-NEXT: csrr a1, vlenb -; RV64-NEXT: li a2, 35 +; RV64-NEXT: li a2, 40 ; RV64-NEXT: mul a1, a1, a2 ; RV64-NEXT: add a1, sp, a1 ; RV64-NEXT: addi a1, a1, 16 @@ -911,40 +933,43 @@ define {<8 x i64>, <8 x i64>, <8 x i64>, <8 x i64>, <8 x i64>, <8 x i64>} @load_ ; RV64-NEXT: vsetivli zero, 8, e64, m4, ta, ma ; RV64-NEXT: vse64.v v8, (a1) ; RV64-NEXT: addi a1, a0, 256 -; RV64-NEXT: vse64.v v4, (a1) +; RV64-NEXT: csrr a2, vlenb +; RV64-NEXT: slli a2, a2, 1 +; RV64-NEXT: add a2, sp, a2 +; RV64-NEXT: addi a2, a2, 16 +; RV64-NEXT: vl4r.v v8, (a2) # Unknown-size Folded Reload +; RV64-NEXT: vse64.v v8, (a1) ; RV64-NEXT: addi a1, a0, 192 ; RV64-NEXT: csrr a2, vlenb -; RV64-NEXT: slli a3, a2, 1 -; RV64-NEXT: add a2, a3, a2 +; RV64-NEXT: li a3, 20 +; RV64-NEXT: mul a2, a2, a3 ; RV64-NEXT: add a2, sp, a2 ; RV64-NEXT: addi a2, a2, 16 ; RV64-NEXT: vl4r.v v8, (a2) # Unknown-size Folded Reload ; RV64-NEXT: vse64.v v8, (a1) ; RV64-NEXT: addi a1, a0, 128 ; RV64-NEXT: csrr a2, vlenb -; RV64-NEXT: slli a3, a2, 3 -; RV64-NEXT: sub a2, a3, a2 +; RV64-NEXT: slli a2, a2, 3 ; RV64-NEXT: add a2, sp, a2 ; RV64-NEXT: addi a2, a2, 16 ; RV64-NEXT: vl4r.v v8, (a2) # Unknown-size Folded Reload ; RV64-NEXT: vse64.v v8, (a1) ; RV64-NEXT: addi a1, a0, 64 ; RV64-NEXT: csrr a2, vlenb -; RV64-NEXT: li a3, 11 +; RV64-NEXT: li a3, 12 ; RV64-NEXT: mul a2, a2, a3 ; RV64-NEXT: add a2, sp, a2 ; RV64-NEXT: addi a2, a2, 16 ; RV64-NEXT: vl4r.v v8, (a2) # Unknown-size Folded Reload ; RV64-NEXT: vse64.v v8, (a1) ; RV64-NEXT: csrr a1, vlenb -; RV64-NEXT: slli a2, a1, 4 -; RV64-NEXT: sub a1, a2, a1 +; RV64-NEXT: slli a1, a1, 4 ; RV64-NEXT: add a1, sp, a1 ; RV64-NEXT: addi a1, a1, 16 ; RV64-NEXT: vl4r.v v8, (a1) # Unknown-size Folded Reload ; RV64-NEXT: vse64.v v8, (a0) ; RV64-NEXT: csrr a0, vlenb -; RV64-NEXT: li a1, 52 +; RV64-NEXT: li a1, 56 ; RV64-NEXT: mul a0, a0, a1 ; RV64-NEXT: add sp, sp, a0 ; RV64-NEXT: addi sp, sp, 16 diff --git a/llvm/test/CodeGen/RISCV/rvv/fixed-vectors-mask-buildvec.ll b/llvm/test/CodeGen/RISCV/rvv/fixed-vectors-mask-buildvec.ll index c295fed2c28c1011366a83227b133fff399c9bf3..023d707f07bff7a88865d518515576e13e601f1f 100644 --- a/llvm/test/CodeGen/RISCV/rvv/fixed-vectors-mask-buildvec.ll +++ b/llvm/test/CodeGen/RISCV/rvv/fixed-vectors-mask-buildvec.ll @@ -286,8 +286,8 @@ define <8 x i1> @buildvec_mask_nonconst_v8i1_2(i1 %x, i1 %y, i1 %z, i1 %w) { ; CHECK-NEXT: vslide1down.vx v9, v9, a1 ; CHECK-NEXT: vslide1down.vx v8, v8, a3 ; CHECK-NEXT: vslide1down.vx v8, v8, zero -; CHECK-NEXT: vmv.v.i v0, 15 ; CHECK-NEXT: vslide1down.vx v8, v8, a2 +; CHECK-NEXT: vmv.v.i v0, 15 ; CHECK-NEXT: vslidedown.vi v8, v9, 4, v0.t ; CHECK-NEXT: vand.vi v8, v8, 1 ; CHECK-NEXT: vmsne.vi v0, v8, 0 @@ -303,8 +303,8 @@ define <8 x i1> @buildvec_mask_nonconst_v8i1_2(i1 %x, i1 %y, i1 %z, i1 %w) { ; ZVE32F-NEXT: vslide1down.vx v9, v9, a1 ; ZVE32F-NEXT: vslide1down.vx v8, v8, a3 ; ZVE32F-NEXT: vslide1down.vx v8, v8, zero -; ZVE32F-NEXT: vmv.v.i v0, 15 ; ZVE32F-NEXT: vslide1down.vx v8, v8, a2 +; ZVE32F-NEXT: vmv.v.i v0, 15 ; ZVE32F-NEXT: vslidedown.vi v8, v9, 4, v0.t ; ZVE32F-NEXT: vand.vi v8, v8, 1 ; ZVE32F-NEXT: vmsne.vi v0, v8, 0 @@ -331,8 +331,8 @@ define <8 x i1> @buildvec_mask_optsize_nonconst_v8i1_2(i1 %x, i1 %y, i1 %z, i1 % ; CHECK-NEXT: vslide1down.vx v9, v9, a1 ; CHECK-NEXT: vslide1down.vx v8, v8, a3 ; CHECK-NEXT: vslide1down.vx v8, v8, zero -; CHECK-NEXT: vmv.v.i v0, 15 ; CHECK-NEXT: vslide1down.vx v8, v8, a2 +; CHECK-NEXT: vmv.v.i v0, 15 ; CHECK-NEXT: vslidedown.vi v8, v9, 4, v0.t ; CHECK-NEXT: vand.vi v8, v8, 1 ; CHECK-NEXT: vmsne.vi v0, v8, 0 @@ -348,8 +348,8 @@ define <8 x i1> @buildvec_mask_optsize_nonconst_v8i1_2(i1 %x, i1 %y, i1 %z, i1 % ; ZVE32F-NEXT: vslide1down.vx v9, v9, a1 ; ZVE32F-NEXT: vslide1down.vx v8, v8, a3 ; ZVE32F-NEXT: vslide1down.vx v8, v8, zero -; ZVE32F-NEXT: vmv.v.i v0, 15 ; ZVE32F-NEXT: vslide1down.vx v8, v8, a2 +; ZVE32F-NEXT: vmv.v.i v0, 15 ; ZVE32F-NEXT: vslidedown.vi v8, v9, 4, v0.t ; ZVE32F-NEXT: vand.vi v8, v8, 1 ; ZVE32F-NEXT: vmsne.vi v0, v8, 0 @@ -375,8 +375,8 @@ define <8 x i1> @buildvec_mask_optsize_nonconst_v8i1(i1 %x, i1 %y) optsize { ; CHECK-NEXT: vslide1down.vx v9, v9, a1 ; CHECK-NEXT: vslide1down.vx v8, v8, a1 ; CHECK-NEXT: vslide1down.vx v8, v8, a1 -; CHECK-NEXT: vmv.v.i v0, 15 ; CHECK-NEXT: vslide1down.vx v8, v8, a1 +; CHECK-NEXT: vmv.v.i v0, 15 ; CHECK-NEXT: vslidedown.vi v8, v9, 4, v0.t ; CHECK-NEXT: vand.vi v8, v8, 1 ; CHECK-NEXT: vmsne.vi v0, v8, 0 @@ -391,8 +391,8 @@ define <8 x i1> @buildvec_mask_optsize_nonconst_v8i1(i1 %x, i1 %y) optsize { ; ZVE32F-NEXT: vslide1down.vx v9, v9, a1 ; ZVE32F-NEXT: vslide1down.vx v8, v8, a1 ; ZVE32F-NEXT: vslide1down.vx v8, v8, a1 -; ZVE32F-NEXT: vmv.v.i v0, 15 ; ZVE32F-NEXT: vslide1down.vx v8, v8, a1 +; ZVE32F-NEXT: vmv.v.i v0, 15 ; ZVE32F-NEXT: vslidedown.vi v8, v9, 4, v0.t ; ZVE32F-NEXT: vand.vi v8, v8, 1 ; ZVE32F-NEXT: vmsne.vi v0, v8, 0 diff --git a/llvm/test/CodeGen/RISCV/rvv/fixed-vectors-mask-splat.ll b/llvm/test/CodeGen/RISCV/rvv/fixed-vectors-mask-splat.ll index 4f7b885d998e5b1d044e67d6b77075d2545c8de5..7fc442c88d101bafa12d10a656cc9e2d7fc42176 100644 --- a/llvm/test/CodeGen/RISCV/rvv/fixed-vectors-mask-splat.ll +++ b/llvm/test/CodeGen/RISCV/rvv/fixed-vectors-mask-splat.ll @@ -25,10 +25,10 @@ define void @splat_v1i1(ptr %x, i1 %y) { ; CHECK-LABEL: splat_v1i1: ; CHECK: # %bb.0: ; CHECK-NEXT: vsetivli zero, 1, e8, mf8, ta, ma -; CHECK-NEXT: andi a1, a1, 1 -; CHECK-NEXT: vmv.s.x v8, a1 -; CHECK-NEXT: vmsne.vi v0, v8, 0 ; CHECK-NEXT: vmv.s.x v8, zero +; CHECK-NEXT: andi a1, a1, 1 +; CHECK-NEXT: vmv.s.x v9, a1 +; CHECK-NEXT: vmsne.vi v0, v9, 0 ; CHECK-NEXT: vmerge.vim v8, v8, 1, v0 ; CHECK-NEXT: vsetivli zero, 8, e8, mf2, ta, ma ; CHECK-NEXT: vmv.v.i v9, 0 diff --git a/llvm/test/CodeGen/RISCV/rvv/fixed-vectors-masked-gather.ll b/llvm/test/CodeGen/RISCV/rvv/fixed-vectors-masked-gather.ll index 9fbc22221f99bd14bc6b987862a049de9df68efd..539a8403c93521ac5c485ca3f347a60e9e623cd3 100644 --- a/llvm/test/CodeGen/RISCV/rvv/fixed-vectors-masked-gather.ll +++ b/llvm/test/CodeGen/RISCV/rvv/fixed-vectors-masked-gather.ll @@ -12728,8 +12728,8 @@ define <8 x i16> @mgather_strided_unaligned(ptr %base) { ; RV32-NEXT: vmv.v.x v8, a3 ; RV32-NEXT: vslide1down.vx v8, v8, a5 ; RV32-NEXT: vslide1down.vx v8, v8, a6 -; RV32-NEXT: vmv.v.i v0, 15 ; RV32-NEXT: vslide1down.vx v8, v8, a7 +; RV32-NEXT: vmv.v.i v0, 15 ; RV32-NEXT: vslidedown.vi v8, v9, 4, v0.t ; RV32-NEXT: ret ; @@ -12803,8 +12803,8 @@ define <8 x i16> @mgather_strided_unaligned(ptr %base) { ; RV64V-NEXT: vmv.v.x v8, a3 ; RV64V-NEXT: vslide1down.vx v8, v8, a5 ; RV64V-NEXT: vslide1down.vx v8, v8, a6 -; RV64V-NEXT: vmv.v.i v0, 15 ; RV64V-NEXT: vslide1down.vx v8, v8, a7 +; RV64V-NEXT: vmv.v.i v0, 15 ; RV64V-NEXT: vslidedown.vi v8, v9, 4, v0.t ; RV64V-NEXT: addi sp, s0, -128 ; RV64V-NEXT: ld ra, 120(sp) # 8-byte Folded Reload @@ -12854,8 +12854,8 @@ define <8 x i16> @mgather_strided_unaligned(ptr %base) { ; RV64ZVE32F-NEXT: vmv.v.x v8, a5 ; RV64ZVE32F-NEXT: vslide1down.vx v8, v8, a6 ; RV64ZVE32F-NEXT: vslide1down.vx v8, v8, a7 -; RV64ZVE32F-NEXT: vmv.v.i v0, 15 ; RV64ZVE32F-NEXT: vslide1down.vx v8, v8, a0 +; RV64ZVE32F-NEXT: vmv.v.i v0, 15 ; RV64ZVE32F-NEXT: vslidedown.vi v8, v9, 4, v0.t ; RV64ZVE32F-NEXT: ret %ptrs = getelementptr inbounds i16, ptr %base, <8 x i32> @@ -12896,8 +12896,8 @@ define <8 x i16> @mgather_strided_2xSEW(ptr %base) { ; RV64ZVE32F-NEXT: vslide1down.vx v10, v8, a3 ; RV64ZVE32F-NEXT: vslide1down.vx v8, v9, a4 ; RV64ZVE32F-NEXT: vslide1down.vx v8, v8, a5 -; RV64ZVE32F-NEXT: vmv.v.i v0, 15 ; RV64ZVE32F-NEXT: vslide1down.vx v8, v8, a6 +; RV64ZVE32F-NEXT: vmv.v.i v0, 15 ; RV64ZVE32F-NEXT: vslidedown.vi v8, v10, 4, v0.t ; RV64ZVE32F-NEXT: ret %ptrs = getelementptr inbounds i16, ptr %base, <8 x i32> @@ -12941,8 +12941,8 @@ define <8 x i16> @mgather_strided_2xSEW_with_offset(ptr %base) { ; RV64ZVE32F-NEXT: vslide1down.vx v10, v8, a4 ; RV64ZVE32F-NEXT: vslide1down.vx v8, v9, a5 ; RV64ZVE32F-NEXT: vslide1down.vx v8, v8, a6 -; RV64ZVE32F-NEXT: vmv.v.i v0, 15 ; RV64ZVE32F-NEXT: vslide1down.vx v8, v8, a7 +; RV64ZVE32F-NEXT: vmv.v.i v0, 15 ; RV64ZVE32F-NEXT: vslidedown.vi v8, v10, 4, v0.t ; RV64ZVE32F-NEXT: ret %ptrs = getelementptr inbounds i16, ptr %base, <8 x i64> @@ -12986,8 +12986,8 @@ define <8 x i16> @mgather_reverse_unit_strided_2xSEW(ptr %base) { ; RV64ZVE32F-NEXT: vslide1down.vx v10, v8, a4 ; RV64ZVE32F-NEXT: vslide1down.vx v8, v9, a5 ; RV64ZVE32F-NEXT: vslide1down.vx v8, v8, a6 -; RV64ZVE32F-NEXT: vmv.v.i v0, 15 ; RV64ZVE32F-NEXT: vslide1down.vx v8, v8, a7 +; RV64ZVE32F-NEXT: vmv.v.i v0, 15 ; RV64ZVE32F-NEXT: vslidedown.vi v8, v10, 4, v0.t ; RV64ZVE32F-NEXT: ret %ptrs = getelementptr inbounds i16, ptr %base, <8 x i64> @@ -13031,8 +13031,8 @@ define <8 x i16> @mgather_reverse_strided_2xSEW(ptr %base) { ; RV64ZVE32F-NEXT: vslide1down.vx v10, v8, a4 ; RV64ZVE32F-NEXT: vslide1down.vx v8, v9, a5 ; RV64ZVE32F-NEXT: vslide1down.vx v8, v8, a6 -; RV64ZVE32F-NEXT: vmv.v.i v0, 15 ; RV64ZVE32F-NEXT: vslide1down.vx v8, v8, a7 +; RV64ZVE32F-NEXT: vmv.v.i v0, 15 ; RV64ZVE32F-NEXT: vslidedown.vi v8, v10, 4, v0.t ; RV64ZVE32F-NEXT: ret %ptrs = getelementptr inbounds i16, ptr %base, <8 x i64> @@ -13074,8 +13074,8 @@ define <8 x i16> @mgather_gather_2xSEW(ptr %base) { ; RV64ZVE32F-NEXT: vslide1down.vx v10, v8, a3 ; RV64ZVE32F-NEXT: vslide1down.vx v8, v9, a4 ; RV64ZVE32F-NEXT: vslide1down.vx v8, v8, a5 -; RV64ZVE32F-NEXT: vmv.v.i v0, 15 ; RV64ZVE32F-NEXT: vslide1down.vx v8, v8, a6 +; RV64ZVE32F-NEXT: vmv.v.i v0, 15 ; RV64ZVE32F-NEXT: vslidedown.vi v8, v10, 4, v0.t ; RV64ZVE32F-NEXT: ret %ptrs = getelementptr inbounds i16, ptr %base, <8 x i32> @@ -13120,8 +13120,8 @@ define <8 x i16> @mgather_gather_2xSEW_unaligned(ptr %base) { ; RV64ZVE32F-NEXT: vslide1down.vx v10, v8, a3 ; RV64ZVE32F-NEXT: vslide1down.vx v8, v9, a4 ; RV64ZVE32F-NEXT: vslide1down.vx v8, v8, a5 -; RV64ZVE32F-NEXT: vmv.v.i v0, 15 ; RV64ZVE32F-NEXT: vslide1down.vx v8, v8, a6 +; RV64ZVE32F-NEXT: vmv.v.i v0, 15 ; RV64ZVE32F-NEXT: vslidedown.vi v8, v10, 4, v0.t ; RV64ZVE32F-NEXT: ret %ptrs = getelementptr inbounds i16, ptr %base, <8 x i32> @@ -13167,8 +13167,8 @@ define <8 x i16> @mgather_gather_2xSEW_unaligned2(ptr %base) { ; RV64ZVE32F-NEXT: vslide1down.vx v10, v8, a4 ; RV64ZVE32F-NEXT: vslide1down.vx v8, v9, a5 ; RV64ZVE32F-NEXT: vslide1down.vx v8, v8, a2 -; RV64ZVE32F-NEXT: vmv.v.i v0, 15 ; RV64ZVE32F-NEXT: vslide1down.vx v8, v8, a6 +; RV64ZVE32F-NEXT: vmv.v.i v0, 15 ; RV64ZVE32F-NEXT: vslidedown.vi v8, v10, 4, v0.t ; RV64ZVE32F-NEXT: ret %ptrs = getelementptr inbounds i16, ptr %base, <8 x i32> @@ -13217,8 +13217,8 @@ define <8 x i16> @mgather_gather_4xSEW(ptr %base) { ; RV64ZVE32F-NEXT: vslide1down.vx v10, v8, a3 ; RV64ZVE32F-NEXT: vslide1down.vx v8, v9, a4 ; RV64ZVE32F-NEXT: vslide1down.vx v8, v8, a5 -; RV64ZVE32F-NEXT: vmv.v.i v0, 15 ; RV64ZVE32F-NEXT: vslide1down.vx v8, v8, a6 +; RV64ZVE32F-NEXT: vmv.v.i v0, 15 ; RV64ZVE32F-NEXT: vslidedown.vi v8, v10, 4, v0.t ; RV64ZVE32F-NEXT: ret %ptrs = getelementptr inbounds i16, ptr %base, <8 x i32> @@ -13264,8 +13264,8 @@ define <8 x i16> @mgather_gather_4xSEW_partial_align(ptr %base) { ; RV64ZVE32F-NEXT: vslide1down.vx v10, v8, a3 ; RV64ZVE32F-NEXT: vslide1down.vx v8, v9, a4 ; RV64ZVE32F-NEXT: vslide1down.vx v8, v8, a5 -; RV64ZVE32F-NEXT: vmv.v.i v0, 15 ; RV64ZVE32F-NEXT: vslide1down.vx v8, v8, a6 +; RV64ZVE32F-NEXT: vmv.v.i v0, 15 ; RV64ZVE32F-NEXT: vslidedown.vi v8, v10, 4, v0.t ; RV64ZVE32F-NEXT: ret %ptrs = getelementptr inbounds i16, ptr %base, <8 x i32> @@ -13320,8 +13320,8 @@ define <8 x i16> @mgather_shuffle_rotate(ptr %base) { ; RV64ZVE32F-NEXT: vslide1down.vx v8, v8, a6 ; RV64ZVE32F-NEXT: vslide1down.vx v9, v9, a1 ; RV64ZVE32F-NEXT: vslide1down.vx v9, v9, a2 -; RV64ZVE32F-NEXT: vmv.v.i v0, 15 ; RV64ZVE32F-NEXT: vslide1down.vx v9, v9, a3 +; RV64ZVE32F-NEXT: vmv.v.i v0, 15 ; RV64ZVE32F-NEXT: vslidedown.vi v8, v9, 4, v0.t ; RV64ZVE32F-NEXT: ret %ptrs = getelementptr inbounds i16, ptr %base, <8 x i64> @@ -13367,8 +13367,8 @@ define <8 x i16> @mgather_shuffle_vrgather(ptr %base) { ; RV64ZVE32F-NEXT: vslide1down.vx v10, v8, a3 ; RV64ZVE32F-NEXT: vslide1down.vx v8, v9, a4 ; RV64ZVE32F-NEXT: vslide1down.vx v8, v8, a5 -; RV64ZVE32F-NEXT: vmv.v.i v0, 15 ; RV64ZVE32F-NEXT: vslide1down.vx v8, v8, a6 +; RV64ZVE32F-NEXT: vmv.v.i v0, 15 ; RV64ZVE32F-NEXT: vslidedown.vi v8, v10, 4, v0.t ; RV64ZVE32F-NEXT: ret %ptrs = getelementptr inbounds i16, ptr %base, <8 x i64> diff --git a/llvm/test/CodeGen/RISCV/rvv/fixed-vectors-reduction-formation.ll b/llvm/test/CodeGen/RISCV/rvv/fixed-vectors-reduction-formation.ll index 2a0ec47a3de01c9a483e1a1e264d6c3a65a5566a..5f456c7824316b2e985592795e4e9b16a0fdbdde 100644 --- a/llvm/test/CodeGen/RISCV/rvv/fixed-vectors-reduction-formation.ll +++ b/llvm/test/CodeGen/RISCV/rvv/fixed-vectors-reduction-formation.ll @@ -221,10 +221,10 @@ define i32 @reduce_sum_16xi32_prefix7(ptr %p) { ; CHECK-LABEL: reduce_sum_16xi32_prefix7: ; CHECK: # %bb.0: ; CHECK-NEXT: vsetivli zero, 8, e32, m2, ta, ma -; CHECK-NEXT: vle32.v v8, (a0) -; CHECK-NEXT: vmv.s.x v10, zero -; CHECK-NEXT: vslideup.vi v8, v10, 7 -; CHECK-NEXT: vredsum.vs v8, v8, v10 +; CHECK-NEXT: vmv.s.x v8, zero +; CHECK-NEXT: vle32.v v10, (a0) +; CHECK-NEXT: vslideup.vi v10, v8, 7 +; CHECK-NEXT: vredsum.vs v8, v10, v8 ; CHECK-NEXT: vmv.x.s a0, v8 ; CHECK-NEXT: ret %v = load <16 x i32>, ptr %p, align 256 @@ -248,9 +248,9 @@ define i32 @reduce_sum_16xi32_prefix8(ptr %p) { ; CHECK-LABEL: reduce_sum_16xi32_prefix8: ; CHECK: # %bb.0: ; CHECK-NEXT: vsetivli zero, 8, e32, m2, ta, ma -; CHECK-NEXT: vle32.v v8, (a0) -; CHECK-NEXT: vmv.s.x v10, zero -; CHECK-NEXT: vredsum.vs v8, v8, v10 +; CHECK-NEXT: vmv.s.x v8, zero +; CHECK-NEXT: vle32.v v10, (a0) +; CHECK-NEXT: vredsum.vs v8, v10, v8 ; CHECK-NEXT: vmv.x.s a0, v8 ; CHECK-NEXT: ret %v = load <16 x i32>, ptr %p, align 256 @@ -670,15 +670,15 @@ define i32 @reduce_smax_16xi32_prefix5(ptr %p) { ; CHECK: # %bb.0: ; CHECK-NEXT: lui a1, 524288 ; CHECK-NEXT: vsetivli zero, 8, e32, m2, ta, ma -; CHECK-NEXT: vle32.v v8, (a0) -; CHECK-NEXT: vmv.s.x v10, a1 +; CHECK-NEXT: vmv.s.x v8, a1 +; CHECK-NEXT: vle32.v v10, (a0) ; CHECK-NEXT: vsetivli zero, 6, e32, m2, tu, ma -; CHECK-NEXT: vslideup.vi v8, v10, 5 +; CHECK-NEXT: vslideup.vi v10, v8, 5 ; CHECK-NEXT: vsetivli zero, 7, e32, m2, tu, ma -; CHECK-NEXT: vslideup.vi v8, v10, 6 +; CHECK-NEXT: vslideup.vi v10, v8, 6 ; CHECK-NEXT: vsetivli zero, 8, e32, m2, ta, ma -; CHECK-NEXT: vslideup.vi v8, v10, 7 -; CHECK-NEXT: vredmax.vs v8, v8, v8 +; CHECK-NEXT: vslideup.vi v10, v8, 7 +; CHECK-NEXT: vredmax.vs v8, v10, v10 ; CHECK-NEXT: vmv.x.s a0, v8 ; CHECK-NEXT: ret %v = load <16 x i32>, ptr %p, align 256 @@ -715,15 +715,15 @@ define i32 @reduce_smin_16xi32_prefix5(ptr %p) { ; CHECK-NEXT: lui a1, 524288 ; CHECK-NEXT: addi a1, a1, -1 ; CHECK-NEXT: vsetivli zero, 8, e32, m2, ta, ma -; CHECK-NEXT: vle32.v v8, (a0) -; CHECK-NEXT: vmv.s.x v10, a1 +; CHECK-NEXT: vmv.s.x v8, a1 +; CHECK-NEXT: vle32.v v10, (a0) ; CHECK-NEXT: vsetivli zero, 6, e32, m2, tu, ma -; CHECK-NEXT: vslideup.vi v8, v10, 5 +; CHECK-NEXT: vslideup.vi v10, v8, 5 ; CHECK-NEXT: vsetivli zero, 7, e32, m2, tu, ma -; CHECK-NEXT: vslideup.vi v8, v10, 6 +; CHECK-NEXT: vslideup.vi v10, v8, 6 ; CHECK-NEXT: vsetivli zero, 8, e32, m2, ta, ma -; CHECK-NEXT: vslideup.vi v8, v10, 7 -; CHECK-NEXT: vredmin.vs v8, v8, v8 +; CHECK-NEXT: vslideup.vi v10, v8, 7 +; CHECK-NEXT: vredmin.vs v8, v10, v10 ; CHECK-NEXT: vmv.x.s a0, v8 ; CHECK-NEXT: ret %v = load <16 x i32>, ptr %p, align 256 @@ -830,9 +830,9 @@ define float @reduce_fadd_16xf32_prefix2(ptr %p) { ; CHECK-LABEL: reduce_fadd_16xf32_prefix2: ; CHECK: # %bb.0: ; CHECK-NEXT: vsetivli zero, 2, e32, mf2, ta, ma -; CHECK-NEXT: vle32.v v8, (a0) -; CHECK-NEXT: vmv.s.x v9, zero -; CHECK-NEXT: vfredusum.vs v8, v8, v9 +; CHECK-NEXT: vmv.s.x v8, zero +; CHECK-NEXT: vle32.v v9, (a0) +; CHECK-NEXT: vfredusum.vs v8, v9, v8 ; CHECK-NEXT: vfmv.f.s fa0, v8 ; CHECK-NEXT: ret %v = load <16 x float>, ptr %p, align 256 @@ -847,15 +847,15 @@ define float @reduce_fadd_16xi32_prefix5(ptr %p) { ; CHECK: # %bb.0: ; CHECK-NEXT: lui a1, 524288 ; CHECK-NEXT: vsetivli zero, 8, e32, m2, ta, ma -; CHECK-NEXT: vle32.v v8, (a0) -; CHECK-NEXT: vmv.s.x v10, a1 +; CHECK-NEXT: vmv.s.x v8, a1 +; CHECK-NEXT: vle32.v v10, (a0) ; CHECK-NEXT: vsetivli zero, 6, e32, m2, tu, ma -; CHECK-NEXT: vslideup.vi v8, v10, 5 +; CHECK-NEXT: vslideup.vi v10, v8, 5 ; CHECK-NEXT: vsetivli zero, 7, e32, m2, tu, ma -; CHECK-NEXT: vslideup.vi v8, v10, 6 +; CHECK-NEXT: vslideup.vi v10, v8, 6 ; CHECK-NEXT: vsetivli zero, 8, e32, m2, ta, ma -; CHECK-NEXT: vslideup.vi v8, v10, 7 -; CHECK-NEXT: vfredusum.vs v8, v8, v10 +; CHECK-NEXT: vslideup.vi v10, v8, 7 +; CHECK-NEXT: vfredusum.vs v8, v10, v8 ; CHECK-NEXT: vfmv.f.s fa0, v8 ; CHECK-NEXT: ret %v = load <16 x float>, ptr %p, align 256 diff --git a/llvm/test/CodeGen/RISCV/rvv/fixed-vectors-reduction-int-vp.ll b/llvm/test/CodeGen/RISCV/rvv/fixed-vectors-reduction-int-vp.ll index 2495178ea762d9372bc496c508fa7bbb18ef50a7..02a989a969960695517f46e0c48fad98f4bd9ae9 100644 --- a/llvm/test/CodeGen/RISCV/rvv/fixed-vectors-reduction-int-vp.ll +++ b/llvm/test/CodeGen/RISCV/rvv/fixed-vectors-reduction-int-vp.ll @@ -574,24 +574,14 @@ define signext i32 @vpreduce_add_v2i32(i32 signext %s, <2 x i32> %v, <2 x i1> %m declare i32 @llvm.vp.reduce.umax.v2i32(i32, <2 x i32>, <2 x i1>, i32) define signext i32 @vpreduce_umax_v2i32(i32 signext %s, <2 x i32> %v, <2 x i1> %m, i32 zeroext %evl) { -; RV32-LABEL: vpreduce_umax_v2i32: -; RV32: # %bb.0: -; RV32-NEXT: vsetivli zero, 1, e32, m1, ta, ma -; RV32-NEXT: vmv.s.x v9, a0 -; RV32-NEXT: vsetvli zero, a1, e32, mf2, ta, ma -; RV32-NEXT: vredmaxu.vs v9, v8, v9, v0.t -; RV32-NEXT: vmv.x.s a0, v9 -; RV32-NEXT: ret -; -; RV64-LABEL: vpreduce_umax_v2i32: -; RV64: # %bb.0: -; RV64-NEXT: andi a0, a0, -1 -; RV64-NEXT: vsetivli zero, 1, e32, m1, ta, ma -; RV64-NEXT: vmv.s.x v9, a0 -; RV64-NEXT: vsetvli zero, a1, e32, mf2, ta, ma -; RV64-NEXT: vredmaxu.vs v9, v8, v9, v0.t -; RV64-NEXT: vmv.x.s a0, v9 -; RV64-NEXT: ret +; CHECK-LABEL: vpreduce_umax_v2i32: +; CHECK: # %bb.0: +; CHECK-NEXT: vsetivli zero, 1, e32, m1, ta, ma +; CHECK-NEXT: vmv.s.x v9, a0 +; CHECK-NEXT: vsetvli zero, a1, e32, mf2, ta, ma +; CHECK-NEXT: vredmaxu.vs v9, v8, v9, v0.t +; CHECK-NEXT: vmv.x.s a0, v9 +; CHECK-NEXT: ret %r = call i32 @llvm.vp.reduce.umax.v2i32(i32 %s, <2 x i32> %v, <2 x i1> %m, i32 %evl) ret i32 %r } @@ -614,24 +604,14 @@ define signext i32 @vpreduce_smax_v2i32(i32 signext %s, <2 x i32> %v, <2 x i1> % declare i32 @llvm.vp.reduce.umin.v2i32(i32, <2 x i32>, <2 x i1>, i32) define signext i32 @vpreduce_umin_v2i32(i32 signext %s, <2 x i32> %v, <2 x i1> %m, i32 zeroext %evl) { -; RV32-LABEL: vpreduce_umin_v2i32: -; RV32: # %bb.0: -; RV32-NEXT: vsetivli zero, 1, e32, m1, ta, ma -; RV32-NEXT: vmv.s.x v9, a0 -; RV32-NEXT: vsetvli zero, a1, e32, mf2, ta, ma -; RV32-NEXT: vredminu.vs v9, v8, v9, v0.t -; RV32-NEXT: vmv.x.s a0, v9 -; RV32-NEXT: ret -; -; RV64-LABEL: vpreduce_umin_v2i32: -; RV64: # %bb.0: -; RV64-NEXT: andi a0, a0, -1 -; RV64-NEXT: vsetivli zero, 1, e32, m1, ta, ma -; RV64-NEXT: vmv.s.x v9, a0 -; RV64-NEXT: vsetvli zero, a1, e32, mf2, ta, ma -; RV64-NEXT: vredminu.vs v9, v8, v9, v0.t -; RV64-NEXT: vmv.x.s a0, v9 -; RV64-NEXT: ret +; CHECK-LABEL: vpreduce_umin_v2i32: +; CHECK: # %bb.0: +; CHECK-NEXT: vsetivli zero, 1, e32, m1, ta, ma +; CHECK-NEXT: vmv.s.x v9, a0 +; CHECK-NEXT: vsetvli zero, a1, e32, mf2, ta, ma +; CHECK-NEXT: vredminu.vs v9, v8, v9, v0.t +; CHECK-NEXT: vmv.x.s a0, v9 +; CHECK-NEXT: ret %r = call i32 @llvm.vp.reduce.umin.v2i32(i32 %s, <2 x i32> %v, <2 x i1> %m, i32 %evl) ret i32 %r } @@ -714,24 +694,14 @@ define signext i32 @vpreduce_add_v4i32(i32 signext %s, <4 x i32> %v, <4 x i1> %m declare i32 @llvm.vp.reduce.umax.v4i32(i32, <4 x i32>, <4 x i1>, i32) define signext i32 @vpreduce_umax_v4i32(i32 signext %s, <4 x i32> %v, <4 x i1> %m, i32 zeroext %evl) { -; RV32-LABEL: vpreduce_umax_v4i32: -; RV32: # %bb.0: -; RV32-NEXT: vsetivli zero, 1, e32, m1, ta, ma -; RV32-NEXT: vmv.s.x v9, a0 -; RV32-NEXT: vsetvli zero, a1, e32, m1, ta, ma -; RV32-NEXT: vredmaxu.vs v9, v8, v9, v0.t -; RV32-NEXT: vmv.x.s a0, v9 -; RV32-NEXT: ret -; -; RV64-LABEL: vpreduce_umax_v4i32: -; RV64: # %bb.0: -; RV64-NEXT: andi a0, a0, -1 -; RV64-NEXT: vsetivli zero, 1, e32, m1, ta, ma -; RV64-NEXT: vmv.s.x v9, a0 -; RV64-NEXT: vsetvli zero, a1, e32, m1, ta, ma -; RV64-NEXT: vredmaxu.vs v9, v8, v9, v0.t -; RV64-NEXT: vmv.x.s a0, v9 -; RV64-NEXT: ret +; CHECK-LABEL: vpreduce_umax_v4i32: +; CHECK: # %bb.0: +; CHECK-NEXT: vsetivli zero, 1, e32, m1, ta, ma +; CHECK-NEXT: vmv.s.x v9, a0 +; CHECK-NEXT: vsetvli zero, a1, e32, m1, ta, ma +; CHECK-NEXT: vredmaxu.vs v9, v8, v9, v0.t +; CHECK-NEXT: vmv.x.s a0, v9 +; CHECK-NEXT: ret %r = call i32 @llvm.vp.reduce.umax.v4i32(i32 %s, <4 x i32> %v, <4 x i1> %m, i32 %evl) ret i32 %r } @@ -754,24 +724,14 @@ define signext i32 @vpreduce_smax_v4i32(i32 signext %s, <4 x i32> %v, <4 x i1> % declare i32 @llvm.vp.reduce.umin.v4i32(i32, <4 x i32>, <4 x i1>, i32) define signext i32 @vpreduce_umin_v4i32(i32 signext %s, <4 x i32> %v, <4 x i1> %m, i32 zeroext %evl) { -; RV32-LABEL: vpreduce_umin_v4i32: -; RV32: # %bb.0: -; RV32-NEXT: vsetivli zero, 1, e32, m1, ta, ma -; RV32-NEXT: vmv.s.x v9, a0 -; RV32-NEXT: vsetvli zero, a1, e32, m1, ta, ma -; RV32-NEXT: vredminu.vs v9, v8, v9, v0.t -; RV32-NEXT: vmv.x.s a0, v9 -; RV32-NEXT: ret -; -; RV64-LABEL: vpreduce_umin_v4i32: -; RV64: # %bb.0: -; RV64-NEXT: andi a0, a0, -1 -; RV64-NEXT: vsetivli zero, 1, e32, m1, ta, ma -; RV64-NEXT: vmv.s.x v9, a0 -; RV64-NEXT: vsetvli zero, a1, e32, m1, ta, ma -; RV64-NEXT: vredminu.vs v9, v8, v9, v0.t -; RV64-NEXT: vmv.x.s a0, v9 -; RV64-NEXT: ret +; CHECK-LABEL: vpreduce_umin_v4i32: +; CHECK: # %bb.0: +; CHECK-NEXT: vsetivli zero, 1, e32, m1, ta, ma +; CHECK-NEXT: vmv.s.x v9, a0 +; CHECK-NEXT: vsetvli zero, a1, e32, m1, ta, ma +; CHECK-NEXT: vredminu.vs v9, v8, v9, v0.t +; CHECK-NEXT: vmv.x.s a0, v9 +; CHECK-NEXT: ret %r = call i32 @llvm.vp.reduce.umin.v4i32(i32 %s, <4 x i32> %v, <4 x i1> %m, i32 %evl) ret i32 %r } diff --git a/llvm/test/CodeGen/RISCV/rvv/fpclamptosat_vec.ll b/llvm/test/CodeGen/RISCV/rvv/fpclamptosat_vec.ll index b3bda5973eb8c4c2e95842e13ffeec65dbf7311a..a6b2d3141f22f9502d7011199048673a5879a998 100644 --- a/llvm/test/CodeGen/RISCV/rvv/fpclamptosat_vec.ll +++ b/llvm/test/CodeGen/RISCV/rvv/fpclamptosat_vec.ll @@ -2190,65 +2190,66 @@ define <2 x i64> @stest_f64i64(<2 x double> %x) { ; CHECK-NOV-NEXT: .cfi_offset s0, -16 ; CHECK-NOV-NEXT: .cfi_offset s1, -24 ; CHECK-NOV-NEXT: .cfi_offset fs0, -32 -; CHECK-NOV-NEXT: fmv.d fs0, fa0 -; CHECK-NOV-NEXT: fmv.d fa0, fa1 +; CHECK-NOV-NEXT: fmv.d fs0, fa1 ; CHECK-NOV-NEXT: call __fixdfti ; CHECK-NOV-NEXT: mv s0, a0 ; CHECK-NOV-NEXT: mv s1, a1 ; CHECK-NOV-NEXT: fmv.d fa0, fs0 ; CHECK-NOV-NEXT: call __fixdfti -; CHECK-NOV-NEXT: li a2, -1 -; CHECK-NOV-NEXT: srli a3, a2, 1 -; CHECK-NOV-NEXT: beqz s1, .LBB18_3 +; CHECK-NOV-NEXT: mv a2, a0 +; CHECK-NOV-NEXT: li a0, -1 +; CHECK-NOV-NEXT: srli a3, a0, 1 +; CHECK-NOV-NEXT: beqz a1, .LBB18_3 ; CHECK-NOV-NEXT: # %bb.1: # %entry -; CHECK-NOV-NEXT: slti a4, s1, 0 -; CHECK-NOV-NEXT: bnez a1, .LBB18_4 +; CHECK-NOV-NEXT: slti a4, a1, 0 +; CHECK-NOV-NEXT: bnez s1, .LBB18_4 ; CHECK-NOV-NEXT: .LBB18_2: -; CHECK-NOV-NEXT: sltu a5, a0, a3 +; CHECK-NOV-NEXT: sltu a5, s0, a3 ; CHECK-NOV-NEXT: beqz a5, .LBB18_5 ; CHECK-NOV-NEXT: j .LBB18_6 ; CHECK-NOV-NEXT: .LBB18_3: -; CHECK-NOV-NEXT: sltu a4, s0, a3 -; CHECK-NOV-NEXT: beqz a1, .LBB18_2 +; CHECK-NOV-NEXT: sltu a4, a2, a3 +; CHECK-NOV-NEXT: beqz s1, .LBB18_2 ; CHECK-NOV-NEXT: .LBB18_4: # %entry -; CHECK-NOV-NEXT: slti a5, a1, 0 +; CHECK-NOV-NEXT: slti a5, s1, 0 ; CHECK-NOV-NEXT: bnez a5, .LBB18_6 ; CHECK-NOV-NEXT: .LBB18_5: # %entry -; CHECK-NOV-NEXT: mv a0, a3 +; CHECK-NOV-NEXT: mv s0, a3 ; CHECK-NOV-NEXT: .LBB18_6: # %entry ; CHECK-NOV-NEXT: neg a6, a5 ; CHECK-NOV-NEXT: neg a5, a4 -; CHECK-NOV-NEXT: and a5, a5, s1 +; CHECK-NOV-NEXT: and a5, a5, a1 ; CHECK-NOV-NEXT: bnez a4, .LBB18_8 ; CHECK-NOV-NEXT: # %bb.7: # %entry -; CHECK-NOV-NEXT: mv s0, a3 +; CHECK-NOV-NEXT: mv a2, a3 ; CHECK-NOV-NEXT: .LBB18_8: # %entry -; CHECK-NOV-NEXT: and a4, a6, a1 -; CHECK-NOV-NEXT: slli a1, a2, 63 -; CHECK-NOV-NEXT: beq a5, a2, .LBB18_11 +; CHECK-NOV-NEXT: and a4, a6, s1 +; CHECK-NOV-NEXT: slli a1, a0, 63 +; CHECK-NOV-NEXT: beq a5, a0, .LBB18_11 ; CHECK-NOV-NEXT: # %bb.9: # %entry ; CHECK-NOV-NEXT: slti a3, a5, 0 ; CHECK-NOV-NEXT: xori a3, a3, 1 -; CHECK-NOV-NEXT: bne a4, a2, .LBB18_12 +; CHECK-NOV-NEXT: bne a4, a0, .LBB18_12 ; CHECK-NOV-NEXT: .LBB18_10: -; CHECK-NOV-NEXT: sltu a2, a1, a0 -; CHECK-NOV-NEXT: beqz a2, .LBB18_13 +; CHECK-NOV-NEXT: sltu a0, a1, s0 +; CHECK-NOV-NEXT: beqz a0, .LBB18_13 ; CHECK-NOV-NEXT: j .LBB18_14 ; CHECK-NOV-NEXT: .LBB18_11: -; CHECK-NOV-NEXT: sltu a3, a1, s0 -; CHECK-NOV-NEXT: beq a4, a2, .LBB18_10 +; CHECK-NOV-NEXT: sltu a3, a1, a2 +; CHECK-NOV-NEXT: beq a4, a0, .LBB18_10 ; CHECK-NOV-NEXT: .LBB18_12: # %entry -; CHECK-NOV-NEXT: slti a2, a4, 0 -; CHECK-NOV-NEXT: xori a2, a2, 1 -; CHECK-NOV-NEXT: bnez a2, .LBB18_14 +; CHECK-NOV-NEXT: slti a0, a4, 0 +; CHECK-NOV-NEXT: xori a0, a0, 1 +; CHECK-NOV-NEXT: bnez a0, .LBB18_14 ; CHECK-NOV-NEXT: .LBB18_13: # %entry -; CHECK-NOV-NEXT: mv a0, a1 +; CHECK-NOV-NEXT: mv s0, a1 ; CHECK-NOV-NEXT: .LBB18_14: # %entry ; CHECK-NOV-NEXT: bnez a3, .LBB18_16 ; CHECK-NOV-NEXT: # %bb.15: # %entry -; CHECK-NOV-NEXT: mv s0, a1 +; CHECK-NOV-NEXT: mv a2, a1 ; CHECK-NOV-NEXT: .LBB18_16: # %entry -; CHECK-NOV-NEXT: mv a1, s0 +; CHECK-NOV-NEXT: mv a0, s0 +; CHECK-NOV-NEXT: mv a1, a2 ; CHECK-NOV-NEXT: ld ra, 24(sp) # 8-byte Folded Reload ; CHECK-NOV-NEXT: ld s0, 16(sp) # 8-byte Folded Reload ; CHECK-NOV-NEXT: ld s1, 8(sp) # 8-byte Folded Reload @@ -2273,43 +2274,43 @@ define <2 x i64> @stest_f64i64(<2 x double> %x) { ; CHECK-V-NEXT: addi a0, sp, 32 ; CHECK-V-NEXT: vs1r.v v8, (a0) # Unknown-size Folded Spill ; CHECK-V-NEXT: vsetivli zero, 1, e64, m1, ta, ma -; CHECK-V-NEXT: vfmv.f.s fa0, v8 +; CHECK-V-NEXT: vslidedown.vi v9, v8, 1 +; CHECK-V-NEXT: vfmv.f.s fa0, v9 ; CHECK-V-NEXT: call __fixdfti ; CHECK-V-NEXT: mv s0, a0 ; CHECK-V-NEXT: mv s1, a1 ; CHECK-V-NEXT: vsetivli zero, 1, e64, m1, ta, ma ; CHECK-V-NEXT: addi a0, sp, 32 ; CHECK-V-NEXT: vl1r.v v8, (a0) # Unknown-size Folded Reload -; CHECK-V-NEXT: vslidedown.vi v8, v8, 1 ; CHECK-V-NEXT: vfmv.f.s fa0, v8 ; CHECK-V-NEXT: call __fixdfti ; CHECK-V-NEXT: li a2, -1 ; CHECK-V-NEXT: srli a3, a2, 1 -; CHECK-V-NEXT: beqz s1, .LBB18_3 +; CHECK-V-NEXT: beqz a1, .LBB18_3 ; CHECK-V-NEXT: # %bb.1: # %entry -; CHECK-V-NEXT: slti a4, s1, 0 -; CHECK-V-NEXT: bnez a1, .LBB18_4 +; CHECK-V-NEXT: slti a4, a1, 0 +; CHECK-V-NEXT: bnez s1, .LBB18_4 ; CHECK-V-NEXT: .LBB18_2: -; CHECK-V-NEXT: sltu a5, a0, a3 +; CHECK-V-NEXT: sltu a5, s0, a3 ; CHECK-V-NEXT: beqz a5, .LBB18_5 ; CHECK-V-NEXT: j .LBB18_6 ; CHECK-V-NEXT: .LBB18_3: -; CHECK-V-NEXT: sltu a4, s0, a3 -; CHECK-V-NEXT: beqz a1, .LBB18_2 +; CHECK-V-NEXT: sltu a4, a0, a3 +; CHECK-V-NEXT: beqz s1, .LBB18_2 ; CHECK-V-NEXT: .LBB18_4: # %entry -; CHECK-V-NEXT: slti a5, a1, 0 +; CHECK-V-NEXT: slti a5, s1, 0 ; CHECK-V-NEXT: bnez a5, .LBB18_6 ; CHECK-V-NEXT: .LBB18_5: # %entry -; CHECK-V-NEXT: mv a0, a3 +; CHECK-V-NEXT: mv s0, a3 ; CHECK-V-NEXT: .LBB18_6: # %entry ; CHECK-V-NEXT: neg a6, a5 ; CHECK-V-NEXT: neg a5, a4 -; CHECK-V-NEXT: and a5, a5, s1 +; CHECK-V-NEXT: and a5, a5, a1 ; CHECK-V-NEXT: bnez a4, .LBB18_8 ; CHECK-V-NEXT: # %bb.7: # %entry -; CHECK-V-NEXT: mv s0, a3 +; CHECK-V-NEXT: mv a0, a3 ; CHECK-V-NEXT: .LBB18_8: # %entry -; CHECK-V-NEXT: and a4, a6, a1 +; CHECK-V-NEXT: and a4, a6, s1 ; CHECK-V-NEXT: slli a1, a2, 63 ; CHECK-V-NEXT: beq a5, a2, .LBB18_11 ; CHECK-V-NEXT: # %bb.9: # %entry @@ -2317,26 +2318,26 @@ define <2 x i64> @stest_f64i64(<2 x double> %x) { ; CHECK-V-NEXT: xori a3, a3, 1 ; CHECK-V-NEXT: bne a4, a2, .LBB18_12 ; CHECK-V-NEXT: .LBB18_10: -; CHECK-V-NEXT: sltu a2, a1, a0 +; CHECK-V-NEXT: sltu a2, a1, s0 ; CHECK-V-NEXT: beqz a2, .LBB18_13 ; CHECK-V-NEXT: j .LBB18_14 ; CHECK-V-NEXT: .LBB18_11: -; CHECK-V-NEXT: sltu a3, a1, s0 +; CHECK-V-NEXT: sltu a3, a1, a0 ; CHECK-V-NEXT: beq a4, a2, .LBB18_10 ; CHECK-V-NEXT: .LBB18_12: # %entry ; CHECK-V-NEXT: slti a2, a4, 0 ; CHECK-V-NEXT: xori a2, a2, 1 ; CHECK-V-NEXT: bnez a2, .LBB18_14 ; CHECK-V-NEXT: .LBB18_13: # %entry -; CHECK-V-NEXT: mv a0, a1 +; CHECK-V-NEXT: mv s0, a1 ; CHECK-V-NEXT: .LBB18_14: # %entry ; CHECK-V-NEXT: bnez a3, .LBB18_16 ; CHECK-V-NEXT: # %bb.15: # %entry -; CHECK-V-NEXT: mv s0, a1 +; CHECK-V-NEXT: mv a0, a1 ; CHECK-V-NEXT: .LBB18_16: # %entry ; CHECK-V-NEXT: vsetivli zero, 2, e64, m1, ta, ma -; CHECK-V-NEXT: vmv.s.x v8, s0 -; CHECK-V-NEXT: vmv.s.x v9, a0 +; CHECK-V-NEXT: vmv.s.x v8, a0 +; CHECK-V-NEXT: vmv.s.x v9, s0 ; CHECK-V-NEXT: vslideup.vi v8, v9, 1 ; CHECK-V-NEXT: csrr a0, vlenb ; CHECK-V-NEXT: slli a0, a0, 1 @@ -2369,19 +2370,19 @@ define <2 x i64> @utest_f64i64(<2 x double> %x) { ; CHECK-NOV-NEXT: .cfi_offset s0, -16 ; CHECK-NOV-NEXT: .cfi_offset s1, -24 ; CHECK-NOV-NEXT: .cfi_offset fs0, -32 -; CHECK-NOV-NEXT: fmv.d fs0, fa0 -; CHECK-NOV-NEXT: fmv.d fa0, fa1 +; CHECK-NOV-NEXT: fmv.d fs0, fa1 ; CHECK-NOV-NEXT: call __fixunsdfti ; CHECK-NOV-NEXT: mv s0, a0 ; CHECK-NOV-NEXT: mv s1, a1 ; CHECK-NOV-NEXT: fmv.d fa0, fs0 ; CHECK-NOV-NEXT: call __fixunsdfti -; CHECK-NOV-NEXT: snez a2, s1 ; CHECK-NOV-NEXT: snez a1, a1 +; CHECK-NOV-NEXT: snez a2, s1 +; CHECK-NOV-NEXT: addi a2, a2, -1 +; CHECK-NOV-NEXT: and a2, a2, s0 ; CHECK-NOV-NEXT: addi a1, a1, -1 -; CHECK-NOV-NEXT: and a0, a1, a0 -; CHECK-NOV-NEXT: addi a1, a2, -1 -; CHECK-NOV-NEXT: and a1, a1, s0 +; CHECK-NOV-NEXT: and a1, a1, a0 +; CHECK-NOV-NEXT: mv a0, a2 ; CHECK-NOV-NEXT: ld ra, 24(sp) # 8-byte Folded Reload ; CHECK-NOV-NEXT: ld s0, 16(sp) # 8-byte Folded Reload ; CHECK-NOV-NEXT: ld s1, 8(sp) # 8-byte Folded Reload @@ -2406,25 +2407,25 @@ define <2 x i64> @utest_f64i64(<2 x double> %x) { ; CHECK-V-NEXT: addi a0, sp, 32 ; CHECK-V-NEXT: vs1r.v v8, (a0) # Unknown-size Folded Spill ; CHECK-V-NEXT: vsetivli zero, 1, e64, m1, ta, ma -; CHECK-V-NEXT: vfmv.f.s fa0, v8 +; CHECK-V-NEXT: vslidedown.vi v9, v8, 1 +; CHECK-V-NEXT: vfmv.f.s fa0, v9 ; CHECK-V-NEXT: call __fixunsdfti ; CHECK-V-NEXT: mv s0, a0 ; CHECK-V-NEXT: mv s1, a1 ; CHECK-V-NEXT: vsetivli zero, 1, e64, m1, ta, ma ; CHECK-V-NEXT: addi a0, sp, 32 ; CHECK-V-NEXT: vl1r.v v8, (a0) # Unknown-size Folded Reload -; CHECK-V-NEXT: vslidedown.vi v8, v8, 1 ; CHECK-V-NEXT: vfmv.f.s fa0, v8 ; CHECK-V-NEXT: call __fixunsdfti -; CHECK-V-NEXT: snez a2, s1 ; CHECK-V-NEXT: snez a1, a1 -; CHECK-V-NEXT: addi a1, a1, -1 -; CHECK-V-NEXT: and a0, a1, a0 +; CHECK-V-NEXT: snez a2, s1 ; CHECK-V-NEXT: addi a2, a2, -1 ; CHECK-V-NEXT: and a2, a2, s0 +; CHECK-V-NEXT: addi a1, a1, -1 +; CHECK-V-NEXT: and a0, a1, a0 ; CHECK-V-NEXT: vsetivli zero, 2, e64, m1, ta, ma -; CHECK-V-NEXT: vmv.s.x v8, a2 -; CHECK-V-NEXT: vmv.s.x v9, a0 +; CHECK-V-NEXT: vmv.s.x v8, a0 +; CHECK-V-NEXT: vmv.s.x v9, a2 ; CHECK-V-NEXT: vslideup.vi v8, v9, 1 ; CHECK-V-NEXT: csrr a0, vlenb ; CHECK-V-NEXT: slli a0, a0, 1 @@ -2466,32 +2467,32 @@ define <2 x i64> @ustest_f64i64(<2 x double> %x) { ; CHECK-NOV-NEXT: # %bb.1: # %entry ; CHECK-NOV-NEXT: li a2, 1 ; CHECK-NOV-NEXT: .LBB20_2: # %entry -; CHECK-NOV-NEXT: slti a4, s1, 1 ; CHECK-NOV-NEXT: slti a3, a1, 1 +; CHECK-NOV-NEXT: slti a4, s1, 1 ; CHECK-NOV-NEXT: blez a1, .LBB20_4 ; CHECK-NOV-NEXT: # %bb.3: # %entry ; CHECK-NOV-NEXT: li a1, 1 ; CHECK-NOV-NEXT: .LBB20_4: # %entry +; CHECK-NOV-NEXT: neg a4, a4 ; CHECK-NOV-NEXT: neg a3, a3 ; CHECK-NOV-NEXT: and a3, a3, a0 -; CHECK-NOV-NEXT: neg a0, a4 ; CHECK-NOV-NEXT: beqz a1, .LBB20_7 ; CHECK-NOV-NEXT: # %bb.5: # %entry ; CHECK-NOV-NEXT: sgtz a1, a1 -; CHECK-NOV-NEXT: and a0, a0, s0 +; CHECK-NOV-NEXT: and a4, a4, s0 ; CHECK-NOV-NEXT: bnez a2, .LBB20_8 ; CHECK-NOV-NEXT: .LBB20_6: -; CHECK-NOV-NEXT: snez a2, a0 +; CHECK-NOV-NEXT: snez a0, a4 ; CHECK-NOV-NEXT: j .LBB20_9 ; CHECK-NOV-NEXT: .LBB20_7: ; CHECK-NOV-NEXT: snez a1, a3 -; CHECK-NOV-NEXT: and a0, a0, s0 +; CHECK-NOV-NEXT: and a4, a4, s0 ; CHECK-NOV-NEXT: beqz a2, .LBB20_6 ; CHECK-NOV-NEXT: .LBB20_8: # %entry -; CHECK-NOV-NEXT: sgtz a2, a2 +; CHECK-NOV-NEXT: sgtz a0, a2 ; CHECK-NOV-NEXT: .LBB20_9: # %entry -; CHECK-NOV-NEXT: neg a2, a2 -; CHECK-NOV-NEXT: and a0, a2, a0 +; CHECK-NOV-NEXT: neg a0, a0 +; CHECK-NOV-NEXT: and a0, a0, a4 ; CHECK-NOV-NEXT: neg a1, a1 ; CHECK-NOV-NEXT: and a1, a1, a3 ; CHECK-NOV-NEXT: ld ra, 24(sp) # 8-byte Folded Reload @@ -2533,15 +2534,15 @@ define <2 x i64> @ustest_f64i64(<2 x double> %x) { ; CHECK-V-NEXT: # %bb.1: # %entry ; CHECK-V-NEXT: li a2, 1 ; CHECK-V-NEXT: .LBB20_2: # %entry -; CHECK-V-NEXT: slti a3, s1, 1 ; CHECK-V-NEXT: slti a4, a1, 1 +; CHECK-V-NEXT: slti a3, s1, 1 ; CHECK-V-NEXT: blez a1, .LBB20_4 ; CHECK-V-NEXT: # %bb.3: # %entry ; CHECK-V-NEXT: li a1, 1 ; CHECK-V-NEXT: .LBB20_4: # %entry +; CHECK-V-NEXT: neg a3, a3 ; CHECK-V-NEXT: neg a4, a4 ; CHECK-V-NEXT: and a0, a4, a0 -; CHECK-V-NEXT: neg a3, a3 ; CHECK-V-NEXT: beqz a1, .LBB20_7 ; CHECK-V-NEXT: # %bb.5: # %entry ; CHECK-V-NEXT: sgtz a1, a1 @@ -2596,65 +2597,66 @@ define <2 x i64> @stest_f32i64(<2 x float> %x) { ; CHECK-NOV-NEXT: .cfi_offset s0, -16 ; CHECK-NOV-NEXT: .cfi_offset s1, -24 ; CHECK-NOV-NEXT: .cfi_offset fs0, -32 -; CHECK-NOV-NEXT: fmv.s fs0, fa0 -; CHECK-NOV-NEXT: fmv.s fa0, fa1 +; CHECK-NOV-NEXT: fmv.s fs0, fa1 ; CHECK-NOV-NEXT: call __fixsfti ; CHECK-NOV-NEXT: mv s0, a0 ; CHECK-NOV-NEXT: mv s1, a1 ; CHECK-NOV-NEXT: fmv.s fa0, fs0 ; CHECK-NOV-NEXT: call __fixsfti -; CHECK-NOV-NEXT: li a2, -1 -; CHECK-NOV-NEXT: srli a3, a2, 1 -; CHECK-NOV-NEXT: beqz s1, .LBB21_3 +; CHECK-NOV-NEXT: mv a2, a0 +; CHECK-NOV-NEXT: li a0, -1 +; CHECK-NOV-NEXT: srli a3, a0, 1 +; CHECK-NOV-NEXT: beqz a1, .LBB21_3 ; CHECK-NOV-NEXT: # %bb.1: # %entry -; CHECK-NOV-NEXT: slti a4, s1, 0 -; CHECK-NOV-NEXT: bnez a1, .LBB21_4 +; CHECK-NOV-NEXT: slti a4, a1, 0 +; CHECK-NOV-NEXT: bnez s1, .LBB21_4 ; CHECK-NOV-NEXT: .LBB21_2: -; CHECK-NOV-NEXT: sltu a5, a0, a3 +; CHECK-NOV-NEXT: sltu a5, s0, a3 ; CHECK-NOV-NEXT: beqz a5, .LBB21_5 ; CHECK-NOV-NEXT: j .LBB21_6 ; CHECK-NOV-NEXT: .LBB21_3: -; CHECK-NOV-NEXT: sltu a4, s0, a3 -; CHECK-NOV-NEXT: beqz a1, .LBB21_2 +; CHECK-NOV-NEXT: sltu a4, a2, a3 +; CHECK-NOV-NEXT: beqz s1, .LBB21_2 ; CHECK-NOV-NEXT: .LBB21_4: # %entry -; CHECK-NOV-NEXT: slti a5, a1, 0 +; CHECK-NOV-NEXT: slti a5, s1, 0 ; CHECK-NOV-NEXT: bnez a5, .LBB21_6 ; CHECK-NOV-NEXT: .LBB21_5: # %entry -; CHECK-NOV-NEXT: mv a0, a3 +; CHECK-NOV-NEXT: mv s0, a3 ; CHECK-NOV-NEXT: .LBB21_6: # %entry ; CHECK-NOV-NEXT: neg a6, a5 ; CHECK-NOV-NEXT: neg a5, a4 -; CHECK-NOV-NEXT: and a5, a5, s1 +; CHECK-NOV-NEXT: and a5, a5, a1 ; CHECK-NOV-NEXT: bnez a4, .LBB21_8 ; CHECK-NOV-NEXT: # %bb.7: # %entry -; CHECK-NOV-NEXT: mv s0, a3 +; CHECK-NOV-NEXT: mv a2, a3 ; CHECK-NOV-NEXT: .LBB21_8: # %entry -; CHECK-NOV-NEXT: and a4, a6, a1 -; CHECK-NOV-NEXT: slli a1, a2, 63 -; CHECK-NOV-NEXT: beq a5, a2, .LBB21_11 +; CHECK-NOV-NEXT: and a4, a6, s1 +; CHECK-NOV-NEXT: slli a1, a0, 63 +; CHECK-NOV-NEXT: beq a5, a0, .LBB21_11 ; CHECK-NOV-NEXT: # %bb.9: # %entry ; CHECK-NOV-NEXT: slti a3, a5, 0 ; CHECK-NOV-NEXT: xori a3, a3, 1 -; CHECK-NOV-NEXT: bne a4, a2, .LBB21_12 +; CHECK-NOV-NEXT: bne a4, a0, .LBB21_12 ; CHECK-NOV-NEXT: .LBB21_10: -; CHECK-NOV-NEXT: sltu a2, a1, a0 -; CHECK-NOV-NEXT: beqz a2, .LBB21_13 +; CHECK-NOV-NEXT: sltu a0, a1, s0 +; CHECK-NOV-NEXT: beqz a0, .LBB21_13 ; CHECK-NOV-NEXT: j .LBB21_14 ; CHECK-NOV-NEXT: .LBB21_11: -; CHECK-NOV-NEXT: sltu a3, a1, s0 -; CHECK-NOV-NEXT: beq a4, a2, .LBB21_10 +; CHECK-NOV-NEXT: sltu a3, a1, a2 +; CHECK-NOV-NEXT: beq a4, a0, .LBB21_10 ; CHECK-NOV-NEXT: .LBB21_12: # %entry -; CHECK-NOV-NEXT: slti a2, a4, 0 -; CHECK-NOV-NEXT: xori a2, a2, 1 -; CHECK-NOV-NEXT: bnez a2, .LBB21_14 +; CHECK-NOV-NEXT: slti a0, a4, 0 +; CHECK-NOV-NEXT: xori a0, a0, 1 +; CHECK-NOV-NEXT: bnez a0, .LBB21_14 ; CHECK-NOV-NEXT: .LBB21_13: # %entry -; CHECK-NOV-NEXT: mv a0, a1 +; CHECK-NOV-NEXT: mv s0, a1 ; CHECK-NOV-NEXT: .LBB21_14: # %entry ; CHECK-NOV-NEXT: bnez a3, .LBB21_16 ; CHECK-NOV-NEXT: # %bb.15: # %entry -; CHECK-NOV-NEXT: mv s0, a1 +; CHECK-NOV-NEXT: mv a2, a1 ; CHECK-NOV-NEXT: .LBB21_16: # %entry -; CHECK-NOV-NEXT: mv a1, s0 +; CHECK-NOV-NEXT: mv a0, s0 +; CHECK-NOV-NEXT: mv a1, a2 ; CHECK-NOV-NEXT: ld ra, 24(sp) # 8-byte Folded Reload ; CHECK-NOV-NEXT: ld s0, 16(sp) # 8-byte Folded Reload ; CHECK-NOV-NEXT: ld s1, 8(sp) # 8-byte Folded Reload @@ -2679,43 +2681,43 @@ define <2 x i64> @stest_f32i64(<2 x float> %x) { ; CHECK-V-NEXT: addi a0, sp, 32 ; CHECK-V-NEXT: vs1r.v v8, (a0) # Unknown-size Folded Spill ; CHECK-V-NEXT: vsetivli zero, 1, e32, mf2, ta, ma -; CHECK-V-NEXT: vfmv.f.s fa0, v8 +; CHECK-V-NEXT: vslidedown.vi v9, v8, 1 +; CHECK-V-NEXT: vfmv.f.s fa0, v9 ; CHECK-V-NEXT: call __fixsfti ; CHECK-V-NEXT: mv s0, a0 ; CHECK-V-NEXT: mv s1, a1 ; CHECK-V-NEXT: vsetivli zero, 1, e32, mf2, ta, ma ; CHECK-V-NEXT: addi a0, sp, 32 ; CHECK-V-NEXT: vl1r.v v8, (a0) # Unknown-size Folded Reload -; CHECK-V-NEXT: vslidedown.vi v8, v8, 1 ; CHECK-V-NEXT: vfmv.f.s fa0, v8 ; CHECK-V-NEXT: call __fixsfti ; CHECK-V-NEXT: li a2, -1 ; CHECK-V-NEXT: srli a3, a2, 1 -; CHECK-V-NEXT: beqz s1, .LBB21_3 +; CHECK-V-NEXT: beqz a1, .LBB21_3 ; CHECK-V-NEXT: # %bb.1: # %entry -; CHECK-V-NEXT: slti a4, s1, 0 -; CHECK-V-NEXT: bnez a1, .LBB21_4 +; CHECK-V-NEXT: slti a4, a1, 0 +; CHECK-V-NEXT: bnez s1, .LBB21_4 ; CHECK-V-NEXT: .LBB21_2: -; CHECK-V-NEXT: sltu a5, a0, a3 +; CHECK-V-NEXT: sltu a5, s0, a3 ; CHECK-V-NEXT: beqz a5, .LBB21_5 ; CHECK-V-NEXT: j .LBB21_6 ; CHECK-V-NEXT: .LBB21_3: -; CHECK-V-NEXT: sltu a4, s0, a3 -; CHECK-V-NEXT: beqz a1, .LBB21_2 +; CHECK-V-NEXT: sltu a4, a0, a3 +; CHECK-V-NEXT: beqz s1, .LBB21_2 ; CHECK-V-NEXT: .LBB21_4: # %entry -; CHECK-V-NEXT: slti a5, a1, 0 +; CHECK-V-NEXT: slti a5, s1, 0 ; CHECK-V-NEXT: bnez a5, .LBB21_6 ; CHECK-V-NEXT: .LBB21_5: # %entry -; CHECK-V-NEXT: mv a0, a3 +; CHECK-V-NEXT: mv s0, a3 ; CHECK-V-NEXT: .LBB21_6: # %entry ; CHECK-V-NEXT: neg a6, a5 ; CHECK-V-NEXT: neg a5, a4 -; CHECK-V-NEXT: and a5, a5, s1 +; CHECK-V-NEXT: and a5, a5, a1 ; CHECK-V-NEXT: bnez a4, .LBB21_8 ; CHECK-V-NEXT: # %bb.7: # %entry -; CHECK-V-NEXT: mv s0, a3 +; CHECK-V-NEXT: mv a0, a3 ; CHECK-V-NEXT: .LBB21_8: # %entry -; CHECK-V-NEXT: and a4, a6, a1 +; CHECK-V-NEXT: and a4, a6, s1 ; CHECK-V-NEXT: slli a1, a2, 63 ; CHECK-V-NEXT: beq a5, a2, .LBB21_11 ; CHECK-V-NEXT: # %bb.9: # %entry @@ -2723,26 +2725,26 @@ define <2 x i64> @stest_f32i64(<2 x float> %x) { ; CHECK-V-NEXT: xori a3, a3, 1 ; CHECK-V-NEXT: bne a4, a2, .LBB21_12 ; CHECK-V-NEXT: .LBB21_10: -; CHECK-V-NEXT: sltu a2, a1, a0 +; CHECK-V-NEXT: sltu a2, a1, s0 ; CHECK-V-NEXT: beqz a2, .LBB21_13 ; CHECK-V-NEXT: j .LBB21_14 ; CHECK-V-NEXT: .LBB21_11: -; CHECK-V-NEXT: sltu a3, a1, s0 +; CHECK-V-NEXT: sltu a3, a1, a0 ; CHECK-V-NEXT: beq a4, a2, .LBB21_10 ; CHECK-V-NEXT: .LBB21_12: # %entry ; CHECK-V-NEXT: slti a2, a4, 0 ; CHECK-V-NEXT: xori a2, a2, 1 ; CHECK-V-NEXT: bnez a2, .LBB21_14 ; CHECK-V-NEXT: .LBB21_13: # %entry -; CHECK-V-NEXT: mv a0, a1 +; CHECK-V-NEXT: mv s0, a1 ; CHECK-V-NEXT: .LBB21_14: # %entry ; CHECK-V-NEXT: bnez a3, .LBB21_16 ; CHECK-V-NEXT: # %bb.15: # %entry -; CHECK-V-NEXT: mv s0, a1 +; CHECK-V-NEXT: mv a0, a1 ; CHECK-V-NEXT: .LBB21_16: # %entry ; CHECK-V-NEXT: vsetivli zero, 2, e64, m1, ta, ma -; CHECK-V-NEXT: vmv.s.x v8, s0 -; CHECK-V-NEXT: vmv.s.x v9, a0 +; CHECK-V-NEXT: vmv.s.x v8, a0 +; CHECK-V-NEXT: vmv.s.x v9, s0 ; CHECK-V-NEXT: vslideup.vi v8, v9, 1 ; CHECK-V-NEXT: csrr a0, vlenb ; CHECK-V-NEXT: slli a0, a0, 1 @@ -2775,19 +2777,19 @@ define <2 x i64> @utest_f32i64(<2 x float> %x) { ; CHECK-NOV-NEXT: .cfi_offset s0, -16 ; CHECK-NOV-NEXT: .cfi_offset s1, -24 ; CHECK-NOV-NEXT: .cfi_offset fs0, -32 -; CHECK-NOV-NEXT: fmv.s fs0, fa0 -; CHECK-NOV-NEXT: fmv.s fa0, fa1 +; CHECK-NOV-NEXT: fmv.s fs0, fa1 ; CHECK-NOV-NEXT: call __fixunssfti ; CHECK-NOV-NEXT: mv s0, a0 ; CHECK-NOV-NEXT: mv s1, a1 ; CHECK-NOV-NEXT: fmv.s fa0, fs0 ; CHECK-NOV-NEXT: call __fixunssfti -; CHECK-NOV-NEXT: snez a2, s1 ; CHECK-NOV-NEXT: snez a1, a1 +; CHECK-NOV-NEXT: snez a2, s1 +; CHECK-NOV-NEXT: addi a2, a2, -1 +; CHECK-NOV-NEXT: and a2, a2, s0 ; CHECK-NOV-NEXT: addi a1, a1, -1 -; CHECK-NOV-NEXT: and a0, a1, a0 -; CHECK-NOV-NEXT: addi a1, a2, -1 -; CHECK-NOV-NEXT: and a1, a1, s0 +; CHECK-NOV-NEXT: and a1, a1, a0 +; CHECK-NOV-NEXT: mv a0, a2 ; CHECK-NOV-NEXT: ld ra, 24(sp) # 8-byte Folded Reload ; CHECK-NOV-NEXT: ld s0, 16(sp) # 8-byte Folded Reload ; CHECK-NOV-NEXT: ld s1, 8(sp) # 8-byte Folded Reload @@ -2812,25 +2814,25 @@ define <2 x i64> @utest_f32i64(<2 x float> %x) { ; CHECK-V-NEXT: addi a0, sp, 32 ; CHECK-V-NEXT: vs1r.v v8, (a0) # Unknown-size Folded Spill ; CHECK-V-NEXT: vsetivli zero, 1, e32, mf2, ta, ma -; CHECK-V-NEXT: vfmv.f.s fa0, v8 +; CHECK-V-NEXT: vslidedown.vi v9, v8, 1 +; CHECK-V-NEXT: vfmv.f.s fa0, v9 ; CHECK-V-NEXT: call __fixunssfti ; CHECK-V-NEXT: mv s0, a0 ; CHECK-V-NEXT: mv s1, a1 ; CHECK-V-NEXT: vsetivli zero, 1, e32, mf2, ta, ma ; CHECK-V-NEXT: addi a0, sp, 32 ; CHECK-V-NEXT: vl1r.v v8, (a0) # Unknown-size Folded Reload -; CHECK-V-NEXT: vslidedown.vi v8, v8, 1 ; CHECK-V-NEXT: vfmv.f.s fa0, v8 ; CHECK-V-NEXT: call __fixunssfti -; CHECK-V-NEXT: snez a2, s1 ; CHECK-V-NEXT: snez a1, a1 -; CHECK-V-NEXT: addi a1, a1, -1 -; CHECK-V-NEXT: and a0, a1, a0 +; CHECK-V-NEXT: snez a2, s1 ; CHECK-V-NEXT: addi a2, a2, -1 ; CHECK-V-NEXT: and a2, a2, s0 +; CHECK-V-NEXT: addi a1, a1, -1 +; CHECK-V-NEXT: and a0, a1, a0 ; CHECK-V-NEXT: vsetivli zero, 2, e64, m1, ta, ma -; CHECK-V-NEXT: vmv.s.x v8, a2 -; CHECK-V-NEXT: vmv.s.x v9, a0 +; CHECK-V-NEXT: vmv.s.x v8, a0 +; CHECK-V-NEXT: vmv.s.x v9, a2 ; CHECK-V-NEXT: vslideup.vi v8, v9, 1 ; CHECK-V-NEXT: csrr a0, vlenb ; CHECK-V-NEXT: slli a0, a0, 1 @@ -2872,32 +2874,32 @@ define <2 x i64> @ustest_f32i64(<2 x float> %x) { ; CHECK-NOV-NEXT: # %bb.1: # %entry ; CHECK-NOV-NEXT: li a2, 1 ; CHECK-NOV-NEXT: .LBB23_2: # %entry -; CHECK-NOV-NEXT: slti a4, s1, 1 ; CHECK-NOV-NEXT: slti a3, a1, 1 +; CHECK-NOV-NEXT: slti a4, s1, 1 ; CHECK-NOV-NEXT: blez a1, .LBB23_4 ; CHECK-NOV-NEXT: # %bb.3: # %entry ; CHECK-NOV-NEXT: li a1, 1 ; CHECK-NOV-NEXT: .LBB23_4: # %entry +; CHECK-NOV-NEXT: neg a4, a4 ; CHECK-NOV-NEXT: neg a3, a3 ; CHECK-NOV-NEXT: and a3, a3, a0 -; CHECK-NOV-NEXT: neg a0, a4 ; CHECK-NOV-NEXT: beqz a1, .LBB23_7 ; CHECK-NOV-NEXT: # %bb.5: # %entry ; CHECK-NOV-NEXT: sgtz a1, a1 -; CHECK-NOV-NEXT: and a0, a0, s0 +; CHECK-NOV-NEXT: and a4, a4, s0 ; CHECK-NOV-NEXT: bnez a2, .LBB23_8 ; CHECK-NOV-NEXT: .LBB23_6: -; CHECK-NOV-NEXT: snez a2, a0 +; CHECK-NOV-NEXT: snez a0, a4 ; CHECK-NOV-NEXT: j .LBB23_9 ; CHECK-NOV-NEXT: .LBB23_7: ; CHECK-NOV-NEXT: snez a1, a3 -; CHECK-NOV-NEXT: and a0, a0, s0 +; CHECK-NOV-NEXT: and a4, a4, s0 ; CHECK-NOV-NEXT: beqz a2, .LBB23_6 ; CHECK-NOV-NEXT: .LBB23_8: # %entry -; CHECK-NOV-NEXT: sgtz a2, a2 +; CHECK-NOV-NEXT: sgtz a0, a2 ; CHECK-NOV-NEXT: .LBB23_9: # %entry -; CHECK-NOV-NEXT: neg a2, a2 -; CHECK-NOV-NEXT: and a0, a2, a0 +; CHECK-NOV-NEXT: neg a0, a0 +; CHECK-NOV-NEXT: and a0, a0, a4 ; CHECK-NOV-NEXT: neg a1, a1 ; CHECK-NOV-NEXT: and a1, a1, a3 ; CHECK-NOV-NEXT: ld ra, 24(sp) # 8-byte Folded Reload @@ -2939,15 +2941,15 @@ define <2 x i64> @ustest_f32i64(<2 x float> %x) { ; CHECK-V-NEXT: # %bb.1: # %entry ; CHECK-V-NEXT: li a2, 1 ; CHECK-V-NEXT: .LBB23_2: # %entry -; CHECK-V-NEXT: slti a3, s1, 1 ; CHECK-V-NEXT: slti a4, a1, 1 +; CHECK-V-NEXT: slti a3, s1, 1 ; CHECK-V-NEXT: blez a1, .LBB23_4 ; CHECK-V-NEXT: # %bb.3: # %entry ; CHECK-V-NEXT: li a1, 1 ; CHECK-V-NEXT: .LBB23_4: # %entry +; CHECK-V-NEXT: neg a3, a3 ; CHECK-V-NEXT: neg a4, a4 ; CHECK-V-NEXT: and a0, a4, a0 -; CHECK-V-NEXT: neg a3, a3 ; CHECK-V-NEXT: beqz a1, .LBB23_7 ; CHECK-V-NEXT: # %bb.5: # %entry ; CHECK-V-NEXT: sgtz a1, a1 @@ -3002,8 +3004,8 @@ define <2 x i64> @stest_f16i64(<2 x half> %x) { ; CHECK-NOV-NEXT: .cfi_offset s0, -16 ; CHECK-NOV-NEXT: .cfi_offset s1, -24 ; CHECK-NOV-NEXT: .cfi_offset s2, -32 -; CHECK-NOV-NEXT: mv s2, a0 -; CHECK-NOV-NEXT: fmv.w.x fa0, a1 +; CHECK-NOV-NEXT: mv s2, a1 +; CHECK-NOV-NEXT: fmv.w.x fa0, a0 ; CHECK-NOV-NEXT: call __extendhfsf2 ; CHECK-NOV-NEXT: call __fixsfti ; CHECK-NOV-NEXT: mv s0, a0 @@ -3011,58 +3013,60 @@ define <2 x i64> @stest_f16i64(<2 x half> %x) { ; CHECK-NOV-NEXT: fmv.w.x fa0, s2 ; CHECK-NOV-NEXT: call __extendhfsf2 ; CHECK-NOV-NEXT: call __fixsfti -; CHECK-NOV-NEXT: li a2, -1 -; CHECK-NOV-NEXT: srli a3, a2, 1 -; CHECK-NOV-NEXT: beqz s1, .LBB24_3 +; CHECK-NOV-NEXT: mv a2, a0 +; CHECK-NOV-NEXT: li a0, -1 +; CHECK-NOV-NEXT: srli a3, a0, 1 +; CHECK-NOV-NEXT: beqz a1, .LBB24_3 ; CHECK-NOV-NEXT: # %bb.1: # %entry -; CHECK-NOV-NEXT: slti a4, s1, 0 -; CHECK-NOV-NEXT: bnez a1, .LBB24_4 +; CHECK-NOV-NEXT: slti a4, a1, 0 +; CHECK-NOV-NEXT: bnez s1, .LBB24_4 ; CHECK-NOV-NEXT: .LBB24_2: -; CHECK-NOV-NEXT: sltu a5, a0, a3 +; CHECK-NOV-NEXT: sltu a5, s0, a3 ; CHECK-NOV-NEXT: beqz a5, .LBB24_5 ; CHECK-NOV-NEXT: j .LBB24_6 ; CHECK-NOV-NEXT: .LBB24_3: -; CHECK-NOV-NEXT: sltu a4, s0, a3 -; CHECK-NOV-NEXT: beqz a1, .LBB24_2 +; CHECK-NOV-NEXT: sltu a4, a2, a3 +; CHECK-NOV-NEXT: beqz s1, .LBB24_2 ; CHECK-NOV-NEXT: .LBB24_4: # %entry -; CHECK-NOV-NEXT: slti a5, a1, 0 +; CHECK-NOV-NEXT: slti a5, s1, 0 ; CHECK-NOV-NEXT: bnez a5, .LBB24_6 ; CHECK-NOV-NEXT: .LBB24_5: # %entry -; CHECK-NOV-NEXT: mv a0, a3 +; CHECK-NOV-NEXT: mv s0, a3 ; CHECK-NOV-NEXT: .LBB24_6: # %entry ; CHECK-NOV-NEXT: neg a6, a5 ; CHECK-NOV-NEXT: neg a5, a4 -; CHECK-NOV-NEXT: and a5, a5, s1 +; CHECK-NOV-NEXT: and a5, a5, a1 ; CHECK-NOV-NEXT: bnez a4, .LBB24_8 ; CHECK-NOV-NEXT: # %bb.7: # %entry -; CHECK-NOV-NEXT: mv s0, a3 +; CHECK-NOV-NEXT: mv a2, a3 ; CHECK-NOV-NEXT: .LBB24_8: # %entry -; CHECK-NOV-NEXT: and a4, a6, a1 -; CHECK-NOV-NEXT: slli a1, a2, 63 -; CHECK-NOV-NEXT: beq a5, a2, .LBB24_11 +; CHECK-NOV-NEXT: and a4, a6, s1 +; CHECK-NOV-NEXT: slli a1, a0, 63 +; CHECK-NOV-NEXT: beq a5, a0, .LBB24_11 ; CHECK-NOV-NEXT: # %bb.9: # %entry ; CHECK-NOV-NEXT: slti a3, a5, 0 ; CHECK-NOV-NEXT: xori a3, a3, 1 -; CHECK-NOV-NEXT: bne a4, a2, .LBB24_12 +; CHECK-NOV-NEXT: bne a4, a0, .LBB24_12 ; CHECK-NOV-NEXT: .LBB24_10: -; CHECK-NOV-NEXT: sltu a2, a1, a0 -; CHECK-NOV-NEXT: beqz a2, .LBB24_13 +; CHECK-NOV-NEXT: sltu a0, a1, s0 +; CHECK-NOV-NEXT: beqz a0, .LBB24_13 ; CHECK-NOV-NEXT: j .LBB24_14 ; CHECK-NOV-NEXT: .LBB24_11: -; CHECK-NOV-NEXT: sltu a3, a1, s0 -; CHECK-NOV-NEXT: beq a4, a2, .LBB24_10 +; CHECK-NOV-NEXT: sltu a3, a1, a2 +; CHECK-NOV-NEXT: beq a4, a0, .LBB24_10 ; CHECK-NOV-NEXT: .LBB24_12: # %entry -; CHECK-NOV-NEXT: slti a2, a4, 0 -; CHECK-NOV-NEXT: xori a2, a2, 1 -; CHECK-NOV-NEXT: bnez a2, .LBB24_14 +; CHECK-NOV-NEXT: slti a0, a4, 0 +; CHECK-NOV-NEXT: xori a0, a0, 1 +; CHECK-NOV-NEXT: bnez a0, .LBB24_14 ; CHECK-NOV-NEXT: .LBB24_13: # %entry -; CHECK-NOV-NEXT: mv a0, a1 +; CHECK-NOV-NEXT: mv s0, a1 ; CHECK-NOV-NEXT: .LBB24_14: # %entry ; CHECK-NOV-NEXT: bnez a3, .LBB24_16 ; CHECK-NOV-NEXT: # %bb.15: # %entry -; CHECK-NOV-NEXT: mv s0, a1 +; CHECK-NOV-NEXT: mv a2, a1 ; CHECK-NOV-NEXT: .LBB24_16: # %entry -; CHECK-NOV-NEXT: mv a1, s0 +; CHECK-NOV-NEXT: mv a0, s0 +; CHECK-NOV-NEXT: mv a1, a2 ; CHECK-NOV-NEXT: ld ra, 24(sp) # 8-byte Folded Reload ; CHECK-NOV-NEXT: ld s0, 16(sp) # 8-byte Folded Reload ; CHECK-NOV-NEXT: ld s1, 8(sp) # 8-byte Folded Reload @@ -3082,8 +3086,8 @@ define <2 x i64> @stest_f16i64(<2 x half> %x) { ; CHECK-V-NEXT: .cfi_offset s0, -16 ; CHECK-V-NEXT: .cfi_offset s1, -24 ; CHECK-V-NEXT: .cfi_offset s2, -32 -; CHECK-V-NEXT: mv s2, a0 -; CHECK-V-NEXT: fmv.w.x fa0, a1 +; CHECK-V-NEXT: mv s2, a1 +; CHECK-V-NEXT: fmv.w.x fa0, a0 ; CHECK-V-NEXT: call __extendhfsf2 ; CHECK-V-NEXT: call __fixsfti ; CHECK-V-NEXT: mv s0, a0 @@ -3093,31 +3097,31 @@ define <2 x i64> @stest_f16i64(<2 x half> %x) { ; CHECK-V-NEXT: call __fixsfti ; CHECK-V-NEXT: li a2, -1 ; CHECK-V-NEXT: srli a3, a2, 1 -; CHECK-V-NEXT: beqz s1, .LBB24_3 +; CHECK-V-NEXT: beqz a1, .LBB24_3 ; CHECK-V-NEXT: # %bb.1: # %entry -; CHECK-V-NEXT: slti a4, s1, 0 -; CHECK-V-NEXT: bnez a1, .LBB24_4 +; CHECK-V-NEXT: slti a4, a1, 0 +; CHECK-V-NEXT: bnez s1, .LBB24_4 ; CHECK-V-NEXT: .LBB24_2: -; CHECK-V-NEXT: sltu a5, a0, a3 +; CHECK-V-NEXT: sltu a5, s0, a3 ; CHECK-V-NEXT: beqz a5, .LBB24_5 ; CHECK-V-NEXT: j .LBB24_6 ; CHECK-V-NEXT: .LBB24_3: -; CHECK-V-NEXT: sltu a4, s0, a3 -; CHECK-V-NEXT: beqz a1, .LBB24_2 +; CHECK-V-NEXT: sltu a4, a0, a3 +; CHECK-V-NEXT: beqz s1, .LBB24_2 ; CHECK-V-NEXT: .LBB24_4: # %entry -; CHECK-V-NEXT: slti a5, a1, 0 +; CHECK-V-NEXT: slti a5, s1, 0 ; CHECK-V-NEXT: bnez a5, .LBB24_6 ; CHECK-V-NEXT: .LBB24_5: # %entry -; CHECK-V-NEXT: mv a0, a3 +; CHECK-V-NEXT: mv s0, a3 ; CHECK-V-NEXT: .LBB24_6: # %entry ; CHECK-V-NEXT: neg a6, a5 ; CHECK-V-NEXT: neg a5, a4 -; CHECK-V-NEXT: and a5, a5, s1 +; CHECK-V-NEXT: and a5, a5, a1 ; CHECK-V-NEXT: bnez a4, .LBB24_8 ; CHECK-V-NEXT: # %bb.7: # %entry -; CHECK-V-NEXT: mv s0, a3 +; CHECK-V-NEXT: mv a0, a3 ; CHECK-V-NEXT: .LBB24_8: # %entry -; CHECK-V-NEXT: and a4, a6, a1 +; CHECK-V-NEXT: and a4, a6, s1 ; CHECK-V-NEXT: slli a1, a2, 63 ; CHECK-V-NEXT: beq a5, a2, .LBB24_11 ; CHECK-V-NEXT: # %bb.9: # %entry @@ -3125,26 +3129,26 @@ define <2 x i64> @stest_f16i64(<2 x half> %x) { ; CHECK-V-NEXT: xori a3, a3, 1 ; CHECK-V-NEXT: bne a4, a2, .LBB24_12 ; CHECK-V-NEXT: .LBB24_10: -; CHECK-V-NEXT: sltu a2, a1, a0 +; CHECK-V-NEXT: sltu a2, a1, s0 ; CHECK-V-NEXT: beqz a2, .LBB24_13 ; CHECK-V-NEXT: j .LBB24_14 ; CHECK-V-NEXT: .LBB24_11: -; CHECK-V-NEXT: sltu a3, a1, s0 +; CHECK-V-NEXT: sltu a3, a1, a0 ; CHECK-V-NEXT: beq a4, a2, .LBB24_10 ; CHECK-V-NEXT: .LBB24_12: # %entry ; CHECK-V-NEXT: slti a2, a4, 0 ; CHECK-V-NEXT: xori a2, a2, 1 ; CHECK-V-NEXT: bnez a2, .LBB24_14 ; CHECK-V-NEXT: .LBB24_13: # %entry -; CHECK-V-NEXT: mv a0, a1 +; CHECK-V-NEXT: mv s0, a1 ; CHECK-V-NEXT: .LBB24_14: # %entry ; CHECK-V-NEXT: bnez a3, .LBB24_16 ; CHECK-V-NEXT: # %bb.15: # %entry -; CHECK-V-NEXT: mv s0, a1 +; CHECK-V-NEXT: mv a0, a1 ; CHECK-V-NEXT: .LBB24_16: # %entry ; CHECK-V-NEXT: vsetivli zero, 2, e64, m1, ta, ma -; CHECK-V-NEXT: vmv.s.x v9, s0 -; CHECK-V-NEXT: vmv.s.x v8, a0 +; CHECK-V-NEXT: vmv.s.x v9, a0 +; CHECK-V-NEXT: vmv.s.x v8, s0 ; CHECK-V-NEXT: vslideup.vi v8, v9, 1 ; CHECK-V-NEXT: ld ra, 24(sp) # 8-byte Folded Reload ; CHECK-V-NEXT: ld s0, 16(sp) # 8-byte Folded Reload @@ -3175,8 +3179,8 @@ define <2 x i64> @utesth_f16i64(<2 x half> %x) { ; CHECK-NOV-NEXT: .cfi_offset s0, -16 ; CHECK-NOV-NEXT: .cfi_offset s1, -24 ; CHECK-NOV-NEXT: .cfi_offset s2, -32 -; CHECK-NOV-NEXT: mv s0, a0 -; CHECK-NOV-NEXT: fmv.w.x fa0, a1 +; CHECK-NOV-NEXT: mv s0, a1 +; CHECK-NOV-NEXT: fmv.w.x fa0, a0 ; CHECK-NOV-NEXT: call __extendhfsf2 ; CHECK-NOV-NEXT: call __fixunssfti ; CHECK-NOV-NEXT: mv s1, a0 @@ -3184,12 +3188,13 @@ define <2 x i64> @utesth_f16i64(<2 x half> %x) { ; CHECK-NOV-NEXT: fmv.w.x fa0, s0 ; CHECK-NOV-NEXT: call __extendhfsf2 ; CHECK-NOV-NEXT: call __fixunssfti -; CHECK-NOV-NEXT: snez a2, s2 ; CHECK-NOV-NEXT: snez a1, a1 +; CHECK-NOV-NEXT: snez a2, s2 +; CHECK-NOV-NEXT: addi a2, a2, -1 +; CHECK-NOV-NEXT: and a2, a2, s1 ; CHECK-NOV-NEXT: addi a1, a1, -1 -; CHECK-NOV-NEXT: and a0, a1, a0 -; CHECK-NOV-NEXT: addi a1, a2, -1 -; CHECK-NOV-NEXT: and a1, a1, s1 +; CHECK-NOV-NEXT: and a1, a1, a0 +; CHECK-NOV-NEXT: mv a0, a2 ; CHECK-NOV-NEXT: ld ra, 24(sp) # 8-byte Folded Reload ; CHECK-NOV-NEXT: ld s0, 16(sp) # 8-byte Folded Reload ; CHECK-NOV-NEXT: ld s1, 8(sp) # 8-byte Folded Reload @@ -3209,8 +3214,8 @@ define <2 x i64> @utesth_f16i64(<2 x half> %x) { ; CHECK-V-NEXT: .cfi_offset s0, -16 ; CHECK-V-NEXT: .cfi_offset s1, -24 ; CHECK-V-NEXT: .cfi_offset s2, -32 -; CHECK-V-NEXT: mv s0, a0 -; CHECK-V-NEXT: fmv.w.x fa0, a1 +; CHECK-V-NEXT: mv s0, a1 +; CHECK-V-NEXT: fmv.w.x fa0, a0 ; CHECK-V-NEXT: call __extendhfsf2 ; CHECK-V-NEXT: call __fixunssfti ; CHECK-V-NEXT: mv s1, a0 @@ -3218,15 +3223,15 @@ define <2 x i64> @utesth_f16i64(<2 x half> %x) { ; CHECK-V-NEXT: fmv.w.x fa0, s0 ; CHECK-V-NEXT: call __extendhfsf2 ; CHECK-V-NEXT: call __fixunssfti -; CHECK-V-NEXT: snez a2, s2 ; CHECK-V-NEXT: snez a1, a1 -; CHECK-V-NEXT: addi a1, a1, -1 -; CHECK-V-NEXT: and a0, a1, a0 +; CHECK-V-NEXT: snez a2, s2 ; CHECK-V-NEXT: addi a2, a2, -1 ; CHECK-V-NEXT: and a2, a2, s1 +; CHECK-V-NEXT: addi a1, a1, -1 +; CHECK-V-NEXT: and a0, a1, a0 ; CHECK-V-NEXT: vsetivli zero, 2, e64, m1, ta, ma -; CHECK-V-NEXT: vmv.s.x v9, a2 -; CHECK-V-NEXT: vmv.s.x v8, a0 +; CHECK-V-NEXT: vmv.s.x v9, a0 +; CHECK-V-NEXT: vmv.s.x v8, a2 ; CHECK-V-NEXT: vslideup.vi v8, v9, 1 ; CHECK-V-NEXT: ld ra, 24(sp) # 8-byte Folded Reload ; CHECK-V-NEXT: ld s0, 16(sp) # 8-byte Folded Reload @@ -3269,32 +3274,32 @@ define <2 x i64> @ustest_f16i64(<2 x half> %x) { ; CHECK-NOV-NEXT: # %bb.1: # %entry ; CHECK-NOV-NEXT: li a2, 1 ; CHECK-NOV-NEXT: .LBB26_2: # %entry -; CHECK-NOV-NEXT: slti a4, s1, 1 ; CHECK-NOV-NEXT: slti a3, a1, 1 +; CHECK-NOV-NEXT: slti a4, s1, 1 ; CHECK-NOV-NEXT: blez a1, .LBB26_4 ; CHECK-NOV-NEXT: # %bb.3: # %entry ; CHECK-NOV-NEXT: li a1, 1 ; CHECK-NOV-NEXT: .LBB26_4: # %entry +; CHECK-NOV-NEXT: neg a4, a4 ; CHECK-NOV-NEXT: neg a3, a3 ; CHECK-NOV-NEXT: and a3, a3, a0 -; CHECK-NOV-NEXT: neg a0, a4 ; CHECK-NOV-NEXT: beqz a1, .LBB26_7 ; CHECK-NOV-NEXT: # %bb.5: # %entry ; CHECK-NOV-NEXT: sgtz a1, a1 -; CHECK-NOV-NEXT: and a0, a0, s0 +; CHECK-NOV-NEXT: and a4, a4, s0 ; CHECK-NOV-NEXT: bnez a2, .LBB26_8 ; CHECK-NOV-NEXT: .LBB26_6: -; CHECK-NOV-NEXT: snez a2, a0 +; CHECK-NOV-NEXT: snez a0, a4 ; CHECK-NOV-NEXT: j .LBB26_9 ; CHECK-NOV-NEXT: .LBB26_7: ; CHECK-NOV-NEXT: snez a1, a3 -; CHECK-NOV-NEXT: and a0, a0, s0 +; CHECK-NOV-NEXT: and a4, a4, s0 ; CHECK-NOV-NEXT: beqz a2, .LBB26_6 ; CHECK-NOV-NEXT: .LBB26_8: # %entry -; CHECK-NOV-NEXT: sgtz a2, a2 +; CHECK-NOV-NEXT: sgtz a0, a2 ; CHECK-NOV-NEXT: .LBB26_9: # %entry -; CHECK-NOV-NEXT: neg a2, a2 -; CHECK-NOV-NEXT: and a0, a2, a0 +; CHECK-NOV-NEXT: neg a0, a0 +; CHECK-NOV-NEXT: and a0, a0, a4 ; CHECK-NOV-NEXT: neg a1, a1 ; CHECK-NOV-NEXT: and a1, a1, a3 ; CHECK-NOV-NEXT: ld ra, 24(sp) # 8-byte Folded Reload @@ -3330,15 +3335,15 @@ define <2 x i64> @ustest_f16i64(<2 x half> %x) { ; CHECK-V-NEXT: # %bb.1: # %entry ; CHECK-V-NEXT: li a2, 1 ; CHECK-V-NEXT: .LBB26_2: # %entry -; CHECK-V-NEXT: slti a3, s1, 1 ; CHECK-V-NEXT: slti a4, a1, 1 +; CHECK-V-NEXT: slti a3, s1, 1 ; CHECK-V-NEXT: blez a1, .LBB26_4 ; CHECK-V-NEXT: # %bb.3: # %entry ; CHECK-V-NEXT: li a1, 1 ; CHECK-V-NEXT: .LBB26_4: # %entry +; CHECK-V-NEXT: neg a3, a3 ; CHECK-V-NEXT: neg a4, a4 ; CHECK-V-NEXT: and a0, a4, a0 -; CHECK-V-NEXT: neg a3, a3 ; CHECK-V-NEXT: beqz a1, .LBB26_7 ; CHECK-V-NEXT: # %bb.5: # %entry ; CHECK-V-NEXT: sgtz a1, a1 @@ -5811,15 +5816,15 @@ define <2 x i64> @ustest_f64i64_mm(<2 x double> %x) { ; CHECK-NOV-NEXT: mv s1, a1 ; CHECK-NOV-NEXT: fmv.d fa0, fs0 ; CHECK-NOV-NEXT: call __fixdfti -; CHECK-NOV-NEXT: mv a2, s1 -; CHECK-NOV-NEXT: mv a3, a1 +; CHECK-NOV-NEXT: mv a2, a1 ; CHECK-NOV-NEXT: blez a1, .LBB47_2 ; CHECK-NOV-NEXT: # %bb.1: # %entry -; CHECK-NOV-NEXT: li a3, 1 +; CHECK-NOV-NEXT: li a2, 1 ; CHECK-NOV-NEXT: .LBB47_2: # %entry -; CHECK-NOV-NEXT: blez a2, .LBB47_4 +; CHECK-NOV-NEXT: mv a3, s1 +; CHECK-NOV-NEXT: blez s1, .LBB47_4 ; CHECK-NOV-NEXT: # %bb.3: # %entry -; CHECK-NOV-NEXT: li a2, 1 +; CHECK-NOV-NEXT: li a3, 1 ; CHECK-NOV-NEXT: .LBB47_4: # %entry ; CHECK-NOV-NEXT: slti a1, a1, 1 ; CHECK-NOV-NEXT: neg a1, a1 @@ -5827,11 +5832,11 @@ define <2 x i64> @ustest_f64i64_mm(<2 x double> %x) { ; CHECK-NOV-NEXT: slti a0, s1, 1 ; CHECK-NOV-NEXT: neg a0, a0 ; CHECK-NOV-NEXT: and a0, a0, s0 +; CHECK-NOV-NEXT: slti a3, a3, 0 +; CHECK-NOV-NEXT: addi a3, a3, -1 +; CHECK-NOV-NEXT: and a0, a3, a0 ; CHECK-NOV-NEXT: slti a2, a2, 0 ; CHECK-NOV-NEXT: addi a2, a2, -1 -; CHECK-NOV-NEXT: and a0, a2, a0 -; CHECK-NOV-NEXT: slti a2, a3, 0 -; CHECK-NOV-NEXT: addi a2, a2, -1 ; CHECK-NOV-NEXT: and a1, a2, a1 ; CHECK-NOV-NEXT: ld ra, 24(sp) # 8-byte Folded Reload ; CHECK-NOV-NEXT: ld s0, 16(sp) # 8-byte Folded Reload @@ -5867,15 +5872,15 @@ define <2 x i64> @ustest_f64i64_mm(<2 x double> %x) { ; CHECK-V-NEXT: vl1r.v v8, (a0) # Unknown-size Folded Reload ; CHECK-V-NEXT: vfmv.f.s fa0, v8 ; CHECK-V-NEXT: call __fixdfti -; CHECK-V-NEXT: mv a2, s1 -; CHECK-V-NEXT: mv a3, a1 +; CHECK-V-NEXT: mv a2, a1 ; CHECK-V-NEXT: blez a1, .LBB47_2 ; CHECK-V-NEXT: # %bb.1: # %entry -; CHECK-V-NEXT: li a3, 1 +; CHECK-V-NEXT: li a2, 1 ; CHECK-V-NEXT: .LBB47_2: # %entry -; CHECK-V-NEXT: blez a2, .LBB47_4 +; CHECK-V-NEXT: mv a3, s1 +; CHECK-V-NEXT: blez s1, .LBB47_4 ; CHECK-V-NEXT: # %bb.3: # %entry -; CHECK-V-NEXT: li a2, 1 +; CHECK-V-NEXT: li a3, 1 ; CHECK-V-NEXT: .LBB47_4: # %entry ; CHECK-V-NEXT: slti a1, a1, 1 ; CHECK-V-NEXT: neg a1, a1 @@ -5883,11 +5888,11 @@ define <2 x i64> @ustest_f64i64_mm(<2 x double> %x) { ; CHECK-V-NEXT: slti a1, s1, 1 ; CHECK-V-NEXT: neg a1, a1 ; CHECK-V-NEXT: and a1, a1, s0 +; CHECK-V-NEXT: slti a3, a3, 0 +; CHECK-V-NEXT: addi a3, a3, -1 +; CHECK-V-NEXT: and a1, a3, a1 ; CHECK-V-NEXT: slti a2, a2, 0 ; CHECK-V-NEXT: addi a2, a2, -1 -; CHECK-V-NEXT: and a1, a2, a1 -; CHECK-V-NEXT: slti a2, a3, 0 -; CHECK-V-NEXT: addi a2, a2, -1 ; CHECK-V-NEXT: and a0, a2, a0 ; CHECK-V-NEXT: vsetivli zero, 2, e64, m1, ta, ma ; CHECK-V-NEXT: vmv.s.x v8, a0 @@ -6197,15 +6202,15 @@ define <2 x i64> @ustest_f32i64_mm(<2 x float> %x) { ; CHECK-NOV-NEXT: mv s1, a1 ; CHECK-NOV-NEXT: fmv.s fa0, fs0 ; CHECK-NOV-NEXT: call __fixsfti -; CHECK-NOV-NEXT: mv a2, s1 -; CHECK-NOV-NEXT: mv a3, a1 +; CHECK-NOV-NEXT: mv a2, a1 ; CHECK-NOV-NEXT: blez a1, .LBB50_2 ; CHECK-NOV-NEXT: # %bb.1: # %entry -; CHECK-NOV-NEXT: li a3, 1 +; CHECK-NOV-NEXT: li a2, 1 ; CHECK-NOV-NEXT: .LBB50_2: # %entry -; CHECK-NOV-NEXT: blez a2, .LBB50_4 +; CHECK-NOV-NEXT: mv a3, s1 +; CHECK-NOV-NEXT: blez s1, .LBB50_4 ; CHECK-NOV-NEXT: # %bb.3: # %entry -; CHECK-NOV-NEXT: li a2, 1 +; CHECK-NOV-NEXT: li a3, 1 ; CHECK-NOV-NEXT: .LBB50_4: # %entry ; CHECK-NOV-NEXT: slti a1, a1, 1 ; CHECK-NOV-NEXT: neg a1, a1 @@ -6213,11 +6218,11 @@ define <2 x i64> @ustest_f32i64_mm(<2 x float> %x) { ; CHECK-NOV-NEXT: slti a0, s1, 1 ; CHECK-NOV-NEXT: neg a0, a0 ; CHECK-NOV-NEXT: and a0, a0, s0 +; CHECK-NOV-NEXT: slti a3, a3, 0 +; CHECK-NOV-NEXT: addi a3, a3, -1 +; CHECK-NOV-NEXT: and a0, a3, a0 ; CHECK-NOV-NEXT: slti a2, a2, 0 ; CHECK-NOV-NEXT: addi a2, a2, -1 -; CHECK-NOV-NEXT: and a0, a2, a0 -; CHECK-NOV-NEXT: slti a2, a3, 0 -; CHECK-NOV-NEXT: addi a2, a2, -1 ; CHECK-NOV-NEXT: and a1, a2, a1 ; CHECK-NOV-NEXT: ld ra, 24(sp) # 8-byte Folded Reload ; CHECK-NOV-NEXT: ld s0, 16(sp) # 8-byte Folded Reload @@ -6253,15 +6258,15 @@ define <2 x i64> @ustest_f32i64_mm(<2 x float> %x) { ; CHECK-V-NEXT: vl1r.v v8, (a0) # Unknown-size Folded Reload ; CHECK-V-NEXT: vfmv.f.s fa0, v8 ; CHECK-V-NEXT: call __fixsfti -; CHECK-V-NEXT: mv a2, s1 -; CHECK-V-NEXT: mv a3, a1 +; CHECK-V-NEXT: mv a2, a1 ; CHECK-V-NEXT: blez a1, .LBB50_2 ; CHECK-V-NEXT: # %bb.1: # %entry -; CHECK-V-NEXT: li a3, 1 +; CHECK-V-NEXT: li a2, 1 ; CHECK-V-NEXT: .LBB50_2: # %entry -; CHECK-V-NEXT: blez a2, .LBB50_4 +; CHECK-V-NEXT: mv a3, s1 +; CHECK-V-NEXT: blez s1, .LBB50_4 ; CHECK-V-NEXT: # %bb.3: # %entry -; CHECK-V-NEXT: li a2, 1 +; CHECK-V-NEXT: li a3, 1 ; CHECK-V-NEXT: .LBB50_4: # %entry ; CHECK-V-NEXT: slti a1, a1, 1 ; CHECK-V-NEXT: neg a1, a1 @@ -6269,11 +6274,11 @@ define <2 x i64> @ustest_f32i64_mm(<2 x float> %x) { ; CHECK-V-NEXT: slti a1, s1, 1 ; CHECK-V-NEXT: neg a1, a1 ; CHECK-V-NEXT: and a1, a1, s0 +; CHECK-V-NEXT: slti a3, a3, 0 +; CHECK-V-NEXT: addi a3, a3, -1 +; CHECK-V-NEXT: and a1, a3, a1 ; CHECK-V-NEXT: slti a2, a2, 0 ; CHECK-V-NEXT: addi a2, a2, -1 -; CHECK-V-NEXT: and a1, a2, a1 -; CHECK-V-NEXT: slti a2, a3, 0 -; CHECK-V-NEXT: addi a2, a2, -1 ; CHECK-V-NEXT: and a0, a2, a0 ; CHECK-V-NEXT: vsetivli zero, 2, e64, m1, ta, ma ; CHECK-V-NEXT: vmv.s.x v8, a0 @@ -6575,15 +6580,15 @@ define <2 x i64> @ustest_f16i64_mm(<2 x half> %x) { ; CHECK-NOV-NEXT: fmv.w.x fa0, s2 ; CHECK-NOV-NEXT: call __extendhfsf2 ; CHECK-NOV-NEXT: call __fixsfti -; CHECK-NOV-NEXT: mv a2, s1 -; CHECK-NOV-NEXT: mv a3, a1 +; CHECK-NOV-NEXT: mv a2, a1 ; CHECK-NOV-NEXT: blez a1, .LBB53_2 ; CHECK-NOV-NEXT: # %bb.1: # %entry -; CHECK-NOV-NEXT: li a3, 1 +; CHECK-NOV-NEXT: li a2, 1 ; CHECK-NOV-NEXT: .LBB53_2: # %entry -; CHECK-NOV-NEXT: blez a2, .LBB53_4 +; CHECK-NOV-NEXT: mv a3, s1 +; CHECK-NOV-NEXT: blez s1, .LBB53_4 ; CHECK-NOV-NEXT: # %bb.3: # %entry -; CHECK-NOV-NEXT: li a2, 1 +; CHECK-NOV-NEXT: li a3, 1 ; CHECK-NOV-NEXT: .LBB53_4: # %entry ; CHECK-NOV-NEXT: slti a1, a1, 1 ; CHECK-NOV-NEXT: neg a1, a1 @@ -6591,11 +6596,11 @@ define <2 x i64> @ustest_f16i64_mm(<2 x half> %x) { ; CHECK-NOV-NEXT: slti a0, s1, 1 ; CHECK-NOV-NEXT: neg a0, a0 ; CHECK-NOV-NEXT: and a0, a0, s0 +; CHECK-NOV-NEXT: slti a3, a3, 0 +; CHECK-NOV-NEXT: addi a3, a3, -1 +; CHECK-NOV-NEXT: and a0, a3, a0 ; CHECK-NOV-NEXT: slti a2, a2, 0 ; CHECK-NOV-NEXT: addi a2, a2, -1 -; CHECK-NOV-NEXT: and a0, a2, a0 -; CHECK-NOV-NEXT: slti a2, a3, 0 -; CHECK-NOV-NEXT: addi a2, a2, -1 ; CHECK-NOV-NEXT: and a1, a2, a1 ; CHECK-NOV-NEXT: ld ra, 24(sp) # 8-byte Folded Reload ; CHECK-NOV-NEXT: ld s0, 16(sp) # 8-byte Folded Reload @@ -6625,15 +6630,15 @@ define <2 x i64> @ustest_f16i64_mm(<2 x half> %x) { ; CHECK-V-NEXT: fmv.w.x fa0, s2 ; CHECK-V-NEXT: call __extendhfsf2 ; CHECK-V-NEXT: call __fixsfti -; CHECK-V-NEXT: mv a2, s1 -; CHECK-V-NEXT: mv a3, a1 +; CHECK-V-NEXT: mv a2, a1 ; CHECK-V-NEXT: blez a1, .LBB53_2 ; CHECK-V-NEXT: # %bb.1: # %entry -; CHECK-V-NEXT: li a3, 1 +; CHECK-V-NEXT: li a2, 1 ; CHECK-V-NEXT: .LBB53_2: # %entry -; CHECK-V-NEXT: blez a2, .LBB53_4 +; CHECK-V-NEXT: mv a3, s1 +; CHECK-V-NEXT: blez s1, .LBB53_4 ; CHECK-V-NEXT: # %bb.3: # %entry -; CHECK-V-NEXT: li a2, 1 +; CHECK-V-NEXT: li a3, 1 ; CHECK-V-NEXT: .LBB53_4: # %entry ; CHECK-V-NEXT: slti a1, a1, 1 ; CHECK-V-NEXT: neg a1, a1 @@ -6641,11 +6646,11 @@ define <2 x i64> @ustest_f16i64_mm(<2 x half> %x) { ; CHECK-V-NEXT: slti a1, s1, 1 ; CHECK-V-NEXT: neg a1, a1 ; CHECK-V-NEXT: and a1, a1, s0 +; CHECK-V-NEXT: slti a3, a3, 0 +; CHECK-V-NEXT: addi a3, a3, -1 +; CHECK-V-NEXT: and a1, a3, a1 ; CHECK-V-NEXT: slti a2, a2, 0 ; CHECK-V-NEXT: addi a2, a2, -1 -; CHECK-V-NEXT: and a1, a2, a1 -; CHECK-V-NEXT: slti a2, a3, 0 -; CHECK-V-NEXT: addi a2, a2, -1 ; CHECK-V-NEXT: and a0, a2, a0 ; CHECK-V-NEXT: vsetivli zero, 2, e64, m1, ta, ma ; CHECK-V-NEXT: vmv.s.x v9, a0 diff --git a/llvm/test/CodeGen/RISCV/rvv/shuffle-reverse.ll b/llvm/test/CodeGen/RISCV/rvv/shuffle-reverse.ll index 032d32109933f3badf0fd1b550e6d0c9bf38c6ce..ab7da9e0faf2b9323b405b75c2dfd1b5d13de550 100644 --- a/llvm/test/CodeGen/RISCV/rvv/shuffle-reverse.ll +++ b/llvm/test/CodeGen/RISCV/rvv/shuffle-reverse.ll @@ -49,8 +49,8 @@ define <8 x i8> @v4i8_2(<4 x i8> %a, <4 x i8> %b) { ; CHECK-NEXT: vid.v v11 ; CHECK-NEXT: vrsub.vi v12, v11, 7 ; CHECK-NEXT: vrgather.vv v10, v8, v12 -; CHECK-NEXT: vmv.v.i v0, 15 ; CHECK-NEXT: vrsub.vi v8, v11, 3 +; CHECK-NEXT: vmv.v.i v0, 15 ; CHECK-NEXT: vrgather.vv v10, v9, v8, v0.t ; CHECK-NEXT: vmv1r.v v8, v10 ; CHECK-NEXT: ret @@ -174,8 +174,8 @@ define <8 x i16> @v4i16_2(<4 x i16> %a, <4 x i16> %b) { ; CHECK-NEXT: vid.v v11 ; CHECK-NEXT: vrsub.vi v12, v11, 7 ; CHECK-NEXT: vrgather.vv v10, v8, v12 -; CHECK-NEXT: vmv.v.i v0, 15 ; CHECK-NEXT: vrsub.vi v8, v11, 3 +; CHECK-NEXT: vmv.v.i v0, 15 ; CHECK-NEXT: vrgather.vv v10, v9, v8, v0.t ; CHECK-NEXT: vmv.v.v v8, v10 ; CHECK-NEXT: ret @@ -492,8 +492,8 @@ define <8 x half> @v4f16_2(<4 x half> %a, <4 x half> %b) { ; CHECK-NEXT: vid.v v11 ; CHECK-NEXT: vrsub.vi v12, v11, 7 ; CHECK-NEXT: vrgather.vv v10, v8, v12 -; CHECK-NEXT: vmv.v.i v0, 15 ; CHECK-NEXT: vrsub.vi v8, v11, 3 +; CHECK-NEXT: vmv.v.i v0, 15 ; CHECK-NEXT: vrgather.vv v10, v9, v8, v0.t ; CHECK-NEXT: vmv.v.v v8, v10 ; CHECK-NEXT: ret diff --git a/llvm/test/CodeGen/RISCV/rvv/vector-interleave-store.ll b/llvm/test/CodeGen/RISCV/rvv/vector-interleave-store.ll index 9a5e86d61c265ea18634174a401c73675ab72c76..922692ed88c9f264746e0c9b98b3517f7a44befd 100644 --- a/llvm/test/CodeGen/RISCV/rvv/vector-interleave-store.ll +++ b/llvm/test/CodeGen/RISCV/rvv/vector-interleave-store.ll @@ -107,14 +107,14 @@ define void @vector_interleave_store_nxv16i64_nxv8i64( %a, %a, @vector_interleave_nxv4i64_nxv2i64( ; CHECK-NEXT: srli a0, a0, 2 ; CHECK-NEXT: vsetvli a1, zero, e16, m1, ta, mu ; CHECK-NEXT: vid.v v12 -; CHECK-NEXT: vand.vi v13, v12, 1 -; CHECK-NEXT: vmsne.vi v0, v13, 0 ; CHECK-NEXT: vsrl.vi v16, v12, 1 +; CHECK-NEXT: vand.vi v12, v12, 1 +; CHECK-NEXT: vmsne.vi v0, v12, 0 ; CHECK-NEXT: vadd.vx v16, v16, a0, v0.t ; CHECK-NEXT: vsetvli zero, zero, e64, m4, ta, ma ; CHECK-NEXT: vrgatherei16.vv v12, v8, v16 @@ -137,9 +137,9 @@ define @vector_interleave_nxv4i64_nxv2i64( ; ZVBB-NEXT: srli a0, a0, 2 ; ZVBB-NEXT: vsetvli a1, zero, e16, m1, ta, mu ; ZVBB-NEXT: vid.v v12 -; ZVBB-NEXT: vand.vi v13, v12, 1 -; ZVBB-NEXT: vmsne.vi v0, v13, 0 ; ZVBB-NEXT: vsrl.vi v16, v12, 1 +; ZVBB-NEXT: vand.vi v12, v12, 1 +; ZVBB-NEXT: vmsne.vi v0, v12, 0 ; ZVBB-NEXT: vadd.vx v16, v16, a0, v0.t ; ZVBB-NEXT: vsetvli zero, zero, e64, m4, ta, ma ; ZVBB-NEXT: vrgatherei16.vv v12, v8, v16 @@ -288,32 +288,44 @@ define @vector_interleave_nxv16i64_nxv8i64( @vector_interleave_nxv16i64_nxv8i64( @vector_interleave_nxv4f64_nxv2f64( @vector_interleave_nxv4f64_nxv2f64( @vector_interleave_nxv16f64_nxv8f64( @vector_interleave_nxv16f64_nxv8f64( @llvm.riscv.vadd.nxv1i8.nxv1i8( + , + , + , + i32) + +declare @llvm.riscv.vadd.mask.nxv1i8.nxv1i8( + , + , + , + , + i32, i32) + +declare @llvm.riscv.vsub.nxv1i8.nxv1i8( + , + , + , + i32) + +declare @llvm.riscv.vmul.nxv1i8.nxv1i8( + , + , + , + i32) + +define @simple_vadd_vv( %0, %1, i32 %2) nounwind { +; CHECK-LABEL: simple_vadd_vv: +; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vsetvli zero, a0, e8, mf8, ta, ma +; CHECK-NEXT: vadd.vv v9, v8, v9 +; CHECK-NEXT: vadd.vv v8, v8, v8 +; CHECK-NEXT: vadd.vv v8, v8, v9 +; CHECK-NEXT: ret +entry: + %a = call @llvm.riscv.vadd.nxv1i8.nxv1i8( + undef, + %0, + %1, + i32 %2) + + %b = call @llvm.riscv.vadd.nxv1i8.nxv1i8( + undef, + %0, + %a, + i32 %2) + + %c = call @llvm.riscv.vadd.nxv1i8.nxv1i8( + undef, + %0, + %b, + i32 %2) + + ret %c +} + +define @simple_vadd_vsub_vv( %0, %1, i32 %2) nounwind { +; CHECK-LABEL: simple_vadd_vsub_vv: +; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vsetvli zero, a0, e8, mf8, ta, ma +; CHECK-NEXT: vsub.vv v9, v8, v9 +; CHECK-NEXT: vadd.vv v8, v8, v8 +; CHECK-NEXT: vadd.vv v8, v8, v9 +; CHECK-NEXT: ret +entry: + %a = call @llvm.riscv.vsub.nxv1i8.nxv1i8( + undef, + %0, + %1, + i32 %2) + + %b = call @llvm.riscv.vadd.nxv1i8.nxv1i8( + undef, + %0, + %a, + i32 %2) + + %c = call @llvm.riscv.vadd.nxv1i8.nxv1i8( + undef, + %0, + %b, + i32 %2) + + ret %c +} + +define @simple_vmul_vv( %0, %1, i32 %2) nounwind { +; CHECK-LABEL: simple_vmul_vv: +; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vsetvli zero, a0, e8, mf8, ta, ma +; CHECK-NEXT: vmul.vv v9, v8, v9 +; CHECK-NEXT: vmul.vv v8, v8, v8 +; CHECK-NEXT: vmul.vv v8, v8, v9 +; CHECK-NEXT: ret +entry: + %a = call @llvm.riscv.vmul.nxv1i8.nxv1i8( + undef, + %0, + %1, + i32 %2) + + %b = call @llvm.riscv.vmul.nxv1i8.nxv1i8( + undef, + %0, + %a, + i32 %2) + + %c = call @llvm.riscv.vmul.nxv1i8.nxv1i8( + undef, + %0, + %b, + i32 %2) + + ret %c +} + +; With passthru and masks. +define @vadd_vv_passthru( %0, %1, i32 %2) nounwind { +; CHECK-LABEL: vadd_vv_passthru: +; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vsetvli zero, a0, e8, mf8, tu, ma +; CHECK-NEXT: vmv1r.v v10, v8 +; CHECK-NEXT: vadd.vv v10, v8, v9 +; CHECK-NEXT: vmv1r.v v9, v8 +; CHECK-NEXT: vadd.vv v9, v8, v8 +; CHECK-NEXT: vadd.vv v8, v9, v10 +; CHECK-NEXT: ret +entry: + %a = call @llvm.riscv.vadd.nxv1i8.nxv1i8( + %0, + %0, + %1, + i32 %2) + + %b = call @llvm.riscv.vadd.nxv1i8.nxv1i8( + %0, + %0, + %a, + i32 %2) + + %c = call @llvm.riscv.vadd.nxv1i8.nxv1i8( + %0, + %0, + %b, + i32 %2) + + ret %c +} + +define @vadd_vv_passthru_negative( %0, %1, i32 %2) nounwind { +; CHECK-LABEL: vadd_vv_passthru_negative: +; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vsetvli zero, a0, e8, mf8, tu, ma +; CHECK-NEXT: vmv1r.v v10, v8 +; CHECK-NEXT: vadd.vv v10, v8, v9 +; CHECK-NEXT: vadd.vv v9, v8, v10 +; CHECK-NEXT: vadd.vv v8, v8, v9 +; CHECK-NEXT: ret +entry: + %a = call @llvm.riscv.vadd.nxv1i8.nxv1i8( + %0, + %0, + %1, + i32 %2) + + %b = call @llvm.riscv.vadd.nxv1i8.nxv1i8( + %1, + %0, + %a, + i32 %2) + + %c = call @llvm.riscv.vadd.nxv1i8.nxv1i8( + %0, + %0, + %b, + i32 %2) + + ret %c +} + +define @vadd_vv_mask( %0, %1, i32 %2, %m) nounwind { +; CHECK-LABEL: vadd_vv_mask: +; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vsetvli zero, a0, e8, mf8, ta, mu +; CHECK-NEXT: vmv1r.v v10, v8 +; CHECK-NEXT: vadd.vv v10, v8, v9, v0.t +; CHECK-NEXT: vmv1r.v v9, v8 +; CHECK-NEXT: vadd.vv v9, v8, v8, v0.t +; CHECK-NEXT: vadd.vv v8, v9, v10, v0.t +; CHECK-NEXT: ret +entry: + %a = call @llvm.riscv.vadd.mask.nxv1i8.nxv1i8( + %0, + %0, + %1, + %m, + i32 %2, i32 1) + + %b = call @llvm.riscv.vadd.mask.nxv1i8.nxv1i8( + %0, + %0, + %a, + %m, + i32 %2, i32 1) + + %c = call @llvm.riscv.vadd.mask.nxv1i8.nxv1i8( + %0, + %0, + %b, + %m, + i32 %2, i32 1) + + ret %c +} + +define @vadd_vv_mask_negative( %0, %1, i32 %2, %m, %m2) nounwind { +; CHECK-LABEL: vadd_vv_mask_negative: +; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vsetvli zero, a0, e8, mf8, ta, mu +; CHECK-NEXT: vmv1r.v v11, v8 +; CHECK-NEXT: vadd.vv v11, v8, v9, v0.t +; CHECK-NEXT: vmv1r.v v9, v8 +; CHECK-NEXT: vadd.vv v9, v8, v11, v0.t +; CHECK-NEXT: vmv1r.v v0, v10 +; CHECK-NEXT: vadd.vv v8, v8, v9, v0.t +; CHECK-NEXT: ret +entry: + %a = call @llvm.riscv.vadd.mask.nxv1i8.nxv1i8( + %0, + %0, + %1, + %m, + i32 %2, i32 1) + + %b = call @llvm.riscv.vadd.mask.nxv1i8.nxv1i8( + %0, + %0, + %a, + %m, + i32 %2, i32 1) + + %c = call @llvm.riscv.vadd.mask.nxv1i8.nxv1i8( + %0, + %0, + %b, + %m2, + i32 %2, i32 1) + + ret %c +} + diff --git a/llvm/test/CodeGen/RISCV/rvv/vmfeq.ll b/llvm/test/CodeGen/RISCV/rvv/vmfeq.ll index ffeb399291e1f9755d4824899100bb641afea2ce..e7184921d87a0886f1b3e24780cf861c9211fe63 100644 --- a/llvm/test/CodeGen/RISCV/rvv/vmfeq.ll +++ b/llvm/test/CodeGen/RISCV/rvv/vmfeq.ll @@ -34,10 +34,9 @@ declare @llvm.riscv.vmfeq.mask.nxv1f16( define @intrinsic_vmfeq_mask_vv_nxv1f16_nxv1f16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfeq_mask_vv_nxv1f16_nxv1f16: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e16, mf4, ta, mu -; CHECK-NEXT: vmfeq.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e16, mf4, ta, mu +; CHECK-NEXT: vmfeq.vv v0, v8, v9 ; CHECK-NEXT: vmfeq.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -86,10 +85,9 @@ declare @llvm.riscv.vmfeq.mask.nxv2f16( define @intrinsic_vmfeq_mask_vv_nxv2f16_nxv2f16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfeq_mask_vv_nxv2f16_nxv2f16: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e16, mf2, ta, mu -; CHECK-NEXT: vmfeq.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e16, mf2, ta, mu +; CHECK-NEXT: vmfeq.vv v0, v8, v9 ; CHECK-NEXT: vmfeq.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -138,10 +136,9 @@ declare @llvm.riscv.vmfeq.mask.nxv4f16( define @intrinsic_vmfeq_mask_vv_nxv4f16_nxv4f16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfeq_mask_vv_nxv4f16_nxv4f16: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e16, m1, ta, mu -; CHECK-NEXT: vmfeq.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e16, m1, ta, mu +; CHECK-NEXT: vmfeq.vv v0, v8, v9 ; CHECK-NEXT: vmfeq.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -190,12 +187,11 @@ declare @llvm.riscv.vmfeq.mask.nxv8f16( define @intrinsic_vmfeq_mask_vv_nxv8f16_nxv8f16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfeq_mask_vv_nxv8f16_nxv8f16: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e16, m2, ta, mu -; CHECK-NEXT: vmfeq.vv v14, v8, v10 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmfeq.vv v0, v8, v10 +; CHECK-NEXT: vmfeq.vv v14, v10, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmfeq.vv v8, v10, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmfeq.nxv8f16( @@ -242,12 +238,11 @@ declare @llvm.riscv.vmfeq.mask.nxv16f16( define @intrinsic_vmfeq_mask_vv_nxv16f16_nxv16f16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfeq_mask_vv_nxv16f16_nxv16f16: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e16, m4, ta, mu -; CHECK-NEXT: vmfeq.vv v20, v8, v12 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmfeq.vv v0, v8, v12 +; CHECK-NEXT: vmfeq.vv v20, v12, v16, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmfeq.vv v8, v12, v16, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmfeq.nxv16f16( @@ -294,10 +289,9 @@ declare @llvm.riscv.vmfeq.mask.nxv1f32( define @intrinsic_vmfeq_mask_vv_nxv1f32_nxv1f32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfeq_mask_vv_nxv1f32_nxv1f32: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e32, mf2, ta, mu -; CHECK-NEXT: vmfeq.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e32, mf2, ta, mu +; CHECK-NEXT: vmfeq.vv v0, v8, v9 ; CHECK-NEXT: vmfeq.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -346,10 +340,9 @@ declare @llvm.riscv.vmfeq.mask.nxv2f32( define @intrinsic_vmfeq_mask_vv_nxv2f32_nxv2f32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfeq_mask_vv_nxv2f32_nxv2f32: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e32, m1, ta, mu -; CHECK-NEXT: vmfeq.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e32, m1, ta, mu +; CHECK-NEXT: vmfeq.vv v0, v8, v9 ; CHECK-NEXT: vmfeq.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -398,12 +391,11 @@ declare @llvm.riscv.vmfeq.mask.nxv4f32( define @intrinsic_vmfeq_mask_vv_nxv4f32_nxv4f32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfeq_mask_vv_nxv4f32_nxv4f32: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e32, m2, ta, mu -; CHECK-NEXT: vmfeq.vv v14, v8, v10 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmfeq.vv v0, v8, v10 +; CHECK-NEXT: vmfeq.vv v14, v10, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmfeq.vv v8, v10, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmfeq.nxv4f32( @@ -450,12 +442,11 @@ declare @llvm.riscv.vmfeq.mask.nxv8f32( define @intrinsic_vmfeq_mask_vv_nxv8f32_nxv8f32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfeq_mask_vv_nxv8f32_nxv8f32: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e32, m4, ta, mu -; CHECK-NEXT: vmfeq.vv v20, v8, v12 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmfeq.vv v0, v8, v12 +; CHECK-NEXT: vmfeq.vv v20, v12, v16, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmfeq.vv v8, v12, v16, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmfeq.nxv8f32( @@ -502,10 +493,9 @@ declare @llvm.riscv.vmfeq.mask.nxv1f64( define @intrinsic_vmfeq_mask_vv_nxv1f64_nxv1f64( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfeq_mask_vv_nxv1f64_nxv1f64: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, mu -; CHECK-NEXT: vmfeq.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, mu +; CHECK-NEXT: vmfeq.vv v0, v8, v9 ; CHECK-NEXT: vmfeq.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -554,12 +544,11 @@ declare @llvm.riscv.vmfeq.mask.nxv2f64( define @intrinsic_vmfeq_mask_vv_nxv2f64_nxv2f64( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfeq_mask_vv_nxv2f64_nxv2f64: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e64, m2, ta, mu -; CHECK-NEXT: vmfeq.vv v14, v8, v10 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmfeq.vv v0, v8, v10 +; CHECK-NEXT: vmfeq.vv v14, v10, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmfeq.vv v8, v10, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmfeq.nxv2f64( @@ -606,12 +595,11 @@ declare @llvm.riscv.vmfeq.mask.nxv4f64( define @intrinsic_vmfeq_mask_vv_nxv4f64_nxv4f64( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfeq_mask_vv_nxv4f64_nxv4f64: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e64, m4, ta, mu -; CHECK-NEXT: vmfeq.vv v20, v8, v12 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmfeq.vv v0, v8, v12 +; CHECK-NEXT: vmfeq.vv v20, v12, v16, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmfeq.vv v8, v12, v16, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmfeq.nxv4f64( diff --git a/llvm/test/CodeGen/RISCV/rvv/vmfge.ll b/llvm/test/CodeGen/RISCV/rvv/vmfge.ll index 993b50a1c81ce885ca54840c85d209952cfbd653..a6dad9eaa4f35814bc6f02c8c6f1484bd6feac68 100644 --- a/llvm/test/CodeGen/RISCV/rvv/vmfge.ll +++ b/llvm/test/CodeGen/RISCV/rvv/vmfge.ll @@ -34,10 +34,9 @@ declare @llvm.riscv.vmfge.mask.nxv1f16( define @intrinsic_vmfge_mask_vv_nxv1f16_nxv1f16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfge_mask_vv_nxv1f16_nxv1f16: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e16, mf4, ta, mu -; CHECK-NEXT: vmfle.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e16, mf4, ta, mu +; CHECK-NEXT: vmfle.vv v0, v9, v8 ; CHECK-NEXT: vmfle.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -86,10 +85,9 @@ declare @llvm.riscv.vmfge.mask.nxv2f16( define @intrinsic_vmfge_mask_vv_nxv2f16_nxv2f16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfge_mask_vv_nxv2f16_nxv2f16: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e16, mf2, ta, mu -; CHECK-NEXT: vmfle.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e16, mf2, ta, mu +; CHECK-NEXT: vmfle.vv v0, v9, v8 ; CHECK-NEXT: vmfle.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -138,10 +136,9 @@ declare @llvm.riscv.vmfge.mask.nxv4f16( define @intrinsic_vmfge_mask_vv_nxv4f16_nxv4f16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfge_mask_vv_nxv4f16_nxv4f16: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e16, m1, ta, mu -; CHECK-NEXT: vmfle.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e16, m1, ta, mu +; CHECK-NEXT: vmfle.vv v0, v9, v8 ; CHECK-NEXT: vmfle.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -190,12 +187,11 @@ declare @llvm.riscv.vmfge.mask.nxv8f16( define @intrinsic_vmfge_mask_vv_nxv8f16_nxv8f16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfge_mask_vv_nxv8f16_nxv8f16: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e16, m2, ta, mu -; CHECK-NEXT: vmfle.vv v14, v10, v8 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmfle.vv v0, v10, v8 +; CHECK-NEXT: vmfle.vv v14, v12, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmfle.vv v8, v12, v10, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmfge.nxv8f16( @@ -242,12 +238,11 @@ declare @llvm.riscv.vmfge.mask.nxv16f16( define @intrinsic_vmfge_mask_vv_nxv16f16_nxv16f16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfge_mask_vv_nxv16f16_nxv16f16: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e16, m4, ta, mu -; CHECK-NEXT: vmfle.vv v20, v12, v8 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmfle.vv v0, v12, v8 +; CHECK-NEXT: vmfle.vv v20, v16, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmfle.vv v8, v16, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmfge.nxv16f16( @@ -294,10 +289,9 @@ declare @llvm.riscv.vmfge.mask.nxv1f32( define @intrinsic_vmfge_mask_vv_nxv1f32_nxv1f32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfge_mask_vv_nxv1f32_nxv1f32: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e32, mf2, ta, mu -; CHECK-NEXT: vmfle.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e32, mf2, ta, mu +; CHECK-NEXT: vmfle.vv v0, v9, v8 ; CHECK-NEXT: vmfle.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -346,10 +340,9 @@ declare @llvm.riscv.vmfge.mask.nxv2f32( define @intrinsic_vmfge_mask_vv_nxv2f32_nxv2f32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfge_mask_vv_nxv2f32_nxv2f32: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e32, m1, ta, mu -; CHECK-NEXT: vmfle.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e32, m1, ta, mu +; CHECK-NEXT: vmfle.vv v0, v9, v8 ; CHECK-NEXT: vmfle.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -398,12 +391,11 @@ declare @llvm.riscv.vmfge.mask.nxv4f32( define @intrinsic_vmfge_mask_vv_nxv4f32_nxv4f32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfge_mask_vv_nxv4f32_nxv4f32: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e32, m2, ta, mu -; CHECK-NEXT: vmfle.vv v14, v10, v8 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmfle.vv v0, v10, v8 +; CHECK-NEXT: vmfle.vv v14, v12, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmfle.vv v8, v12, v10, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmfge.nxv4f32( @@ -450,12 +442,11 @@ declare @llvm.riscv.vmfge.mask.nxv8f32( define @intrinsic_vmfge_mask_vv_nxv8f32_nxv8f32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfge_mask_vv_nxv8f32_nxv8f32: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e32, m4, ta, mu -; CHECK-NEXT: vmfle.vv v20, v12, v8 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmfle.vv v0, v12, v8 +; CHECK-NEXT: vmfle.vv v20, v16, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmfle.vv v8, v16, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmfge.nxv8f32( @@ -502,10 +493,9 @@ declare @llvm.riscv.vmfge.mask.nxv1f64( define @intrinsic_vmfge_mask_vv_nxv1f64_nxv1f64( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfge_mask_vv_nxv1f64_nxv1f64: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, mu -; CHECK-NEXT: vmfle.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, mu +; CHECK-NEXT: vmfle.vv v0, v9, v8 ; CHECK-NEXT: vmfle.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -554,12 +544,11 @@ declare @llvm.riscv.vmfge.mask.nxv2f64( define @intrinsic_vmfge_mask_vv_nxv2f64_nxv2f64( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfge_mask_vv_nxv2f64_nxv2f64: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e64, m2, ta, mu -; CHECK-NEXT: vmfle.vv v14, v10, v8 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmfle.vv v0, v10, v8 +; CHECK-NEXT: vmfle.vv v14, v12, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmfle.vv v8, v12, v10, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmfge.nxv2f64( @@ -606,12 +595,11 @@ declare @llvm.riscv.vmfge.mask.nxv4f64( define @intrinsic_vmfge_mask_vv_nxv4f64_nxv4f64( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfge_mask_vv_nxv4f64_nxv4f64: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e64, m4, ta, mu -; CHECK-NEXT: vmfle.vv v20, v12, v8 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmfle.vv v0, v12, v8 +; CHECK-NEXT: vmfle.vv v20, v16, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmfle.vv v8, v16, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmfge.nxv4f64( diff --git a/llvm/test/CodeGen/RISCV/rvv/vmfgt.ll b/llvm/test/CodeGen/RISCV/rvv/vmfgt.ll index 427f0eb28e7df5ed3d5e5ffcb997861e86f23723..f643a4036381c3b67e1aa44bc07324a25ec9dbad 100644 --- a/llvm/test/CodeGen/RISCV/rvv/vmfgt.ll +++ b/llvm/test/CodeGen/RISCV/rvv/vmfgt.ll @@ -34,10 +34,9 @@ declare @llvm.riscv.vmfgt.mask.nxv1f16( define @intrinsic_vmfgt_mask_vv_nxv1f16_nxv1f16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfgt_mask_vv_nxv1f16_nxv1f16: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e16, mf4, ta, mu -; CHECK-NEXT: vmflt.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e16, mf4, ta, mu +; CHECK-NEXT: vmflt.vv v0, v9, v8 ; CHECK-NEXT: vmflt.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -86,10 +85,9 @@ declare @llvm.riscv.vmfgt.mask.nxv2f16( define @intrinsic_vmfgt_mask_vv_nxv2f16_nxv2f16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfgt_mask_vv_nxv2f16_nxv2f16: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e16, mf2, ta, mu -; CHECK-NEXT: vmflt.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e16, mf2, ta, mu +; CHECK-NEXT: vmflt.vv v0, v9, v8 ; CHECK-NEXT: vmflt.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -138,10 +136,9 @@ declare @llvm.riscv.vmfgt.mask.nxv4f16( define @intrinsic_vmfgt_mask_vv_nxv4f16_nxv4f16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfgt_mask_vv_nxv4f16_nxv4f16: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e16, m1, ta, mu -; CHECK-NEXT: vmflt.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e16, m1, ta, mu +; CHECK-NEXT: vmflt.vv v0, v9, v8 ; CHECK-NEXT: vmflt.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -190,12 +187,11 @@ declare @llvm.riscv.vmfgt.mask.nxv8f16( define @intrinsic_vmfgt_mask_vv_nxv8f16_nxv8f16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfgt_mask_vv_nxv8f16_nxv8f16: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e16, m2, ta, mu -; CHECK-NEXT: vmflt.vv v14, v10, v8 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmflt.vv v0, v10, v8 +; CHECK-NEXT: vmflt.vv v14, v12, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmflt.vv v8, v12, v10, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmfgt.nxv8f16( @@ -242,12 +238,11 @@ declare @llvm.riscv.vmfgt.mask.nxv16f16( define @intrinsic_vmfgt_mask_vv_nxv16f16_nxv16f16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfgt_mask_vv_nxv16f16_nxv16f16: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e16, m4, ta, mu -; CHECK-NEXT: vmflt.vv v20, v12, v8 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmflt.vv v0, v12, v8 +; CHECK-NEXT: vmflt.vv v20, v16, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmflt.vv v8, v16, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmfgt.nxv16f16( @@ -294,10 +289,9 @@ declare @llvm.riscv.vmfgt.mask.nxv1f32( define @intrinsic_vmfgt_mask_vv_nxv1f32_nxv1f32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfgt_mask_vv_nxv1f32_nxv1f32: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e32, mf2, ta, mu -; CHECK-NEXT: vmflt.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e32, mf2, ta, mu +; CHECK-NEXT: vmflt.vv v0, v9, v8 ; CHECK-NEXT: vmflt.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -346,10 +340,9 @@ declare @llvm.riscv.vmfgt.mask.nxv2f32( define @intrinsic_vmfgt_mask_vv_nxv2f32_nxv2f32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfgt_mask_vv_nxv2f32_nxv2f32: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e32, m1, ta, mu -; CHECK-NEXT: vmflt.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e32, m1, ta, mu +; CHECK-NEXT: vmflt.vv v0, v9, v8 ; CHECK-NEXT: vmflt.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -398,12 +391,11 @@ declare @llvm.riscv.vmfgt.mask.nxv4f32( define @intrinsic_vmfgt_mask_vv_nxv4f32_nxv4f32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfgt_mask_vv_nxv4f32_nxv4f32: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e32, m2, ta, mu -; CHECK-NEXT: vmflt.vv v14, v10, v8 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmflt.vv v0, v10, v8 +; CHECK-NEXT: vmflt.vv v14, v12, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmflt.vv v8, v12, v10, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmfgt.nxv4f32( @@ -450,12 +442,11 @@ declare @llvm.riscv.vmfgt.mask.nxv8f32( define @intrinsic_vmfgt_mask_vv_nxv8f32_nxv8f32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfgt_mask_vv_nxv8f32_nxv8f32: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e32, m4, ta, mu -; CHECK-NEXT: vmflt.vv v20, v12, v8 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmflt.vv v0, v12, v8 +; CHECK-NEXT: vmflt.vv v20, v16, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmflt.vv v8, v16, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmfgt.nxv8f32( @@ -502,10 +493,9 @@ declare @llvm.riscv.vmfgt.mask.nxv1f64( define @intrinsic_vmfgt_mask_vv_nxv1f64_nxv1f64( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfgt_mask_vv_nxv1f64_nxv1f64: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, mu -; CHECK-NEXT: vmflt.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, mu +; CHECK-NEXT: vmflt.vv v0, v9, v8 ; CHECK-NEXT: vmflt.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -554,12 +544,11 @@ declare @llvm.riscv.vmfgt.mask.nxv2f64( define @intrinsic_vmfgt_mask_vv_nxv2f64_nxv2f64( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfgt_mask_vv_nxv2f64_nxv2f64: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e64, m2, ta, mu -; CHECK-NEXT: vmflt.vv v14, v10, v8 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmflt.vv v0, v10, v8 +; CHECK-NEXT: vmflt.vv v14, v12, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmflt.vv v8, v12, v10, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmfgt.nxv2f64( @@ -606,12 +595,11 @@ declare @llvm.riscv.vmfgt.mask.nxv4f64( define @intrinsic_vmfgt_mask_vv_nxv4f64_nxv4f64( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfgt_mask_vv_nxv4f64_nxv4f64: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e64, m4, ta, mu -; CHECK-NEXT: vmflt.vv v20, v12, v8 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmflt.vv v0, v12, v8 +; CHECK-NEXT: vmflt.vv v20, v16, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmflt.vv v8, v16, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmfgt.nxv4f64( diff --git a/llvm/test/CodeGen/RISCV/rvv/vmfle.ll b/llvm/test/CodeGen/RISCV/rvv/vmfle.ll index e5327632fc04f6bbbc436c2387dfcf0934233407..6c52364c1fbd56f7273f3d2682016537807b23ab 100644 --- a/llvm/test/CodeGen/RISCV/rvv/vmfle.ll +++ b/llvm/test/CodeGen/RISCV/rvv/vmfle.ll @@ -34,10 +34,9 @@ declare @llvm.riscv.vmfle.mask.nxv1f16( define @intrinsic_vmfle_mask_vv_nxv1f16_nxv1f16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfle_mask_vv_nxv1f16_nxv1f16: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e16, mf4, ta, mu -; CHECK-NEXT: vmfle.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e16, mf4, ta, mu +; CHECK-NEXT: vmfle.vv v0, v8, v9 ; CHECK-NEXT: vmfle.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -86,10 +85,9 @@ declare @llvm.riscv.vmfle.mask.nxv2f16( define @intrinsic_vmfle_mask_vv_nxv2f16_nxv2f16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfle_mask_vv_nxv2f16_nxv2f16: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e16, mf2, ta, mu -; CHECK-NEXT: vmfle.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e16, mf2, ta, mu +; CHECK-NEXT: vmfle.vv v0, v8, v9 ; CHECK-NEXT: vmfle.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -138,10 +136,9 @@ declare @llvm.riscv.vmfle.mask.nxv4f16( define @intrinsic_vmfle_mask_vv_nxv4f16_nxv4f16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfle_mask_vv_nxv4f16_nxv4f16: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e16, m1, ta, mu -; CHECK-NEXT: vmfle.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e16, m1, ta, mu +; CHECK-NEXT: vmfle.vv v0, v8, v9 ; CHECK-NEXT: vmfle.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -190,12 +187,11 @@ declare @llvm.riscv.vmfle.mask.nxv8f16( define @intrinsic_vmfle_mask_vv_nxv8f16_nxv8f16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfle_mask_vv_nxv8f16_nxv8f16: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e16, m2, ta, mu -; CHECK-NEXT: vmfle.vv v14, v8, v10 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmfle.vv v0, v8, v10 +; CHECK-NEXT: vmfle.vv v14, v10, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmfle.vv v8, v10, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmfle.nxv8f16( @@ -242,12 +238,11 @@ declare @llvm.riscv.vmfle.mask.nxv16f16( define @intrinsic_vmfle_mask_vv_nxv16f16_nxv16f16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfle_mask_vv_nxv16f16_nxv16f16: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e16, m4, ta, mu -; CHECK-NEXT: vmfle.vv v20, v8, v12 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmfle.vv v0, v8, v12 +; CHECK-NEXT: vmfle.vv v20, v12, v16, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmfle.vv v8, v12, v16, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmfle.nxv16f16( @@ -294,10 +289,9 @@ declare @llvm.riscv.vmfle.mask.nxv1f32( define @intrinsic_vmfle_mask_vv_nxv1f32_nxv1f32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfle_mask_vv_nxv1f32_nxv1f32: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e32, mf2, ta, mu -; CHECK-NEXT: vmfle.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e32, mf2, ta, mu +; CHECK-NEXT: vmfle.vv v0, v8, v9 ; CHECK-NEXT: vmfle.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -346,10 +340,9 @@ declare @llvm.riscv.vmfle.mask.nxv2f32( define @intrinsic_vmfle_mask_vv_nxv2f32_nxv2f32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfle_mask_vv_nxv2f32_nxv2f32: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e32, m1, ta, mu -; CHECK-NEXT: vmfle.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e32, m1, ta, mu +; CHECK-NEXT: vmfle.vv v0, v8, v9 ; CHECK-NEXT: vmfle.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -398,12 +391,11 @@ declare @llvm.riscv.vmfle.mask.nxv4f32( define @intrinsic_vmfle_mask_vv_nxv4f32_nxv4f32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfle_mask_vv_nxv4f32_nxv4f32: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e32, m2, ta, mu -; CHECK-NEXT: vmfle.vv v14, v8, v10 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmfle.vv v0, v8, v10 +; CHECK-NEXT: vmfle.vv v14, v10, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmfle.vv v8, v10, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmfle.nxv4f32( @@ -450,12 +442,11 @@ declare @llvm.riscv.vmfle.mask.nxv8f32( define @intrinsic_vmfle_mask_vv_nxv8f32_nxv8f32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfle_mask_vv_nxv8f32_nxv8f32: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e32, m4, ta, mu -; CHECK-NEXT: vmfle.vv v20, v8, v12 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmfle.vv v0, v8, v12 +; CHECK-NEXT: vmfle.vv v20, v12, v16, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmfle.vv v8, v12, v16, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmfle.nxv8f32( @@ -502,10 +493,9 @@ declare @llvm.riscv.vmfle.mask.nxv1f64( define @intrinsic_vmfle_mask_vv_nxv1f64_nxv1f64( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfle_mask_vv_nxv1f64_nxv1f64: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, mu -; CHECK-NEXT: vmfle.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, mu +; CHECK-NEXT: vmfle.vv v0, v8, v9 ; CHECK-NEXT: vmfle.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -554,12 +544,11 @@ declare @llvm.riscv.vmfle.mask.nxv2f64( define @intrinsic_vmfle_mask_vv_nxv2f64_nxv2f64( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfle_mask_vv_nxv2f64_nxv2f64: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e64, m2, ta, mu -; CHECK-NEXT: vmfle.vv v14, v8, v10 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmfle.vv v0, v8, v10 +; CHECK-NEXT: vmfle.vv v14, v10, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmfle.vv v8, v10, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmfle.nxv2f64( @@ -606,12 +595,11 @@ declare @llvm.riscv.vmfle.mask.nxv4f64( define @intrinsic_vmfle_mask_vv_nxv4f64_nxv4f64( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfle_mask_vv_nxv4f64_nxv4f64: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e64, m4, ta, mu -; CHECK-NEXT: vmfle.vv v20, v8, v12 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmfle.vv v0, v8, v12 +; CHECK-NEXT: vmfle.vv v20, v12, v16, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmfle.vv v8, v12, v16, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmfle.nxv4f64( diff --git a/llvm/test/CodeGen/RISCV/rvv/vmflt.ll b/llvm/test/CodeGen/RISCV/rvv/vmflt.ll index 64f257e355ceae91433e4b852d9c3a6b7e38c913..37a9c6b081a1dfc6ce0f10275b8c1391d80d1f34 100644 --- a/llvm/test/CodeGen/RISCV/rvv/vmflt.ll +++ b/llvm/test/CodeGen/RISCV/rvv/vmflt.ll @@ -34,10 +34,9 @@ declare @llvm.riscv.vmflt.mask.nxv1f16( define @intrinsic_vmflt_mask_vv_nxv1f16_nxv1f16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmflt_mask_vv_nxv1f16_nxv1f16: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e16, mf4, ta, mu -; CHECK-NEXT: vmflt.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e16, mf4, ta, mu +; CHECK-NEXT: vmflt.vv v0, v8, v9 ; CHECK-NEXT: vmflt.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -86,10 +85,9 @@ declare @llvm.riscv.vmflt.mask.nxv2f16( define @intrinsic_vmflt_mask_vv_nxv2f16_nxv2f16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmflt_mask_vv_nxv2f16_nxv2f16: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e16, mf2, ta, mu -; CHECK-NEXT: vmflt.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e16, mf2, ta, mu +; CHECK-NEXT: vmflt.vv v0, v8, v9 ; CHECK-NEXT: vmflt.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -138,10 +136,9 @@ declare @llvm.riscv.vmflt.mask.nxv4f16( define @intrinsic_vmflt_mask_vv_nxv4f16_nxv4f16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmflt_mask_vv_nxv4f16_nxv4f16: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e16, m1, ta, mu -; CHECK-NEXT: vmflt.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e16, m1, ta, mu +; CHECK-NEXT: vmflt.vv v0, v8, v9 ; CHECK-NEXT: vmflt.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -190,12 +187,11 @@ declare @llvm.riscv.vmflt.mask.nxv8f16( define @intrinsic_vmflt_mask_vv_nxv8f16_nxv8f16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmflt_mask_vv_nxv8f16_nxv8f16: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e16, m2, ta, mu -; CHECK-NEXT: vmflt.vv v14, v8, v10 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmflt.vv v0, v8, v10 +; CHECK-NEXT: vmflt.vv v14, v10, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmflt.vv v8, v10, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmflt.nxv8f16( @@ -242,12 +238,11 @@ declare @llvm.riscv.vmflt.mask.nxv16f16( define @intrinsic_vmflt_mask_vv_nxv16f16_nxv16f16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmflt_mask_vv_nxv16f16_nxv16f16: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e16, m4, ta, mu -; CHECK-NEXT: vmflt.vv v20, v8, v12 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmflt.vv v0, v8, v12 +; CHECK-NEXT: vmflt.vv v20, v12, v16, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmflt.vv v8, v12, v16, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmflt.nxv16f16( @@ -294,10 +289,9 @@ declare @llvm.riscv.vmflt.mask.nxv1f32( define @intrinsic_vmflt_mask_vv_nxv1f32_nxv1f32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmflt_mask_vv_nxv1f32_nxv1f32: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e32, mf2, ta, mu -; CHECK-NEXT: vmflt.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e32, mf2, ta, mu +; CHECK-NEXT: vmflt.vv v0, v8, v9 ; CHECK-NEXT: vmflt.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -346,10 +340,9 @@ declare @llvm.riscv.vmflt.mask.nxv2f32( define @intrinsic_vmflt_mask_vv_nxv2f32_nxv2f32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmflt_mask_vv_nxv2f32_nxv2f32: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e32, m1, ta, mu -; CHECK-NEXT: vmflt.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e32, m1, ta, mu +; CHECK-NEXT: vmflt.vv v0, v8, v9 ; CHECK-NEXT: vmflt.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -398,12 +391,11 @@ declare @llvm.riscv.vmflt.mask.nxv4f32( define @intrinsic_vmflt_mask_vv_nxv4f32_nxv4f32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmflt_mask_vv_nxv4f32_nxv4f32: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e32, m2, ta, mu -; CHECK-NEXT: vmflt.vv v14, v8, v10 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmflt.vv v0, v8, v10 +; CHECK-NEXT: vmflt.vv v14, v10, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmflt.vv v8, v10, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmflt.nxv4f32( @@ -450,12 +442,11 @@ declare @llvm.riscv.vmflt.mask.nxv8f32( define @intrinsic_vmflt_mask_vv_nxv8f32_nxv8f32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmflt_mask_vv_nxv8f32_nxv8f32: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e32, m4, ta, mu -; CHECK-NEXT: vmflt.vv v20, v8, v12 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmflt.vv v0, v8, v12 +; CHECK-NEXT: vmflt.vv v20, v12, v16, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmflt.vv v8, v12, v16, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmflt.nxv8f32( @@ -502,10 +493,9 @@ declare @llvm.riscv.vmflt.mask.nxv1f64( define @intrinsic_vmflt_mask_vv_nxv1f64_nxv1f64( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmflt_mask_vv_nxv1f64_nxv1f64: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, mu -; CHECK-NEXT: vmflt.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, mu +; CHECK-NEXT: vmflt.vv v0, v8, v9 ; CHECK-NEXT: vmflt.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -554,12 +544,11 @@ declare @llvm.riscv.vmflt.mask.nxv2f64( define @intrinsic_vmflt_mask_vv_nxv2f64_nxv2f64( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmflt_mask_vv_nxv2f64_nxv2f64: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e64, m2, ta, mu -; CHECK-NEXT: vmflt.vv v14, v8, v10 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmflt.vv v0, v8, v10 +; CHECK-NEXT: vmflt.vv v14, v10, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmflt.vv v8, v10, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmflt.nxv2f64( @@ -606,12 +595,11 @@ declare @llvm.riscv.vmflt.mask.nxv4f64( define @intrinsic_vmflt_mask_vv_nxv4f64_nxv4f64( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmflt_mask_vv_nxv4f64_nxv4f64: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e64, m4, ta, mu -; CHECK-NEXT: vmflt.vv v20, v8, v12 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmflt.vv v0, v8, v12 +; CHECK-NEXT: vmflt.vv v20, v12, v16, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmflt.vv v8, v12, v16, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmflt.nxv4f64( diff --git a/llvm/test/CodeGen/RISCV/rvv/vmfne.ll b/llvm/test/CodeGen/RISCV/rvv/vmfne.ll index 6f6a2a5e8783c6b6cf8546785358144116746e65..5defce42091e55a51ed3928bcd5b0e9a08e58149 100644 --- a/llvm/test/CodeGen/RISCV/rvv/vmfne.ll +++ b/llvm/test/CodeGen/RISCV/rvv/vmfne.ll @@ -34,10 +34,9 @@ declare @llvm.riscv.vmfne.mask.nxv1f16( define @intrinsic_vmfne_mask_vv_nxv1f16_nxv1f16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfne_mask_vv_nxv1f16_nxv1f16: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e16, mf4, ta, mu -; CHECK-NEXT: vmfne.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e16, mf4, ta, mu +; CHECK-NEXT: vmfne.vv v0, v8, v9 ; CHECK-NEXT: vmfne.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -86,10 +85,9 @@ declare @llvm.riscv.vmfne.mask.nxv2f16( define @intrinsic_vmfne_mask_vv_nxv2f16_nxv2f16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfne_mask_vv_nxv2f16_nxv2f16: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e16, mf2, ta, mu -; CHECK-NEXT: vmfne.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e16, mf2, ta, mu +; CHECK-NEXT: vmfne.vv v0, v8, v9 ; CHECK-NEXT: vmfne.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -138,10 +136,9 @@ declare @llvm.riscv.vmfne.mask.nxv4f16( define @intrinsic_vmfne_mask_vv_nxv4f16_nxv4f16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfne_mask_vv_nxv4f16_nxv4f16: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e16, m1, ta, mu -; CHECK-NEXT: vmfne.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e16, m1, ta, mu +; CHECK-NEXT: vmfne.vv v0, v8, v9 ; CHECK-NEXT: vmfne.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -190,12 +187,11 @@ declare @llvm.riscv.vmfne.mask.nxv8f16( define @intrinsic_vmfne_mask_vv_nxv8f16_nxv8f16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfne_mask_vv_nxv8f16_nxv8f16: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e16, m2, ta, mu -; CHECK-NEXT: vmfne.vv v14, v8, v10 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmfne.vv v0, v8, v10 +; CHECK-NEXT: vmfne.vv v14, v10, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmfne.vv v8, v10, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmfne.nxv8f16( @@ -242,12 +238,11 @@ declare @llvm.riscv.vmfne.mask.nxv16f16( define @intrinsic_vmfne_mask_vv_nxv16f16_nxv16f16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfne_mask_vv_nxv16f16_nxv16f16: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e16, m4, ta, mu -; CHECK-NEXT: vmfne.vv v20, v8, v12 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmfne.vv v0, v8, v12 +; CHECK-NEXT: vmfne.vv v20, v12, v16, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmfne.vv v8, v12, v16, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmfne.nxv16f16( @@ -294,10 +289,9 @@ declare @llvm.riscv.vmfne.mask.nxv1f32( define @intrinsic_vmfne_mask_vv_nxv1f32_nxv1f32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfne_mask_vv_nxv1f32_nxv1f32: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e32, mf2, ta, mu -; CHECK-NEXT: vmfne.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e32, mf2, ta, mu +; CHECK-NEXT: vmfne.vv v0, v8, v9 ; CHECK-NEXT: vmfne.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -346,10 +340,9 @@ declare @llvm.riscv.vmfne.mask.nxv2f32( define @intrinsic_vmfne_mask_vv_nxv2f32_nxv2f32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfne_mask_vv_nxv2f32_nxv2f32: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e32, m1, ta, mu -; CHECK-NEXT: vmfne.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e32, m1, ta, mu +; CHECK-NEXT: vmfne.vv v0, v8, v9 ; CHECK-NEXT: vmfne.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -398,12 +391,11 @@ declare @llvm.riscv.vmfne.mask.nxv4f32( define @intrinsic_vmfne_mask_vv_nxv4f32_nxv4f32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfne_mask_vv_nxv4f32_nxv4f32: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e32, m2, ta, mu -; CHECK-NEXT: vmfne.vv v14, v8, v10 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmfne.vv v0, v8, v10 +; CHECK-NEXT: vmfne.vv v14, v10, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmfne.vv v8, v10, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmfne.nxv4f32( @@ -450,12 +442,11 @@ declare @llvm.riscv.vmfne.mask.nxv8f32( define @intrinsic_vmfne_mask_vv_nxv8f32_nxv8f32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfne_mask_vv_nxv8f32_nxv8f32: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e32, m4, ta, mu -; CHECK-NEXT: vmfne.vv v20, v8, v12 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmfne.vv v0, v8, v12 +; CHECK-NEXT: vmfne.vv v20, v12, v16, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmfne.vv v8, v12, v16, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmfne.nxv8f32( @@ -502,10 +493,9 @@ declare @llvm.riscv.vmfne.mask.nxv1f64( define @intrinsic_vmfne_mask_vv_nxv1f64_nxv1f64( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfne_mask_vv_nxv1f64_nxv1f64: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, mu -; CHECK-NEXT: vmfne.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, mu +; CHECK-NEXT: vmfne.vv v0, v8, v9 ; CHECK-NEXT: vmfne.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -554,12 +544,11 @@ declare @llvm.riscv.vmfne.mask.nxv2f64( define @intrinsic_vmfne_mask_vv_nxv2f64_nxv2f64( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfne_mask_vv_nxv2f64_nxv2f64: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e64, m2, ta, mu -; CHECK-NEXT: vmfne.vv v14, v8, v10 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmfne.vv v0, v8, v10 +; CHECK-NEXT: vmfne.vv v14, v10, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmfne.vv v8, v10, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmfne.nxv2f64( @@ -606,12 +595,11 @@ declare @llvm.riscv.vmfne.mask.nxv4f64( define @intrinsic_vmfne_mask_vv_nxv4f64_nxv4f64( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmfne_mask_vv_nxv4f64_nxv4f64: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e64, m4, ta, mu -; CHECK-NEXT: vmfne.vv v20, v8, v12 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmfne.vv v0, v8, v12 +; CHECK-NEXT: vmfne.vv v20, v12, v16, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmfne.vv v8, v12, v16, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmfne.nxv4f64( diff --git a/llvm/test/CodeGen/RISCV/rvv/vmseq.ll b/llvm/test/CodeGen/RISCV/rvv/vmseq.ll index da1c751b566304bfda51494c0ea6b7aa10daa634..cc6c1f585bb7d8f87d00b6c06791094a61fada1e 100644 --- a/llvm/test/CodeGen/RISCV/rvv/vmseq.ll +++ b/llvm/test/CodeGen/RISCV/rvv/vmseq.ll @@ -34,10 +34,9 @@ declare @llvm.riscv.vmseq.mask.nxv1i8( define @intrinsic_vmseq_mask_vv_nxv1i8_nxv1i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmseq_mask_vv_nxv1i8_nxv1i8: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e8, mf8, ta, mu -; CHECK-NEXT: vmseq.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e8, mf8, ta, mu +; CHECK-NEXT: vmseq.vv v0, v8, v9 ; CHECK-NEXT: vmseq.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -86,10 +85,9 @@ declare @llvm.riscv.vmseq.mask.nxv2i8( define @intrinsic_vmseq_mask_vv_nxv2i8_nxv2i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmseq_mask_vv_nxv2i8_nxv2i8: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e8, mf4, ta, mu -; CHECK-NEXT: vmseq.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e8, mf4, ta, mu +; CHECK-NEXT: vmseq.vv v0, v8, v9 ; CHECK-NEXT: vmseq.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -138,10 +136,9 @@ declare @llvm.riscv.vmseq.mask.nxv4i8( define @intrinsic_vmseq_mask_vv_nxv4i8_nxv4i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmseq_mask_vv_nxv4i8_nxv4i8: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e8, mf2, ta, mu -; CHECK-NEXT: vmseq.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e8, mf2, ta, mu +; CHECK-NEXT: vmseq.vv v0, v8, v9 ; CHECK-NEXT: vmseq.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -190,10 +187,9 @@ declare @llvm.riscv.vmseq.mask.nxv8i8( define @intrinsic_vmseq_mask_vv_nxv8i8_nxv8i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmseq_mask_vv_nxv8i8_nxv8i8: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e8, m1, ta, mu -; CHECK-NEXT: vmseq.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e8, m1, ta, mu +; CHECK-NEXT: vmseq.vv v0, v8, v9 ; CHECK-NEXT: vmseq.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -242,12 +238,11 @@ declare @llvm.riscv.vmseq.mask.nxv16i8( define @intrinsic_vmseq_mask_vv_nxv16i8_nxv16i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmseq_mask_vv_nxv16i8_nxv16i8: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e8, m2, ta, mu -; CHECK-NEXT: vmseq.vv v14, v8, v10 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmseq.vv v0, v8, v10 +; CHECK-NEXT: vmseq.vv v14, v10, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmseq.vv v8, v10, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmseq.nxv16i8( @@ -294,12 +289,11 @@ declare @llvm.riscv.vmseq.mask.nxv32i8( define @intrinsic_vmseq_mask_vv_nxv32i8_nxv32i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmseq_mask_vv_nxv32i8_nxv32i8: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e8, m4, ta, mu -; CHECK-NEXT: vmseq.vv v20, v8, v12 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmseq.vv v0, v8, v12 +; CHECK-NEXT: vmseq.vv v20, v12, v16, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmseq.vv v8, v12, v16, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmseq.nxv32i8( @@ -346,10 +340,9 @@ declare @llvm.riscv.vmseq.mask.nxv1i16( define @intrinsic_vmseq_mask_vv_nxv1i16_nxv1i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmseq_mask_vv_nxv1i16_nxv1i16: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e16, mf4, ta, mu -; CHECK-NEXT: vmseq.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e16, mf4, ta, mu +; CHECK-NEXT: vmseq.vv v0, v8, v9 ; CHECK-NEXT: vmseq.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -398,10 +391,9 @@ declare @llvm.riscv.vmseq.mask.nxv2i16( define @intrinsic_vmseq_mask_vv_nxv2i16_nxv2i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmseq_mask_vv_nxv2i16_nxv2i16: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e16, mf2, ta, mu -; CHECK-NEXT: vmseq.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e16, mf2, ta, mu +; CHECK-NEXT: vmseq.vv v0, v8, v9 ; CHECK-NEXT: vmseq.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -450,10 +442,9 @@ declare @llvm.riscv.vmseq.mask.nxv4i16( define @intrinsic_vmseq_mask_vv_nxv4i16_nxv4i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmseq_mask_vv_nxv4i16_nxv4i16: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e16, m1, ta, mu -; CHECK-NEXT: vmseq.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e16, m1, ta, mu +; CHECK-NEXT: vmseq.vv v0, v8, v9 ; CHECK-NEXT: vmseq.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -502,12 +493,11 @@ declare @llvm.riscv.vmseq.mask.nxv8i16( define @intrinsic_vmseq_mask_vv_nxv8i16_nxv8i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmseq_mask_vv_nxv8i16_nxv8i16: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e16, m2, ta, mu -; CHECK-NEXT: vmseq.vv v14, v8, v10 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmseq.vv v0, v8, v10 +; CHECK-NEXT: vmseq.vv v14, v10, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmseq.vv v8, v10, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmseq.nxv8i16( @@ -554,12 +544,11 @@ declare @llvm.riscv.vmseq.mask.nxv16i16( define @intrinsic_vmseq_mask_vv_nxv16i16_nxv16i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmseq_mask_vv_nxv16i16_nxv16i16: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e16, m4, ta, mu -; CHECK-NEXT: vmseq.vv v20, v8, v12 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmseq.vv v0, v8, v12 +; CHECK-NEXT: vmseq.vv v20, v12, v16, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmseq.vv v8, v12, v16, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmseq.nxv16i16( @@ -606,10 +595,9 @@ declare @llvm.riscv.vmseq.mask.nxv1i32( define @intrinsic_vmseq_mask_vv_nxv1i32_nxv1i32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmseq_mask_vv_nxv1i32_nxv1i32: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e32, mf2, ta, mu -; CHECK-NEXT: vmseq.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e32, mf2, ta, mu +; CHECK-NEXT: vmseq.vv v0, v8, v9 ; CHECK-NEXT: vmseq.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -658,10 +646,9 @@ declare @llvm.riscv.vmseq.mask.nxv2i32( define @intrinsic_vmseq_mask_vv_nxv2i32_nxv2i32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmseq_mask_vv_nxv2i32_nxv2i32: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e32, m1, ta, mu -; CHECK-NEXT: vmseq.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e32, m1, ta, mu +; CHECK-NEXT: vmseq.vv v0, v8, v9 ; CHECK-NEXT: vmseq.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -710,12 +697,11 @@ declare @llvm.riscv.vmseq.mask.nxv4i32( define @intrinsic_vmseq_mask_vv_nxv4i32_nxv4i32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmseq_mask_vv_nxv4i32_nxv4i32: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e32, m2, ta, mu -; CHECK-NEXT: vmseq.vv v14, v8, v10 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmseq.vv v0, v8, v10 +; CHECK-NEXT: vmseq.vv v14, v10, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmseq.vv v8, v10, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmseq.nxv4i32( @@ -762,12 +748,11 @@ declare @llvm.riscv.vmseq.mask.nxv8i32( define @intrinsic_vmseq_mask_vv_nxv8i32_nxv8i32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmseq_mask_vv_nxv8i32_nxv8i32: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e32, m4, ta, mu -; CHECK-NEXT: vmseq.vv v20, v8, v12 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmseq.vv v0, v8, v12 +; CHECK-NEXT: vmseq.vv v20, v12, v16, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmseq.vv v8, v12, v16, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmseq.nxv8i32( @@ -814,10 +799,9 @@ declare @llvm.riscv.vmseq.mask.nxv1i64( define @intrinsic_vmseq_mask_vv_nxv1i64_nxv1i64( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmseq_mask_vv_nxv1i64_nxv1i64: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, mu -; CHECK-NEXT: vmseq.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, mu +; CHECK-NEXT: vmseq.vv v0, v8, v9 ; CHECK-NEXT: vmseq.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -866,12 +850,11 @@ declare @llvm.riscv.vmseq.mask.nxv2i64( define @intrinsic_vmseq_mask_vv_nxv2i64_nxv2i64( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmseq_mask_vv_nxv2i64_nxv2i64: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e64, m2, ta, mu -; CHECK-NEXT: vmseq.vv v14, v8, v10 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmseq.vv v0, v8, v10 +; CHECK-NEXT: vmseq.vv v14, v10, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmseq.vv v8, v10, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmseq.nxv2i64( @@ -918,12 +901,11 @@ declare @llvm.riscv.vmseq.mask.nxv4i64( define @intrinsic_vmseq_mask_vv_nxv4i64_nxv4i64( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmseq_mask_vv_nxv4i64_nxv4i64: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e64, m4, ta, mu -; CHECK-NEXT: vmseq.vv v20, v8, v12 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmseq.vv v0, v8, v12 +; CHECK-NEXT: vmseq.vv v20, v12, v16, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmseq.vv v8, v12, v16, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmseq.nxv4i64( diff --git a/llvm/test/CodeGen/RISCV/rvv/vmsge.ll b/llvm/test/CodeGen/RISCV/rvv/vmsge.ll index 502fb9b24148f7123e8729808394049b0b8ea248..c8f9b60a3f2da6c6d8979c1b29d11b0526ad122e 100644 --- a/llvm/test/CodeGen/RISCV/rvv/vmsge.ll +++ b/llvm/test/CodeGen/RISCV/rvv/vmsge.ll @@ -34,10 +34,9 @@ declare @llvm.riscv.vmsge.mask.nxv1i8( define @intrinsic_vmsge_mask_vv_nxv1i8_nxv1i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsge_mask_vv_nxv1i8_nxv1i8: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e8, mf8, ta, mu -; CHECK-NEXT: vmsle.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e8, mf8, ta, mu +; CHECK-NEXT: vmsle.vv v0, v9, v8 ; CHECK-NEXT: vmsle.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -86,10 +85,9 @@ declare @llvm.riscv.vmsge.mask.nxv2i8( define @intrinsic_vmsge_mask_vv_nxv2i8_nxv2i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsge_mask_vv_nxv2i8_nxv2i8: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e8, mf4, ta, mu -; CHECK-NEXT: vmsle.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e8, mf4, ta, mu +; CHECK-NEXT: vmsle.vv v0, v9, v8 ; CHECK-NEXT: vmsle.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -138,10 +136,9 @@ declare @llvm.riscv.vmsge.mask.nxv4i8( define @intrinsic_vmsge_mask_vv_nxv4i8_nxv4i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsge_mask_vv_nxv4i8_nxv4i8: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e8, mf2, ta, mu -; CHECK-NEXT: vmsle.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e8, mf2, ta, mu +; CHECK-NEXT: vmsle.vv v0, v9, v8 ; CHECK-NEXT: vmsle.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -190,10 +187,9 @@ declare @llvm.riscv.vmsge.mask.nxv8i8( define @intrinsic_vmsge_mask_vv_nxv8i8_nxv8i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsge_mask_vv_nxv8i8_nxv8i8: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e8, m1, ta, mu -; CHECK-NEXT: vmsle.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e8, m1, ta, mu +; CHECK-NEXT: vmsle.vv v0, v9, v8 ; CHECK-NEXT: vmsle.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -242,12 +238,11 @@ declare @llvm.riscv.vmsge.mask.nxv16i8( define @intrinsic_vmsge_mask_vv_nxv16i8_nxv16i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsge_mask_vv_nxv16i8_nxv16i8: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e8, m2, ta, mu -; CHECK-NEXT: vmsle.vv v14, v10, v8 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsle.vv v0, v10, v8 +; CHECK-NEXT: vmsle.vv v14, v12, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmsle.vv v8, v12, v10, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsge.nxv16i8( @@ -294,12 +289,11 @@ declare @llvm.riscv.vmsge.mask.nxv32i8( define @intrinsic_vmsge_mask_vv_nxv32i8_nxv32i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsge_mask_vv_nxv32i8_nxv32i8: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e8, m4, ta, mu -; CHECK-NEXT: vmsle.vv v20, v12, v8 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsle.vv v0, v12, v8 +; CHECK-NEXT: vmsle.vv v20, v16, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmsle.vv v8, v16, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsge.nxv32i8( @@ -346,10 +340,9 @@ declare @llvm.riscv.vmsge.mask.nxv1i16( define @intrinsic_vmsge_mask_vv_nxv1i16_nxv1i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsge_mask_vv_nxv1i16_nxv1i16: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e16, mf4, ta, mu -; CHECK-NEXT: vmsle.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e16, mf4, ta, mu +; CHECK-NEXT: vmsle.vv v0, v9, v8 ; CHECK-NEXT: vmsle.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -398,10 +391,9 @@ declare @llvm.riscv.vmsge.mask.nxv2i16( define @intrinsic_vmsge_mask_vv_nxv2i16_nxv2i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsge_mask_vv_nxv2i16_nxv2i16: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e16, mf2, ta, mu -; CHECK-NEXT: vmsle.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e16, mf2, ta, mu +; CHECK-NEXT: vmsle.vv v0, v9, v8 ; CHECK-NEXT: vmsle.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -450,10 +442,9 @@ declare @llvm.riscv.vmsge.mask.nxv4i16( define @intrinsic_vmsge_mask_vv_nxv4i16_nxv4i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsge_mask_vv_nxv4i16_nxv4i16: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e16, m1, ta, mu -; CHECK-NEXT: vmsle.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e16, m1, ta, mu +; CHECK-NEXT: vmsle.vv v0, v9, v8 ; CHECK-NEXT: vmsle.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -502,12 +493,11 @@ declare @llvm.riscv.vmsge.mask.nxv8i16( define @intrinsic_vmsge_mask_vv_nxv8i16_nxv8i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsge_mask_vv_nxv8i16_nxv8i16: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e16, m2, ta, mu -; CHECK-NEXT: vmsle.vv v14, v10, v8 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsle.vv v0, v10, v8 +; CHECK-NEXT: vmsle.vv v14, v12, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmsle.vv v8, v12, v10, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsge.nxv8i16( @@ -554,12 +544,11 @@ declare @llvm.riscv.vmsge.mask.nxv16i16( define @intrinsic_vmsge_mask_vv_nxv16i16_nxv16i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsge_mask_vv_nxv16i16_nxv16i16: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e16, m4, ta, mu -; CHECK-NEXT: vmsle.vv v20, v12, v8 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsle.vv v0, v12, v8 +; CHECK-NEXT: vmsle.vv v20, v16, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmsle.vv v8, v16, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsge.nxv16i16( @@ -606,10 +595,9 @@ declare @llvm.riscv.vmsge.mask.nxv1i32( define @intrinsic_vmsge_mask_vv_nxv1i32_nxv1i32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsge_mask_vv_nxv1i32_nxv1i32: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e32, mf2, ta, mu -; CHECK-NEXT: vmsle.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e32, mf2, ta, mu +; CHECK-NEXT: vmsle.vv v0, v9, v8 ; CHECK-NEXT: vmsle.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -658,10 +646,9 @@ declare @llvm.riscv.vmsge.mask.nxv2i32( define @intrinsic_vmsge_mask_vv_nxv2i32_nxv2i32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsge_mask_vv_nxv2i32_nxv2i32: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e32, m1, ta, mu -; CHECK-NEXT: vmsle.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e32, m1, ta, mu +; CHECK-NEXT: vmsle.vv v0, v9, v8 ; CHECK-NEXT: vmsle.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -710,12 +697,11 @@ declare @llvm.riscv.vmsge.mask.nxv4i32( define @intrinsic_vmsge_mask_vv_nxv4i32_nxv4i32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsge_mask_vv_nxv4i32_nxv4i32: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e32, m2, ta, mu -; CHECK-NEXT: vmsle.vv v14, v10, v8 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsle.vv v0, v10, v8 +; CHECK-NEXT: vmsle.vv v14, v12, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmsle.vv v8, v12, v10, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsge.nxv4i32( @@ -762,12 +748,11 @@ declare @llvm.riscv.vmsge.mask.nxv8i32( define @intrinsic_vmsge_mask_vv_nxv8i32_nxv8i32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsge_mask_vv_nxv8i32_nxv8i32: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e32, m4, ta, mu -; CHECK-NEXT: vmsle.vv v20, v12, v8 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsle.vv v0, v12, v8 +; CHECK-NEXT: vmsle.vv v20, v16, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmsle.vv v8, v16, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsge.nxv8i32( @@ -814,10 +799,9 @@ declare @llvm.riscv.vmsge.mask.nxv1i64( define @intrinsic_vmsge_mask_vv_nxv1i64_nxv1i64( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsge_mask_vv_nxv1i64_nxv1i64: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, mu -; CHECK-NEXT: vmsle.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, mu +; CHECK-NEXT: vmsle.vv v0, v9, v8 ; CHECK-NEXT: vmsle.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -866,12 +850,11 @@ declare @llvm.riscv.vmsge.mask.nxv2i64( define @intrinsic_vmsge_mask_vv_nxv2i64_nxv2i64( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsge_mask_vv_nxv2i64_nxv2i64: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e64, m2, ta, mu -; CHECK-NEXT: vmsle.vv v14, v10, v8 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsle.vv v0, v10, v8 +; CHECK-NEXT: vmsle.vv v14, v12, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmsle.vv v8, v12, v10, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsge.nxv2i64( @@ -918,12 +901,11 @@ declare @llvm.riscv.vmsge.mask.nxv4i64( define @intrinsic_vmsge_mask_vv_nxv4i64_nxv4i64( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsge_mask_vv_nxv4i64_nxv4i64: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e64, m4, ta, mu -; CHECK-NEXT: vmsle.vv v20, v12, v8 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsle.vv v0, v12, v8 +; CHECK-NEXT: vmsle.vv v20, v16, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmsle.vv v8, v16, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsge.nxv4i64( diff --git a/llvm/test/CodeGen/RISCV/rvv/vmsgeu.ll b/llvm/test/CodeGen/RISCV/rvv/vmsgeu.ll index 9410a99d81423f5f63821e9d2b620e74c8f29c6f..b6c6d9e90f6109b42fb82c99091618a3b54c2bca 100644 --- a/llvm/test/CodeGen/RISCV/rvv/vmsgeu.ll +++ b/llvm/test/CodeGen/RISCV/rvv/vmsgeu.ll @@ -34,10 +34,9 @@ declare @llvm.riscv.vmsgeu.mask.nxv1i8( define @intrinsic_vmsgeu_mask_vv_nxv1i8_nxv1i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgeu_mask_vv_nxv1i8_nxv1i8: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e8, mf8, ta, mu -; CHECK-NEXT: vmsleu.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e8, mf8, ta, mu +; CHECK-NEXT: vmsleu.vv v0, v9, v8 ; CHECK-NEXT: vmsleu.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -86,10 +85,9 @@ declare @llvm.riscv.vmsgeu.mask.nxv2i8( define @intrinsic_vmsgeu_mask_vv_nxv2i8_nxv2i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgeu_mask_vv_nxv2i8_nxv2i8: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e8, mf4, ta, mu -; CHECK-NEXT: vmsleu.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e8, mf4, ta, mu +; CHECK-NEXT: vmsleu.vv v0, v9, v8 ; CHECK-NEXT: vmsleu.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -138,10 +136,9 @@ declare @llvm.riscv.vmsgeu.mask.nxv4i8( define @intrinsic_vmsgeu_mask_vv_nxv4i8_nxv4i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgeu_mask_vv_nxv4i8_nxv4i8: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e8, mf2, ta, mu -; CHECK-NEXT: vmsleu.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e8, mf2, ta, mu +; CHECK-NEXT: vmsleu.vv v0, v9, v8 ; CHECK-NEXT: vmsleu.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -190,10 +187,9 @@ declare @llvm.riscv.vmsgeu.mask.nxv8i8( define @intrinsic_vmsgeu_mask_vv_nxv8i8_nxv8i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgeu_mask_vv_nxv8i8_nxv8i8: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e8, m1, ta, mu -; CHECK-NEXT: vmsleu.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e8, m1, ta, mu +; CHECK-NEXT: vmsleu.vv v0, v9, v8 ; CHECK-NEXT: vmsleu.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -242,12 +238,11 @@ declare @llvm.riscv.vmsgeu.mask.nxv16i8( define @intrinsic_vmsgeu_mask_vv_nxv16i8_nxv16i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgeu_mask_vv_nxv16i8_nxv16i8: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e8, m2, ta, mu -; CHECK-NEXT: vmsleu.vv v14, v10, v8 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsleu.vv v0, v10, v8 +; CHECK-NEXT: vmsleu.vv v14, v12, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmsleu.vv v8, v12, v10, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsgeu.nxv16i8( @@ -294,12 +289,11 @@ declare @llvm.riscv.vmsgeu.mask.nxv32i8( define @intrinsic_vmsgeu_mask_vv_nxv32i8_nxv32i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgeu_mask_vv_nxv32i8_nxv32i8: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e8, m4, ta, mu -; CHECK-NEXT: vmsleu.vv v20, v12, v8 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsleu.vv v0, v12, v8 +; CHECK-NEXT: vmsleu.vv v20, v16, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmsleu.vv v8, v16, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsgeu.nxv32i8( @@ -346,10 +340,9 @@ declare @llvm.riscv.vmsgeu.mask.nxv1i16( define @intrinsic_vmsgeu_mask_vv_nxv1i16_nxv1i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgeu_mask_vv_nxv1i16_nxv1i16: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e16, mf4, ta, mu -; CHECK-NEXT: vmsleu.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e16, mf4, ta, mu +; CHECK-NEXT: vmsleu.vv v0, v9, v8 ; CHECK-NEXT: vmsleu.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -398,10 +391,9 @@ declare @llvm.riscv.vmsgeu.mask.nxv2i16( define @intrinsic_vmsgeu_mask_vv_nxv2i16_nxv2i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgeu_mask_vv_nxv2i16_nxv2i16: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e16, mf2, ta, mu -; CHECK-NEXT: vmsleu.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e16, mf2, ta, mu +; CHECK-NEXT: vmsleu.vv v0, v9, v8 ; CHECK-NEXT: vmsleu.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -450,10 +442,9 @@ declare @llvm.riscv.vmsgeu.mask.nxv4i16( define @intrinsic_vmsgeu_mask_vv_nxv4i16_nxv4i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgeu_mask_vv_nxv4i16_nxv4i16: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e16, m1, ta, mu -; CHECK-NEXT: vmsleu.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e16, m1, ta, mu +; CHECK-NEXT: vmsleu.vv v0, v9, v8 ; CHECK-NEXT: vmsleu.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -502,12 +493,11 @@ declare @llvm.riscv.vmsgeu.mask.nxv8i16( define @intrinsic_vmsgeu_mask_vv_nxv8i16_nxv8i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgeu_mask_vv_nxv8i16_nxv8i16: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e16, m2, ta, mu -; CHECK-NEXT: vmsleu.vv v14, v10, v8 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsleu.vv v0, v10, v8 +; CHECK-NEXT: vmsleu.vv v14, v12, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmsleu.vv v8, v12, v10, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsgeu.nxv8i16( @@ -554,12 +544,11 @@ declare @llvm.riscv.vmsgeu.mask.nxv16i16( define @intrinsic_vmsgeu_mask_vv_nxv16i16_nxv16i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgeu_mask_vv_nxv16i16_nxv16i16: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e16, m4, ta, mu -; CHECK-NEXT: vmsleu.vv v20, v12, v8 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsleu.vv v0, v12, v8 +; CHECK-NEXT: vmsleu.vv v20, v16, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmsleu.vv v8, v16, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsgeu.nxv16i16( @@ -606,10 +595,9 @@ declare @llvm.riscv.vmsgeu.mask.nxv1i32( define @intrinsic_vmsgeu_mask_vv_nxv1i32_nxv1i32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgeu_mask_vv_nxv1i32_nxv1i32: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e32, mf2, ta, mu -; CHECK-NEXT: vmsleu.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e32, mf2, ta, mu +; CHECK-NEXT: vmsleu.vv v0, v9, v8 ; CHECK-NEXT: vmsleu.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -658,10 +646,9 @@ declare @llvm.riscv.vmsgeu.mask.nxv2i32( define @intrinsic_vmsgeu_mask_vv_nxv2i32_nxv2i32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgeu_mask_vv_nxv2i32_nxv2i32: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e32, m1, ta, mu -; CHECK-NEXT: vmsleu.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e32, m1, ta, mu +; CHECK-NEXT: vmsleu.vv v0, v9, v8 ; CHECK-NEXT: vmsleu.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -710,12 +697,11 @@ declare @llvm.riscv.vmsgeu.mask.nxv4i32( define @intrinsic_vmsgeu_mask_vv_nxv4i32_nxv4i32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgeu_mask_vv_nxv4i32_nxv4i32: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e32, m2, ta, mu -; CHECK-NEXT: vmsleu.vv v14, v10, v8 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsleu.vv v0, v10, v8 +; CHECK-NEXT: vmsleu.vv v14, v12, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmsleu.vv v8, v12, v10, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsgeu.nxv4i32( @@ -762,12 +748,11 @@ declare @llvm.riscv.vmsgeu.mask.nxv8i32( define @intrinsic_vmsgeu_mask_vv_nxv8i32_nxv8i32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgeu_mask_vv_nxv8i32_nxv8i32: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e32, m4, ta, mu -; CHECK-NEXT: vmsleu.vv v20, v12, v8 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsleu.vv v0, v12, v8 +; CHECK-NEXT: vmsleu.vv v20, v16, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmsleu.vv v8, v16, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsgeu.nxv8i32( @@ -814,10 +799,9 @@ declare @llvm.riscv.vmsgeu.mask.nxv1i64( define @intrinsic_vmsgeu_mask_vv_nxv1i64_nxv1i64( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgeu_mask_vv_nxv1i64_nxv1i64: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, mu -; CHECK-NEXT: vmsleu.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, mu +; CHECK-NEXT: vmsleu.vv v0, v9, v8 ; CHECK-NEXT: vmsleu.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -866,12 +850,11 @@ declare @llvm.riscv.vmsgeu.mask.nxv2i64( define @intrinsic_vmsgeu_mask_vv_nxv2i64_nxv2i64( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgeu_mask_vv_nxv2i64_nxv2i64: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e64, m2, ta, mu -; CHECK-NEXT: vmsleu.vv v14, v10, v8 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsleu.vv v0, v10, v8 +; CHECK-NEXT: vmsleu.vv v14, v12, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmsleu.vv v8, v12, v10, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsgeu.nxv2i64( @@ -918,12 +901,11 @@ declare @llvm.riscv.vmsgeu.mask.nxv4i64( define @intrinsic_vmsgeu_mask_vv_nxv4i64_nxv4i64( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgeu_mask_vv_nxv4i64_nxv4i64: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e64, m4, ta, mu -; CHECK-NEXT: vmsleu.vv v20, v12, v8 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsleu.vv v0, v12, v8 +; CHECK-NEXT: vmsleu.vv v20, v16, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmsleu.vv v8, v16, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsgeu.nxv4i64( diff --git a/llvm/test/CodeGen/RISCV/rvv/vmsgt.ll b/llvm/test/CodeGen/RISCV/rvv/vmsgt.ll index b7a676e7f2dd37c1cf260b5beb4521748ac16623..dfd7096a65ebb98a5a77c7ac8c48318edf013030 100644 --- a/llvm/test/CodeGen/RISCV/rvv/vmsgt.ll +++ b/llvm/test/CodeGen/RISCV/rvv/vmsgt.ll @@ -34,10 +34,9 @@ declare @llvm.riscv.vmsgt.mask.nxv1i8( define @intrinsic_vmsgt_mask_vv_nxv1i8_nxv1i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgt_mask_vv_nxv1i8_nxv1i8: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e8, mf8, ta, mu -; CHECK-NEXT: vmslt.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e8, mf8, ta, mu +; CHECK-NEXT: vmslt.vv v0, v9, v8 ; CHECK-NEXT: vmslt.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -86,10 +85,9 @@ declare @llvm.riscv.vmsgt.mask.nxv2i8( define @intrinsic_vmsgt_mask_vv_nxv2i8_nxv2i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgt_mask_vv_nxv2i8_nxv2i8: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e8, mf4, ta, mu -; CHECK-NEXT: vmslt.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e8, mf4, ta, mu +; CHECK-NEXT: vmslt.vv v0, v9, v8 ; CHECK-NEXT: vmslt.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -138,10 +136,9 @@ declare @llvm.riscv.vmsgt.mask.nxv4i8( define @intrinsic_vmsgt_mask_vv_nxv4i8_nxv4i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgt_mask_vv_nxv4i8_nxv4i8: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e8, mf2, ta, mu -; CHECK-NEXT: vmslt.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e8, mf2, ta, mu +; CHECK-NEXT: vmslt.vv v0, v9, v8 ; CHECK-NEXT: vmslt.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -190,10 +187,9 @@ declare @llvm.riscv.vmsgt.mask.nxv8i8( define @intrinsic_vmsgt_mask_vv_nxv8i8_nxv8i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgt_mask_vv_nxv8i8_nxv8i8: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e8, m1, ta, mu -; CHECK-NEXT: vmslt.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e8, m1, ta, mu +; CHECK-NEXT: vmslt.vv v0, v9, v8 ; CHECK-NEXT: vmslt.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -242,12 +238,11 @@ declare @llvm.riscv.vmsgt.mask.nxv16i8( define @intrinsic_vmsgt_mask_vv_nxv16i8_nxv16i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgt_mask_vv_nxv16i8_nxv16i8: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e8, m2, ta, mu -; CHECK-NEXT: vmslt.vv v14, v10, v8 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmslt.vv v0, v10, v8 +; CHECK-NEXT: vmslt.vv v14, v12, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmslt.vv v8, v12, v10, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsgt.nxv16i8( @@ -294,12 +289,11 @@ declare @llvm.riscv.vmsgt.mask.nxv32i8( define @intrinsic_vmsgt_mask_vv_nxv32i8_nxv32i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgt_mask_vv_nxv32i8_nxv32i8: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e8, m4, ta, mu -; CHECK-NEXT: vmslt.vv v20, v12, v8 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmslt.vv v0, v12, v8 +; CHECK-NEXT: vmslt.vv v20, v16, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmslt.vv v8, v16, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsgt.nxv32i8( @@ -346,10 +340,9 @@ declare @llvm.riscv.vmsgt.mask.nxv1i16( define @intrinsic_vmsgt_mask_vv_nxv1i16_nxv1i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgt_mask_vv_nxv1i16_nxv1i16: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e16, mf4, ta, mu -; CHECK-NEXT: vmslt.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e16, mf4, ta, mu +; CHECK-NEXT: vmslt.vv v0, v9, v8 ; CHECK-NEXT: vmslt.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -398,10 +391,9 @@ declare @llvm.riscv.vmsgt.mask.nxv2i16( define @intrinsic_vmsgt_mask_vv_nxv2i16_nxv2i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgt_mask_vv_nxv2i16_nxv2i16: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e16, mf2, ta, mu -; CHECK-NEXT: vmslt.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e16, mf2, ta, mu +; CHECK-NEXT: vmslt.vv v0, v9, v8 ; CHECK-NEXT: vmslt.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -450,10 +442,9 @@ declare @llvm.riscv.vmsgt.mask.nxv4i16( define @intrinsic_vmsgt_mask_vv_nxv4i16_nxv4i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgt_mask_vv_nxv4i16_nxv4i16: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e16, m1, ta, mu -; CHECK-NEXT: vmslt.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e16, m1, ta, mu +; CHECK-NEXT: vmslt.vv v0, v9, v8 ; CHECK-NEXT: vmslt.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -502,12 +493,11 @@ declare @llvm.riscv.vmsgt.mask.nxv8i16( define @intrinsic_vmsgt_mask_vv_nxv8i16_nxv8i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgt_mask_vv_nxv8i16_nxv8i16: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e16, m2, ta, mu -; CHECK-NEXT: vmslt.vv v14, v10, v8 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmslt.vv v0, v10, v8 +; CHECK-NEXT: vmslt.vv v14, v12, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmslt.vv v8, v12, v10, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsgt.nxv8i16( @@ -554,12 +544,11 @@ declare @llvm.riscv.vmsgt.mask.nxv16i16( define @intrinsic_vmsgt_mask_vv_nxv16i16_nxv16i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgt_mask_vv_nxv16i16_nxv16i16: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e16, m4, ta, mu -; CHECK-NEXT: vmslt.vv v20, v12, v8 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmslt.vv v0, v12, v8 +; CHECK-NEXT: vmslt.vv v20, v16, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmslt.vv v8, v16, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsgt.nxv16i16( @@ -606,10 +595,9 @@ declare @llvm.riscv.vmsgt.mask.nxv1i32( define @intrinsic_vmsgt_mask_vv_nxv1i32_nxv1i32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgt_mask_vv_nxv1i32_nxv1i32: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e32, mf2, ta, mu -; CHECK-NEXT: vmslt.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e32, mf2, ta, mu +; CHECK-NEXT: vmslt.vv v0, v9, v8 ; CHECK-NEXT: vmslt.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -658,10 +646,9 @@ declare @llvm.riscv.vmsgt.mask.nxv2i32( define @intrinsic_vmsgt_mask_vv_nxv2i32_nxv2i32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgt_mask_vv_nxv2i32_nxv2i32: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e32, m1, ta, mu -; CHECK-NEXT: vmslt.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e32, m1, ta, mu +; CHECK-NEXT: vmslt.vv v0, v9, v8 ; CHECK-NEXT: vmslt.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -710,12 +697,11 @@ declare @llvm.riscv.vmsgt.mask.nxv4i32( define @intrinsic_vmsgt_mask_vv_nxv4i32_nxv4i32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgt_mask_vv_nxv4i32_nxv4i32: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e32, m2, ta, mu -; CHECK-NEXT: vmslt.vv v14, v10, v8 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmslt.vv v0, v10, v8 +; CHECK-NEXT: vmslt.vv v14, v12, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmslt.vv v8, v12, v10, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsgt.nxv4i32( @@ -762,12 +748,11 @@ declare @llvm.riscv.vmsgt.mask.nxv8i32( define @intrinsic_vmsgt_mask_vv_nxv8i32_nxv8i32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgt_mask_vv_nxv8i32_nxv8i32: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e32, m4, ta, mu -; CHECK-NEXT: vmslt.vv v20, v12, v8 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmslt.vv v0, v12, v8 +; CHECK-NEXT: vmslt.vv v20, v16, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmslt.vv v8, v16, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsgt.nxv8i32( @@ -814,10 +799,9 @@ declare @llvm.riscv.vmsgt.mask.nxv1i64( define @intrinsic_vmsgt_mask_vv_nxv1i64_nxv1i64( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgt_mask_vv_nxv1i64_nxv1i64: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, mu -; CHECK-NEXT: vmslt.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, mu +; CHECK-NEXT: vmslt.vv v0, v9, v8 ; CHECK-NEXT: vmslt.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -866,12 +850,11 @@ declare @llvm.riscv.vmsgt.mask.nxv2i64( define @intrinsic_vmsgt_mask_vv_nxv2i64_nxv2i64( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgt_mask_vv_nxv2i64_nxv2i64: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e64, m2, ta, mu -; CHECK-NEXT: vmslt.vv v14, v10, v8 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmslt.vv v0, v10, v8 +; CHECK-NEXT: vmslt.vv v14, v12, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmslt.vv v8, v12, v10, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsgt.nxv2i64( @@ -918,12 +901,11 @@ declare @llvm.riscv.vmsgt.mask.nxv4i64( define @intrinsic_vmsgt_mask_vv_nxv4i64_nxv4i64( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgt_mask_vv_nxv4i64_nxv4i64: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e64, m4, ta, mu -; CHECK-NEXT: vmslt.vv v20, v12, v8 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmslt.vv v0, v12, v8 +; CHECK-NEXT: vmslt.vv v20, v16, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmslt.vv v8, v16, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsgt.nxv4i64( diff --git a/llvm/test/CodeGen/RISCV/rvv/vmsgtu.ll b/llvm/test/CodeGen/RISCV/rvv/vmsgtu.ll index 88a632de067a68cca31715c983b009e2c4a3adf3..8826be03bbebb8962ec0819c1c99f02eb16ff942 100644 --- a/llvm/test/CodeGen/RISCV/rvv/vmsgtu.ll +++ b/llvm/test/CodeGen/RISCV/rvv/vmsgtu.ll @@ -34,10 +34,9 @@ declare @llvm.riscv.vmsgtu.mask.nxv1i8( define @intrinsic_vmsgtu_mask_vv_nxv1i8_nxv1i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgtu_mask_vv_nxv1i8_nxv1i8: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e8, mf8, ta, mu -; CHECK-NEXT: vmsltu.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e8, mf8, ta, mu +; CHECK-NEXT: vmsltu.vv v0, v9, v8 ; CHECK-NEXT: vmsltu.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -86,10 +85,9 @@ declare @llvm.riscv.vmsgtu.mask.nxv2i8( define @intrinsic_vmsgtu_mask_vv_nxv2i8_nxv2i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgtu_mask_vv_nxv2i8_nxv2i8: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e8, mf4, ta, mu -; CHECK-NEXT: vmsltu.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e8, mf4, ta, mu +; CHECK-NEXT: vmsltu.vv v0, v9, v8 ; CHECK-NEXT: vmsltu.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -138,10 +136,9 @@ declare @llvm.riscv.vmsgtu.mask.nxv4i8( define @intrinsic_vmsgtu_mask_vv_nxv4i8_nxv4i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgtu_mask_vv_nxv4i8_nxv4i8: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e8, mf2, ta, mu -; CHECK-NEXT: vmsltu.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e8, mf2, ta, mu +; CHECK-NEXT: vmsltu.vv v0, v9, v8 ; CHECK-NEXT: vmsltu.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -190,10 +187,9 @@ declare @llvm.riscv.vmsgtu.mask.nxv8i8( define @intrinsic_vmsgtu_mask_vv_nxv8i8_nxv8i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgtu_mask_vv_nxv8i8_nxv8i8: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e8, m1, ta, mu -; CHECK-NEXT: vmsltu.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e8, m1, ta, mu +; CHECK-NEXT: vmsltu.vv v0, v9, v8 ; CHECK-NEXT: vmsltu.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -242,12 +238,11 @@ declare @llvm.riscv.vmsgtu.mask.nxv16i8( define @intrinsic_vmsgtu_mask_vv_nxv16i8_nxv16i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgtu_mask_vv_nxv16i8_nxv16i8: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e8, m2, ta, mu -; CHECK-NEXT: vmsltu.vv v14, v10, v8 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsltu.vv v0, v10, v8 +; CHECK-NEXT: vmsltu.vv v14, v12, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmsltu.vv v8, v12, v10, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsgtu.nxv16i8( @@ -294,12 +289,11 @@ declare @llvm.riscv.vmsgtu.mask.nxv32i8( define @intrinsic_vmsgtu_mask_vv_nxv32i8_nxv32i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgtu_mask_vv_nxv32i8_nxv32i8: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e8, m4, ta, mu -; CHECK-NEXT: vmsltu.vv v20, v12, v8 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsltu.vv v0, v12, v8 +; CHECK-NEXT: vmsltu.vv v20, v16, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmsltu.vv v8, v16, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsgtu.nxv32i8( @@ -346,10 +340,9 @@ declare @llvm.riscv.vmsgtu.mask.nxv1i16( define @intrinsic_vmsgtu_mask_vv_nxv1i16_nxv1i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgtu_mask_vv_nxv1i16_nxv1i16: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e16, mf4, ta, mu -; CHECK-NEXT: vmsltu.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e16, mf4, ta, mu +; CHECK-NEXT: vmsltu.vv v0, v9, v8 ; CHECK-NEXT: vmsltu.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -398,10 +391,9 @@ declare @llvm.riscv.vmsgtu.mask.nxv2i16( define @intrinsic_vmsgtu_mask_vv_nxv2i16_nxv2i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgtu_mask_vv_nxv2i16_nxv2i16: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e16, mf2, ta, mu -; CHECK-NEXT: vmsltu.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e16, mf2, ta, mu +; CHECK-NEXT: vmsltu.vv v0, v9, v8 ; CHECK-NEXT: vmsltu.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -450,10 +442,9 @@ declare @llvm.riscv.vmsgtu.mask.nxv4i16( define @intrinsic_vmsgtu_mask_vv_nxv4i16_nxv4i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgtu_mask_vv_nxv4i16_nxv4i16: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e16, m1, ta, mu -; CHECK-NEXT: vmsltu.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e16, m1, ta, mu +; CHECK-NEXT: vmsltu.vv v0, v9, v8 ; CHECK-NEXT: vmsltu.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -502,12 +493,11 @@ declare @llvm.riscv.vmsgtu.mask.nxv8i16( define @intrinsic_vmsgtu_mask_vv_nxv8i16_nxv8i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgtu_mask_vv_nxv8i16_nxv8i16: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e16, m2, ta, mu -; CHECK-NEXT: vmsltu.vv v14, v10, v8 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsltu.vv v0, v10, v8 +; CHECK-NEXT: vmsltu.vv v14, v12, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmsltu.vv v8, v12, v10, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsgtu.nxv8i16( @@ -554,12 +544,11 @@ declare @llvm.riscv.vmsgtu.mask.nxv16i16( define @intrinsic_vmsgtu_mask_vv_nxv16i16_nxv16i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgtu_mask_vv_nxv16i16_nxv16i16: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e16, m4, ta, mu -; CHECK-NEXT: vmsltu.vv v20, v12, v8 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsltu.vv v0, v12, v8 +; CHECK-NEXT: vmsltu.vv v20, v16, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmsltu.vv v8, v16, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsgtu.nxv16i16( @@ -606,10 +595,9 @@ declare @llvm.riscv.vmsgtu.mask.nxv1i32( define @intrinsic_vmsgtu_mask_vv_nxv1i32_nxv1i32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgtu_mask_vv_nxv1i32_nxv1i32: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e32, mf2, ta, mu -; CHECK-NEXT: vmsltu.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e32, mf2, ta, mu +; CHECK-NEXT: vmsltu.vv v0, v9, v8 ; CHECK-NEXT: vmsltu.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -658,10 +646,9 @@ declare @llvm.riscv.vmsgtu.mask.nxv2i32( define @intrinsic_vmsgtu_mask_vv_nxv2i32_nxv2i32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgtu_mask_vv_nxv2i32_nxv2i32: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e32, m1, ta, mu -; CHECK-NEXT: vmsltu.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e32, m1, ta, mu +; CHECK-NEXT: vmsltu.vv v0, v9, v8 ; CHECK-NEXT: vmsltu.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -710,12 +697,11 @@ declare @llvm.riscv.vmsgtu.mask.nxv4i32( define @intrinsic_vmsgtu_mask_vv_nxv4i32_nxv4i32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgtu_mask_vv_nxv4i32_nxv4i32: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e32, m2, ta, mu -; CHECK-NEXT: vmsltu.vv v14, v10, v8 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsltu.vv v0, v10, v8 +; CHECK-NEXT: vmsltu.vv v14, v12, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmsltu.vv v8, v12, v10, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsgtu.nxv4i32( @@ -762,12 +748,11 @@ declare @llvm.riscv.vmsgtu.mask.nxv8i32( define @intrinsic_vmsgtu_mask_vv_nxv8i32_nxv8i32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgtu_mask_vv_nxv8i32_nxv8i32: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e32, m4, ta, mu -; CHECK-NEXT: vmsltu.vv v20, v12, v8 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsltu.vv v0, v12, v8 +; CHECK-NEXT: vmsltu.vv v20, v16, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmsltu.vv v8, v16, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsgtu.nxv8i32( @@ -814,10 +799,9 @@ declare @llvm.riscv.vmsgtu.mask.nxv1i64( define @intrinsic_vmsgtu_mask_vv_nxv1i64_nxv1i64( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgtu_mask_vv_nxv1i64_nxv1i64: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, mu -; CHECK-NEXT: vmsltu.vv v8, v9, v8 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, mu +; CHECK-NEXT: vmsltu.vv v0, v9, v8 ; CHECK-NEXT: vmsltu.vv v11, v10, v9, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -866,12 +850,11 @@ declare @llvm.riscv.vmsgtu.mask.nxv2i64( define @intrinsic_vmsgtu_mask_vv_nxv2i64_nxv2i64( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgtu_mask_vv_nxv2i64_nxv2i64: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e64, m2, ta, mu -; CHECK-NEXT: vmsltu.vv v14, v10, v8 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsltu.vv v0, v10, v8 +; CHECK-NEXT: vmsltu.vv v14, v12, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmsltu.vv v8, v12, v10, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsgtu.nxv2i64( @@ -918,12 +901,11 @@ declare @llvm.riscv.vmsgtu.mask.nxv4i64( define @intrinsic_vmsgtu_mask_vv_nxv4i64_nxv4i64( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsgtu_mask_vv_nxv4i64_nxv4i64: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e64, m4, ta, mu -; CHECK-NEXT: vmsltu.vv v20, v12, v8 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsltu.vv v0, v12, v8 +; CHECK-NEXT: vmsltu.vv v20, v16, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmsltu.vv v8, v16, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsgtu.nxv4i64( diff --git a/llvm/test/CodeGen/RISCV/rvv/vmsle.ll b/llvm/test/CodeGen/RISCV/rvv/vmsle.ll index 2248ba03adfe7986cd82888bb13345ee2e25e29a..5d5a28edbfe1519c8f03bedf09cd7236dffba949 100644 --- a/llvm/test/CodeGen/RISCV/rvv/vmsle.ll +++ b/llvm/test/CodeGen/RISCV/rvv/vmsle.ll @@ -34,10 +34,9 @@ declare @llvm.riscv.vmsle.mask.nxv1i8( define @intrinsic_vmsle_mask_vv_nxv1i8_nxv1i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsle_mask_vv_nxv1i8_nxv1i8: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e8, mf8, ta, mu -; CHECK-NEXT: vmsle.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e8, mf8, ta, mu +; CHECK-NEXT: vmsle.vv v0, v8, v9 ; CHECK-NEXT: vmsle.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -86,10 +85,9 @@ declare @llvm.riscv.vmsle.mask.nxv2i8( define @intrinsic_vmsle_mask_vv_nxv2i8_nxv2i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsle_mask_vv_nxv2i8_nxv2i8: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e8, mf4, ta, mu -; CHECK-NEXT: vmsle.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e8, mf4, ta, mu +; CHECK-NEXT: vmsle.vv v0, v8, v9 ; CHECK-NEXT: vmsle.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -138,10 +136,9 @@ declare @llvm.riscv.vmsle.mask.nxv4i8( define @intrinsic_vmsle_mask_vv_nxv4i8_nxv4i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsle_mask_vv_nxv4i8_nxv4i8: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e8, mf2, ta, mu -; CHECK-NEXT: vmsle.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e8, mf2, ta, mu +; CHECK-NEXT: vmsle.vv v0, v8, v9 ; CHECK-NEXT: vmsle.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -190,10 +187,9 @@ declare @llvm.riscv.vmsle.mask.nxv8i8( define @intrinsic_vmsle_mask_vv_nxv8i8_nxv8i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsle_mask_vv_nxv8i8_nxv8i8: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e8, m1, ta, mu -; CHECK-NEXT: vmsle.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e8, m1, ta, mu +; CHECK-NEXT: vmsle.vv v0, v8, v9 ; CHECK-NEXT: vmsle.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -242,12 +238,11 @@ declare @llvm.riscv.vmsle.mask.nxv16i8( define @intrinsic_vmsle_mask_vv_nxv16i8_nxv16i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsle_mask_vv_nxv16i8_nxv16i8: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e8, m2, ta, mu -; CHECK-NEXT: vmsle.vv v14, v8, v10 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsle.vv v0, v8, v10 +; CHECK-NEXT: vmsle.vv v14, v10, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmsle.vv v8, v10, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsle.nxv16i8( @@ -294,12 +289,11 @@ declare @llvm.riscv.vmsle.mask.nxv32i8( define @intrinsic_vmsle_mask_vv_nxv32i8_nxv32i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsle_mask_vv_nxv32i8_nxv32i8: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e8, m4, ta, mu -; CHECK-NEXT: vmsle.vv v20, v8, v12 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsle.vv v0, v8, v12 +; CHECK-NEXT: vmsle.vv v20, v12, v16, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmsle.vv v8, v12, v16, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsle.nxv32i8( @@ -346,10 +340,9 @@ declare @llvm.riscv.vmsle.mask.nxv1i16( define @intrinsic_vmsle_mask_vv_nxv1i16_nxv1i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsle_mask_vv_nxv1i16_nxv1i16: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e16, mf4, ta, mu -; CHECK-NEXT: vmsle.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e16, mf4, ta, mu +; CHECK-NEXT: vmsle.vv v0, v8, v9 ; CHECK-NEXT: vmsle.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -398,10 +391,9 @@ declare @llvm.riscv.vmsle.mask.nxv2i16( define @intrinsic_vmsle_mask_vv_nxv2i16_nxv2i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsle_mask_vv_nxv2i16_nxv2i16: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e16, mf2, ta, mu -; CHECK-NEXT: vmsle.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e16, mf2, ta, mu +; CHECK-NEXT: vmsle.vv v0, v8, v9 ; CHECK-NEXT: vmsle.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -450,10 +442,9 @@ declare @llvm.riscv.vmsle.mask.nxv4i16( define @intrinsic_vmsle_mask_vv_nxv4i16_nxv4i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsle_mask_vv_nxv4i16_nxv4i16: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e16, m1, ta, mu -; CHECK-NEXT: vmsle.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e16, m1, ta, mu +; CHECK-NEXT: vmsle.vv v0, v8, v9 ; CHECK-NEXT: vmsle.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -502,12 +493,11 @@ declare @llvm.riscv.vmsle.mask.nxv8i16( define @intrinsic_vmsle_mask_vv_nxv8i16_nxv8i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsle_mask_vv_nxv8i16_nxv8i16: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e16, m2, ta, mu -; CHECK-NEXT: vmsle.vv v14, v8, v10 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsle.vv v0, v8, v10 +; CHECK-NEXT: vmsle.vv v14, v10, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmsle.vv v8, v10, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsle.nxv8i16( @@ -554,12 +544,11 @@ declare @llvm.riscv.vmsle.mask.nxv16i16( define @intrinsic_vmsle_mask_vv_nxv16i16_nxv16i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsle_mask_vv_nxv16i16_nxv16i16: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e16, m4, ta, mu -; CHECK-NEXT: vmsle.vv v20, v8, v12 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsle.vv v0, v8, v12 +; CHECK-NEXT: vmsle.vv v20, v12, v16, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmsle.vv v8, v12, v16, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsle.nxv16i16( @@ -606,10 +595,9 @@ declare @llvm.riscv.vmsle.mask.nxv1i32( define @intrinsic_vmsle_mask_vv_nxv1i32_nxv1i32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsle_mask_vv_nxv1i32_nxv1i32: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e32, mf2, ta, mu -; CHECK-NEXT: vmsle.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e32, mf2, ta, mu +; CHECK-NEXT: vmsle.vv v0, v8, v9 ; CHECK-NEXT: vmsle.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -658,10 +646,9 @@ declare @llvm.riscv.vmsle.mask.nxv2i32( define @intrinsic_vmsle_mask_vv_nxv2i32_nxv2i32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsle_mask_vv_nxv2i32_nxv2i32: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e32, m1, ta, mu -; CHECK-NEXT: vmsle.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e32, m1, ta, mu +; CHECK-NEXT: vmsle.vv v0, v8, v9 ; CHECK-NEXT: vmsle.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -710,12 +697,11 @@ declare @llvm.riscv.vmsle.mask.nxv4i32( define @intrinsic_vmsle_mask_vv_nxv4i32_nxv4i32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsle_mask_vv_nxv4i32_nxv4i32: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e32, m2, ta, mu -; CHECK-NEXT: vmsle.vv v14, v8, v10 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsle.vv v0, v8, v10 +; CHECK-NEXT: vmsle.vv v14, v10, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmsle.vv v8, v10, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsle.nxv4i32( @@ -762,12 +748,11 @@ declare @llvm.riscv.vmsle.mask.nxv8i32( define @intrinsic_vmsle_mask_vv_nxv8i32_nxv8i32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsle_mask_vv_nxv8i32_nxv8i32: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e32, m4, ta, mu -; CHECK-NEXT: vmsle.vv v20, v8, v12 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsle.vv v0, v8, v12 +; CHECK-NEXT: vmsle.vv v20, v12, v16, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmsle.vv v8, v12, v16, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsle.nxv8i32( @@ -814,10 +799,9 @@ declare @llvm.riscv.vmsle.mask.nxv1i64( define @intrinsic_vmsle_mask_vv_nxv1i64_nxv1i64( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsle_mask_vv_nxv1i64_nxv1i64: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, mu -; CHECK-NEXT: vmsle.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, mu +; CHECK-NEXT: vmsle.vv v0, v8, v9 ; CHECK-NEXT: vmsle.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -866,12 +850,11 @@ declare @llvm.riscv.vmsle.mask.nxv2i64( define @intrinsic_vmsle_mask_vv_nxv2i64_nxv2i64( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsle_mask_vv_nxv2i64_nxv2i64: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e64, m2, ta, mu -; CHECK-NEXT: vmsle.vv v14, v8, v10 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsle.vv v0, v8, v10 +; CHECK-NEXT: vmsle.vv v14, v10, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmsle.vv v8, v10, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsle.nxv2i64( @@ -918,12 +901,11 @@ declare @llvm.riscv.vmsle.mask.nxv4i64( define @intrinsic_vmsle_mask_vv_nxv4i64_nxv4i64( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsle_mask_vv_nxv4i64_nxv4i64: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e64, m4, ta, mu -; CHECK-NEXT: vmsle.vv v20, v8, v12 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsle.vv v0, v8, v12 +; CHECK-NEXT: vmsle.vv v20, v12, v16, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmsle.vv v8, v12, v16, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsle.nxv4i64( diff --git a/llvm/test/CodeGen/RISCV/rvv/vmsleu.ll b/llvm/test/CodeGen/RISCV/rvv/vmsleu.ll index 57bae83b25e0e5a7f93dade81b910e054d02a7bd..c58ac2d0718314196ae2f7f781768b89711c4df7 100644 --- a/llvm/test/CodeGen/RISCV/rvv/vmsleu.ll +++ b/llvm/test/CodeGen/RISCV/rvv/vmsleu.ll @@ -34,10 +34,9 @@ declare @llvm.riscv.vmsleu.mask.nxv1i8( define @intrinsic_vmsleu_mask_vv_nxv1i8_nxv1i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsleu_mask_vv_nxv1i8_nxv1i8: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e8, mf8, ta, mu -; CHECK-NEXT: vmsleu.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e8, mf8, ta, mu +; CHECK-NEXT: vmsleu.vv v0, v8, v9 ; CHECK-NEXT: vmsleu.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -86,10 +85,9 @@ declare @llvm.riscv.vmsleu.mask.nxv2i8( define @intrinsic_vmsleu_mask_vv_nxv2i8_nxv2i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsleu_mask_vv_nxv2i8_nxv2i8: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e8, mf4, ta, mu -; CHECK-NEXT: vmsleu.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e8, mf4, ta, mu +; CHECK-NEXT: vmsleu.vv v0, v8, v9 ; CHECK-NEXT: vmsleu.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -138,10 +136,9 @@ declare @llvm.riscv.vmsleu.mask.nxv4i8( define @intrinsic_vmsleu_mask_vv_nxv4i8_nxv4i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsleu_mask_vv_nxv4i8_nxv4i8: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e8, mf2, ta, mu -; CHECK-NEXT: vmsleu.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e8, mf2, ta, mu +; CHECK-NEXT: vmsleu.vv v0, v8, v9 ; CHECK-NEXT: vmsleu.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -190,10 +187,9 @@ declare @llvm.riscv.vmsleu.mask.nxv8i8( define @intrinsic_vmsleu_mask_vv_nxv8i8_nxv8i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsleu_mask_vv_nxv8i8_nxv8i8: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e8, m1, ta, mu -; CHECK-NEXT: vmsleu.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e8, m1, ta, mu +; CHECK-NEXT: vmsleu.vv v0, v8, v9 ; CHECK-NEXT: vmsleu.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -242,12 +238,11 @@ declare @llvm.riscv.vmsleu.mask.nxv16i8( define @intrinsic_vmsleu_mask_vv_nxv16i8_nxv16i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsleu_mask_vv_nxv16i8_nxv16i8: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e8, m2, ta, mu -; CHECK-NEXT: vmsleu.vv v14, v8, v10 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsleu.vv v0, v8, v10 +; CHECK-NEXT: vmsleu.vv v14, v10, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmsleu.vv v8, v10, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsleu.nxv16i8( @@ -294,12 +289,11 @@ declare @llvm.riscv.vmsleu.mask.nxv32i8( define @intrinsic_vmsleu_mask_vv_nxv32i8_nxv32i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsleu_mask_vv_nxv32i8_nxv32i8: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e8, m4, ta, mu -; CHECK-NEXT: vmsleu.vv v20, v8, v12 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsleu.vv v0, v8, v12 +; CHECK-NEXT: vmsleu.vv v20, v12, v16, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmsleu.vv v8, v12, v16, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsleu.nxv32i8( @@ -346,10 +340,9 @@ declare @llvm.riscv.vmsleu.mask.nxv1i16( define @intrinsic_vmsleu_mask_vv_nxv1i16_nxv1i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsleu_mask_vv_nxv1i16_nxv1i16: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e16, mf4, ta, mu -; CHECK-NEXT: vmsleu.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e16, mf4, ta, mu +; CHECK-NEXT: vmsleu.vv v0, v8, v9 ; CHECK-NEXT: vmsleu.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -398,10 +391,9 @@ declare @llvm.riscv.vmsleu.mask.nxv2i16( define @intrinsic_vmsleu_mask_vv_nxv2i16_nxv2i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsleu_mask_vv_nxv2i16_nxv2i16: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e16, mf2, ta, mu -; CHECK-NEXT: vmsleu.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e16, mf2, ta, mu +; CHECK-NEXT: vmsleu.vv v0, v8, v9 ; CHECK-NEXT: vmsleu.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -450,10 +442,9 @@ declare @llvm.riscv.vmsleu.mask.nxv4i16( define @intrinsic_vmsleu_mask_vv_nxv4i16_nxv4i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsleu_mask_vv_nxv4i16_nxv4i16: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e16, m1, ta, mu -; CHECK-NEXT: vmsleu.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e16, m1, ta, mu +; CHECK-NEXT: vmsleu.vv v0, v8, v9 ; CHECK-NEXT: vmsleu.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -502,12 +493,11 @@ declare @llvm.riscv.vmsleu.mask.nxv8i16( define @intrinsic_vmsleu_mask_vv_nxv8i16_nxv8i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsleu_mask_vv_nxv8i16_nxv8i16: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e16, m2, ta, mu -; CHECK-NEXT: vmsleu.vv v14, v8, v10 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsleu.vv v0, v8, v10 +; CHECK-NEXT: vmsleu.vv v14, v10, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmsleu.vv v8, v10, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsleu.nxv8i16( @@ -554,12 +544,11 @@ declare @llvm.riscv.vmsleu.mask.nxv16i16( define @intrinsic_vmsleu_mask_vv_nxv16i16_nxv16i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsleu_mask_vv_nxv16i16_nxv16i16: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e16, m4, ta, mu -; CHECK-NEXT: vmsleu.vv v20, v8, v12 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsleu.vv v0, v8, v12 +; CHECK-NEXT: vmsleu.vv v20, v12, v16, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmsleu.vv v8, v12, v16, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsleu.nxv16i16( @@ -606,10 +595,9 @@ declare @llvm.riscv.vmsleu.mask.nxv1i32( define @intrinsic_vmsleu_mask_vv_nxv1i32_nxv1i32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsleu_mask_vv_nxv1i32_nxv1i32: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e32, mf2, ta, mu -; CHECK-NEXT: vmsleu.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e32, mf2, ta, mu +; CHECK-NEXT: vmsleu.vv v0, v8, v9 ; CHECK-NEXT: vmsleu.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -658,10 +646,9 @@ declare @llvm.riscv.vmsleu.mask.nxv2i32( define @intrinsic_vmsleu_mask_vv_nxv2i32_nxv2i32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsleu_mask_vv_nxv2i32_nxv2i32: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e32, m1, ta, mu -; CHECK-NEXT: vmsleu.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e32, m1, ta, mu +; CHECK-NEXT: vmsleu.vv v0, v8, v9 ; CHECK-NEXT: vmsleu.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -710,12 +697,11 @@ declare @llvm.riscv.vmsleu.mask.nxv4i32( define @intrinsic_vmsleu_mask_vv_nxv4i32_nxv4i32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsleu_mask_vv_nxv4i32_nxv4i32: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e32, m2, ta, mu -; CHECK-NEXT: vmsleu.vv v14, v8, v10 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsleu.vv v0, v8, v10 +; CHECK-NEXT: vmsleu.vv v14, v10, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmsleu.vv v8, v10, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsleu.nxv4i32( @@ -762,12 +748,11 @@ declare @llvm.riscv.vmsleu.mask.nxv8i32( define @intrinsic_vmsleu_mask_vv_nxv8i32_nxv8i32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsleu_mask_vv_nxv8i32_nxv8i32: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e32, m4, ta, mu -; CHECK-NEXT: vmsleu.vv v20, v8, v12 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsleu.vv v0, v8, v12 +; CHECK-NEXT: vmsleu.vv v20, v12, v16, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmsleu.vv v8, v12, v16, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsleu.nxv8i32( @@ -814,10 +799,9 @@ declare @llvm.riscv.vmsleu.mask.nxv1i64( define @intrinsic_vmsleu_mask_vv_nxv1i64_nxv1i64( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsleu_mask_vv_nxv1i64_nxv1i64: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, mu -; CHECK-NEXT: vmsleu.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, mu +; CHECK-NEXT: vmsleu.vv v0, v8, v9 ; CHECK-NEXT: vmsleu.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -866,12 +850,11 @@ declare @llvm.riscv.vmsleu.mask.nxv2i64( define @intrinsic_vmsleu_mask_vv_nxv2i64_nxv2i64( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsleu_mask_vv_nxv2i64_nxv2i64: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e64, m2, ta, mu -; CHECK-NEXT: vmsleu.vv v14, v8, v10 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsleu.vv v0, v8, v10 +; CHECK-NEXT: vmsleu.vv v14, v10, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmsleu.vv v8, v10, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsleu.nxv2i64( @@ -918,12 +901,11 @@ declare @llvm.riscv.vmsleu.mask.nxv4i64( define @intrinsic_vmsleu_mask_vv_nxv4i64_nxv4i64( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsleu_mask_vv_nxv4i64_nxv4i64: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e64, m4, ta, mu -; CHECK-NEXT: vmsleu.vv v20, v8, v12 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsleu.vv v0, v8, v12 +; CHECK-NEXT: vmsleu.vv v20, v12, v16, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmsleu.vv v8, v12, v16, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsleu.nxv4i64( diff --git a/llvm/test/CodeGen/RISCV/rvv/vmslt.ll b/llvm/test/CodeGen/RISCV/rvv/vmslt.ll index 6783f7feb624c5674117d6c93b0a9cf32067242c..6c6e580b043d1aebc66e6c072cf9b783efe5bf53 100644 --- a/llvm/test/CodeGen/RISCV/rvv/vmslt.ll +++ b/llvm/test/CodeGen/RISCV/rvv/vmslt.ll @@ -34,10 +34,9 @@ declare @llvm.riscv.vmslt.mask.nxv1i8( define @intrinsic_vmslt_mask_vv_nxv1i8_nxv1i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmslt_mask_vv_nxv1i8_nxv1i8: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e8, mf8, ta, mu -; CHECK-NEXT: vmslt.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e8, mf8, ta, mu +; CHECK-NEXT: vmslt.vv v0, v8, v9 ; CHECK-NEXT: vmslt.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -86,10 +85,9 @@ declare @llvm.riscv.vmslt.mask.nxv2i8( define @intrinsic_vmslt_mask_vv_nxv2i8_nxv2i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmslt_mask_vv_nxv2i8_nxv2i8: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e8, mf4, ta, mu -; CHECK-NEXT: vmslt.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e8, mf4, ta, mu +; CHECK-NEXT: vmslt.vv v0, v8, v9 ; CHECK-NEXT: vmslt.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -138,10 +136,9 @@ declare @llvm.riscv.vmslt.mask.nxv4i8( define @intrinsic_vmslt_mask_vv_nxv4i8_nxv4i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmslt_mask_vv_nxv4i8_nxv4i8: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e8, mf2, ta, mu -; CHECK-NEXT: vmslt.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e8, mf2, ta, mu +; CHECK-NEXT: vmslt.vv v0, v8, v9 ; CHECK-NEXT: vmslt.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -190,10 +187,9 @@ declare @llvm.riscv.vmslt.mask.nxv8i8( define @intrinsic_vmslt_mask_vv_nxv8i8_nxv8i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmslt_mask_vv_nxv8i8_nxv8i8: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e8, m1, ta, mu -; CHECK-NEXT: vmslt.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e8, m1, ta, mu +; CHECK-NEXT: vmslt.vv v0, v8, v9 ; CHECK-NEXT: vmslt.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -242,12 +238,11 @@ declare @llvm.riscv.vmslt.mask.nxv16i8( define @intrinsic_vmslt_mask_vv_nxv16i8_nxv16i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmslt_mask_vv_nxv16i8_nxv16i8: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e8, m2, ta, mu -; CHECK-NEXT: vmslt.vv v14, v8, v10 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmslt.vv v0, v8, v10 +; CHECK-NEXT: vmslt.vv v14, v10, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmslt.vv v8, v10, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmslt.nxv16i8( @@ -294,12 +289,11 @@ declare @llvm.riscv.vmslt.mask.nxv32i8( define @intrinsic_vmslt_mask_vv_nxv32i8_nxv32i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmslt_mask_vv_nxv32i8_nxv32i8: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e8, m4, ta, mu -; CHECK-NEXT: vmslt.vv v20, v8, v12 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmslt.vv v0, v8, v12 +; CHECK-NEXT: vmslt.vv v20, v12, v16, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmslt.vv v8, v12, v16, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmslt.nxv32i8( @@ -346,10 +340,9 @@ declare @llvm.riscv.vmslt.mask.nxv1i16( define @intrinsic_vmslt_mask_vv_nxv1i16_nxv1i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmslt_mask_vv_nxv1i16_nxv1i16: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e16, mf4, ta, mu -; CHECK-NEXT: vmslt.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e16, mf4, ta, mu +; CHECK-NEXT: vmslt.vv v0, v8, v9 ; CHECK-NEXT: vmslt.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -398,10 +391,9 @@ declare @llvm.riscv.vmslt.mask.nxv2i16( define @intrinsic_vmslt_mask_vv_nxv2i16_nxv2i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmslt_mask_vv_nxv2i16_nxv2i16: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e16, mf2, ta, mu -; CHECK-NEXT: vmslt.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e16, mf2, ta, mu +; CHECK-NEXT: vmslt.vv v0, v8, v9 ; CHECK-NEXT: vmslt.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -450,10 +442,9 @@ declare @llvm.riscv.vmslt.mask.nxv4i16( define @intrinsic_vmslt_mask_vv_nxv4i16_nxv4i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmslt_mask_vv_nxv4i16_nxv4i16: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e16, m1, ta, mu -; CHECK-NEXT: vmslt.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e16, m1, ta, mu +; CHECK-NEXT: vmslt.vv v0, v8, v9 ; CHECK-NEXT: vmslt.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -502,12 +493,11 @@ declare @llvm.riscv.vmslt.mask.nxv8i16( define @intrinsic_vmslt_mask_vv_nxv8i16_nxv8i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmslt_mask_vv_nxv8i16_nxv8i16: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e16, m2, ta, mu -; CHECK-NEXT: vmslt.vv v14, v8, v10 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmslt.vv v0, v8, v10 +; CHECK-NEXT: vmslt.vv v14, v10, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmslt.vv v8, v10, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmslt.nxv8i16( @@ -554,12 +544,11 @@ declare @llvm.riscv.vmslt.mask.nxv16i16( define @intrinsic_vmslt_mask_vv_nxv16i16_nxv16i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmslt_mask_vv_nxv16i16_nxv16i16: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e16, m4, ta, mu -; CHECK-NEXT: vmslt.vv v20, v8, v12 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmslt.vv v0, v8, v12 +; CHECK-NEXT: vmslt.vv v20, v12, v16, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmslt.vv v8, v12, v16, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmslt.nxv16i16( @@ -606,10 +595,9 @@ declare @llvm.riscv.vmslt.mask.nxv1i32( define @intrinsic_vmslt_mask_vv_nxv1i32_nxv1i32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmslt_mask_vv_nxv1i32_nxv1i32: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e32, mf2, ta, mu -; CHECK-NEXT: vmslt.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e32, mf2, ta, mu +; CHECK-NEXT: vmslt.vv v0, v8, v9 ; CHECK-NEXT: vmslt.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -658,10 +646,9 @@ declare @llvm.riscv.vmslt.mask.nxv2i32( define @intrinsic_vmslt_mask_vv_nxv2i32_nxv2i32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmslt_mask_vv_nxv2i32_nxv2i32: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e32, m1, ta, mu -; CHECK-NEXT: vmslt.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e32, m1, ta, mu +; CHECK-NEXT: vmslt.vv v0, v8, v9 ; CHECK-NEXT: vmslt.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -710,12 +697,11 @@ declare @llvm.riscv.vmslt.mask.nxv4i32( define @intrinsic_vmslt_mask_vv_nxv4i32_nxv4i32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmslt_mask_vv_nxv4i32_nxv4i32: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e32, m2, ta, mu -; CHECK-NEXT: vmslt.vv v14, v8, v10 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmslt.vv v0, v8, v10 +; CHECK-NEXT: vmslt.vv v14, v10, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmslt.vv v8, v10, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmslt.nxv4i32( @@ -762,12 +748,11 @@ declare @llvm.riscv.vmslt.mask.nxv8i32( define @intrinsic_vmslt_mask_vv_nxv8i32_nxv8i32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmslt_mask_vv_nxv8i32_nxv8i32: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e32, m4, ta, mu -; CHECK-NEXT: vmslt.vv v20, v8, v12 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmslt.vv v0, v8, v12 +; CHECK-NEXT: vmslt.vv v20, v12, v16, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmslt.vv v8, v12, v16, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmslt.nxv8i32( @@ -814,10 +799,9 @@ declare @llvm.riscv.vmslt.mask.nxv1i64( define @intrinsic_vmslt_mask_vv_nxv1i64_nxv1i64( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmslt_mask_vv_nxv1i64_nxv1i64: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, mu -; CHECK-NEXT: vmslt.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, mu +; CHECK-NEXT: vmslt.vv v0, v8, v9 ; CHECK-NEXT: vmslt.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -866,12 +850,11 @@ declare @llvm.riscv.vmslt.mask.nxv2i64( define @intrinsic_vmslt_mask_vv_nxv2i64_nxv2i64( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmslt_mask_vv_nxv2i64_nxv2i64: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e64, m2, ta, mu -; CHECK-NEXT: vmslt.vv v14, v8, v10 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmslt.vv v0, v8, v10 +; CHECK-NEXT: vmslt.vv v14, v10, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmslt.vv v8, v10, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmslt.nxv2i64( @@ -918,12 +901,11 @@ declare @llvm.riscv.vmslt.mask.nxv4i64( define @intrinsic_vmslt_mask_vv_nxv4i64_nxv4i64( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmslt_mask_vv_nxv4i64_nxv4i64: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e64, m4, ta, mu -; CHECK-NEXT: vmslt.vv v20, v8, v12 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmslt.vv v0, v8, v12 +; CHECK-NEXT: vmslt.vv v20, v12, v16, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmslt.vv v8, v12, v16, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmslt.nxv4i64( diff --git a/llvm/test/CodeGen/RISCV/rvv/vmsltu.ll b/llvm/test/CodeGen/RISCV/rvv/vmsltu.ll index b082b735a0207295ce4b6795573ba0dc72dfb294..76f3e449ab58f59ab8b22408bd8794b0b7f2ec57 100644 --- a/llvm/test/CodeGen/RISCV/rvv/vmsltu.ll +++ b/llvm/test/CodeGen/RISCV/rvv/vmsltu.ll @@ -34,10 +34,9 @@ declare @llvm.riscv.vmsltu.mask.nxv1i8( define @intrinsic_vmsltu_mask_vv_nxv1i8_nxv1i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsltu_mask_vv_nxv1i8_nxv1i8: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e8, mf8, ta, mu -; CHECK-NEXT: vmsltu.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e8, mf8, ta, mu +; CHECK-NEXT: vmsltu.vv v0, v8, v9 ; CHECK-NEXT: vmsltu.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -86,10 +85,9 @@ declare @llvm.riscv.vmsltu.mask.nxv2i8( define @intrinsic_vmsltu_mask_vv_nxv2i8_nxv2i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsltu_mask_vv_nxv2i8_nxv2i8: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e8, mf4, ta, mu -; CHECK-NEXT: vmsltu.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e8, mf4, ta, mu +; CHECK-NEXT: vmsltu.vv v0, v8, v9 ; CHECK-NEXT: vmsltu.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -138,10 +136,9 @@ declare @llvm.riscv.vmsltu.mask.nxv4i8( define @intrinsic_vmsltu_mask_vv_nxv4i8_nxv4i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsltu_mask_vv_nxv4i8_nxv4i8: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e8, mf2, ta, mu -; CHECK-NEXT: vmsltu.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e8, mf2, ta, mu +; CHECK-NEXT: vmsltu.vv v0, v8, v9 ; CHECK-NEXT: vmsltu.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -190,10 +187,9 @@ declare @llvm.riscv.vmsltu.mask.nxv8i8( define @intrinsic_vmsltu_mask_vv_nxv8i8_nxv8i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsltu_mask_vv_nxv8i8_nxv8i8: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e8, m1, ta, mu -; CHECK-NEXT: vmsltu.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e8, m1, ta, mu +; CHECK-NEXT: vmsltu.vv v0, v8, v9 ; CHECK-NEXT: vmsltu.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -242,12 +238,11 @@ declare @llvm.riscv.vmsltu.mask.nxv16i8( define @intrinsic_vmsltu_mask_vv_nxv16i8_nxv16i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsltu_mask_vv_nxv16i8_nxv16i8: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e8, m2, ta, mu -; CHECK-NEXT: vmsltu.vv v14, v8, v10 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsltu.vv v0, v8, v10 +; CHECK-NEXT: vmsltu.vv v14, v10, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmsltu.vv v8, v10, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsltu.nxv16i8( @@ -294,12 +289,11 @@ declare @llvm.riscv.vmsltu.mask.nxv32i8( define @intrinsic_vmsltu_mask_vv_nxv32i8_nxv32i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsltu_mask_vv_nxv32i8_nxv32i8: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e8, m4, ta, mu -; CHECK-NEXT: vmsltu.vv v20, v8, v12 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsltu.vv v0, v8, v12 +; CHECK-NEXT: vmsltu.vv v20, v12, v16, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmsltu.vv v8, v12, v16, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsltu.nxv32i8( @@ -346,10 +340,9 @@ declare @llvm.riscv.vmsltu.mask.nxv1i16( define @intrinsic_vmsltu_mask_vv_nxv1i16_nxv1i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsltu_mask_vv_nxv1i16_nxv1i16: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e16, mf4, ta, mu -; CHECK-NEXT: vmsltu.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e16, mf4, ta, mu +; CHECK-NEXT: vmsltu.vv v0, v8, v9 ; CHECK-NEXT: vmsltu.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -398,10 +391,9 @@ declare @llvm.riscv.vmsltu.mask.nxv2i16( define @intrinsic_vmsltu_mask_vv_nxv2i16_nxv2i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsltu_mask_vv_nxv2i16_nxv2i16: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e16, mf2, ta, mu -; CHECK-NEXT: vmsltu.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e16, mf2, ta, mu +; CHECK-NEXT: vmsltu.vv v0, v8, v9 ; CHECK-NEXT: vmsltu.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -450,10 +442,9 @@ declare @llvm.riscv.vmsltu.mask.nxv4i16( define @intrinsic_vmsltu_mask_vv_nxv4i16_nxv4i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsltu_mask_vv_nxv4i16_nxv4i16: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e16, m1, ta, mu -; CHECK-NEXT: vmsltu.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e16, m1, ta, mu +; CHECK-NEXT: vmsltu.vv v0, v8, v9 ; CHECK-NEXT: vmsltu.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -502,12 +493,11 @@ declare @llvm.riscv.vmsltu.mask.nxv8i16( define @intrinsic_vmsltu_mask_vv_nxv8i16_nxv8i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsltu_mask_vv_nxv8i16_nxv8i16: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e16, m2, ta, mu -; CHECK-NEXT: vmsltu.vv v14, v8, v10 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsltu.vv v0, v8, v10 +; CHECK-NEXT: vmsltu.vv v14, v10, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmsltu.vv v8, v10, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsltu.nxv8i16( @@ -554,12 +544,11 @@ declare @llvm.riscv.vmsltu.mask.nxv16i16( define @intrinsic_vmsltu_mask_vv_nxv16i16_nxv16i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsltu_mask_vv_nxv16i16_nxv16i16: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e16, m4, ta, mu -; CHECK-NEXT: vmsltu.vv v20, v8, v12 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsltu.vv v0, v8, v12 +; CHECK-NEXT: vmsltu.vv v20, v12, v16, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmsltu.vv v8, v12, v16, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsltu.nxv16i16( @@ -606,10 +595,9 @@ declare @llvm.riscv.vmsltu.mask.nxv1i32( define @intrinsic_vmsltu_mask_vv_nxv1i32_nxv1i32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsltu_mask_vv_nxv1i32_nxv1i32: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e32, mf2, ta, mu -; CHECK-NEXT: vmsltu.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e32, mf2, ta, mu +; CHECK-NEXT: vmsltu.vv v0, v8, v9 ; CHECK-NEXT: vmsltu.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -658,10 +646,9 @@ declare @llvm.riscv.vmsltu.mask.nxv2i32( define @intrinsic_vmsltu_mask_vv_nxv2i32_nxv2i32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsltu_mask_vv_nxv2i32_nxv2i32: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e32, m1, ta, mu -; CHECK-NEXT: vmsltu.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e32, m1, ta, mu +; CHECK-NEXT: vmsltu.vv v0, v8, v9 ; CHECK-NEXT: vmsltu.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -710,12 +697,11 @@ declare @llvm.riscv.vmsltu.mask.nxv4i32( define @intrinsic_vmsltu_mask_vv_nxv4i32_nxv4i32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsltu_mask_vv_nxv4i32_nxv4i32: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e32, m2, ta, mu -; CHECK-NEXT: vmsltu.vv v14, v8, v10 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsltu.vv v0, v8, v10 +; CHECK-NEXT: vmsltu.vv v14, v10, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmsltu.vv v8, v10, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsltu.nxv4i32( @@ -762,12 +748,11 @@ declare @llvm.riscv.vmsltu.mask.nxv8i32( define @intrinsic_vmsltu_mask_vv_nxv8i32_nxv8i32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsltu_mask_vv_nxv8i32_nxv8i32: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e32, m4, ta, mu -; CHECK-NEXT: vmsltu.vv v20, v8, v12 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsltu.vv v0, v8, v12 +; CHECK-NEXT: vmsltu.vv v20, v12, v16, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmsltu.vv v8, v12, v16, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsltu.nxv8i32( @@ -814,10 +799,9 @@ declare @llvm.riscv.vmsltu.mask.nxv1i64( define @intrinsic_vmsltu_mask_vv_nxv1i64_nxv1i64( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsltu_mask_vv_nxv1i64_nxv1i64: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, mu -; CHECK-NEXT: vmsltu.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, mu +; CHECK-NEXT: vmsltu.vv v0, v8, v9 ; CHECK-NEXT: vmsltu.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -866,12 +850,11 @@ declare @llvm.riscv.vmsltu.mask.nxv2i64( define @intrinsic_vmsltu_mask_vv_nxv2i64_nxv2i64( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsltu_mask_vv_nxv2i64_nxv2i64: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e64, m2, ta, mu -; CHECK-NEXT: vmsltu.vv v14, v8, v10 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsltu.vv v0, v8, v10 +; CHECK-NEXT: vmsltu.vv v14, v10, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmsltu.vv v8, v10, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsltu.nxv2i64( @@ -918,12 +901,11 @@ declare @llvm.riscv.vmsltu.mask.nxv4i64( define @intrinsic_vmsltu_mask_vv_nxv4i64_nxv4i64( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsltu_mask_vv_nxv4i64_nxv4i64: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e64, m4, ta, mu -; CHECK-NEXT: vmsltu.vv v20, v8, v12 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsltu.vv v0, v8, v12 +; CHECK-NEXT: vmsltu.vv v20, v12, v16, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmsltu.vv v8, v12, v16, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsltu.nxv4i64( diff --git a/llvm/test/CodeGen/RISCV/rvv/vmsne.ll b/llvm/test/CodeGen/RISCV/rvv/vmsne.ll index bb4575e5d72cbed8d8fb95e357a2f1b3eb8461b4..161c1bc4314fcbb688f3ec5af81976a02e0961b5 100644 --- a/llvm/test/CodeGen/RISCV/rvv/vmsne.ll +++ b/llvm/test/CodeGen/RISCV/rvv/vmsne.ll @@ -34,10 +34,9 @@ declare @llvm.riscv.vmsne.mask.nxv1i8( define @intrinsic_vmsne_mask_vv_nxv1i8_nxv1i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsne_mask_vv_nxv1i8_nxv1i8: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e8, mf8, ta, mu -; CHECK-NEXT: vmsne.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e8, mf8, ta, mu +; CHECK-NEXT: vmsne.vv v0, v8, v9 ; CHECK-NEXT: vmsne.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -86,10 +85,9 @@ declare @llvm.riscv.vmsne.mask.nxv2i8( define @intrinsic_vmsne_mask_vv_nxv2i8_nxv2i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsne_mask_vv_nxv2i8_nxv2i8: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e8, mf4, ta, mu -; CHECK-NEXT: vmsne.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e8, mf4, ta, mu +; CHECK-NEXT: vmsne.vv v0, v8, v9 ; CHECK-NEXT: vmsne.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -138,10 +136,9 @@ declare @llvm.riscv.vmsne.mask.nxv4i8( define @intrinsic_vmsne_mask_vv_nxv4i8_nxv4i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsne_mask_vv_nxv4i8_nxv4i8: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e8, mf2, ta, mu -; CHECK-NEXT: vmsne.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e8, mf2, ta, mu +; CHECK-NEXT: vmsne.vv v0, v8, v9 ; CHECK-NEXT: vmsne.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -190,10 +187,9 @@ declare @llvm.riscv.vmsne.mask.nxv8i8( define @intrinsic_vmsne_mask_vv_nxv8i8_nxv8i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsne_mask_vv_nxv8i8_nxv8i8: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e8, m1, ta, mu -; CHECK-NEXT: vmsne.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e8, m1, ta, mu +; CHECK-NEXT: vmsne.vv v0, v8, v9 ; CHECK-NEXT: vmsne.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -242,12 +238,11 @@ declare @llvm.riscv.vmsne.mask.nxv16i8( define @intrinsic_vmsne_mask_vv_nxv16i8_nxv16i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsne_mask_vv_nxv16i8_nxv16i8: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e8, m2, ta, mu -; CHECK-NEXT: vmsne.vv v14, v8, v10 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsne.vv v0, v8, v10 +; CHECK-NEXT: vmsne.vv v14, v10, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmsne.vv v8, v10, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsne.nxv16i8( @@ -294,12 +289,11 @@ declare @llvm.riscv.vmsne.mask.nxv32i8( define @intrinsic_vmsne_mask_vv_nxv32i8_nxv32i8( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsne_mask_vv_nxv32i8_nxv32i8: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e8, m4, ta, mu -; CHECK-NEXT: vmsne.vv v20, v8, v12 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsne.vv v0, v8, v12 +; CHECK-NEXT: vmsne.vv v20, v12, v16, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmsne.vv v8, v12, v16, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsne.nxv32i8( @@ -346,10 +340,9 @@ declare @llvm.riscv.vmsne.mask.nxv1i16( define @intrinsic_vmsne_mask_vv_nxv1i16_nxv1i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsne_mask_vv_nxv1i16_nxv1i16: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e16, mf4, ta, mu -; CHECK-NEXT: vmsne.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e16, mf4, ta, mu +; CHECK-NEXT: vmsne.vv v0, v8, v9 ; CHECK-NEXT: vmsne.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -398,10 +391,9 @@ declare @llvm.riscv.vmsne.mask.nxv2i16( define @intrinsic_vmsne_mask_vv_nxv2i16_nxv2i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsne_mask_vv_nxv2i16_nxv2i16: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e16, mf2, ta, mu -; CHECK-NEXT: vmsne.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e16, mf2, ta, mu +; CHECK-NEXT: vmsne.vv v0, v8, v9 ; CHECK-NEXT: vmsne.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -450,10 +442,9 @@ declare @llvm.riscv.vmsne.mask.nxv4i16( define @intrinsic_vmsne_mask_vv_nxv4i16_nxv4i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsne_mask_vv_nxv4i16_nxv4i16: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e16, m1, ta, mu -; CHECK-NEXT: vmsne.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e16, m1, ta, mu +; CHECK-NEXT: vmsne.vv v0, v8, v9 ; CHECK-NEXT: vmsne.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -502,12 +493,11 @@ declare @llvm.riscv.vmsne.mask.nxv8i16( define @intrinsic_vmsne_mask_vv_nxv8i16_nxv8i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsne_mask_vv_nxv8i16_nxv8i16: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e16, m2, ta, mu -; CHECK-NEXT: vmsne.vv v14, v8, v10 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsne.vv v0, v8, v10 +; CHECK-NEXT: vmsne.vv v14, v10, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmsne.vv v8, v10, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsne.nxv8i16( @@ -554,12 +544,11 @@ declare @llvm.riscv.vmsne.mask.nxv16i16( define @intrinsic_vmsne_mask_vv_nxv16i16_nxv16i16( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsne_mask_vv_nxv16i16_nxv16i16: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e16, m4, ta, mu -; CHECK-NEXT: vmsne.vv v20, v8, v12 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsne.vv v0, v8, v12 +; CHECK-NEXT: vmsne.vv v20, v12, v16, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmsne.vv v8, v12, v16, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsne.nxv16i16( @@ -606,10 +595,9 @@ declare @llvm.riscv.vmsne.mask.nxv1i32( define @intrinsic_vmsne_mask_vv_nxv1i32_nxv1i32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsne_mask_vv_nxv1i32_nxv1i32: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e32, mf2, ta, mu -; CHECK-NEXT: vmsne.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv1r.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e32, mf2, ta, mu +; CHECK-NEXT: vmsne.vv v0, v8, v9 ; CHECK-NEXT: vmsne.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv1r.v v0, v11 ; CHECK-NEXT: ret @@ -658,10 +646,9 @@ declare @llvm.riscv.vmsne.mask.nxv2i32( define @intrinsic_vmsne_mask_vv_nxv2i32_nxv2i32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsne_mask_vv_nxv2i32_nxv2i32: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e32, m1, ta, mu -; CHECK-NEXT: vmsne.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e32, m1, ta, mu +; CHECK-NEXT: vmsne.vv v0, v8, v9 ; CHECK-NEXT: vmsne.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -710,12 +697,11 @@ declare @llvm.riscv.vmsne.mask.nxv4i32( define @intrinsic_vmsne_mask_vv_nxv4i32_nxv4i32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsne_mask_vv_nxv4i32_nxv4i32: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e32, m2, ta, mu -; CHECK-NEXT: vmsne.vv v14, v8, v10 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsne.vv v0, v8, v10 +; CHECK-NEXT: vmsne.vv v14, v10, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmsne.vv v8, v10, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsne.nxv4i32( @@ -762,12 +748,11 @@ declare @llvm.riscv.vmsne.mask.nxv8i32( define @intrinsic_vmsne_mask_vv_nxv8i32_nxv8i32( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsne_mask_vv_nxv8i32_nxv8i32: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e32, m4, ta, mu -; CHECK-NEXT: vmsne.vv v20, v8, v12 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsne.vv v0, v8, v12 +; CHECK-NEXT: vmsne.vv v20, v12, v16, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmsne.vv v8, v12, v16, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsne.nxv8i32( @@ -814,10 +799,9 @@ declare @llvm.riscv.vmsne.mask.nxv1i64( define @intrinsic_vmsne_mask_vv_nxv1i64_nxv1i64( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsne_mask_vv_nxv1i64_nxv1i64: ; CHECK: # %bb.0: # %entry -; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, mu -; CHECK-NEXT: vmsne.vv v8, v8, v9 ; CHECK-NEXT: vmv1r.v v11, v0 -; CHECK-NEXT: vmv.v.v v0, v8 +; CHECK-NEXT: vsetvli zero, a0, e64, m1, ta, mu +; CHECK-NEXT: vmsne.vv v0, v8, v9 ; CHECK-NEXT: vmsne.vv v11, v9, v10, v0.t ; CHECK-NEXT: vmv.v.v v0, v11 ; CHECK-NEXT: ret @@ -866,12 +850,11 @@ declare @llvm.riscv.vmsne.mask.nxv2i64( define @intrinsic_vmsne_mask_vv_nxv2i64_nxv2i64( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsne_mask_vv_nxv2i64_nxv2i64: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v14, v0 ; CHECK-NEXT: vsetvli zero, a0, e64, m2, ta, mu -; CHECK-NEXT: vmsne.vv v14, v8, v10 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsne.vv v0, v8, v10 +; CHECK-NEXT: vmsne.vv v14, v10, v12, v0.t ; CHECK-NEXT: vmv1r.v v0, v14 -; CHECK-NEXT: vmsne.vv v8, v10, v12, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsne.nxv2i64( @@ -918,12 +901,11 @@ declare @llvm.riscv.vmsne.mask.nxv4i64( define @intrinsic_vmsne_mask_vv_nxv4i64_nxv4i64( %0, %1, %2, %3, iXLen %4) nounwind { ; CHECK-LABEL: intrinsic_vmsne_mask_vv_nxv4i64_nxv4i64: ; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vmv1r.v v20, v0 ; CHECK-NEXT: vsetvli zero, a0, e64, m4, ta, mu -; CHECK-NEXT: vmsne.vv v20, v8, v12 -; CHECK-NEXT: vmv1r.v v8, v0 +; CHECK-NEXT: vmsne.vv v0, v8, v12 +; CHECK-NEXT: vmsne.vv v20, v12, v16, v0.t ; CHECK-NEXT: vmv1r.v v0, v20 -; CHECK-NEXT: vmsne.vv v8, v12, v16, v0.t -; CHECK-NEXT: vmv1r.v v0, v8 ; CHECK-NEXT: ret entry: %mask = call @llvm.riscv.vmsne.nxv4i64( diff --git a/llvm/test/CodeGen/RISCV/rvv/vreductions-int-vp.ll b/llvm/test/CodeGen/RISCV/rvv/vreductions-int-vp.ll index 618e169e1f9654651a9f7b72903ead10e3be1792..7bcf37b1af3c8fabd1d2b31ec26698d95f7f7cf8 100644 --- a/llvm/test/CodeGen/RISCV/rvv/vreductions-int-vp.ll +++ b/llvm/test/CodeGen/RISCV/rvv/vreductions-int-vp.ll @@ -841,24 +841,14 @@ define signext i32 @vpreduce_add_nxv1i32(i32 signext %s, %v, declare i32 @llvm.vp.reduce.umax.nxv1i32(i32, , , i32) define signext i32 @vpreduce_umax_nxv1i32(i32 signext %s, %v, %m, i32 zeroext %evl) { -; RV32-LABEL: vpreduce_umax_nxv1i32: -; RV32: # %bb.0: -; RV32-NEXT: vsetivli zero, 1, e32, m1, ta, ma -; RV32-NEXT: vmv.s.x v9, a0 -; RV32-NEXT: vsetvli zero, a1, e32, mf2, ta, ma -; RV32-NEXT: vredmaxu.vs v9, v8, v9, v0.t -; RV32-NEXT: vmv.x.s a0, v9 -; RV32-NEXT: ret -; -; RV64-LABEL: vpreduce_umax_nxv1i32: -; RV64: # %bb.0: -; RV64-NEXT: andi a0, a0, -1 -; RV64-NEXT: vsetivli zero, 1, e32, m1, ta, ma -; RV64-NEXT: vmv.s.x v9, a0 -; RV64-NEXT: vsetvli zero, a1, e32, mf2, ta, ma -; RV64-NEXT: vredmaxu.vs v9, v8, v9, v0.t -; RV64-NEXT: vmv.x.s a0, v9 -; RV64-NEXT: ret +; CHECK-LABEL: vpreduce_umax_nxv1i32: +; CHECK: # %bb.0: +; CHECK-NEXT: vsetivli zero, 1, e32, m1, ta, ma +; CHECK-NEXT: vmv.s.x v9, a0 +; CHECK-NEXT: vsetvli zero, a1, e32, mf2, ta, ma +; CHECK-NEXT: vredmaxu.vs v9, v8, v9, v0.t +; CHECK-NEXT: vmv.x.s a0, v9 +; CHECK-NEXT: ret %r = call i32 @llvm.vp.reduce.umax.nxv1i32(i32 %s, %v, %m, i32 %evl) ret i32 %r } @@ -881,24 +871,14 @@ define signext i32 @vpreduce_smax_nxv1i32(i32 signext %s, %v, declare i32 @llvm.vp.reduce.umin.nxv1i32(i32, , , i32) define signext i32 @vpreduce_umin_nxv1i32(i32 signext %s, %v, %m, i32 zeroext %evl) { -; RV32-LABEL: vpreduce_umin_nxv1i32: -; RV32: # %bb.0: -; RV32-NEXT: vsetivli zero, 1, e32, m1, ta, ma -; RV32-NEXT: vmv.s.x v9, a0 -; RV32-NEXT: vsetvli zero, a1, e32, mf2, ta, ma -; RV32-NEXT: vredminu.vs v9, v8, v9, v0.t -; RV32-NEXT: vmv.x.s a0, v9 -; RV32-NEXT: ret -; -; RV64-LABEL: vpreduce_umin_nxv1i32: -; RV64: # %bb.0: -; RV64-NEXT: andi a0, a0, -1 -; RV64-NEXT: vsetivli zero, 1, e32, m1, ta, ma -; RV64-NEXT: vmv.s.x v9, a0 -; RV64-NEXT: vsetvli zero, a1, e32, mf2, ta, ma -; RV64-NEXT: vredminu.vs v9, v8, v9, v0.t -; RV64-NEXT: vmv.x.s a0, v9 -; RV64-NEXT: ret +; CHECK-LABEL: vpreduce_umin_nxv1i32: +; CHECK: # %bb.0: +; CHECK-NEXT: vsetivli zero, 1, e32, m1, ta, ma +; CHECK-NEXT: vmv.s.x v9, a0 +; CHECK-NEXT: vsetvli zero, a1, e32, mf2, ta, ma +; CHECK-NEXT: vredminu.vs v9, v8, v9, v0.t +; CHECK-NEXT: vmv.x.s a0, v9 +; CHECK-NEXT: ret %r = call i32 @llvm.vp.reduce.umin.nxv1i32(i32 %s, %v, %m, i32 %evl) ret i32 %r } @@ -981,24 +961,14 @@ define signext i32 @vpreduce_add_nxv2i32(i32 signext %s, %v, declare i32 @llvm.vp.reduce.umax.nxv2i32(i32, , , i32) define signext i32 @vpreduce_umax_nxv2i32(i32 signext %s, %v, %m, i32 zeroext %evl) { -; RV32-LABEL: vpreduce_umax_nxv2i32: -; RV32: # %bb.0: -; RV32-NEXT: vsetivli zero, 1, e32, m1, ta, ma -; RV32-NEXT: vmv.s.x v9, a0 -; RV32-NEXT: vsetvli zero, a1, e32, m1, ta, ma -; RV32-NEXT: vredmaxu.vs v9, v8, v9, v0.t -; RV32-NEXT: vmv.x.s a0, v9 -; RV32-NEXT: ret -; -; RV64-LABEL: vpreduce_umax_nxv2i32: -; RV64: # %bb.0: -; RV64-NEXT: andi a0, a0, -1 -; RV64-NEXT: vsetivli zero, 1, e32, m1, ta, ma -; RV64-NEXT: vmv.s.x v9, a0 -; RV64-NEXT: vsetvli zero, a1, e32, m1, ta, ma -; RV64-NEXT: vredmaxu.vs v9, v8, v9, v0.t -; RV64-NEXT: vmv.x.s a0, v9 -; RV64-NEXT: ret +; CHECK-LABEL: vpreduce_umax_nxv2i32: +; CHECK: # %bb.0: +; CHECK-NEXT: vsetivli zero, 1, e32, m1, ta, ma +; CHECK-NEXT: vmv.s.x v9, a0 +; CHECK-NEXT: vsetvli zero, a1, e32, m1, ta, ma +; CHECK-NEXT: vredmaxu.vs v9, v8, v9, v0.t +; CHECK-NEXT: vmv.x.s a0, v9 +; CHECK-NEXT: ret %r = call i32 @llvm.vp.reduce.umax.nxv2i32(i32 %s, %v, %m, i32 %evl) ret i32 %r } @@ -1021,24 +991,14 @@ define signext i32 @vpreduce_smax_nxv2i32(i32 signext %s, %v, declare i32 @llvm.vp.reduce.umin.nxv2i32(i32, , , i32) define signext i32 @vpreduce_umin_nxv2i32(i32 signext %s, %v, %m, i32 zeroext %evl) { -; RV32-LABEL: vpreduce_umin_nxv2i32: -; RV32: # %bb.0: -; RV32-NEXT: vsetivli zero, 1, e32, m1, ta, ma -; RV32-NEXT: vmv.s.x v9, a0 -; RV32-NEXT: vsetvli zero, a1, e32, m1, ta, ma -; RV32-NEXT: vredminu.vs v9, v8, v9, v0.t -; RV32-NEXT: vmv.x.s a0, v9 -; RV32-NEXT: ret -; -; RV64-LABEL: vpreduce_umin_nxv2i32: -; RV64: # %bb.0: -; RV64-NEXT: andi a0, a0, -1 -; RV64-NEXT: vsetivli zero, 1, e32, m1, ta, ma -; RV64-NEXT: vmv.s.x v9, a0 -; RV64-NEXT: vsetvli zero, a1, e32, m1, ta, ma -; RV64-NEXT: vredminu.vs v9, v8, v9, v0.t -; RV64-NEXT: vmv.x.s a0, v9 -; RV64-NEXT: ret +; CHECK-LABEL: vpreduce_umin_nxv2i32: +; CHECK: # %bb.0: +; CHECK-NEXT: vsetivli zero, 1, e32, m1, ta, ma +; CHECK-NEXT: vmv.s.x v9, a0 +; CHECK-NEXT: vsetvli zero, a1, e32, m1, ta, ma +; CHECK-NEXT: vredminu.vs v9, v8, v9, v0.t +; CHECK-NEXT: vmv.x.s a0, v9 +; CHECK-NEXT: ret %r = call i32 @llvm.vp.reduce.umin.nxv2i32(i32 %s, %v, %m, i32 %evl) ret i32 %r } @@ -1121,24 +1081,14 @@ define signext i32 @vpreduce_add_nxv4i32(i32 signext %s, %v, declare i32 @llvm.vp.reduce.umax.nxv4i32(i32, , , i32) define signext i32 @vpreduce_umax_nxv4i32(i32 signext %s, %v, %m, i32 zeroext %evl) { -; RV32-LABEL: vpreduce_umax_nxv4i32: -; RV32: # %bb.0: -; RV32-NEXT: vsetivli zero, 1, e32, m1, ta, ma -; RV32-NEXT: vmv.s.x v10, a0 -; RV32-NEXT: vsetvli zero, a1, e32, m2, ta, ma -; RV32-NEXT: vredmaxu.vs v10, v8, v10, v0.t -; RV32-NEXT: vmv.x.s a0, v10 -; RV32-NEXT: ret -; -; RV64-LABEL: vpreduce_umax_nxv4i32: -; RV64: # %bb.0: -; RV64-NEXT: andi a0, a0, -1 -; RV64-NEXT: vsetivli zero, 1, e32, m1, ta, ma -; RV64-NEXT: vmv.s.x v10, a0 -; RV64-NEXT: vsetvli zero, a1, e32, m2, ta, ma -; RV64-NEXT: vredmaxu.vs v10, v8, v10, v0.t -; RV64-NEXT: vmv.x.s a0, v10 -; RV64-NEXT: ret +; CHECK-LABEL: vpreduce_umax_nxv4i32: +; CHECK: # %bb.0: +; CHECK-NEXT: vsetivli zero, 1, e32, m1, ta, ma +; CHECK-NEXT: vmv.s.x v10, a0 +; CHECK-NEXT: vsetvli zero, a1, e32, m2, ta, ma +; CHECK-NEXT: vredmaxu.vs v10, v8, v10, v0.t +; CHECK-NEXT: vmv.x.s a0, v10 +; CHECK-NEXT: ret %r = call i32 @llvm.vp.reduce.umax.nxv4i32(i32 %s, %v, %m, i32 %evl) ret i32 %r } @@ -1146,56 +1096,30 @@ define signext i32 @vpreduce_umax_nxv4i32(i32 signext %s, %v, declare i32 @llvm.vp.reduce.umax.nxv32i32(i32, , , i32) define signext i32 @vpreduce_umax_nxv32i32(i32 signext %s, %v, %m, i32 zeroext %evl) { -; RV32-LABEL: vpreduce_umax_nxv32i32: -; RV32: # %bb.0: -; RV32-NEXT: csrr a3, vlenb -; RV32-NEXT: srli a2, a3, 2 -; RV32-NEXT: vsetvli a4, zero, e8, mf2, ta, ma -; RV32-NEXT: vslidedown.vx v24, v0, a2 -; RV32-NEXT: slli a3, a3, 1 -; RV32-NEXT: sub a2, a1, a3 -; RV32-NEXT: sltu a4, a1, a2 -; RV32-NEXT: addi a4, a4, -1 -; RV32-NEXT: and a2, a4, a2 -; RV32-NEXT: bltu a1, a3, .LBB67_2 -; RV32-NEXT: # %bb.1: -; RV32-NEXT: mv a1, a3 -; RV32-NEXT: .LBB67_2: -; RV32-NEXT: vsetvli zero, zero, e32, m2, ta, ma -; RV32-NEXT: vmv.s.x v25, a0 -; RV32-NEXT: vsetvli zero, a1, e32, m8, ta, ma -; RV32-NEXT: vredmaxu.vs v25, v8, v25, v0.t -; RV32-NEXT: vsetvli zero, a2, e32, m8, ta, ma -; RV32-NEXT: vmv1r.v v0, v24 -; RV32-NEXT: vredmaxu.vs v25, v16, v25, v0.t -; RV32-NEXT: vmv.x.s a0, v25 -; RV32-NEXT: ret -; -; RV64-LABEL: vpreduce_umax_nxv32i32: -; RV64: # %bb.0: -; RV64-NEXT: csrr a3, vlenb -; RV64-NEXT: srli a2, a3, 2 -; RV64-NEXT: vsetvli a4, zero, e8, mf2, ta, ma -; RV64-NEXT: vslidedown.vx v24, v0, a2 -; RV64-NEXT: andi a2, a0, -1 -; RV64-NEXT: slli a3, a3, 1 -; RV64-NEXT: sub a0, a1, a3 -; RV64-NEXT: sltu a4, a1, a0 -; RV64-NEXT: addi a4, a4, -1 -; RV64-NEXT: and a0, a4, a0 -; RV64-NEXT: bltu a1, a3, .LBB67_2 -; RV64-NEXT: # %bb.1: -; RV64-NEXT: mv a1, a3 -; RV64-NEXT: .LBB67_2: -; RV64-NEXT: vsetvli zero, zero, e32, m2, ta, ma -; RV64-NEXT: vmv.s.x v25, a2 -; RV64-NEXT: vsetvli zero, a1, e32, m8, ta, ma -; RV64-NEXT: vredmaxu.vs v25, v8, v25, v0.t -; RV64-NEXT: vsetvli zero, a0, e32, m8, ta, ma -; RV64-NEXT: vmv1r.v v0, v24 -; RV64-NEXT: vredmaxu.vs v25, v16, v25, v0.t -; RV64-NEXT: vmv.x.s a0, v25 -; RV64-NEXT: ret +; CHECK-LABEL: vpreduce_umax_nxv32i32: +; CHECK: # %bb.0: +; CHECK-NEXT: csrr a3, vlenb +; CHECK-NEXT: srli a2, a3, 2 +; CHECK-NEXT: vsetvli a4, zero, e8, mf2, ta, ma +; CHECK-NEXT: vslidedown.vx v24, v0, a2 +; CHECK-NEXT: slli a3, a3, 1 +; CHECK-NEXT: sub a2, a1, a3 +; CHECK-NEXT: sltu a4, a1, a2 +; CHECK-NEXT: addi a4, a4, -1 +; CHECK-NEXT: and a2, a4, a2 +; CHECK-NEXT: bltu a1, a3, .LBB67_2 +; CHECK-NEXT: # %bb.1: +; CHECK-NEXT: mv a1, a3 +; CHECK-NEXT: .LBB67_2: +; CHECK-NEXT: vsetvli zero, zero, e32, m2, ta, ma +; CHECK-NEXT: vmv.s.x v25, a0 +; CHECK-NEXT: vsetvli zero, a1, e32, m8, ta, ma +; CHECK-NEXT: vredmaxu.vs v25, v8, v25, v0.t +; CHECK-NEXT: vsetvli zero, a2, e32, m8, ta, ma +; CHECK-NEXT: vmv1r.v v0, v24 +; CHECK-NEXT: vredmaxu.vs v25, v16, v25, v0.t +; CHECK-NEXT: vmv.x.s a0, v25 +; CHECK-NEXT: ret %r = call i32 @llvm.vp.reduce.umax.nxv32i32(i32 %s, %v, %m, i32 %evl) ret i32 %r } @@ -1218,24 +1142,14 @@ define signext i32 @vpreduce_smax_nxv4i32(i32 signext %s, %v, declare i32 @llvm.vp.reduce.umin.nxv4i32(i32, , , i32) define signext i32 @vpreduce_umin_nxv4i32(i32 signext %s, %v, %m, i32 zeroext %evl) { -; RV32-LABEL: vpreduce_umin_nxv4i32: -; RV32: # %bb.0: -; RV32-NEXT: vsetivli zero, 1, e32, m1, ta, ma -; RV32-NEXT: vmv.s.x v10, a0 -; RV32-NEXT: vsetvli zero, a1, e32, m2, ta, ma -; RV32-NEXT: vredminu.vs v10, v8, v10, v0.t -; RV32-NEXT: vmv.x.s a0, v10 -; RV32-NEXT: ret -; -; RV64-LABEL: vpreduce_umin_nxv4i32: -; RV64: # %bb.0: -; RV64-NEXT: andi a0, a0, -1 -; RV64-NEXT: vsetivli zero, 1, e32, m1, ta, ma -; RV64-NEXT: vmv.s.x v10, a0 -; RV64-NEXT: vsetvli zero, a1, e32, m2, ta, ma -; RV64-NEXT: vredminu.vs v10, v8, v10, v0.t -; RV64-NEXT: vmv.x.s a0, v10 -; RV64-NEXT: ret +; CHECK-LABEL: vpreduce_umin_nxv4i32: +; CHECK: # %bb.0: +; CHECK-NEXT: vsetivli zero, 1, e32, m1, ta, ma +; CHECK-NEXT: vmv.s.x v10, a0 +; CHECK-NEXT: vsetvli zero, a1, e32, m2, ta, ma +; CHECK-NEXT: vredminu.vs v10, v8, v10, v0.t +; CHECK-NEXT: vmv.x.s a0, v10 +; CHECK-NEXT: ret %r = call i32 @llvm.vp.reduce.umin.nxv4i32(i32 %s, %v, %m, i32 %evl) ret i32 %r } diff --git a/llvm/test/CodeGen/RISCV/rvv/vsetvli-insert-crossbb.ll b/llvm/test/CodeGen/RISCV/rvv/vsetvli-insert-crossbb.ll index 621445fb2dc5e40e1a548da3789589fc70af562b..4ff2fc7a5fff5db485580f64bb7dd07c68c78f35 100644 --- a/llvm/test/CodeGen/RISCV/rvv/vsetvli-insert-crossbb.ll +++ b/llvm/test/CodeGen/RISCV/rvv/vsetvli-insert-crossbb.ll @@ -487,6 +487,54 @@ for.end: ; preds = %for.body, %entry ret void } +define void @saxpy_vec_demanded_fields(i64 %n, float %a, ptr nocapture readonly %x, ptr nocapture %y) { +; CHECK-LABEL: saxpy_vec_demanded_fields: +; CHECK: # %bb.0: # %entry +; CHECK-NEXT: vsetvli a3, a0, e32, m8, ta, ma +; CHECK-NEXT: beqz a3, .LBB9_2 +; CHECK-NEXT: .LBB9_1: # %for.body +; CHECK-NEXT: # =>This Inner Loop Header: Depth=1 +; CHECK-NEXT: vsetvli zero, a3, e32, m8, ta, ma +; CHECK-NEXT: vle32.v v8, (a1) +; CHECK-NEXT: vle32.v v16, (a2) +; CHECK-NEXT: slli a4, a3, 2 +; CHECK-NEXT: add a1, a1, a4 +; CHECK-NEXT: vsetvli zero, zero, e32, m8, tu, ma +; CHECK-NEXT: vfmacc.vf v16, fa0, v8 +; CHECK-NEXT: vse32.v v16, (a2) +; CHECK-NEXT: sub a0, a0, a3 +; CHECK-NEXT: vsetvli a3, a0, e16, m4, ta, ma +; CHECK-NEXT: add a2, a2, a4 +; CHECK-NEXT: bnez a3, .LBB9_1 +; CHECK-NEXT: .LBB9_2: # %for.end +; CHECK-NEXT: ret +entry: + %0 = tail call i64 @llvm.riscv.vsetvli.i64(i64 %n, i64 2, i64 3) + %cmp.not13 = icmp eq i64 %0, 0 + br i1 %cmp.not13, label %for.end, label %for.body + +for.body: ; preds = %for.body, %entry + %1 = phi i64 [ %7, %for.body ], [ %0, %entry ] + %n.addr.016 = phi i64 [ %sub, %for.body ], [ %n, %entry ] + %x.addr.015 = phi ptr [ %add.ptr, %for.body ], [ %x, %entry ] + %y.addr.014 = phi ptr [ %add.ptr1, %for.body ], [ %y, %entry ] + %2 = bitcast ptr %x.addr.015 to ptr + %3 = tail call @llvm.riscv.vle.nxv16f32.i64( undef, ptr %2, i64 %1) + %add.ptr = getelementptr inbounds float, ptr %x.addr.015, i64 %1 + %4 = bitcast ptr %y.addr.014 to ptr + %5 = tail call @llvm.riscv.vle.nxv16f32.i64( undef, ptr %4, i64 %1) + %6 = tail call @llvm.riscv.vfmacc.nxv16f32.f32.i64( %5, float %a, %3, i64 7, i64 %1, i64 0) + tail call void @llvm.riscv.vse.nxv16f32.i64( %6, ptr %4, i64 %1) + %add.ptr1 = getelementptr inbounds float, ptr %y.addr.014, i64 %1 + %sub = sub i64 %n.addr.016, %1 + %7 = tail call i64 @llvm.riscv.vsetvli.i64(i64 %sub, i64 1, i64 2) + %cmp.not = icmp eq i64 %7, 0 + br i1 %cmp.not, label %for.end, label %for.body + +for.end: ; preds = %for.body, %entry + ret void +} + declare i64 @llvm.riscv.vsetvli.i64(i64, i64 immarg, i64 immarg) declare @llvm.riscv.vle.nxv16f32.i64(, ptr nocapture, i64) declare @llvm.riscv.vfmacc.nxv16f32.f32.i64(, float, , i64, i64, i64) @@ -501,12 +549,12 @@ define @test_vsetvli_x0_x0(ptr %x, ptr %y, ; CHECK-NEXT: vsetvli zero, a2, e32, m1, ta, ma ; CHECK-NEXT: vle32.v v9, (a0) ; CHECK-NEXT: andi a3, a3, 1 -; CHECK-NEXT: beqz a3, .LBB9_2 +; CHECK-NEXT: beqz a3, .LBB10_2 ; CHECK-NEXT: # %bb.1: # %if ; CHECK-NEXT: vle16.v v10, (a1) ; CHECK-NEXT: vsetvli zero, zero, e16, mf2, ta, ma ; CHECK-NEXT: vwcvt.x.x.v v8, v10 -; CHECK-NEXT: .LBB9_2: # %if.end +; CHECK-NEXT: .LBB10_2: # %if.end ; CHECK-NEXT: vsetvli zero, zero, e32, m1, ta, ma ; CHECK-NEXT: vadd.vv v8, v9, v8 ; CHECK-NEXT: ret @@ -540,19 +588,19 @@ define @test_vsetvli_x0_x0_2(ptr %x, ptr %y, ptr %z, i64 %vl, ; CHECK-NEXT: vsetvli zero, a3, e32, m1, ta, ma ; CHECK-NEXT: vle32.v v9, (a0) ; CHECK-NEXT: andi a4, a4, 1 -; CHECK-NEXT: beqz a4, .LBB10_2 +; CHECK-NEXT: beqz a4, .LBB11_2 ; CHECK-NEXT: # %bb.1: # %if ; CHECK-NEXT: vle16.v v10, (a1) ; CHECK-NEXT: vsetvli zero, zero, e16, mf2, ta, ma ; CHECK-NEXT: vwadd.wv v9, v9, v10 -; CHECK-NEXT: .LBB10_2: # %if.end +; CHECK-NEXT: .LBB11_2: # %if.end ; CHECK-NEXT: andi a5, a5, 1 -; CHECK-NEXT: beqz a5, .LBB10_4 +; CHECK-NEXT: beqz a5, .LBB11_4 ; CHECK-NEXT: # %bb.3: # %if2 ; CHECK-NEXT: vsetvli zero, zero, e16, mf2, ta, ma ; CHECK-NEXT: vle16.v v10, (a2) ; CHECK-NEXT: vwadd.wv v9, v9, v10 -; CHECK-NEXT: .LBB10_4: # %if2.end +; CHECK-NEXT: .LBB11_4: # %if2.end ; CHECK-NEXT: vsetvli zero, zero, e32, m1, ta, ma ; CHECK-NEXT: vadd.vv v8, v9, v8 ; CHECK-NEXT: ret @@ -586,11 +634,11 @@ define void @vlmax(i64 %N, ptr %c, ptr %a, ptr %b) { ; CHECK-LABEL: vlmax: ; CHECK: # %bb.0: # %entry ; CHECK-NEXT: vsetvli a6, zero, e64, m1, ta, ma -; CHECK-NEXT: blez a0, .LBB11_3 +; CHECK-NEXT: blez a0, .LBB12_3 ; CHECK-NEXT: # %bb.1: # %for.body.preheader ; CHECK-NEXT: li a5, 0 ; CHECK-NEXT: slli a4, a6, 3 -; CHECK-NEXT: .LBB11_2: # %for.body +; CHECK-NEXT: .LBB12_2: # %for.body ; CHECK-NEXT: # =>This Inner Loop Header: Depth=1 ; CHECK-NEXT: vle64.v v8, (a2) ; CHECK-NEXT: vle64.v v9, (a3) @@ -600,8 +648,8 @@ define void @vlmax(i64 %N, ptr %c, ptr %a, ptr %b) { ; CHECK-NEXT: add a1, a1, a4 ; CHECK-NEXT: add a3, a3, a4 ; CHECK-NEXT: add a2, a2, a4 -; CHECK-NEXT: blt a5, a0, .LBB11_2 -; CHECK-NEXT: .LBB11_3: # %for.end +; CHECK-NEXT: blt a5, a0, .LBB12_2 +; CHECK-NEXT: .LBB12_3: # %for.end ; CHECK-NEXT: ret entry: %0 = tail call i64 @llvm.riscv.vsetvlimax.i64(i64 3, i64 0) @@ -633,18 +681,18 @@ define void @vector_init_vlmax(i64 %N, ptr %c) { ; CHECK-LABEL: vector_init_vlmax: ; CHECK: # %bb.0: # %entry ; CHECK-NEXT: vsetvli a2, zero, e64, m1, ta, ma -; CHECK-NEXT: blez a0, .LBB12_3 +; CHECK-NEXT: blez a0, .LBB13_3 ; CHECK-NEXT: # %bb.1: # %for.body.preheader ; CHECK-NEXT: li a3, 0 ; CHECK-NEXT: slli a4, a2, 3 ; CHECK-NEXT: vmv.v.i v8, 0 -; CHECK-NEXT: .LBB12_2: # %for.body +; CHECK-NEXT: .LBB13_2: # %for.body ; CHECK-NEXT: # =>This Inner Loop Header: Depth=1 ; CHECK-NEXT: vse64.v v8, (a1) ; CHECK-NEXT: add a3, a3, a2 ; CHECK-NEXT: add a1, a1, a4 -; CHECK-NEXT: blt a3, a0, .LBB12_2 -; CHECK-NEXT: .LBB12_3: # %for.end +; CHECK-NEXT: blt a3, a0, .LBB13_2 +; CHECK-NEXT: .LBB13_3: # %for.end ; CHECK-NEXT: ret entry: %0 = tail call i64 @llvm.riscv.vsetvlimax.i64(i64 3, i64 0) @@ -669,20 +717,20 @@ define void @vector_init_vsetvli_N(i64 %N, ptr %c) { ; CHECK-LABEL: vector_init_vsetvli_N: ; CHECK: # %bb.0: # %entry ; CHECK-NEXT: vsetvli a2, a0, e64, m1, ta, ma -; CHECK-NEXT: blez a0, .LBB13_3 +; CHECK-NEXT: blez a0, .LBB14_3 ; CHECK-NEXT: # %bb.1: # %for.body.preheader ; CHECK-NEXT: li a3, 0 ; CHECK-NEXT: slli a4, a2, 3 ; CHECK-NEXT: vsetvli a5, zero, e64, m1, ta, ma ; CHECK-NEXT: vmv.v.i v8, 0 -; CHECK-NEXT: .LBB13_2: # %for.body +; CHECK-NEXT: .LBB14_2: # %for.body ; CHECK-NEXT: # =>This Inner Loop Header: Depth=1 ; CHECK-NEXT: vsetvli zero, a2, e64, m1, ta, ma ; CHECK-NEXT: vse64.v v8, (a1) ; CHECK-NEXT: add a3, a3, a2 ; CHECK-NEXT: add a1, a1, a4 -; CHECK-NEXT: blt a3, a0, .LBB13_2 -; CHECK-NEXT: .LBB13_3: # %for.end +; CHECK-NEXT: blt a3, a0, .LBB14_2 +; CHECK-NEXT: .LBB14_3: # %for.end ; CHECK-NEXT: ret entry: %0 = tail call i64 @llvm.riscv.vsetvli(i64 %N, i64 3, i64 0) @@ -711,13 +759,13 @@ define void @vector_init_vsetvli_fv(i64 %N, ptr %c) { ; CHECK-NEXT: slli a4, a3, 3 ; CHECK-NEXT: vsetvli a5, zero, e64, m1, ta, ma ; CHECK-NEXT: vmv.v.i v8, 0 -; CHECK-NEXT: .LBB14_1: # %for.body +; CHECK-NEXT: .LBB15_1: # %for.body ; CHECK-NEXT: # =>This Inner Loop Header: Depth=1 ; CHECK-NEXT: vsetivli zero, 4, e64, m1, ta, ma ; CHECK-NEXT: vse64.v v8, (a1) ; CHECK-NEXT: add a2, a2, a3 ; CHECK-NEXT: add a1, a1, a4 -; CHECK-NEXT: blt a2, a0, .LBB14_1 +; CHECK-NEXT: blt a2, a0, .LBB15_1 ; CHECK-NEXT: # %bb.2: # %for.end ; CHECK-NEXT: ret entry: @@ -745,13 +793,13 @@ define void @vector_init_vsetvli_fv2(i64 %N, ptr %c) { ; CHECK-NEXT: li a2, 0 ; CHECK-NEXT: vsetvli a3, zero, e64, m1, ta, ma ; CHECK-NEXT: vmv.v.i v8, 0 -; CHECK-NEXT: .LBB15_1: # %for.body +; CHECK-NEXT: .LBB16_1: # %for.body ; CHECK-NEXT: # =>This Inner Loop Header: Depth=1 ; CHECK-NEXT: vsetivli zero, 4, e64, m1, ta, ma ; CHECK-NEXT: vse64.v v8, (a1) ; CHECK-NEXT: addi a2, a2, 4 ; CHECK-NEXT: addi a1, a1, 32 -; CHECK-NEXT: blt a2, a0, .LBB15_1 +; CHECK-NEXT: blt a2, a0, .LBB16_1 ; CHECK-NEXT: # %bb.2: # %for.end ; CHECK-NEXT: ret entry: @@ -779,13 +827,13 @@ define void @vector_init_vsetvli_fv3(i64 %N, ptr %c) { ; CHECK-NEXT: li a2, 0 ; CHECK-NEXT: vsetvli a3, zero, e64, m1, ta, ma ; CHECK-NEXT: vmv.v.i v8, 0 -; CHECK-NEXT: .LBB16_1: # %for.body +; CHECK-NEXT: .LBB17_1: # %for.body ; CHECK-NEXT: # =>This Inner Loop Header: Depth=1 ; CHECK-NEXT: vsetivli zero, 4, e64, m1, ta, ma ; CHECK-NEXT: vse64.v v8, (a1) ; CHECK-NEXT: addi a2, a2, 4 ; CHECK-NEXT: addi a1, a1, 32 -; CHECK-NEXT: blt a2, a0, .LBB16_1 +; CHECK-NEXT: blt a2, a0, .LBB17_1 ; CHECK-NEXT: # %bb.2: # %for.end ; CHECK-NEXT: ret entry: @@ -861,10 +909,10 @@ define @compat_store_consistency(i1 %cond, %a, %b @@ -886,16 +934,16 @@ define @test_ratio_only_vmv_s_x(ptr %x, ptr %y, i1 %cond) nou ; CHECK-LABEL: test_ratio_only_vmv_s_x: ; CHECK: # %bb.0: # %entry ; CHECK-NEXT: andi a2, a2, 1 -; CHECK-NEXT: beqz a2, .LBB20_2 +; CHECK-NEXT: beqz a2, .LBB21_2 ; CHECK-NEXT: # %bb.1: # %if ; CHECK-NEXT: vsetivli zero, 2, e16, mf2, ta, ma ; CHECK-NEXT: vle16.v v9, (a1) ; CHECK-NEXT: vwcvt.x.x.v v8, v9 -; CHECK-NEXT: j .LBB20_3 -; CHECK-NEXT: .LBB20_2: +; CHECK-NEXT: j .LBB21_3 +; CHECK-NEXT: .LBB21_2: ; CHECK-NEXT: vsetivli zero, 2, e32, m1, ta, ma ; CHECK-NEXT: vle32.v v8, (a0) -; CHECK-NEXT: .LBB20_3: # %if.end +; CHECK-NEXT: .LBB21_3: # %if.end ; CHECK-NEXT: vsetvli zero, zero, e32, m1, tu, ma ; CHECK-NEXT: vmv.s.x v8, zero ; CHECK-NEXT: ret @@ -918,16 +966,16 @@ define @test_ratio_only_vmv_s_x2(ptr %x, ptr %y, i1 %cond) no ; CHECK-LABEL: test_ratio_only_vmv_s_x2: ; CHECK: # %bb.0: # %entry ; CHECK-NEXT: andi a2, a2, 1 -; CHECK-NEXT: beqz a2, .LBB21_2 +; CHECK-NEXT: beqz a2, .LBB22_2 ; CHECK-NEXT: # %bb.1: # %if ; CHECK-NEXT: vsetivli zero, 2, e32, m1, ta, ma ; CHECK-NEXT: vle32.v v8, (a0) -; CHECK-NEXT: j .LBB21_3 -; CHECK-NEXT: .LBB21_2: +; CHECK-NEXT: j .LBB22_3 +; CHECK-NEXT: .LBB22_2: ; CHECK-NEXT: vsetivli zero, 2, e16, mf2, ta, ma ; CHECK-NEXT: vle16.v v9, (a1) ; CHECK-NEXT: vwcvt.x.x.v v8, v9 -; CHECK-NEXT: .LBB21_3: # %if.end +; CHECK-NEXT: .LBB22_3: # %if.end ; CHECK-NEXT: vsetvli zero, zero, e32, m1, tu, ma ; CHECK-NEXT: vmv.s.x v8, zero ; CHECK-NEXT: ret @@ -953,13 +1001,13 @@ define void @pre_over_vle(ptr %A) { ; CHECK: # %bb.0: # %entry ; CHECK-NEXT: addi a1, a0, 800 ; CHECK-NEXT: vsetivli zero, 2, e32, mf2, ta, ma -; CHECK-NEXT: .LBB22_1: # %vector.body +; CHECK-NEXT: .LBB23_1: # %vector.body ; CHECK-NEXT: # =>This Inner Loop Header: Depth=1 ; CHECK-NEXT: vle8.v v8, (a0) ; CHECK-NEXT: vsext.vf4 v9, v8 ; CHECK-NEXT: vse32.v v9, (a0) ; CHECK-NEXT: addi a0, a0, 8 -; CHECK-NEXT: bne a0, a1, .LBB22_1 +; CHECK-NEXT: bne a0, a1, .LBB23_1 ; CHECK-NEXT: # %bb.2: # %exit ; CHECK-NEXT: ret entry: diff --git a/llvm/test/CodeGen/RISCV/rvv/vsetvli-insert-crossbb.mir b/llvm/test/CodeGen/RISCV/rvv/vsetvli-insert-crossbb.mir index fdcce72a01eb3df1003f58ea2dd638133df867a0..16c4a1a0a89ec28742d51abd2c5e73641d89a4b5 100644 --- a/llvm/test/CodeGen/RISCV/rvv/vsetvli-insert-crossbb.mir +++ b/llvm/test/CodeGen/RISCV/rvv/vsetvli-insert-crossbb.mir @@ -130,6 +130,10 @@ ret void } + define void @pre_undemanded_vl() { + ret void + } + declare i32 @llvm.vector.reduce.add.v4i32(<4 x i32>) declare @llvm.riscv.vadd.nxv1i64.nxv1i64.i64(, , , i64) #1 @@ -517,10 +521,10 @@ body: | ; CHECK-NEXT: [[COPY1:%[0-9]+]]:gpr = COPY $x10 ; CHECK-NEXT: [[DEF:%[0-9]+]]:gpr = IMPLICIT_DEF ; CHECK-NEXT: %pt:vr = IMPLICIT_DEF - ; CHECK-NEXT: dead [[PseudoVSETVLIX0_:%[0-9]+]]:gpr = PseudoVSETVLIX0 $x0, 223 /* e64, mf2, ta, ma */, implicit-def $vl, implicit-def $vtype + ; CHECK-NEXT: dead [[PseudoVSETVLIX0_:%[0-9]+]]:gpr = PseudoVSETVLIX0 killed $x0, 223 /* e64, mf2, ta, ma */, implicit-def $vl, implicit-def $vtype ; CHECK-NEXT: [[PseudoVID_V_MF2_:%[0-9]+]]:vr = PseudoVID_V_MF2 %pt, -1, 6 /* e64 */, 0 /* tu, mu */, implicit $vl, implicit $vtype ; CHECK-NEXT: %pt2:vr = IMPLICIT_DEF - ; CHECK-NEXT: dead [[PseudoVSETVLIX0_1:%[0-9]+]]:gpr = PseudoVSETVLIX0 $x0, 215 /* e32, mf2, ta, ma */, implicit-def $vl, implicit-def $vtype + ; CHECK-NEXT: dead [[PseudoVSETVLIX0_1:%[0-9]+]]:gpr = PseudoVSETVLIX0 killed $x0, 215 /* e32, mf2, ta, ma */, implicit-def $vl, implicit-def $vtype ; CHECK-NEXT: [[PseudoVMV_V_I_MF2_:%[0-9]+]]:vrnov0 = PseudoVMV_V_I_MF2 %pt2, 0, -1, 5 /* e32 */, 0 /* tu, mu */, implicit $vl, implicit $vtype ; CHECK-NEXT: {{ $}} ; CHECK-NEXT: bb.1: @@ -609,7 +613,7 @@ body: | ; CHECK-NEXT: [[SRLI:%[0-9]+]]:gpr = SRLI [[PseudoReadVLENB]], 3 ; CHECK-NEXT: [[COPY1:%[0-9]+]]:gpr = COPY $x11 ; CHECK-NEXT: %pt:vr = IMPLICIT_DEF - ; CHECK-NEXT: dead [[PseudoVSETVLIX0_:%[0-9]+]]:gpr = PseudoVSETVLIX0 $x0, 216 /* e64, m1, ta, ma */, implicit-def $vl, implicit-def $vtype + ; CHECK-NEXT: dead [[PseudoVSETVLIX0_:%[0-9]+]]:gpr = PseudoVSETVLIX0 killed $x0, 216 /* e64, m1, ta, ma */, implicit-def $vl, implicit-def $vtype ; CHECK-NEXT: [[PseudoVID_V_M1_:%[0-9]+]]:vr = PseudoVID_V_M1 %pt, -1, 6 /* e64 */, 0 /* tu, mu */, implicit $vl, implicit $vtype ; CHECK-NEXT: [[COPY2:%[0-9]+]]:gpr = COPY $x0 ; CHECK-NEXT: {{ $}} @@ -681,7 +685,7 @@ body: | ; CHECK-NEXT: [[SRLI:%[0-9]+]]:gpr = SRLI [[PseudoReadVLENB]], 3 ; CHECK-NEXT: [[COPY1:%[0-9]+]]:gpr = COPY $x11 ; CHECK-NEXT: %pt:vr = IMPLICIT_DEF - ; CHECK-NEXT: dead [[PseudoVSETVLIX0_:%[0-9]+]]:gpr = PseudoVSETVLIX0 $x0, 216 /* e64, m1, ta, ma */, implicit-def $vl, implicit-def $vtype + ; CHECK-NEXT: dead [[PseudoVSETVLIX0_:%[0-9]+]]:gpr = PseudoVSETVLIX0 killed $x0, 216 /* e64, m1, ta, ma */, implicit-def $vl, implicit-def $vtype ; CHECK-NEXT: [[PseudoVID_V_M1_:%[0-9]+]]:vr = PseudoVID_V_M1 %pt, -1, 6 /* e64 */, 3 /* ta, ma */, implicit $vl, implicit $vtype ; CHECK-NEXT: [[COPY2:%[0-9]+]]:gpr = COPY $x0 ; CHECK-NEXT: {{ $}} @@ -866,7 +870,7 @@ body: | ; CHECK-NEXT: %t3:vr = COPY $v2 ; CHECK-NEXT: %t4:vr = COPY $v3 ; CHECK-NEXT: %t5:vrnov0 = COPY $v1 - ; CHECK-NEXT: dead [[PseudoVSETVLIX0_:%[0-9]+]]:gpr = PseudoVSETVLIX0 $x0, 216 /* e64, m1, ta, ma */, implicit-def $vl, implicit-def $vtype + ; CHECK-NEXT: dead [[PseudoVSETVLIX0_:%[0-9]+]]:gpr = PseudoVSETVLIX0 killed $x0, 216 /* e64, m1, ta, ma */, implicit-def $vl, implicit-def $vtype ; CHECK-NEXT: %t6:vr = PseudoVMSEQ_VI_M1 %t1, 0, -1, 6 /* e64 */, implicit $vl, implicit $vtype ; CHECK-NEXT: PseudoBR %bb.1 ; CHECK-NEXT: {{ $}} @@ -949,7 +953,7 @@ body: | ; CHECK-NEXT: %vlenb:gpr = PseudoReadVLENB ; CHECK-NEXT: %inc:gpr = SRLI killed %vlenb, 3 ; CHECK-NEXT: %pt:vr = IMPLICIT_DEF - ; CHECK-NEXT: dead [[PseudoVSETVLIX0_:%[0-9]+]]:gpr = PseudoVSETVLIX0 $x0, 216 /* e64, m1, ta, ma */, implicit-def $vl, implicit-def $vtype + ; CHECK-NEXT: dead [[PseudoVSETVLIX0_:%[0-9]+]]:gpr = PseudoVSETVLIX0 killed $x0, 216 /* e64, m1, ta, ma */, implicit-def $vl, implicit-def $vtype ; CHECK-NEXT: [[PseudoVID_V_M1_:%[0-9]+]]:vr = PseudoVID_V_M1 %pt, -1, 6 /* e64 */, 0 /* tu, mu */, implicit $vl, implicit $vtype ; CHECK-NEXT: [[COPY3:%[0-9]+]]:gpr = COPY $x0 ; CHECK-NEXT: PseudoBR %bb.1 @@ -1041,3 +1045,12 @@ body: | PseudoRET ... +--- +name: pre_undemanded_vl +body: | + bb.0: + PseudoBR %bb.1 + bb.1: + %x:gpr = PseudoVMV_X_S undef $noreg, 6 + PseudoBR %bb.1 +... diff --git a/llvm/test/CodeGen/RISCV/rvv/vsetvli-insert.mir b/llvm/test/CodeGen/RISCV/rvv/vsetvli-insert.mir index e8620c848f8d3d59509c8ce7920b6fc5a76d7e99..e567897aa86897033b493ce33d005db5bdbafa0a 100644 --- a/llvm/test/CodeGen/RISCV/rvv/vsetvli-insert.mir +++ b/llvm/test/CodeGen/RISCV/rvv/vsetvli-insert.mir @@ -1,6 +1,6 @@ # NOTE: Assertions have been autogenerated by utils/update_mir_test_checks.py # RUN: llc %s -o - -mtriple=riscv64 -mattr=v \ -# RUN: -run-pass=riscv-insert-vsetvli | FileCheck %s +# RUN: -run-pass=riscv-insert-vsetvli,riscv-coalesce-vsetvli | FileCheck %s --- | source_filename = "vsetvli-insert.ll" @@ -166,7 +166,7 @@ body: | ; CHECK-NEXT: dead $x0 = PseudoVSETVLI [[COPY]], 216 /* e64, m1, ta, ma */, implicit-def $vl, implicit-def $vtype ; CHECK-NEXT: [[PseudoVLE64_V_M1_:%[0-9]+]]:vr = PseudoVLE64_V_M1 %pt, [[COPY2]], $noreg, 6 /* e64 */, 0 /* tu, mu */, implicit $vl, implicit $vtype ; CHECK-NEXT: %pt2:vr = IMPLICIT_DEF - ; CHECK-NEXT: [[PseudoVADD_VV_M1_:%[0-9]+]]:vr = PseudoVADD_VV_M1 %pt2, killed [[PseudoVLE64_V_M1_]], [[COPY1]], $noreg, 6 /* e64 */, 0 /* tu, mu */, implicit $vl, implicit $vtype + ; CHECK-NEXT: [[PseudoVADD_VV_M1_:%[0-9]+]]:vr = PseudoVADD_VV_M1 %pt2, [[PseudoVLE64_V_M1_]], [[COPY1]], $noreg, 6 /* e64 */, 0 /* tu, mu */, implicit $vl, implicit $vtype ; CHECK-NEXT: $v8 = COPY [[PseudoVADD_VV_M1_]] ; CHECK-NEXT: PseudoRET implicit $v8 %2:gprnox0 = COPY $x11 @@ -208,7 +208,7 @@ body: | ; CHECK-NEXT: dead $x0 = PseudoVSETVLI [[COPY]], 216 /* e64, m1, ta, ma */, implicit-def $vl, implicit-def $vtype ; CHECK-NEXT: [[PseudoVLE32_V_MF2_:%[0-9]+]]:vr = PseudoVLE32_V_MF2 %pt, [[COPY1]], $noreg, 5 /* e32 */, 0 /* tu, mu */, implicit $vl, implicit $vtype ; CHECK-NEXT: %dead:vr = IMPLICIT_DEF - ; CHECK-NEXT: early-clobber %3:vr = PseudoVZEXT_VF2_M1 %dead, killed [[PseudoVLE32_V_MF2_]], $noreg, 6 /* e64 */, 0 /* tu, mu */, implicit $vl, implicit $vtype + ; CHECK-NEXT: early-clobber %3:vr = PseudoVZEXT_VF2_M1 %dead, [[PseudoVLE32_V_MF2_]], $noreg, 6 /* e64 */, 0 /* tu, mu */, implicit $vl, implicit $vtype ; CHECK-NEXT: $v8 = COPY %3 ; CHECK-NEXT: PseudoRET implicit $v8 %1:gprnox0 = COPY $x11 @@ -282,8 +282,8 @@ body: | ; CHECK-NEXT: [[PseudoVLE64_V_M1_:%[0-9]+]]:vr = PseudoVLE64_V_M1 %pt, [[COPY1]], 2, 6 /* e64 */, 0 /* tu, mu */, implicit $vl, implicit $vtype :: (load (s128) from %ir.x) ; CHECK-NEXT: [[PseudoVLE64_V_M1_1:%[0-9]+]]:vr = PseudoVLE64_V_M1 %pt2, [[COPY]], 2, 6 /* e64 */, 0 /* tu, mu */, implicit $vl, implicit $vtype :: (load (s128) from %ir.y) ; CHECK-NEXT: %pt3:vr = IMPLICIT_DEF - ; CHECK-NEXT: [[PseudoVADD_VV_M1_:%[0-9]+]]:vr = PseudoVADD_VV_M1 %pt3, killed [[PseudoVLE64_V_M1_]], killed [[PseudoVLE64_V_M1_1]], 2, 6 /* e64 */, 0 /* tu, mu */, implicit $vl, implicit $vtype - ; CHECK-NEXT: PseudoVSE64_V_M1 killed [[PseudoVADD_VV_M1_]], [[COPY1]], 2, 6 /* e64 */, implicit $vl, implicit $vtype :: (store (s128) into %ir.x) + ; CHECK-NEXT: [[PseudoVADD_VV_M1_:%[0-9]+]]:vr = PseudoVADD_VV_M1 %pt3, [[PseudoVLE64_V_M1_]], [[PseudoVLE64_V_M1_1]], 2, 6 /* e64 */, 0 /* tu, mu */, implicit $vl, implicit $vtype + ; CHECK-NEXT: PseudoVSE64_V_M1 [[PseudoVADD_VV_M1_]], [[COPY1]], 2, 6 /* e64 */, implicit $vl, implicit $vtype :: (store (s128) into %ir.x) ; CHECK-NEXT: PseudoRET %1:gpr = COPY $x11 %0:gpr = COPY $x10 @@ -324,12 +324,12 @@ body: | ; CHECK-NEXT: %pt:vr = IMPLICIT_DEF ; CHECK-NEXT: dead $x0 = PseudoVSETIVLI 2, 216 /* e64, m1, ta, ma */, implicit-def $vl, implicit-def $vtype ; CHECK-NEXT: [[PseudoVLE64_V_M1_:%[0-9]+]]:vr = PseudoVLE64_V_M1 %pt, [[COPY]], 2, 6 /* e64 */, 0 /* tu, mu */, implicit $vl, implicit $vtype :: (load (s128) from %ir.x) - ; CHECK-NEXT: dead [[PseudoVSETVLIX0_:%[0-9]+]]:gpr = PseudoVSETVLIX0 $x0, 216 /* e64, m1, ta, ma */, implicit-def $vl, implicit-def $vtype + ; CHECK-NEXT: dead [[PseudoVSETVLIX0_:%[0-9]+]]:gpr = PseudoVSETVLIX0 killed $x0, 216 /* e64, m1, ta, ma */, implicit-def $vl, implicit-def $vtype ; CHECK-NEXT: [[PseudoVMV_V_I_M1_:%[0-9]+]]:vr = PseudoVMV_V_I_M1 $noreg, 0, -1, 6 /* e64 */, 0 /* tu, mu */, implicit $vl, implicit $vtype ; CHECK-NEXT: [[DEF:%[0-9]+]]:vr = IMPLICIT_DEF ; CHECK-NEXT: dead $x0 = PseudoVSETIVLI 2, 216 /* e64, m1, ta, ma */, implicit-def $vl, implicit-def $vtype - ; CHECK-NEXT: [[PseudoVREDSUM_VS_M1_E8_:%[0-9]+]]:vr = PseudoVREDSUM_VS_M1_E8 [[DEF]], killed [[PseudoVLE64_V_M1_]], killed [[PseudoVMV_V_I_M1_]], 2, 6 /* e64 */, 1 /* ta, mu */, implicit $vl, implicit $vtype - ; CHECK-NEXT: [[PseudoVMV_X_S:%[0-9]+]]:gpr = PseudoVMV_X_S killed [[PseudoVREDSUM_VS_M1_E8_]], 6 /* e64 */, implicit $vtype + ; CHECK-NEXT: [[PseudoVREDSUM_VS_M1_E8_:%[0-9]+]]:vr = PseudoVREDSUM_VS_M1_E8 [[DEF]], [[PseudoVLE64_V_M1_]], [[PseudoVMV_V_I_M1_]], 2, 6 /* e64 */, 1 /* ta, mu */, implicit $vl, implicit $vtype + ; CHECK-NEXT: [[PseudoVMV_X_S:%[0-9]+]]:gpr = PseudoVMV_X_S [[PseudoVREDSUM_VS_M1_E8_]], 6 /* e64 */, implicit $vtype ; CHECK-NEXT: $x10 = COPY [[PseudoVMV_X_S]] ; CHECK-NEXT: PseudoRET implicit $x10 %0:gpr = COPY $x10 @@ -370,7 +370,7 @@ body: | ; CHECK-NEXT: [[COPY:%[0-9]+]]:gprnox0 = COPY $x10 ; CHECK-NEXT: [[COPY1:%[0-9]+]]:vr = COPY $v9 ; CHECK-NEXT: [[COPY2:%[0-9]+]]:vr = COPY $v8 - ; CHECK-NEXT: [[PseudoVSETVLI:%[0-9]+]]:gprnox0 = PseudoVSETVLI [[COPY]], 88 /* e64, m1, ta, mu */, implicit-def $vl, implicit-def $vtype + ; CHECK-NEXT: dead [[PseudoVSETVLI:%[0-9]+]]:gprnox0 = PseudoVSETVLI [[COPY]], 88 /* e64, m1, ta, mu */, implicit-def $vl, implicit-def $vtype ; CHECK-NEXT: %pt:vr = IMPLICIT_DEF ; CHECK-NEXT: [[PseudoVADD_VV_M1_:%[0-9]+]]:vr = PseudoVADD_VV_M1 %pt, [[COPY2]], [[COPY1]], $noreg, 6 /* e64 */, 0 /* tu, mu */, implicit $vl, implicit $vtype ; CHECK-NEXT: $v8 = COPY [[PseudoVADD_VV_M1_]] @@ -418,7 +418,7 @@ body: | ; CHECK-NEXT: INLINEASM &"", 1 /* sideeffect attdialect */ ; CHECK-NEXT: %pt2:vr = IMPLICIT_DEF ; CHECK-NEXT: dead $x0 = PseudoVSETVLI [[COPY]], 216 /* e64, m1, ta, ma */, implicit-def $vl, implicit-def $vtype - ; CHECK-NEXT: [[PseudoVADD_VV_M1_:%[0-9]+]]:vr = PseudoVADD_VV_M1 %pt2, killed [[PseudoVLE64_V_M1_]], [[COPY1]], $noreg, 6 /* e64 */, 0 /* tu, mu */, implicit $vl, implicit $vtype + ; CHECK-NEXT: [[PseudoVADD_VV_M1_:%[0-9]+]]:vr = PseudoVADD_VV_M1 %pt2, [[PseudoVLE64_V_M1_]], [[COPY1]], $noreg, 6 /* e64 */, 0 /* tu, mu */, implicit $vl, implicit $vtype ; CHECK-NEXT: $v8 = COPY [[PseudoVADD_VV_M1_]] ; CHECK-NEXT: PseudoRET implicit $v8 %2:gprnox0 = COPY $x11 @@ -445,9 +445,9 @@ body: | ; CHECK-NEXT: {{ $}} ; CHECK-NEXT: %pt:vrm2 = IMPLICIT_DEF ; CHECK-NEXT: dead $x0 = PseudoVSETIVLI 4, 217 /* e64, m2, ta, ma */, implicit-def $vl, implicit-def $vtype - ; CHECK-NEXT: [[PseudoVID_V_M2_:%[0-9]+]]:vrm2 = PseudoVID_V_M2 %pt, 4, 6 /* e64 */, 3 /* ta, ma */, implicit $vl, implicit $vtype + ; CHECK-NEXT: dead [[PseudoVID_V_M2_:%[0-9]+]]:vrm2 = PseudoVID_V_M2 %pt, 4, 6 /* e64 */, 3 /* ta, ma */, implicit $vl, implicit $vtype ; CHECK-NEXT: dead $x0 = PseudoVSETVLIX0 killed $x0, 198 /* e8, mf4, ta, ma */, implicit-def $vl, implicit-def $vtype, implicit $vl - ; CHECK-NEXT: [[PseudoVMV_V_I_MF4_:%[0-9]+]]:vr = PseudoVMV_V_I_MF4 $noreg, 0, 4, 3 /* e8 */, 0 /* tu, mu */, implicit $vl, implicit $vtype + ; CHECK-NEXT: dead [[PseudoVMV_V_I_MF4_:%[0-9]+]]:vr = PseudoVMV_V_I_MF4 $noreg, 0, 4, 3 /* e8 */, 0 /* tu, mu */, implicit $vl, implicit $vtype ; CHECK-NEXT: PseudoRET %pt:vrm2 = IMPLICIT_DEF %0:vrm2 = PseudoVID_V_M2 %pt, 4, 6, 3 @@ -467,14 +467,14 @@ body: | ; CHECK-NEXT: {{ $}} ; CHECK-NEXT: %cond:gpr = COPY $x10 ; CHECK-NEXT: dead $x0 = PseudoVSETIVLI 2, 215 /* e32, mf2, ta, ma */, implicit-def $vl, implicit-def $vtype - ; CHECK-NEXT: [[PseudoVMV_V_I_MF2_:%[0-9]+]]:vr = PseudoVMV_V_I_MF2 $noreg, 1, 2, 5 /* e32 */, 0 /* tu, mu */, implicit $vl, implicit $vtype + ; CHECK-NEXT: dead [[PseudoVMV_V_I_MF2_:%[0-9]+]]:vr = PseudoVMV_V_I_MF2 $noreg, 1, 2, 5 /* e32 */, 0 /* tu, mu */, implicit $vl, implicit $vtype ; CHECK-NEXT: BEQ %cond, $x0, %bb.2 ; CHECK-NEXT: {{ $}} ; CHECK-NEXT: bb.1: ; CHECK-NEXT: successors: %bb.2(0x80000000) ; CHECK-NEXT: {{ $}} ; CHECK-NEXT: dead $x0 = PseudoVSETVLIX0 killed $x0, 216 /* e64, m1, ta, ma */, implicit-def $vl, implicit-def $vtype, implicit $vl - ; CHECK-NEXT: [[PseudoVMV_V_I_M1_:%[0-9]+]]:vr = PseudoVMV_V_I_M1 $noreg, 1, 2, 6 /* e64 */, 0 /* tu, mu */, implicit $vl, implicit $vtype + ; CHECK-NEXT: dead [[PseudoVMV_V_I_M1_:%[0-9]+]]:vr = PseudoVMV_V_I_M1 $noreg, 1, 2, 6 /* e64 */, 0 /* tu, mu */, implicit $vl, implicit $vtype ; CHECK-NEXT: {{ $}} ; CHECK-NEXT: bb.2: ; CHECK-NEXT: successors: %bb.4(0x40000000), %bb.3(0x40000000) @@ -488,8 +488,8 @@ body: | ; CHECK-NEXT: {{ $}} ; CHECK-NEXT: bb.4: ; CHECK-NEXT: $x0 = PseudoVSETIVLI 2, 215 /* e32, mf2, ta, ma */, implicit-def $vl, implicit-def $vtype - ; CHECK-NEXT: [[PseudoVMV_X_S:%[0-9]+]]:gpr = PseudoVMV_X_S $noreg, 5 /* e32 */, implicit $vtype - ; CHECK-NEXT: [[PseudoVMV_V_I_MF2_1:%[0-9]+]]:vr = PseudoVMV_V_I_MF2 $noreg, 1, 2, 5 /* e32 */, 0 /* tu, mu */, implicit $vl, implicit $vtype + ; CHECK-NEXT: dead [[PseudoVMV_X_S:%[0-9]+]]:gpr = PseudoVMV_X_S $noreg, 5 /* e32 */, implicit $vtype + ; CHECK-NEXT: dead [[PseudoVMV_V_I_MF2_1:%[0-9]+]]:vr = PseudoVMV_V_I_MF2 $noreg, 1, 2, 5 /* e32 */, 0 /* tu, mu */, implicit $vl, implicit $vtype ; CHECK-NEXT: PseudoRET bb.0: liveins: $x10 @@ -517,10 +517,10 @@ body: | ; CHECK: liveins: $x1 ; CHECK-NEXT: {{ $}} ; CHECK-NEXT: dead $x0 = PseudoVSETIVLI 3, 216 /* e64, m1, ta, ma */, implicit-def $vl, implicit-def $vtype - ; CHECK-NEXT: [[COPY:%[0-9]+]]:gpr = COPY $vtype + ; CHECK-NEXT: dead [[COPY:%[0-9]+]]:gpr = COPY $vtype ; CHECK-NEXT: $vl = COPY $x1 ; CHECK-NEXT: dead $x0 = PseudoVSETIVLI 3, 216 /* e64, m1, ta, ma */, implicit-def $vl, implicit-def $vtype - ; CHECK-NEXT: [[PseudoVADD_VV_M1_:%[0-9]+]]:vr = PseudoVADD_VV_M1 $noreg, $noreg, $noreg, 3, 6 /* e64 */, 0 /* tu, mu */, implicit $vl, implicit $vtype + ; CHECK-NEXT: dead [[PseudoVADD_VV_M1_:%[0-9]+]]:vr = PseudoVADD_VV_M1 $noreg, $noreg, $noreg, 3, 6 /* e64 */, 0 /* tu, mu */, implicit $vl, implicit $vtype ; CHECK-NEXT: PseudoRET dead $x0 = PseudoVSETIVLI 3, 216, implicit-def $vl, implicit-def $vtype %1:gpr = COPY $vtype diff --git a/llvm/test/CodeGen/RISCV/rvv/vwadd-sdnode.ll b/llvm/test/CodeGen/RISCV/rvv/vwadd-sdnode.ll index 21ddf1a6e114d45384005afb8f1fefd873e3d11d..d70f619c3601a3eb459d03c378d8508faef86bd6 100644 --- a/llvm/test/CodeGen/RISCV/rvv/vwadd-sdnode.ll +++ b/llvm/test/CodeGen/RISCV/rvv/vwadd-sdnode.ll @@ -1484,7 +1484,6 @@ define @vwadd_vx_splat_zext( %va, i32 %b) { ; ; RV64-LABEL: vwadd_vx_splat_zext: ; RV64: # %bb.0: -; RV64-NEXT: andi a0, a0, -1 ; RV64-NEXT: vsetvli a1, zero, e32, m4, ta, ma ; RV64-NEXT: vwaddu.vx v16, v8, a0 ; RV64-NEXT: vmv8r.v v8, v16 diff --git a/llvm/test/CodeGen/RISCV/rvv/zvlsseg-spill.mir b/llvm/test/CodeGen/RISCV/rvv/zvlsseg-spill.mir index d0b76e7e4535b8d925072ed4beaea954692cd11f..fcd852f1210df545477a9ea9ae47a124c7e49c95 100644 --- a/llvm/test/CodeGen/RISCV/rvv/zvlsseg-spill.mir +++ b/llvm/test/CodeGen/RISCV/rvv/zvlsseg-spill.mir @@ -27,7 +27,7 @@ body: | ; CHECK-NEXT: $x12 = frame-setup SLLI killed $x12, 3 ; CHECK-NEXT: $x2 = frame-setup SUB $x2, killed $x12 ; CHECK-NEXT: frame-setup CFI_INSTRUCTION escape 0x0f, 0x0d, 0x72, 0x00, 0x11, 0x10, 0x22, 0x11, 0x08, 0x92, 0xa2, 0x38, 0x00, 0x1e, 0x22 - ; CHECK-NEXT: dead $x0 = PseudoVSETVLI killed renamable $x11, 152 /* e64, m1, tu, ma */, implicit-def $vl, implicit-def $vtype + ; CHECK-NEXT: dead $x0 = PseudoVSETVLI killed renamable $x11, 216 /* e64, m1, ta, ma */, implicit-def $vl, implicit-def $vtype ; CHECK-NEXT: $v0_v1_v2_v3_v4_v5_v6 = PseudoVLSEG7E64_V_M1 undef $v0_v1_v2_v3_v4_v5_v6, renamable $x10, $noreg, 6 /* e64 */, 0 /* tu, mu */, implicit $vl, implicit $vtype ; CHECK-NEXT: $x11 = ADDI $x2, 16 ; CHECK-NEXT: $x12 = PseudoReadVLENB diff --git a/llvm/test/CodeGen/RISCV/xaluo.ll b/llvm/test/CodeGen/RISCV/xaluo.ll index ac67c0769f7056d1c129c3e99645e3db304dc71b..b1efe53290e8ee142bf492a1a53a94cdfcbdd961 100644 --- a/llvm/test/CodeGen/RISCV/xaluo.ll +++ b/llvm/test/CodeGen/RISCV/xaluo.ll @@ -1268,12 +1268,13 @@ define zeroext i1 @smulo2.i32(i32 signext %v1, ptr %res) { ; RV32ZBA-LABEL: smulo2.i32: ; RV32ZBA: # %bb.0: # %entry ; RV32ZBA-NEXT: li a2, 13 -; RV32ZBA-NEXT: mulh a3, a0, a2 -; RV32ZBA-NEXT: mul a2, a0, a2 -; RV32ZBA-NEXT: srai a0, a2, 31 -; RV32ZBA-NEXT: xor a0, a3, a0 +; RV32ZBA-NEXT: mulh a2, a0, a2 +; RV32ZBA-NEXT: sh1add a3, a0, a0 +; RV32ZBA-NEXT: sh2add a3, a3, a0 +; RV32ZBA-NEXT: srai a0, a3, 31 +; RV32ZBA-NEXT: xor a0, a2, a0 ; RV32ZBA-NEXT: snez a0, a0 -; RV32ZBA-NEXT: sw a2, 0(a1) +; RV32ZBA-NEXT: sw a3, 0(a1) ; RV32ZBA-NEXT: ret ; ; RV64ZBA-LABEL: smulo2.i32: @@ -1577,13 +1578,15 @@ define zeroext i1 @smulo2.i64(i64 %v1, ptr %res) { ; RV32ZBA: # %bb.0: # %entry ; RV32ZBA-NEXT: li a3, 13 ; RV32ZBA-NEXT: mulhu a4, a0, a3 -; RV32ZBA-NEXT: mul a5, a1, a3 +; RV32ZBA-NEXT: sh1add a5, a1, a1 +; RV32ZBA-NEXT: sh2add a5, a5, a1 ; RV32ZBA-NEXT: add a4, a5, a4 ; RV32ZBA-NEXT: sltu a5, a4, a5 ; RV32ZBA-NEXT: mulhu a6, a1, a3 ; RV32ZBA-NEXT: add a5, a6, a5 ; RV32ZBA-NEXT: srai a1, a1, 31 -; RV32ZBA-NEXT: mul a6, a1, a3 +; RV32ZBA-NEXT: sh1add a6, a1, a1 +; RV32ZBA-NEXT: sh2add a6, a6, a1 ; RV32ZBA-NEXT: add a6, a5, a6 ; RV32ZBA-NEXT: srai a7, a4, 31 ; RV32ZBA-NEXT: xor t0, a6, a7 @@ -1593,7 +1596,8 @@ define zeroext i1 @smulo2.i64(i64 %v1, ptr %res) { ; RV32ZBA-NEXT: xor a1, a1, a7 ; RV32ZBA-NEXT: or a1, t0, a1 ; RV32ZBA-NEXT: snez a1, a1 -; RV32ZBA-NEXT: mul a0, a0, a3 +; RV32ZBA-NEXT: sh1add a3, a0, a0 +; RV32ZBA-NEXT: sh2add a0, a3, a0 ; RV32ZBA-NEXT: sw a0, 0(a2) ; RV32ZBA-NEXT: sw a4, 4(a2) ; RV32ZBA-NEXT: mv a0, a1 @@ -1602,12 +1606,13 @@ define zeroext i1 @smulo2.i64(i64 %v1, ptr %res) { ; RV64ZBA-LABEL: smulo2.i64: ; RV64ZBA: # %bb.0: # %entry ; RV64ZBA-NEXT: li a2, 13 -; RV64ZBA-NEXT: mulh a3, a0, a2 -; RV64ZBA-NEXT: mul a2, a0, a2 -; RV64ZBA-NEXT: srai a0, a2, 63 -; RV64ZBA-NEXT: xor a0, a3, a0 +; RV64ZBA-NEXT: mulh a2, a0, a2 +; RV64ZBA-NEXT: sh1add a3, a0, a0 +; RV64ZBA-NEXT: sh2add a3, a3, a0 +; RV64ZBA-NEXT: srai a0, a3, 63 +; RV64ZBA-NEXT: xor a0, a2, a0 ; RV64ZBA-NEXT: snez a0, a0 -; RV64ZBA-NEXT: sd a2, 0(a1) +; RV64ZBA-NEXT: sd a3, 0(a1) ; RV64ZBA-NEXT: ret ; ; RV32ZICOND-LABEL: smulo2.i64: @@ -1743,19 +1748,20 @@ define zeroext i1 @umulo2.i32(i32 signext %v1, ptr %res) { ; ; RV32ZBA-LABEL: umulo2.i32: ; RV32ZBA: # %bb.0: # %entry -; RV32ZBA-NEXT: li a3, 13 -; RV32ZBA-NEXT: mulhu a2, a0, a3 +; RV32ZBA-NEXT: li a2, 13 +; RV32ZBA-NEXT: mulhu a2, a0, a2 ; RV32ZBA-NEXT: snez a2, a2 -; RV32ZBA-NEXT: mul a0, a0, a3 +; RV32ZBA-NEXT: sh1add a3, a0, a0 +; RV32ZBA-NEXT: sh2add a0, a3, a0 ; RV32ZBA-NEXT: sw a0, 0(a1) ; RV32ZBA-NEXT: mv a0, a2 ; RV32ZBA-NEXT: ret ; ; RV64ZBA-LABEL: umulo2.i32: ; RV64ZBA: # %bb.0: # %entry -; RV64ZBA-NEXT: zext.w a0, a0 -; RV64ZBA-NEXT: sh1add a2, a0, a0 -; RV64ZBA-NEXT: sh2add a2, a2, a0 +; RV64ZBA-NEXT: zext.w a2, a0 +; RV64ZBA-NEXT: sh1add.uw a0, a0, a2 +; RV64ZBA-NEXT: sh2add a2, a0, a2 ; RV64ZBA-NEXT: srli a0, a2, 32 ; RV64ZBA-NEXT: snez a0, a0 ; RV64ZBA-NEXT: sw a2, 0(a1) @@ -1995,25 +2001,28 @@ define zeroext i1 @umulo2.i64(i64 %v1, ptr %res) { ; RV32ZBA-LABEL: umulo2.i64: ; RV32ZBA: # %bb.0: # %entry ; RV32ZBA-NEXT: li a3, 13 -; RV32ZBA-NEXT: mul a4, a1, a3 -; RV32ZBA-NEXT: mulhu a5, a0, a3 -; RV32ZBA-NEXT: add a4, a5, a4 -; RV32ZBA-NEXT: sltu a5, a4, a5 +; RV32ZBA-NEXT: mulhu a4, a0, a3 +; RV32ZBA-NEXT: sh1add a5, a1, a1 +; RV32ZBA-NEXT: sh2add a5, a5, a1 +; RV32ZBA-NEXT: add a5, a4, a5 +; RV32ZBA-NEXT: sltu a4, a5, a4 ; RV32ZBA-NEXT: mulhu a1, a1, a3 ; RV32ZBA-NEXT: snez a1, a1 -; RV32ZBA-NEXT: or a1, a1, a5 -; RV32ZBA-NEXT: mul a0, a0, a3 +; RV32ZBA-NEXT: or a1, a1, a4 +; RV32ZBA-NEXT: sh1add a3, a0, a0 +; RV32ZBA-NEXT: sh2add a0, a3, a0 ; RV32ZBA-NEXT: sw a0, 0(a2) -; RV32ZBA-NEXT: sw a4, 4(a2) +; RV32ZBA-NEXT: sw a5, 4(a2) ; RV32ZBA-NEXT: mv a0, a1 ; RV32ZBA-NEXT: ret ; ; RV64ZBA-LABEL: umulo2.i64: ; RV64ZBA: # %bb.0: # %entry -; RV64ZBA-NEXT: li a3, 13 -; RV64ZBA-NEXT: mulhu a2, a0, a3 +; RV64ZBA-NEXT: li a2, 13 +; RV64ZBA-NEXT: mulhu a2, a0, a2 ; RV64ZBA-NEXT: snez a2, a2 -; RV64ZBA-NEXT: mul a0, a0, a3 +; RV64ZBA-NEXT: sh1add a3, a0, a0 +; RV64ZBA-NEXT: sh2add a0, a3, a0 ; RV64ZBA-NEXT: sd a0, 0(a1) ; RV64ZBA-NEXT: mv a0, a2 ; RV64ZBA-NEXT: ret diff --git a/llvm/test/CodeGen/SPIRV/pointers/argument-ptr-to-struct.ll b/llvm/test/CodeGen/SPIRV/pointers/argument-ptr-to-struct.ll new file mode 100644 index 0000000000000000000000000000000000000000..ac72ec28c37d9d77f9a9beb16ad9de9700ba1c35 --- /dev/null +++ b/llvm/test/CodeGen/SPIRV/pointers/argument-ptr-to-struct.ll @@ -0,0 +1,37 @@ +; RUN: llc -O0 -mtriple=spirv64-unknown-unknown %s -o - | FileCheck %s +; RUN: %if spirv-tools %{ llc -O0 -mtriple=spirv64-unknown-unknown %s -o - -filetype=obj | spirv-val %} + +; CHECK-DAG: %[[#VOID:]] = OpTypeVoid +; CHECK-DAG: %[[#FLOAT:]] = OpTypeFloat 32 +; CHECK-DAG: %[[#UCHAR:]] = OpTypeInt 8 0 +; CHECK-DAG: %[[#UINT:]] = OpTypeInt 32 0 +; CHECK-DAG: %[[#STRUCT_S:]] = OpTypeStruct %[[#FLOAT]] %[[#UCHAR]] %[[#UINT]] +; CHECK-DAG: %[[#PTR_STRUCT_S:]] = OpTypePointer Function %[[#STRUCT_S]] +; CHECK-DAG: %[[#FUNC_TYPE_K:]] = OpTypeFunction %[[#VOID]] %[[#PTR_STRUCT_S]] +; CHECK-DAG: %[[#FUNC_TYPE_H:]] = OpTypeFunction %[[#UINT]] %[[#PTR_STRUCT_S]] + +; CHECK: %[[#]] = OpFunction %[[#VOID]] None %[[#FUNC_TYPE_K]] +; CHECK: %[[#]] = OpFunctionParameter %[[#PTR_STRUCT_S]] + +; CHECK: %[[#]] = OpFunction %[[#UINT]] None %[[#FUNC_TYPE_H]] +; CHECK: %[[#]] = OpFunctionParameter %[[#PTR_STRUCT_S]] + +%struct.s = type { float, i8, i32 } + +define spir_kernel void @k(ptr noundef byval(%struct.s) align 4 %x) { +entry: + %c = getelementptr inbounds %struct.s, ptr %x, i32 0, i32 2 + %l = load i32, ptr %c, align 4 + %add = add nsw i32 %l, 1 + %c1 = getelementptr inbounds %struct.s, ptr %x, i32 0, i32 2 + store i32 %add, ptr %c1, align 4 + ret void +} + +define spir_func i32 @h(ptr noundef byval(%struct.s) align 4 %x) { +entry: + %c = getelementptr inbounds %struct.s, ptr %x, i32 0, i32 2 + %l = load i32, ptr %c, align 4 + %add = add nsw i32 %l, 1 + ret i32 %add +} diff --git a/llvm/test/CodeGen/SPIRV/pointers/global-ptrtoint.ll b/llvm/test/CodeGen/SPIRV/pointers/global-ptrtoint.ll new file mode 100644 index 0000000000000000000000000000000000000000..d0c64b4353ec684d5963d9230cc4f9a02551c155 --- /dev/null +++ b/llvm/test/CodeGen/SPIRV/pointers/global-ptrtoint.ll @@ -0,0 +1,28 @@ +; This test is to check that correct virtual register type is created after ptrtoint. + +; RUN: llc -O0 -mtriple=spirv64-unknown-unknown %s -o - | FileCheck %s +; RUN: %if spirv-tools %{ llc -O0 -mtriple=spirv64-unknown-unknown %s -o - -filetype=obj | spirv-val %} + +; RUN: llc -O0 -mtriple=spirv32-unknown-unknown %s -o - | FileCheck %s +; RUN: %if spirv-tools %{ llc -O0 -mtriple=spirv32-unknown-unknown %s -o - -filetype=obj | spirv-val %} + +; CHECK: OpName %[[GlobalValue:.*]] "dev_global" +; CHECK-DAG: %[[TyI64:.*]] = OpTypeInt 64 0 +; CHECK-DAG: %[[TyStruct:.*]] = OpTypeStruct %[[TyI64]] %[[TyI64]] +; CHECK-DAG: %[[Const128:.*]] = OpConstant %[[TyI64]] 128 +; CHECK-DAG: %[[GlobalValue]] = OpVariable +; CHECK-DAG: %[[PtrToInt:.*]] = OpSpecConstantOp %[[TyI64]] 117 %12 +; TODO: The following bitcast line looks unneeded and we may expect it to be removed in future +; CHECK-DAG: %[[UseGlobalValue:.*]] = OpSpecConstantOp %[[TyI64]] 124 %[[PtrToInt]] +; CHECK-DAG: %[[ConstComposite:.*]] = OpConstantComposite %[[TyStruct]] %[[Const128]] %[[UseGlobalValue]] +; CHECK-DAG: %[[TyPtrStruct:.*]] = OpTypePointer CrossWorkgroup %[[TyStruct]] +; CHECK: OpVariable %[[TyPtrStruct]] CrossWorkgroup %[[ConstComposite]] +; CHECK: OpFunction + +@dev_global = addrspace(1) global [2 x i32] zeroinitializer +@__AsanDeviceGlobalMetadata = addrspace(1) global { i64, i64 } { i64 128, i64 ptrtoint (ptr addrspace(1) @dev_global to i64) } + +define void @foo() { +entry: + ret void +} diff --git a/llvm/test/CodeGen/SPIRV/pointers/variables-storage-class.ll b/llvm/test/CodeGen/SPIRV/pointers/variables-storage-class.ll new file mode 100644 index 0000000000000000000000000000000000000000..034feed72dc7bc9217f4bbe2d6f69917ec7edc21 --- /dev/null +++ b/llvm/test/CodeGen/SPIRV/pointers/variables-storage-class.ll @@ -0,0 +1,19 @@ +; RUN: llc -O0 -mtriple=spirv64-unknown-unknown %s -o - | FileCheck %s +; RUN: %if spirv-tools %{ llc -O0 -mtriple=spirv64-unknown-unknown %s -o - -filetype=obj | spirv-val %} + +@Ptr = addrspace(1) global ptr addrspace(1) null +@Init = private addrspace(2) constant i32 123 + +; CHECK-DAG: %[[#PTR:]] = OpVariable %[[#]] UniformConstant %[[#]] +; CHECK-DAG: %[[#INIT:]] = OpVariable %[[#]] CrossWorkgroup %[[#]] + +; CHECK: %[[#]] = OpLoad %[[#]] %[[#INIT]] Aligned 8 +; CHECK: OpCopyMemorySized %[[#]] %[[#PTR]] %[[#]] Aligned 4 + +define spir_kernel void @Foo() { + %l = load ptr addrspace(1), ptr addrspace(1) @Ptr, align 8 + call void @llvm.memcpy.p1.p2.i64(ptr addrspace(1) align 4 %l, ptr addrspace(2) align 1 @Init, i64 4, i1 false) + ret void +} + +declare void @llvm.memcpy.p1.p2.i64(ptr addrspace(1) noalias nocapture writeonly, ptr addrspace(2) noalias nocapture readonly, i64, i1 immarg) diff --git a/llvm/test/CodeGen/SPIRV/printf.ll b/llvm/test/CodeGen/SPIRV/printf.ll new file mode 100644 index 0000000000000000000000000000000000000000..483fc1f244e57ce8363de4574a952d3a2aeb9299 --- /dev/null +++ b/llvm/test/CodeGen/SPIRV/printf.ll @@ -0,0 +1,40 @@ +; RUN: llc -O0 -mtriple=spirv64-unknown-unknown %s -o - | FileCheck %s +; RUN: %if spirv-tools %{ llc -O0 -mtriple=spirv64-unknown-unknown %s -o - -filetype=obj | spirv-val %} + +; RUN: llc -O0 -mtriple=spirv32-unknown-unknown %s -o - | FileCheck %s +; RUN: %if spirv-tools %{ llc -O0 -mtriple=spirv32-unknown-unknown %s -o - -filetype=obj | spirv-val %} + +; CHECK: %[[#ExtImport:]] = OpExtInstImport "OpenCL.std" +; CHECK: %[[#Char:]] = OpTypeInt 8 0 +; CHECK: %[[#CharPtr:]] = OpTypePointer UniformConstant %[[#Char]] +; CHECK: %[[#GV:]] = OpVariable %[[#]] UniformConstant %[[#]] +; CHECK: OpFunction +; CHECK: %[[#Arg1:]] = OpFunctionParameter +; CHECK: %[[#Arg2:]] = OpFunctionParameter +; CHECK: %[[#CastedGV:]] = OpBitcast %[[#CharPtr]] %[[#GV]] +; CHECK-NEXT: OpExtInst %[[#]] %[[#ExtImport]] printf %[[#CastedGV]] %[[#ArgConst:]] +; CHECK-NEXT: OpExtInst %[[#]] %[[#ExtImport]] printf %[[#CastedGV]] %[[#ArgConst]] +; CHECK-NEXT: OpExtInst %[[#]] %[[#ExtImport]] printf %[[#Arg1]] %[[#ArgConst:]] +; CHECK-NEXT: OpExtInst %[[#]] %[[#ExtImport]] printf %[[#Arg1]] %[[#ArgConst]] +; CHECK-NEXT: %[[#CastedArg2:]] = OpBitcast %[[#CharPtr]] %[[#Arg2]] +; CHECK-NEXT: OpExtInst %[[#]] %[[#ExtImport]] printf %[[#CastedArg2]] %[[#ArgConst]] +; CHECK-NEXT: OpExtInst %[[#]] %[[#ExtImport]] printf %[[#CastedArg2]] %[[#ArgConst]] +; CHECK: OpFunctionEnd + +%struct = type { [6 x i8] } + +@FmtStr = internal addrspace(2) constant [6 x i8] c"c=%c\0A\00", align 1 + +define spir_kernel void @foo(ptr addrspace(2) %_arg_fmt1, ptr addrspace(2) byval(%struct) %_arg_fmt2) { +entry: + %r1 = tail call spir_func i32 (ptr addrspace(2), ...) @_Z6printfPU3AS2Kcz(ptr addrspace(2) @FmtStr, i8 signext 97) + %r2 = tail call spir_func i32 (ptr addrspace(2), ...) @_Z18__spirv_ocl_printfPU3AS2Kcz(ptr addrspace(2) @FmtStr, i8 signext 97) + %r3 = tail call spir_func i32 (ptr addrspace(2), ...) @_Z6printfPU3AS2Kcz(ptr addrspace(2) %_arg_fmt1, i8 signext 97) + %r4 = tail call spir_func i32 (ptr addrspace(2), ...) @_Z18__spirv_ocl_printfPU3AS2Kcz(ptr addrspace(2) %_arg_fmt1, i8 signext 97) + %r5 = tail call spir_func i32 (ptr addrspace(2), ...) @_Z6printfPU3AS2Kcz(ptr addrspace(2) %_arg_fmt2, i8 signext 97) + %r6 = tail call spir_func i32 (ptr addrspace(2), ...) @_Z18__spirv_ocl_printfPU3AS2Kcz(ptr addrspace(2) %_arg_fmt2, i8 signext 97) + ret void +} + +declare dso_local spir_func i32 @_Z6printfPU3AS2Kcz(ptr addrspace(2), ...) +declare dso_local spir_func i32 @_Z18__spirv_ocl_printfPU3AS2Kcz(ptr addrspace(2), ...) diff --git a/llvm/test/CodeGen/SPIRV/transcoding/memcpy-zext.ll b/llvm/test/CodeGen/SPIRV/transcoding/memcpy-zext.ll index ea0197548a8154926059530bf15d3ea92d0b758d..89fa93b4fcda1cbb8b73e34aca020dbc0b445439 100644 --- a/llvm/test/CodeGen/SPIRV/transcoding/memcpy-zext.ll +++ b/llvm/test/CodeGen/SPIRV/transcoding/memcpy-zext.ll @@ -3,8 +3,7 @@ ; RUN: llc -O0 -mtriple=spirv64-unknown-unknown %s -o - | FileCheck %s --check-prefixes=CHECK,CHECK-64 ; RUN: %if spirv-tools %{ llc -O0 -mtriple=spirv64-unknown-unknown %s -o - -filetype=obj | spirv-val %} -; CHECK-64-DAG: %[[#i64:]] = OpTypeInt 64 0 - +; CHECK-DAG: %[[#i64:]] = OpTypeInt 64 0 ; CHECK-DAG: %[[#i8:]] = OpTypeInt 8 0 ; CHECK-DAG: %[[#i32:]] = OpTypeInt 32 0 ; CHECK-DAG: %[[#one:]] = OpConstant %[[#i32]] 1 @@ -14,19 +13,28 @@ ; CHECK-DAG: %[[#test_arr_init:]] = OpConstantComposite %[[#i32x3]] %[[#one]] %[[#two]] %[[#three]] ; CHECK-DAG: %[[#szconst1024:]] = OpConstant %[[#i32]] 1024 ; CHECK-DAG: %[[#szconst42:]] = OpConstant %[[#i8]] 42 +; CHECK-DAG: %[[#szconst123:]] = OpConstant %[[#i64]] 123 ; CHECK-DAG: %[[#const_i32x3_ptr:]] = OpTypePointer UniformConstant %[[#i32x3]] ; CHECK-DAG: %[[#test_arr:]] = OpVariable %[[#const_i32x3_ptr]] UniformConstant %[[#test_arr_init]] ; CHECK-DAG: %[[#i32x3_ptr:]] = OpTypePointer Function %[[#i32x3]] ; CHECK: %[[#arr:]] = OpVariable %[[#i32x3_ptr]] Function ; CHECK-32: OpCopyMemorySized %[[#arr]] %[[#test_arr]] %[[#szconst1024]] -; CHECK-64: %[[#szconstext1024:]] = OpUConvert %[[#i64:]] %[[#szconst1024:]] -; CHECK-64: OpCopyMemorySized %[[#arr]] %[[#test_arr]] %[[#szconstext1024]] - ; CHECK-32: %[[#szconstext42:]] = OpUConvert %[[#i32:]] %[[#szconst42:]] ; CHECK-32: OpCopyMemorySized %[[#arr]] %[[#test_arr]] %[[#szconstext42]] +; CHECK-32: OpCopyMemorySized %[[#arr]] %[[#test_arr]] %[[#szconst123]] + +; If/when Backend stoped rewrite actual reg size of i8/i16/i32/i64 with i32, +; i32 = G_TRUNC i64 would appear for the 32-bit target, switching the following +; TODO patterns instead of the last line above. +; TODO: %[[#szconstext123:]] = OpUConvert %[[#i32:]] %[[#szconst123:]] +; TODO: OpCopyMemorySized %[[#arr]] %[[#test_arr]] %[[#szconst123]] + +; CHECK-64: %[[#szconstext1024:]] = OpUConvert %[[#i64:]] %[[#szconst1024:]] +; CHECK-64: OpCopyMemorySized %[[#arr]] %[[#test_arr]] %[[#szconstext1024]] ; CHECK-64: %[[#szconstext42:]] = OpUConvert %[[#i64:]] %[[#szconst42:]] ; CHECK-64: OpCopyMemorySized %[[#arr]] %[[#test_arr]] %[[#szconstext42]] +; CHECK-64: OpCopyMemorySized %[[#arr]] %[[#test_arr]] %[[#szconst123]] @__const.test.arr = private unnamed_addr addrspace(2) constant [3 x i32] [i32 1, i32 2, i32 3] @@ -36,8 +44,10 @@ entry: %dest = bitcast ptr %arr to ptr call void @llvm.memcpy.p0.p2.i32(ptr align 4 %dest, ptr addrspace(2) align 4 @__const.test.arr, i32 1024, i1 false) call void @llvm.memcpy.p0.p2.i8(ptr align 4 %dest, ptr addrspace(2) align 4 @__const.test.arr, i8 42, i1 false) + call void @llvm.memcpy.p0.p2.i64(ptr align 4 %dest, ptr addrspace(2) align 4 @__const.test.arr, i64 123, i1 false) ret void } declare void @llvm.memcpy.p0.p2.i32(ptr nocapture writeonly, ptr addrspace(2) nocapture readonly, i32, i1) declare void @llvm.memcpy.p0.p2.i8(ptr nocapture writeonly, ptr addrspace(2) nocapture readonly, i8, i1) +declare void @llvm.memcpy.p0.p2.i64(ptr nocapture writeonly, ptr addrspace(2) nocapture readonly, i64, i1) diff --git a/llvm/test/CodeGen/SPIRV/transcoding/spirv-event-null.ll b/llvm/test/CodeGen/SPIRV/transcoding/spirv-event-null.ll new file mode 100644 index 0000000000000000000000000000000000000000..fe0d96f2773ec6ff33703099e4eb47d67beb296e --- /dev/null +++ b/llvm/test/CodeGen/SPIRV/transcoding/spirv-event-null.ll @@ -0,0 +1,33 @@ +; RUN: llc -O0 -mtriple=spirv32-unknown-unknown %s -o - | FileCheck %s +; RUN: %if spirv-tools %{ llc -O0 -mtriple=spirv32-unknown-unknown %s -o - -filetype=obj | spirv-val %} + +; RUN: llc -O0 -mtriple=spirv64-unknown-unknown %s -o - | FileCheck %s +; RUN: %if spirv-tools %{ llc -O0 -mtriple=spirv64-unknown-unknown %s -o - -filetype=obj | spirv-val %} + +; CHECK-DAG: %[[#TyEvent:]] = OpTypeEvent +; CHECK-DAG: %[[#TyStruct:]] = OpTypeStruct %[[#TyEvent]] +; CHECK-DAG: %[[#ConstEvent:]] = OpConstantNull %[[#TyEvent]] +; CHECK-DAG: %[[#TyEventPtr:]] = OpTypePointer Function %[[#TyEvent]] +; CHECK-DAG: %[[#TyStructPtr:]] = OpTypePointer Function %[[#TyStruct]] +; CHECK: OpFunction +; CHECK: OpFunctionParameter +; CHECK: %[[#Src:]] = OpFunctionParameter +; CHECK: OpVariable %[[#TyStructPtr]] Function +; CHECK: %[[#EventVar:]] = OpVariable %[[#TyEventPtr]] Function +; CHECK: %[[#Dest:]] = OpInBoundsPtrAccessChain +; CHECK: %[[#CopyRes:]] = OpGroupAsyncCopy %[[#TyEvent]] %[[#]] %[[#Dest]] %[[#Src]] %[[#]] %[[#]] %[[#ConstEvent]] +; CHECK: OpStore %[[#EventVar]] %[[#CopyRes]] + +%"class.sycl::_V1::device_event" = type { target("spirv.Event") } + +define spir_kernel void @foo(ptr addrspace(1) %_arg_out_ptr, ptr addrspace(3) noundef %_arg_local_acc) { +entry: + %var = alloca %"class.sycl::_V1::device_event" + %dev_event.i.sroa.0 = alloca target("spirv.Event") + %add.ptr.i26 = getelementptr inbounds i32, ptr addrspace(1) %_arg_out_ptr, i64 0 + %call3.i = tail call spir_func target("spirv.Event") @_Z22__spirv_GroupAsyncCopyjPU3AS1iPU3AS3Kimm9ocl_event(i32 2, ptr addrspace(1) %add.ptr.i26, ptr addrspace(3) %_arg_local_acc, i64 16, i64 10, target("spirv.Event") zeroinitializer) + store target("spirv.Event") %call3.i, ptr %dev_event.i.sroa.0 + ret void +} + +declare dso_local spir_func target("spirv.Event") @_Z22__spirv_GroupAsyncCopyjPU3AS1iPU3AS3Kimm9ocl_event(i32, ptr addrspace(1), ptr addrspace(3), i64, i64, target("spirv.Event")) diff --git a/llvm/test/CodeGen/SPIRV/types/or-i1.ll b/llvm/test/CodeGen/SPIRV/types/or-i1.ll new file mode 100644 index 0000000000000000000000000000000000000000..32dc258d85554fd10db67a8f224529941923b10f --- /dev/null +++ b/llvm/test/CodeGen/SPIRV/types/or-i1.ll @@ -0,0 +1,17 @@ +; RUN: llc -O0 -mtriple=spirv64-unknown-unknown %s -o - | FileCheck %s +; RUN: %if spirv-tools %{ llc -O0 -mtriple=spirv64-unknown-unknown %s -o - -filetype=obj | spirv-val %} + +; CHECK-DAG: %[[#BOOL:]] = OpTypeBool +; CHECK: %[[#BOOL:]] = OpLogicalOr %[[#BOOL]] %[[#]] %[[#]] + +define spir_kernel void @foo( + ptr addrspace(1) nocapture noundef writeonly %Dst, + i32 %a, i32 %b) local_unnamed_addr #0 { +entry: + %a1 = trunc i32 %a to i1 + %b1 = trunc i32 %b to i1 + %ab1 = or i1 %a1, %b1 + %ab32 = zext i1 %ab1 to i32 + store i32 %ab32, ptr addrspace(1) %Dst + ret void +} diff --git a/llvm/test/CodeGen/X86/abdu-vector-128.ll b/llvm/test/CodeGen/X86/abdu-vector-128.ll index dd180b67e492a0f970c5175545f677851d0e8a0d..0c33e8973c2d20435bbe3f3472446e4503756dba 100644 --- a/llvm/test/CodeGen/X86/abdu-vector-128.ll +++ b/llvm/test/CodeGen/X86/abdu-vector-128.ll @@ -715,43 +715,41 @@ define <2 x i64> @abd_cmp_v2i64_multiuse_cmp(<2 x i64> %a, <2 x i64> %b) nounwin ; ; SSE42-LABEL: abd_cmp_v2i64_multiuse_cmp: ; SSE42: # %bb.0: -; SSE42-NEXT: movdqa {{.*#+}} xmm2 = [9223372036854775808,9223372036854775808] +; SSE42-NEXT: movdqa %xmm0, %xmm2 +; SSE42-NEXT: psubq %xmm1, %xmm2 ; SSE42-NEXT: movdqa %xmm1, %xmm3 -; SSE42-NEXT: pxor %xmm2, %xmm3 -; SSE42-NEXT: pxor %xmm0, %xmm2 -; SSE42-NEXT: pcmpgtq %xmm3, %xmm2 -; SSE42-NEXT: movdqa %xmm0, %xmm3 -; SSE42-NEXT: psubq %xmm1, %xmm3 -; SSE42-NEXT: psubq %xmm0, %xmm1 -; SSE42-NEXT: movdqa %xmm2, %xmm0 -; SSE42-NEXT: blendvpd %xmm0, %xmm3, %xmm1 -; SSE42-NEXT: paddq %xmm1, %xmm2 -; SSE42-NEXT: movdqa %xmm2, %xmm0 +; SSE42-NEXT: psubq %xmm0, %xmm3 +; SSE42-NEXT: movdqa {{.*#+}} xmm4 = [9223372036854775808,9223372036854775808] +; SSE42-NEXT: pxor %xmm4, %xmm1 +; SSE42-NEXT: pxor %xmm4, %xmm0 +; SSE42-NEXT: pcmpgtq %xmm1, %xmm0 +; SSE42-NEXT: blendvpd %xmm0, %xmm2, %xmm3 +; SSE42-NEXT: paddq %xmm3, %xmm0 ; SSE42-NEXT: retq ; ; AVX1-LABEL: abd_cmp_v2i64_multiuse_cmp: ; AVX1: # %bb.0: -; AVX1-NEXT: vmovddup {{.*#+}} xmm2 = [9223372036854775808,9223372036854775808] -; AVX1-NEXT: # xmm2 = mem[0,0] -; AVX1-NEXT: vpxor %xmm2, %xmm1, %xmm3 -; AVX1-NEXT: vpxor %xmm2, %xmm0, %xmm2 -; AVX1-NEXT: vpcmpgtq %xmm3, %xmm2, %xmm2 -; AVX1-NEXT: vpsubq %xmm1, %xmm0, %xmm3 -; AVX1-NEXT: vpsubq %xmm0, %xmm1, %xmm0 -; AVX1-NEXT: vblendvpd %xmm2, %xmm3, %xmm0, %xmm0 -; AVX1-NEXT: vpaddq %xmm0, %xmm2, %xmm0 +; AVX1-NEXT: vpsubq %xmm1, %xmm0, %xmm2 +; AVX1-NEXT: vpsubq %xmm0, %xmm1, %xmm3 +; AVX1-NEXT: vmovddup {{.*#+}} xmm4 = [9223372036854775808,9223372036854775808] +; AVX1-NEXT: # xmm4 = mem[0,0] +; AVX1-NEXT: vpxor %xmm4, %xmm1, %xmm1 +; AVX1-NEXT: vpxor %xmm4, %xmm0, %xmm0 +; AVX1-NEXT: vpcmpgtq %xmm1, %xmm0, %xmm0 +; AVX1-NEXT: vblendvpd %xmm0, %xmm2, %xmm3, %xmm1 +; AVX1-NEXT: vpaddq %xmm1, %xmm0, %xmm0 ; AVX1-NEXT: retq ; ; AVX2-LABEL: abd_cmp_v2i64_multiuse_cmp: ; AVX2: # %bb.0: -; AVX2-NEXT: vpbroadcastq {{.*#+}} xmm2 = [9223372036854775808,9223372036854775808] -; AVX2-NEXT: vpxor %xmm2, %xmm1, %xmm3 -; AVX2-NEXT: vpxor %xmm2, %xmm0, %xmm2 -; AVX2-NEXT: vpcmpgtq %xmm3, %xmm2, %xmm2 -; AVX2-NEXT: vpsubq %xmm1, %xmm0, %xmm3 -; AVX2-NEXT: vpsubq %xmm0, %xmm1, %xmm0 -; AVX2-NEXT: vblendvpd %xmm2, %xmm3, %xmm0, %xmm0 -; AVX2-NEXT: vpaddq %xmm0, %xmm2, %xmm0 +; AVX2-NEXT: vpsubq %xmm1, %xmm0, %xmm2 +; AVX2-NEXT: vpsubq %xmm0, %xmm1, %xmm3 +; AVX2-NEXT: vpbroadcastq {{.*#+}} xmm4 = [9223372036854775808,9223372036854775808] +; AVX2-NEXT: vpxor %xmm4, %xmm1, %xmm1 +; AVX2-NEXT: vpxor %xmm4, %xmm0, %xmm0 +; AVX2-NEXT: vpcmpgtq %xmm1, %xmm0, %xmm0 +; AVX2-NEXT: vblendvpd %xmm0, %xmm2, %xmm3, %xmm1 +; AVX2-NEXT: vpaddq %xmm1, %xmm0, %xmm0 ; AVX2-NEXT: retq ; ; AVX512-LABEL: abd_cmp_v2i64_multiuse_cmp: diff --git a/llvm/test/CodeGen/X86/apx/kmov-postrapseudos.ll b/llvm/test/CodeGen/X86/apx/kmov-postrapseudos.ll index 017024c173c3f7efcbdf0dbeb3213ab690aafb12..b2cb2c3e04b3f4bbaad479e2a3036b3308db53ab 100644 --- a/llvm/test/CodeGen/X86/apx/kmov-postrapseudos.ll +++ b/llvm/test/CodeGen/X86/apx/kmov-postrapseudos.ll @@ -52,10 +52,7 @@ alloca_21: define i32 @kmovrk_1(<4 x ptr> %arg) { ; AVX512-LABEL: kmovrk_1: ; AVX512: # %bb.0: # %bb -; AVX512-NEXT: # kill: def $ymm0 killed $ymm0 def $zmm0 -; AVX512-NEXT: vptestmq %zmm0, %zmm0, %k0 # encoding: [0x62,0xf2,0xfd,0x48,0x27,0xc0] -; AVX512-NEXT: kmovw %k0, %eax # EVEX TO VEX Compression encoding: [0xc5,0xf8,0x93,0xc0] -; AVX512-NEXT: testb $15, %al # encoding: [0xa8,0x0f] +; AVX512-NEXT: vptest %ymm0, %ymm0 # encoding: [0xc4,0xe2,0x7d,0x17,0xc0] ; AVX512-NEXT: jne .LBB2_1 # encoding: [0x75,A] ; AVX512-NEXT: # fixup A - offset: 1, value: .LBB2_1-1, kind: FK_PCRel_1 ; AVX512-NEXT: # %bb.2: # %bb3 @@ -66,10 +63,7 @@ define i32 @kmovrk_1(<4 x ptr> %arg) { ; ; AVX512BW-LABEL: kmovrk_1: ; AVX512BW: # %bb.0: # %bb -; AVX512BW-NEXT: # kill: def $ymm0 killed $ymm0 def $zmm0 -; AVX512BW-NEXT: vptestmq %zmm0, %zmm0, %k0 # encoding: [0x62,0xf2,0xfd,0x48,0x27,0xc0] -; AVX512BW-NEXT: kmovd %k0, %eax # EVEX TO VEX Compression encoding: [0xc5,0xfb,0x93,0xc0] -; AVX512BW-NEXT: testb $15, %al # encoding: [0xa8,0x0f] +; AVX512BW-NEXT: vptest %ymm0, %ymm0 # encoding: [0xc4,0xe2,0x7d,0x17,0xc0] ; AVX512BW-NEXT: jne .LBB2_1 # encoding: [0x75,A] ; AVX512BW-NEXT: # fixup A - offset: 1, value: .LBB2_1-1, kind: FK_PCRel_1 ; AVX512BW-NEXT: # %bb.2: # %bb3 diff --git a/llvm/test/CodeGen/X86/avx512-broadcast-arith.ll b/llvm/test/CodeGen/X86/avx512-broadcast-arith.ll index 13d1265a249d1fa35f9802dd52cff630cee443d6..7e48b3719cf0ffa4249ea7923809c6b6527111ce 100644 --- a/llvm/test/CodeGen/X86/avx512-broadcast-arith.ll +++ b/llvm/test/CodeGen/X86/avx512-broadcast-arith.ll @@ -30,13 +30,13 @@ define <64 x i8> @add_v64i8_broadcasts(<64 x i8> %a0, i64 %a1, i8 %a2) { ; AVX512F-NEXT: vinserti128 $1, %xmm4, %ymm3, %ymm3 ; AVX512F-NEXT: vinserti64x4 $1, %ymm2, %zmm3, %zmm2 ; AVX512F-NEXT: vpternlogq $216, %zmm2, %zmm1, %zmm0 -; AVX512F-NEXT: vpaddb %ymm1, %ymm0, %ymm3 -; AVX512F-NEXT: vextracti64x4 $1, %zmm0, %ymm0 +; AVX512F-NEXT: vextracti64x4 $1, %zmm0, %ymm3 +; AVX512F-NEXT: vpaddb %ymm1, %ymm3, %ymm3 ; AVX512F-NEXT: vpaddb %ymm1, %ymm0, %ymm0 -; AVX512F-NEXT: vinserti64x4 $1, %ymm0, %zmm3, %zmm4 +; AVX512F-NEXT: vinserti64x4 $1, %ymm3, %zmm0, %zmm4 +; AVX512F-NEXT: vpaddb %ymm1, %ymm3, %ymm3 ; AVX512F-NEXT: vpaddb %ymm1, %ymm0, %ymm0 -; AVX512F-NEXT: vpaddb %ymm1, %ymm3, %ymm1 -; AVX512F-NEXT: vinserti64x4 $1, %ymm0, %zmm1, %zmm0 +; AVX512F-NEXT: vinserti64x4 $1, %ymm3, %zmm0, %zmm0 ; AVX512F-NEXT: vpternlogq $226, %zmm4, %zmm2, %zmm0 ; AVX512F-NEXT: retq ; diff --git a/llvm/test/CodeGen/X86/combine-mul.ll b/llvm/test/CodeGen/X86/combine-mul.ll index 8d2bb77a9e1af68d98fb6500b0b671c824d90549..5d7bf4a2c9788ff9c1fd4ca8723869301f8e6097 100644 --- a/llvm/test/CodeGen/X86/combine-mul.ll +++ b/llvm/test/CodeGen/X86/combine-mul.ll @@ -80,13 +80,13 @@ define <4 x i32> @combine_vec_mul_pow2b(<4 x i32> %x) { define <4 x i64> @combine_vec_mul_pow2c(<4 x i64> %x) { ; SSE-LABEL: combine_vec_mul_pow2c: ; SSE: # %bb.0: +; SSE-NEXT: movdqa %xmm0, %xmm2 +; SSE-NEXT: paddq %xmm0, %xmm2 +; SSE-NEXT: pblendw {{.*#+}} xmm0 = xmm0[0,1,2,3],xmm2[4,5,6,7] ; SSE-NEXT: movdqa %xmm1, %xmm2 ; SSE-NEXT: psllq $4, %xmm2 ; SSE-NEXT: psllq $2, %xmm1 ; SSE-NEXT: pblendw {{.*#+}} xmm1 = xmm1[0,1,2,3],xmm2[4,5,6,7] -; SSE-NEXT: movdqa %xmm0, %xmm2 -; SSE-NEXT: paddq %xmm0, %xmm2 -; SSE-NEXT: pblendw {{.*#+}} xmm0 = xmm0[0,1,2,3],xmm2[4,5,6,7] ; SSE-NEXT: retq ; ; AVX-LABEL: combine_vec_mul_pow2c: @@ -399,14 +399,12 @@ define i64 @combine_mul_self_demandedbits(i64 %x) { ; SSE: # %bb.0: ; SSE-NEXT: movq %rdi, %rax ; SSE-NEXT: imulq %rdi, %rax -; SSE-NEXT: andq $-3, %rax ; SSE-NEXT: retq ; ; AVX-LABEL: combine_mul_self_demandedbits: ; AVX: # %bb.0: ; AVX-NEXT: movq %rdi, %rax ; AVX-NEXT: imulq %rdi, %rax -; AVX-NEXT: andq $-3, %rax ; AVX-NEXT: retq %1 = mul i64 %x, %x %2 = and i64 %1, -3 diff --git a/llvm/test/CodeGen/X86/combine-or-shuffle.ll b/llvm/test/CodeGen/X86/combine-or-shuffle.ll new file mode 100644 index 0000000000000000000000000000000000000000..175d21a4f7067c8615d1dd171ea5d656be229976 --- /dev/null +++ b/llvm/test/CodeGen/X86/combine-or-shuffle.ll @@ -0,0 +1,862 @@ +; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py +; RUN: llc < %s -mtriple=x86_64-unknown-linux-gnu -mattr=+sse | FileCheck %s -check-prefixes=SSE,SSE2 +; RUN: llc < %s -mtriple=x86_64-unknown-linux-gnu -mattr=+sse4.1 | FileCheck %s -check-prefixes=SSE,SSE4 +; RUN: llc < %s -mtriple=x86_64-unknown-linux-gnu -mattr=+avx | FileCheck %s -check-prefixes=AVX,AVX1 +; RUN: llc < %s -mtriple=x86_64-unknown-linux-gnu -mattr=+avx2 | FileCheck %s -check-prefixes=AVX,AVX2 +; RUN: llc < %s -mtriple=x86_64-unknown-linux-gnu -mcpu=x86-64-v4 | FileCheck %s -check-prefixes=AVX,AVX512 + +; Verify that each of the following test cases is folded into a single +; instruction which performs a blend operation. + +define <2 x i64> @test1(<2 x i64> %a, <2 x i64> %b) { +; SSE2-LABEL: test1: +; SSE2: # %bb.0: +; SSE2-NEXT: shufps {{.*#+}} xmm0 = xmm0[0,1],xmm1[2,3] +; SSE2-NEXT: retq +; +; SSE4-LABEL: test1: +; SSE4: # %bb.0: +; SSE4-NEXT: blendps {{.*#+}} xmm0 = xmm0[0,1],xmm1[2,3] +; SSE4-NEXT: retq +; +; AVX-LABEL: test1: +; AVX: # %bb.0: +; AVX-NEXT: vblendps {{.*#+}} xmm0 = xmm0[0,1],xmm1[2,3] +; AVX-NEXT: retq + %shuf1 = shufflevector <2 x i64> %a, <2 x i64> zeroinitializer, <2 x i32> + %shuf2 = shufflevector <2 x i64> %b, <2 x i64> zeroinitializer, <2 x i32> + %or = or <2 x i64> %shuf1, %shuf2 + ret <2 x i64> %or +} + + +define <4 x i32> @test2(<4 x i32> %a, <4 x i32> %b) { +; SSE2-LABEL: test2: +; SSE2: # %bb.0: +; SSE2-NEXT: movsd {{.*#+}} xmm0 = xmm1[0],xmm0[1] +; SSE2-NEXT: retq +; +; SSE4-LABEL: test2: +; SSE4: # %bb.0: +; SSE4-NEXT: blendps {{.*#+}} xmm0 = xmm1[0,1],xmm0[2,3] +; SSE4-NEXT: retq +; +; AVX-LABEL: test2: +; AVX: # %bb.0: +; AVX-NEXT: vblendps {{.*#+}} xmm0 = xmm1[0,1],xmm0[2,3] +; AVX-NEXT: retq + %shuf1 = shufflevector <4 x i32> %a, <4 x i32> zeroinitializer, <4 x i32> + %shuf2 = shufflevector <4 x i32> %b, <4 x i32> zeroinitializer, <4 x i32> + %or = or <4 x i32> %shuf1, %shuf2 + ret <4 x i32> %or +} + + +define <2 x i64> @test3(<2 x i64> %a, <2 x i64> %b) { +; SSE2-LABEL: test3: +; SSE2: # %bb.0: +; SSE2-NEXT: movsd {{.*#+}} xmm0 = xmm1[0],xmm0[1] +; SSE2-NEXT: retq +; +; SSE4-LABEL: test3: +; SSE4: # %bb.0: +; SSE4-NEXT: blendps {{.*#+}} xmm0 = xmm1[0,1],xmm0[2,3] +; SSE4-NEXT: retq +; +; AVX-LABEL: test3: +; AVX: # %bb.0: +; AVX-NEXT: vblendps {{.*#+}} xmm0 = xmm1[0,1],xmm0[2,3] +; AVX-NEXT: retq + %shuf1 = shufflevector <2 x i64> %a, <2 x i64> zeroinitializer, <2 x i32> + %shuf2 = shufflevector <2 x i64> %b, <2 x i64> zeroinitializer, <2 x i32> + %or = or <2 x i64> %shuf1, %shuf2 + ret <2 x i64> %or +} + + +define <4 x i32> @test4(<4 x i32> %a, <4 x i32> %b) { +; SSE2-LABEL: test4: +; SSE2: # %bb.0: +; SSE2-NEXT: movss {{.*#+}} xmm1 = xmm0[0],xmm1[1,2,3] +; SSE2-NEXT: movaps %xmm1, %xmm0 +; SSE2-NEXT: retq +; +; SSE4-LABEL: test4: +; SSE4: # %bb.0: +; SSE4-NEXT: blendps {{.*#+}} xmm0 = xmm0[0],xmm1[1,2,3] +; SSE4-NEXT: retq +; +; AVX-LABEL: test4: +; AVX: # %bb.0: +; AVX-NEXT: vblendps {{.*#+}} xmm0 = xmm0[0],xmm1[1,2,3] +; AVX-NEXT: retq + %shuf1 = shufflevector <4 x i32> %a, <4 x i32> zeroinitializer, <4 x i32> + %shuf2 = shufflevector <4 x i32> %b, <4 x i32> zeroinitializer, <4 x i32> + %or = or <4 x i32> %shuf1, %shuf2 + ret <4 x i32> %or +} + + +define <4 x i32> @test5(<4 x i32> %a, <4 x i32> %b) { +; SSE2-LABEL: test5: +; SSE2: # %bb.0: +; SSE2-NEXT: movss {{.*#+}} xmm0 = xmm1[0],xmm0[1,2,3] +; SSE2-NEXT: retq +; +; SSE4-LABEL: test5: +; SSE4: # %bb.0: +; SSE4-NEXT: blendps {{.*#+}} xmm0 = xmm1[0],xmm0[1,2,3] +; SSE4-NEXT: retq +; +; AVX-LABEL: test5: +; AVX: # %bb.0: +; AVX-NEXT: vblendps {{.*#+}} xmm0 = xmm1[0],xmm0[1,2,3] +; AVX-NEXT: retq + %shuf1 = shufflevector <4 x i32> %a, <4 x i32> zeroinitializer, <4 x i32> + %shuf2 = shufflevector <4 x i32> %b, <4 x i32> zeroinitializer, <4 x i32> + %or = or <4 x i32> %shuf1, %shuf2 + ret <4 x i32> %or +} + + +define <4 x i32> @test6(<4 x i32> %a, <4 x i32> %b) { +; SSE2-LABEL: test6: +; SSE2: # %bb.0: +; SSE2-NEXT: shufps {{.*#+}} xmm0 = xmm0[0,1],xmm1[2,3] +; SSE2-NEXT: retq +; +; SSE4-LABEL: test6: +; SSE4: # %bb.0: +; SSE4-NEXT: blendps {{.*#+}} xmm0 = xmm0[0,1],xmm1[2,3] +; SSE4-NEXT: retq +; +; AVX-LABEL: test6: +; AVX: # %bb.0: +; AVX-NEXT: vblendps {{.*#+}} xmm0 = xmm0[0,1],xmm1[2,3] +; AVX-NEXT: retq + %shuf1 = shufflevector <4 x i32> %a, <4 x i32> zeroinitializer, <4 x i32> + %shuf2 = shufflevector <4 x i32> %b, <4 x i32> zeroinitializer, <4 x i32> + %or = or <4 x i32> %shuf1, %shuf2 + ret <4 x i32> %or +} + + +define <4 x i32> @test7(<4 x i32> %a, <4 x i32> %b) { +; SSE2-LABEL: test7: +; SSE2: # %bb.0: +; SSE2-NEXT: shufps {{.*#+}} xmm0 = xmm0[0,1],xmm1[2,3] +; SSE2-NEXT: retq +; +; SSE4-LABEL: test7: +; SSE4: # %bb.0: +; SSE4-NEXT: blendps {{.*#+}} xmm0 = xmm0[0,1],xmm1[2,3] +; SSE4-NEXT: retq +; +; AVX-LABEL: test7: +; AVX: # %bb.0: +; AVX-NEXT: vblendps {{.*#+}} xmm0 = xmm0[0,1],xmm1[2,3] +; AVX-NEXT: retq + %and1 = and <4 x i32> %a, + %and2 = and <4 x i32> %b, + %or = or <4 x i32> %and1, %and2 + ret <4 x i32> %or +} + + +define <2 x i64> @test8(<2 x i64> %a, <2 x i64> %b) { +; SSE2-LABEL: test8: +; SSE2: # %bb.0: +; SSE2-NEXT: shufps {{.*#+}} xmm0 = xmm0[0,1],xmm1[2,3] +; SSE2-NEXT: retq +; +; SSE4-LABEL: test8: +; SSE4: # %bb.0: +; SSE4-NEXT: blendps {{.*#+}} xmm0 = xmm0[0,1],xmm1[2,3] +; SSE4-NEXT: retq +; +; AVX-LABEL: test8: +; AVX: # %bb.0: +; AVX-NEXT: vblendps {{.*#+}} xmm0 = xmm0[0,1],xmm1[2,3] +; AVX-NEXT: retq + %and1 = and <2 x i64> %a, + %and2 = and <2 x i64> %b, + %or = or <2 x i64> %and1, %and2 + ret <2 x i64> %or +} + + +define <4 x i32> @test9(<4 x i32> %a, <4 x i32> %b) { +; SSE2-LABEL: test9: +; SSE2: # %bb.0: +; SSE2-NEXT: movsd {{.*#+}} xmm0 = xmm1[0],xmm0[1] +; SSE2-NEXT: retq +; +; SSE4-LABEL: test9: +; SSE4: # %bb.0: +; SSE4-NEXT: blendps {{.*#+}} xmm0 = xmm1[0,1],xmm0[2,3] +; SSE4-NEXT: retq +; +; AVX-LABEL: test9: +; AVX: # %bb.0: +; AVX-NEXT: vblendps {{.*#+}} xmm0 = xmm1[0,1],xmm0[2,3] +; AVX-NEXT: retq + %and1 = and <4 x i32> %a, + %and2 = and <4 x i32> %b, + %or = or <4 x i32> %and1, %and2 + ret <4 x i32> %or +} + + +define <2 x i64> @test10(<2 x i64> %a, <2 x i64> %b) { +; SSE2-LABEL: test10: +; SSE2: # %bb.0: +; SSE2-NEXT: movsd {{.*#+}} xmm0 = xmm1[0],xmm0[1] +; SSE2-NEXT: retq +; +; SSE4-LABEL: test10: +; SSE4: # %bb.0: +; SSE4-NEXT: blendps {{.*#+}} xmm0 = xmm1[0,1],xmm0[2,3] +; SSE4-NEXT: retq +; +; AVX-LABEL: test10: +; AVX: # %bb.0: +; AVX-NEXT: vblendps {{.*#+}} xmm0 = xmm1[0,1],xmm0[2,3] +; AVX-NEXT: retq + %and1 = and <2 x i64> %a, + %and2 = and <2 x i64> %b, + %or = or <2 x i64> %and1, %and2 + ret <2 x i64> %or +} + + +define <4 x i32> @test11(<4 x i32> %a, <4 x i32> %b) { +; SSE2-LABEL: test11: +; SSE2: # %bb.0: +; SSE2-NEXT: movss {{.*#+}} xmm1 = xmm0[0],xmm1[1,2,3] +; SSE2-NEXT: movaps %xmm1, %xmm0 +; SSE2-NEXT: retq +; +; SSE4-LABEL: test11: +; SSE4: # %bb.0: +; SSE4-NEXT: blendps {{.*#+}} xmm0 = xmm0[0],xmm1[1,2,3] +; SSE4-NEXT: retq +; +; AVX-LABEL: test11: +; AVX: # %bb.0: +; AVX-NEXT: vblendps {{.*#+}} xmm0 = xmm0[0],xmm1[1,2,3] +; AVX-NEXT: retq + %and1 = and <4 x i32> %a, + %and2 = and <4 x i32> %b, + %or = or <4 x i32> %and1, %and2 + ret <4 x i32> %or +} + + +define <4 x i32> @test12(<4 x i32> %a, <4 x i32> %b) { +; SSE2-LABEL: test12: +; SSE2: # %bb.0: +; SSE2-NEXT: movss {{.*#+}} xmm0 = xmm1[0],xmm0[1,2,3] +; SSE2-NEXT: retq +; +; SSE4-LABEL: test12: +; SSE4: # %bb.0: +; SSE4-NEXT: blendps {{.*#+}} xmm0 = xmm1[0],xmm0[1,2,3] +; SSE4-NEXT: retq +; +; AVX-LABEL: test12: +; AVX: # %bb.0: +; AVX-NEXT: vblendps {{.*#+}} xmm0 = xmm1[0],xmm0[1,2,3] +; AVX-NEXT: retq + %and1 = and <4 x i32> %a, + %and2 = and <4 x i32> %b, + %or = or <4 x i32> %and1, %and2 + ret <4 x i32> %or +} + + +; Verify that the following test cases are folded into single shuffles. + +define <4 x i32> @test13(<4 x i32> %a, <4 x i32> %b) { +; SSE-LABEL: test13: +; SSE: # %bb.0: +; SSE-NEXT: shufps {{.*#+}} xmm0 = xmm0[1,1],xmm1[2,3] +; SSE-NEXT: retq +; +; AVX-LABEL: test13: +; AVX: # %bb.0: +; AVX-NEXT: vshufps {{.*#+}} xmm0 = xmm0[1,1],xmm1[2,3] +; AVX-NEXT: retq + %shuf1 = shufflevector <4 x i32> %a, <4 x i32> zeroinitializer, <4 x i32> + %shuf2 = shufflevector <4 x i32> %b, <4 x i32> zeroinitializer, <4 x i32> + %or = or <4 x i32> %shuf1, %shuf2 + ret <4 x i32> %or +} + + +define <2 x i64> @test14(<2 x i64> %a, <2 x i64> %b) { +; SSE-LABEL: test14: +; SSE: # %bb.0: +; SSE-NEXT: movlhps {{.*#+}} xmm0 = xmm0[0],xmm1[0] +; SSE-NEXT: retq +; +; AVX-LABEL: test14: +; AVX: # %bb.0: +; AVX-NEXT: vmovlhps {{.*#+}} xmm0 = xmm0[0],xmm1[0] +; AVX-NEXT: retq + %shuf1 = shufflevector <2 x i64> %a, <2 x i64> zeroinitializer, <2 x i32> + %shuf2 = shufflevector <2 x i64> %b, <2 x i64> zeroinitializer, <2 x i32> + %or = or <2 x i64> %shuf1, %shuf2 + ret <2 x i64> %or +} + + +define <4 x i32> @test15(<4 x i32> %a, <4 x i32> %b) { +; SSE-LABEL: test15: +; SSE: # %bb.0: +; SSE-NEXT: shufps {{.*#+}} xmm1 = xmm1[2,1],xmm0[2,1] +; SSE-NEXT: movaps %xmm1, %xmm0 +; SSE-NEXT: retq +; +; AVX-LABEL: test15: +; AVX: # %bb.0: +; AVX-NEXT: vshufps {{.*#+}} xmm0 = xmm1[2,1],xmm0[2,1] +; AVX-NEXT: retq + %shuf1 = shufflevector <4 x i32> %a, <4 x i32> zeroinitializer, <4 x i32> + %shuf2 = shufflevector <4 x i32> %b, <4 x i32> zeroinitializer, <4 x i32> + %or = or <4 x i32> %shuf1, %shuf2 + ret <4 x i32> %or +} + + +define <2 x i64> @test16(<2 x i64> %a, <2 x i64> %b) { +; SSE-LABEL: test16: +; SSE: # %bb.0: +; SSE-NEXT: movlhps {{.*#+}} xmm1 = xmm1[0],xmm0[0] +; SSE-NEXT: movaps %xmm1, %xmm0 +; SSE-NEXT: retq +; +; AVX-LABEL: test16: +; AVX: # %bb.0: +; AVX-NEXT: vmovlhps {{.*#+}} xmm0 = xmm1[0],xmm0[0] +; AVX-NEXT: retq + %shuf1 = shufflevector <2 x i64> %a, <2 x i64> zeroinitializer, <2 x i32> + %shuf2 = shufflevector <2 x i64> %b, <2 x i64> zeroinitializer, <2 x i32> + %or = or <2 x i64> %shuf1, %shuf2 + ret <2 x i64> %or +} + + +; Verify that the dag-combiner does not fold a OR of two shuffles into a single +; shuffle instruction when the shuffle indexes are not compatible. + +define <4 x i32> @test17(<4 x i32> %a, <4 x i32> %b) { +; SSE-LABEL: test17: +; SSE: # %bb.0: +; SSE-NEXT: psllq $32, %xmm0 +; SSE-NEXT: movq {{.*#+}} xmm1 = xmm1[0],zero +; SSE-NEXT: por %xmm1, %xmm0 +; SSE-NEXT: retq +; +; AVX-LABEL: test17: +; AVX: # %bb.0: +; AVX-NEXT: vpsllq $32, %xmm0, %xmm0 +; AVX-NEXT: vmovq {{.*#+}} xmm1 = xmm1[0],zero +; AVX-NEXT: vpor %xmm1, %xmm0, %xmm0 +; AVX-NEXT: retq + %shuf1 = shufflevector <4 x i32> %a, <4 x i32> zeroinitializer, <4 x i32> + %shuf2 = shufflevector <4 x i32> %b, <4 x i32> zeroinitializer, <4 x i32> + %or = or <4 x i32> %shuf1, %shuf2 + ret <4 x i32> %or +} + + +define <4 x i32> @test18(<4 x i32> %a, <4 x i32> %b) { +; SSE2-LABEL: test18: +; SSE2: # %bb.0: +; SSE2-NEXT: xorps %xmm2, %xmm2 +; SSE2-NEXT: xorps %xmm3, %xmm3 +; SSE2-NEXT: movss {{.*#+}} xmm3 = xmm0[0],xmm3[1,2,3] +; SSE2-NEXT: pshufd {{.*#+}} xmm0 = xmm3[1,0,1,1] +; SSE2-NEXT: movss {{.*#+}} xmm2 = xmm1[0],xmm2[1,2,3] +; SSE2-NEXT: orps %xmm0, %xmm2 +; SSE2-NEXT: movaps %xmm2, %xmm0 +; SSE2-NEXT: retq +; +; SSE4-LABEL: test18: +; SSE4: # %bb.0: +; SSE4-NEXT: pxor %xmm2, %xmm2 +; SSE4-NEXT: pblendw {{.*#+}} xmm0 = xmm0[0,1],xmm2[2,3,4,5,6,7] +; SSE4-NEXT: pshufd {{.*#+}} xmm0 = xmm0[1,0,1,1] +; SSE4-NEXT: pblendw {{.*#+}} xmm2 = xmm1[0,1],xmm2[2,3,4,5,6,7] +; SSE4-NEXT: por %xmm0, %xmm2 +; SSE4-NEXT: movdqa %xmm2, %xmm0 +; SSE4-NEXT: retq +; +; AVX1-LABEL: test18: +; AVX1: # %bb.0: +; AVX1-NEXT: vxorps %xmm2, %xmm2, %xmm2 +; AVX1-NEXT: vblendps {{.*#+}} xmm0 = xmm0[0],xmm2[1,2,3] +; AVX1-NEXT: vshufps {{.*#+}} xmm0 = xmm0[1,0,1,1] +; AVX1-NEXT: vblendps {{.*#+}} xmm1 = xmm1[0],xmm2[1,2,3] +; AVX1-NEXT: vorps %xmm1, %xmm0, %xmm0 +; AVX1-NEXT: retq +; +; AVX2-LABEL: test18: +; AVX2: # %bb.0: +; AVX2-NEXT: vxorps %xmm2, %xmm2, %xmm2 +; AVX2-NEXT: vblendps {{.*#+}} xmm0 = xmm0[0],xmm2[1,2,3] +; AVX2-NEXT: vshufps {{.*#+}} xmm0 = xmm0[1,0,1,1] +; AVX2-NEXT: vblendps {{.*#+}} xmm1 = xmm1[0],xmm2[1,2,3] +; AVX2-NEXT: vorps %xmm1, %xmm0, %xmm0 +; AVX2-NEXT: retq +; +; AVX512-LABEL: test18: +; AVX512: # %bb.0: +; AVX512-NEXT: vpshufb {{.*#+}} xmm0 = zero,zero,zero,zero,xmm0[0,1,2,3],zero,zero,zero,zero,zero,zero,zero,zero +; AVX512-NEXT: vpxor %xmm2, %xmm2, %xmm2 +; AVX512-NEXT: vpblendw {{.*#+}} xmm1 = xmm1[0,1],xmm2[2,3,4,5,6,7] +; AVX512-NEXT: vpor %xmm1, %xmm0, %xmm0 +; AVX512-NEXT: retq + %shuf1 = shufflevector <4 x i32> %a, <4 x i32> zeroinitializer, <4 x i32> + %shuf2 = shufflevector <4 x i32> %b, <4 x i32> zeroinitializer, <4 x i32> + %or = or <4 x i32> %shuf1, %shuf2 + ret <4 x i32> %or +} + + +define <4 x i32> @test19(<4 x i32> %a, <4 x i32> %b) { +; SSE2-LABEL: test19: +; SSE2: # %bb.0: +; SSE2-NEXT: pshufd {{.*#+}} xmm0 = xmm0[0,3,2,3] +; SSE2-NEXT: pxor %xmm2, %xmm2 +; SSE2-NEXT: punpckldq {{.*#+}} xmm2 = xmm2[0],xmm0[0],xmm2[1],xmm0[1] +; SSE2-NEXT: movdqa %xmm1, %xmm0 +; SSE2-NEXT: pslldq {{.*#+}} xmm0 = zero,zero,zero,zero,zero,zero,zero,zero,xmm0[0,1,2,3,4,5,6,7] +; SSE2-NEXT: shufps {{.*#+}} xmm0 = xmm0[2,0],xmm1[2,2] +; SSE2-NEXT: orps %xmm2, %xmm0 +; SSE2-NEXT: retq +; +; SSE4-LABEL: test19: +; SSE4: # %bb.0: +; SSE4-NEXT: pshufd {{.*#+}} xmm2 = xmm0[0,0,2,3] +; SSE4-NEXT: pxor %xmm3, %xmm3 +; SSE4-NEXT: pblendw {{.*#+}} xmm2 = xmm3[0,1],xmm2[2,3],xmm3[4,5],xmm2[6,7] +; SSE4-NEXT: pshufd {{.*#+}} xmm0 = xmm1[0,1,2,2] +; SSE4-NEXT: pblendw {{.*#+}} xmm0 = xmm0[0,1],xmm3[2,3],xmm0[4,5,6,7] +; SSE4-NEXT: por %xmm2, %xmm0 +; SSE4-NEXT: retq +; +; AVX1-LABEL: test19: +; AVX1: # %bb.0: +; AVX1-NEXT: vshufps {{.*#+}} xmm0 = xmm0[0,0,2,3] +; AVX1-NEXT: vxorps %xmm2, %xmm2, %xmm2 +; AVX1-NEXT: vblendps {{.*#+}} xmm0 = xmm2[0],xmm0[1],xmm2[2],xmm0[3] +; AVX1-NEXT: vshufps {{.*#+}} xmm1 = xmm1[0,1,2,2] +; AVX1-NEXT: vblendps {{.*#+}} xmm1 = xmm1[0],xmm2[1],xmm1[2,3] +; AVX1-NEXT: vorps %xmm1, %xmm0, %xmm0 +; AVX1-NEXT: retq +; +; AVX2-LABEL: test19: +; AVX2: # %bb.0: +; AVX2-NEXT: vshufps {{.*#+}} xmm0 = xmm0[0,0,2,3] +; AVX2-NEXT: vxorps %xmm2, %xmm2, %xmm2 +; AVX2-NEXT: vblendps {{.*#+}} xmm0 = xmm2[0],xmm0[1],xmm2[2],xmm0[3] +; AVX2-NEXT: vshufps {{.*#+}} xmm1 = xmm1[0,1,2,2] +; AVX2-NEXT: vblendps {{.*#+}} xmm1 = xmm1[0],xmm2[1],xmm1[2,3] +; AVX2-NEXT: vorps %xmm1, %xmm0, %xmm0 +; AVX2-NEXT: retq +; +; AVX512-LABEL: test19: +; AVX512: # %bb.0: +; AVX512-NEXT: vpshufb {{.*#+}} xmm0 = zero,zero,zero,zero,xmm0[0,1,2,3],zero,zero,zero,zero,xmm0[12,13,14,15] +; AVX512-NEXT: vpshufb {{.*#+}} xmm1 = xmm1[0,1,2,3],zero,zero,zero,zero,xmm1[8,9,10,11,8,9,10,11] +; AVX512-NEXT: vpor %xmm1, %xmm0, %xmm0 +; AVX512-NEXT: retq + %shuf1 = shufflevector <4 x i32> %a, <4 x i32> zeroinitializer, <4 x i32> + %shuf2 = shufflevector <4 x i32> %b, <4 x i32> zeroinitializer, <4 x i32> + %or = or <4 x i32> %shuf1, %shuf2 + ret <4 x i32> %or +} + + +define <2 x i64> @test20(<2 x i64> %a, <2 x i64> %b) { +; SSE-LABEL: test20: +; SSE: # %bb.0: +; SSE-NEXT: por %xmm1, %xmm0 +; SSE-NEXT: movq {{.*#+}} xmm0 = xmm0[0],zero +; SSE-NEXT: retq +; +; AVX-LABEL: test20: +; AVX: # %bb.0: +; AVX-NEXT: vpor %xmm1, %xmm0, %xmm0 +; AVX-NEXT: vmovq {{.*#+}} xmm0 = xmm0[0],zero +; AVX-NEXT: retq + %shuf1 = shufflevector <2 x i64> %a, <2 x i64> zeroinitializer, <2 x i32> + %shuf2 = shufflevector <2 x i64> %b, <2 x i64> zeroinitializer, <2 x i32> + %or = or <2 x i64> %shuf1, %shuf2 + ret <2 x i64> %or +} + + +define <2 x i64> @test21(<2 x i64> %a, <2 x i64> %b) { +; SSE-LABEL: test21: +; SSE: # %bb.0: +; SSE-NEXT: por %xmm1, %xmm0 +; SSE-NEXT: pslldq {{.*#+}} xmm0 = zero,zero,zero,zero,zero,zero,zero,zero,xmm0[0,1,2,3,4,5,6,7] +; SSE-NEXT: retq +; +; AVX1-LABEL: test21: +; AVX1: # %bb.0: +; AVX1-NEXT: vpor %xmm1, %xmm0, %xmm0 +; AVX1-NEXT: vpslldq {{.*#+}} xmm0 = zero,zero,zero,zero,zero,zero,zero,zero,xmm0[0,1,2,3,4,5,6,7] +; AVX1-NEXT: retq +; +; AVX2-LABEL: test21: +; AVX2: # %bb.0: +; AVX2-NEXT: vpor %xmm1, %xmm0, %xmm0 +; AVX2-NEXT: vpslldq {{.*#+}} xmm0 = zero,zero,zero,zero,zero,zero,zero,zero,xmm0[0,1,2,3,4,5,6,7] +; AVX2-NEXT: retq +; +; AVX512-LABEL: test21: +; AVX512: # %bb.0: +; AVX512-NEXT: vorpd %xmm1, %xmm0, %xmm0 +; AVX512-NEXT: vpslldq {{.*#+}} xmm0 = zero,zero,zero,zero,zero,zero,zero,zero,xmm0[0,1,2,3,4,5,6,7] +; AVX512-NEXT: retq + %shuf1 = shufflevector <2 x i64> %a, <2 x i64> zeroinitializer, <2 x i32> + %shuf2 = shufflevector <2 x i64> %b, <2 x i64> zeroinitializer, <2 x i32> + %or = or <2 x i64> %shuf1, %shuf2 + ret <2 x i64> %or +} + + +; Verify that the dag-combiner keeps the correct domain for float/double vectors +; bitcast to use the mask-or blend combine. + +define <2 x double> @test22(<2 x double> %a0, <2 x double> %a1) { +; SSE2-LABEL: test22: +; SSE2: # %bb.0: +; SSE2-NEXT: movsd {{.*#+}} xmm0 = xmm1[0],xmm0[1] +; SSE2-NEXT: retq +; +; SSE4-LABEL: test22: +; SSE4: # %bb.0: +; SSE4-NEXT: blendps {{.*#+}} xmm0 = xmm1[0,1],xmm0[2,3] +; SSE4-NEXT: retq +; +; AVX-LABEL: test22: +; AVX: # %bb.0: +; AVX-NEXT: vblendps {{.*#+}} xmm0 = xmm1[0,1],xmm0[2,3] +; AVX-NEXT: retq + %bc1 = bitcast <2 x double> %a0 to <2 x i64> + %bc2 = bitcast <2 x double> %a1 to <2 x i64> + %and1 = and <2 x i64> %bc1, + %and2 = and <2 x i64> %bc2, + %or = or <2 x i64> %and1, %and2 + %bc3 = bitcast <2 x i64> %or to <2 x double> + ret <2 x double> %bc3 +} + + +define <4 x float> @test23(<4 x float> %a0, <4 x float> %a1) { +; SSE2-LABEL: test23: +; SSE2: # %bb.0: +; SSE2-NEXT: shufps {{.*#+}} xmm0 = xmm0[1,2],xmm1[0,3] +; SSE2-NEXT: shufps {{.*#+}} xmm0 = xmm0[2,0,1,3] +; SSE2-NEXT: retq +; +; SSE4-LABEL: test23: +; SSE4: # %bb.0: +; SSE4-NEXT: blendps {{.*#+}} xmm0 = xmm1[0],xmm0[1,2],xmm1[3] +; SSE4-NEXT: retq +; +; AVX-LABEL: test23: +; AVX: # %bb.0: +; AVX-NEXT: vblendps {{.*#+}} xmm0 = xmm1[0],xmm0[1,2],xmm1[3] +; AVX-NEXT: retq + %bc1 = bitcast <4 x float> %a0 to <4 x i32> + %bc2 = bitcast <4 x float> %a1 to <4 x i32> + %and1 = and <4 x i32> %bc1, + %and2 = and <4 x i32> %bc2, + %or = or <4 x i32> %and1, %and2 + %bc3 = bitcast <4 x i32> %or to <4 x float> + ret <4 x float> %bc3 +} + + +define <4 x float> @test24(<4 x float> %a0, <4 x float> %a1) { +; SSE2-LABEL: test24: +; SSE2: # %bb.0: +; SSE2-NEXT: movsd {{.*#+}} xmm0 = xmm1[0],xmm0[1] +; SSE2-NEXT: retq +; +; SSE4-LABEL: test24: +; SSE4: # %bb.0: +; SSE4-NEXT: blendps {{.*#+}} xmm0 = xmm1[0,1],xmm0[2,3] +; SSE4-NEXT: retq +; +; AVX-LABEL: test24: +; AVX: # %bb.0: +; AVX-NEXT: vblendps {{.*#+}} xmm0 = xmm1[0,1],xmm0[2,3] +; AVX-NEXT: retq + %bc1 = bitcast <4 x float> %a0 to <2 x i64> + %bc2 = bitcast <4 x float> %a1 to <2 x i64> + %and1 = and <2 x i64> %bc1, + %and2 = and <2 x i64> %bc2, + %or = or <2 x i64> %and1, %and2 + %bc3 = bitcast <2 x i64> %or to <4 x float> + ret <4 x float> %bc3 +} + + +define <4 x float> @test25(<4 x float> %a0) { +; SSE2-LABEL: test25: +; SSE2: # %bb.0: +; SSE2-NEXT: shufps {{.*#+}} xmm0 = xmm0[1,2],mem[0,3] +; SSE2-NEXT: shufps {{.*#+}} xmm0 = xmm0[2,0,1,3] +; SSE2-NEXT: retq +; +; SSE4-LABEL: test25: +; SSE4: # %bb.0: +; SSE4-NEXT: blendps {{.*#+}} xmm0 = mem[0],xmm0[1,2],mem[3] +; SSE4-NEXT: retq +; +; AVX1-LABEL: test25: +; AVX1: # %bb.0: +; AVX1-NEXT: vblendps {{.*#+}} xmm0 = mem[0],xmm0[1,2],mem[3] +; AVX1-NEXT: retq +; +; AVX2-LABEL: test25: +; AVX2: # %bb.0: +; AVX2-NEXT: vbroadcastss {{.*#+}} xmm1 = [1.0E+0,1.0E+0,1.0E+0,1.0E+0] +; AVX2-NEXT: vblendps {{.*#+}} xmm0 = xmm1[0],xmm0[1,2],xmm1[3] +; AVX2-NEXT: retq +; +; AVX512-LABEL: test25: +; AVX512: # %bb.0: +; AVX512-NEXT: vbroadcastss {{.*#+}} xmm1 = [1.0E+0,1.0E+0,1.0E+0,1.0E+0] +; AVX512-NEXT: vblendps {{.*#+}} xmm0 = xmm1[0],xmm0[1,2],xmm1[3] +; AVX512-NEXT: retq + %bc1 = bitcast <4 x float> %a0 to <4 x i32> + %bc2 = bitcast <4 x float> to <4 x i32> + %and1 = and <4 x i32> %bc1, + %and2 = and <4 x i32> %bc2, + %or = or <4 x i32> %and1, %and2 + %bc3 = bitcast <4 x i32> %or to <4 x float> + ret <4 x float> %bc3 +} + + +; Verify that the DAGCombiner doesn't crash in the attempt to check if a shuffle +; with illegal type has a legal mask. Method 'isShuffleMaskLegal' only knows how to +; handle legal vector value types. +define <4 x i8> @test_crash(<4 x i8> %a, <4 x i8> %b) { +; SSE2-LABEL: test_crash: +; SSE2: # %bb.0: +; SSE2-NEXT: movaps {{.*#+}} xmm2 = [65535,0,65535,65535,65535,65535,65535,65535] +; SSE2-NEXT: andps %xmm2, %xmm1 +; SSE2-NEXT: andnps %xmm0, %xmm2 +; SSE2-NEXT: orps %xmm1, %xmm2 +; SSE2-NEXT: movaps %xmm2, %xmm0 +; SSE2-NEXT: retq +; +; SSE4-LABEL: test_crash: +; SSE4: # %bb.0: +; SSE4-NEXT: pblendw {{.*#+}} xmm0 = xmm1[0],xmm0[1],xmm1[2,3,4,5,6,7] +; SSE4-NEXT: retq +; +; AVX-LABEL: test_crash: +; AVX: # %bb.0: +; AVX-NEXT: vpblendw {{.*#+}} xmm0 = xmm1[0],xmm0[1],xmm1[2,3,4,5,6,7] +; AVX-NEXT: retq + %shuf1 = shufflevector <4 x i8> %a, <4 x i8> zeroinitializer, <4 x i32> + %shuf2 = shufflevector <4 x i8> %b, <4 x i8> zeroinitializer, <4 x i32> + %or = or <4 x i8> %shuf1, %shuf2 + ret <4 x i8> %or +} + +; Verify that we can fold regardless of which operand is the zeroinitializer + +define <4 x i32> @test2b(<4 x i32> %a, <4 x i32> %b) { +; SSE2-LABEL: test2b: +; SSE2: # %bb.0: +; SSE2-NEXT: movsd {{.*#+}} xmm0 = xmm1[0],xmm0[1] +; SSE2-NEXT: retq +; +; SSE4-LABEL: test2b: +; SSE4: # %bb.0: +; SSE4-NEXT: blendps {{.*#+}} xmm0 = xmm1[0,1],xmm0[2,3] +; SSE4-NEXT: retq +; +; AVX-LABEL: test2b: +; AVX: # %bb.0: +; AVX-NEXT: vblendps {{.*#+}} xmm0 = xmm1[0,1],xmm0[2,3] +; AVX-NEXT: retq + %shuf1 = shufflevector <4 x i32> zeroinitializer, <4 x i32> %a, <4 x i32> + %shuf2 = shufflevector <4 x i32> %b, <4 x i32> zeroinitializer, <4 x i32> + %or = or <4 x i32> %shuf1, %shuf2 + ret <4 x i32> %or +} + +define <4 x i32> @test2c(<4 x i32> %a, <4 x i32> %b) { +; SSE2-LABEL: test2c: +; SSE2: # %bb.0: +; SSE2-NEXT: movsd {{.*#+}} xmm0 = xmm1[0],xmm0[1] +; SSE2-NEXT: retq +; +; SSE4-LABEL: test2c: +; SSE4: # %bb.0: +; SSE4-NEXT: blendps {{.*#+}} xmm0 = xmm1[0,1],xmm0[2,3] +; SSE4-NEXT: retq +; +; AVX-LABEL: test2c: +; AVX: # %bb.0: +; AVX-NEXT: vblendps {{.*#+}} xmm0 = xmm1[0,1],xmm0[2,3] +; AVX-NEXT: retq + %shuf1 = shufflevector <4 x i32> zeroinitializer, <4 x i32> %a, <4 x i32> + %shuf2 = shufflevector <4 x i32> zeroinitializer, <4 x i32> %b, <4 x i32> + %or = or <4 x i32> %shuf1, %shuf2 + ret <4 x i32> %or +} + + +define <4 x i32> @test2d(<4 x i32> %a, <4 x i32> %b) { +; SSE2-LABEL: test2d: +; SSE2: # %bb.0: +; SSE2-NEXT: movsd {{.*#+}} xmm0 = xmm1[0],xmm0[1] +; SSE2-NEXT: retq +; +; SSE4-LABEL: test2d: +; SSE4: # %bb.0: +; SSE4-NEXT: blendps {{.*#+}} xmm0 = xmm1[0,1],xmm0[2,3] +; SSE4-NEXT: retq +; +; AVX-LABEL: test2d: +; AVX: # %bb.0: +; AVX-NEXT: vblendps {{.*#+}} xmm0 = xmm1[0,1],xmm0[2,3] +; AVX-NEXT: retq + %shuf1 = shufflevector <4 x i32> %a, <4 x i32> zeroinitializer, <4 x i32> + %shuf2 = shufflevector <4 x i32> zeroinitializer, <4 x i32> %b, <4 x i32> + %or = or <4 x i32> %shuf1, %shuf2 + ret <4 x i32> %or +} + +; Make sure we can have an undef where an index pointing to the zero vector should be + +define <4 x i32> @test2e(<4 x i32> %a, <4 x i32> %b) { +; SSE2-LABEL: test2e: +; SSE2: # %bb.0: +; SSE2-NEXT: movsd {{.*#+}} xmm0 = xmm1[0],xmm0[1] +; SSE2-NEXT: retq +; +; SSE4-LABEL: test2e: +; SSE4: # %bb.0: +; SSE4-NEXT: blendps {{.*#+}} xmm0 = xmm1[0,1],xmm0[2,3] +; SSE4-NEXT: retq +; +; AVX-LABEL: test2e: +; AVX: # %bb.0: +; AVX-NEXT: vblendps {{.*#+}} xmm0 = xmm1[0,1],xmm0[2,3] +; AVX-NEXT: retq + %shuf1 = shufflevector <4 x i32> %a, <4 x i32> , <4 x i32> + %shuf2 = shufflevector <4 x i32> %b, <4 x i32> , <4 x i32> + %or = or <4 x i32> %shuf1, %shuf2 + ret <4 x i32> %or +} + +define <4 x i32> @test2f(<4 x i32> %a, <4 x i32> %b) { +; SSE2-LABEL: test2f: +; SSE2: # %bb.0: +; SSE2-NEXT: movsd {{.*#+}} xmm0 = xmm1[0],xmm0[1] +; SSE2-NEXT: retq +; +; SSE4-LABEL: test2f: +; SSE4: # %bb.0: +; SSE4-NEXT: blendps {{.*#+}} xmm0 = xmm1[0,1],xmm0[2,3] +; SSE4-NEXT: retq +; +; AVX-LABEL: test2f: +; AVX: # %bb.0: +; AVX-NEXT: vblendps {{.*#+}} xmm0 = xmm1[0,1],xmm0[2,3] +; AVX-NEXT: retq + %shuf1 = shufflevector <4 x i32> %a, <4 x i32> , <4 x i32> + %shuf2 = shufflevector <4 x i32> %b, <4 x i32> , <4 x i32> + %or = or <4 x i32> %shuf1, %shuf2 + ret <4 x i32> %or +} + +; (or (and X, c1), c2) -> (and (or X, c2), c1|c2) iff (c1 & c2) != 0 + +define <2 x i64> @or_and_v2i64(<2 x i64> %a0) { +; SSE-LABEL: or_and_v2i64: +; SSE: # %bb.0: +; SSE-NEXT: orps {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm0 +; SSE-NEXT: andps {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm0 +; SSE-NEXT: retq +; +; AVX1-LABEL: or_and_v2i64: +; AVX1: # %bb.0: +; AVX1-NEXT: vorps {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm0, %xmm0 +; AVX1-NEXT: vandps {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm0, %xmm0 +; AVX1-NEXT: retq +; +; AVX2-LABEL: or_and_v2i64: +; AVX2: # %bb.0: +; AVX2-NEXT: vorps {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm0, %xmm0 +; AVX2-NEXT: vandps {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm0, %xmm0 +; AVX2-NEXT: retq +; +; AVX512-LABEL: or_and_v2i64: +; AVX512: # %bb.0: +; AVX512-NEXT: vpbroadcastq {{.*#+}} xmm1 = [7,7] +; AVX512-NEXT: vpternlogq $200, {{\.?LCPI[0-9]+_[0-9]+}}(%rip){1to2}, %xmm1, %xmm0 +; AVX512-NEXT: retq + %1 = and <2 x i64> %a0, + %2 = or <2 x i64> %1, + ret <2 x i64> %2 +} + +define <4 x i32> @or_and_v4i32(<4 x i32> %a0) { +; SSE-LABEL: or_and_v4i32: +; SSE: # %bb.0: +; SSE-NEXT: orps {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm0 +; SSE-NEXT: andps {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm0 +; SSE-NEXT: retq +; +; AVX1-LABEL: or_and_v4i32: +; AVX1: # %bb.0: +; AVX1-NEXT: vorps {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm0, %xmm0 +; AVX1-NEXT: vandps {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm0, %xmm0 +; AVX1-NEXT: retq +; +; AVX2-LABEL: or_and_v4i32: +; AVX2: # %bb.0: +; AVX2-NEXT: vorps {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm0, %xmm0 +; AVX2-NEXT: vandps {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm0, %xmm0 +; AVX2-NEXT: retq +; +; AVX512-LABEL: or_and_v4i32: +; AVX512: # %bb.0: +; AVX512-NEXT: vpmovsxbd {{.*#+}} xmm1 = [3,3,15,7] +; AVX512-NEXT: vpternlogd $200, {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm1, %xmm0 +; AVX512-NEXT: retq + %1 = and <4 x i32> %a0, + %2 = or <4 x i32> %1, + ret <4 x i32> %2 +} + +; If all masked bits are going to be set, that's a constant fold. + +define <4 x i32> @or_and_v4i32_fold(<4 x i32> %a0) { +; SSE-LABEL: or_and_v4i32_fold: +; SSE: # %bb.0: +; SSE-NEXT: movaps {{.*#+}} xmm0 = [3,3,3,3] +; SSE-NEXT: retq +; +; AVX-LABEL: or_and_v4i32_fold: +; AVX: # %bb.0: +; AVX-NEXT: vbroadcastss {{.*#+}} xmm0 = [3,3,3,3] +; AVX-NEXT: retq + %1 = and <4 x i32> %a0, + %2 = or <4 x i32> %1, + ret <4 x i32> %2 +} diff --git a/llvm/test/CodeGen/X86/combine-or.ll b/llvm/test/CodeGen/X86/combine-or.ll index 5188de543f72bf4ee3c3f09dd2674e931382fa91..3b2102f46a297a605ce76e34f014b676c66fda4c 100644 --- a/llvm/test/CodeGen/X86/combine-or.ll +++ b/llvm/test/CodeGen/X86/combine-or.ll @@ -1,6 +1,8 @@ ; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py -; RUN: llc < %s -mtriple=x86_64-unknown-linux-gnu -mcpu=corei7 | FileCheck %s -check-prefixes=CHECK,CHECK-LV -; RUN: llc < %s -mtriple=x86_64-unknown-linux-gnu -mcpu=corei7 -early-live-intervals | FileCheck %s -check-prefixes=CHECK,CHECK-LIS +; RUN: llc < %s -mtriple=x86_64-unknown-linux-gnu -mcpu=corei7 | FileCheck %s -check-prefixes=CHECK,SSE +; RUN: llc < %s -mtriple=x86_64-unknown-linux-gnu -mcpu=corei7 -early-live-intervals | FileCheck %s -check-prefixes=CHECK,SSE +; RUN: llc < %s -mtriple=x86_64-unknown-linux-gnu -mcpu=corei7-avx | FileCheck %s -check-prefixes=CHECK,AVX,AVX1 +; RUN: llc < %s -mtriple=x86_64-unknown-linux-gnu -mcpu=x86-64-v3 | FileCheck %s -check-prefixes=CHECK,AVX,AVX2 define i32 @or_self(i32 %x) { ; CHECK-LABEL: or_self: @@ -19,472 +21,34 @@ define <4 x i32> @or_self_vec(<4 x i32> %x) { ret <4 x i32> %or } -; Verify that each of the following test cases is folded into a single -; instruction which performs a blend operation. - -define <2 x i64> @test1(<2 x i64> %a, <2 x i64> %b) { -; CHECK-LABEL: test1: -; CHECK: # %bb.0: -; CHECK-NEXT: blendps {{.*#+}} xmm0 = xmm0[0,1],xmm1[2,3] -; CHECK-NEXT: retq - %shuf1 = shufflevector <2 x i64> %a, <2 x i64> zeroinitializer, <2 x i32> - %shuf2 = shufflevector <2 x i64> %b, <2 x i64> zeroinitializer, <2 x i32> - %or = or <2 x i64> %shuf1, %shuf2 - ret <2 x i64> %or -} - - -define <4 x i32> @test2(<4 x i32> %a, <4 x i32> %b) { -; CHECK-LABEL: test2: -; CHECK: # %bb.0: -; CHECK-NEXT: blendps {{.*#+}} xmm0 = xmm1[0,1],xmm0[2,3] -; CHECK-NEXT: retq - %shuf1 = shufflevector <4 x i32> %a, <4 x i32> zeroinitializer, <4 x i32> - %shuf2 = shufflevector <4 x i32> %b, <4 x i32> zeroinitializer, <4 x i32> - %or = or <4 x i32> %shuf1, %shuf2 - ret <4 x i32> %or -} - - -define <2 x i64> @test3(<2 x i64> %a, <2 x i64> %b) { -; CHECK-LABEL: test3: -; CHECK: # %bb.0: -; CHECK-NEXT: blendps {{.*#+}} xmm0 = xmm1[0,1],xmm0[2,3] -; CHECK-NEXT: retq - %shuf1 = shufflevector <2 x i64> %a, <2 x i64> zeroinitializer, <2 x i32> - %shuf2 = shufflevector <2 x i64> %b, <2 x i64> zeroinitializer, <2 x i32> - %or = or <2 x i64> %shuf1, %shuf2 - ret <2 x i64> %or -} - - -define <4 x i32> @test4(<4 x i32> %a, <4 x i32> %b) { -; CHECK-LABEL: test4: -; CHECK: # %bb.0: -; CHECK-NEXT: blendps {{.*#+}} xmm0 = xmm0[0],xmm1[1,2,3] -; CHECK-NEXT: retq - %shuf1 = shufflevector <4 x i32> %a, <4 x i32> zeroinitializer, <4 x i32> - %shuf2 = shufflevector <4 x i32> %b, <4 x i32> zeroinitializer, <4 x i32> - %or = or <4 x i32> %shuf1, %shuf2 - ret <4 x i32> %or -} - - -define <4 x i32> @test5(<4 x i32> %a, <4 x i32> %b) { -; CHECK-LABEL: test5: -; CHECK: # %bb.0: -; CHECK-NEXT: blendps {{.*#+}} xmm0 = xmm1[0],xmm0[1,2,3] -; CHECK-NEXT: retq - %shuf1 = shufflevector <4 x i32> %a, <4 x i32> zeroinitializer, <4 x i32> - %shuf2 = shufflevector <4 x i32> %b, <4 x i32> zeroinitializer, <4 x i32> - %or = or <4 x i32> %shuf1, %shuf2 - ret <4 x i32> %or -} - - -define <4 x i32> @test6(<4 x i32> %a, <4 x i32> %b) { -; CHECK-LABEL: test6: -; CHECK: # %bb.0: -; CHECK-NEXT: blendps {{.*#+}} xmm0 = xmm0[0,1],xmm1[2,3] -; CHECK-NEXT: retq - %shuf1 = shufflevector <4 x i32> %a, <4 x i32> zeroinitializer, <4 x i32> - %shuf2 = shufflevector <4 x i32> %b, <4 x i32> zeroinitializer, <4 x i32> - %or = or <4 x i32> %shuf1, %shuf2 - ret <4 x i32> %or -} - - -define <4 x i32> @test7(<4 x i32> %a, <4 x i32> %b) { -; CHECK-LABEL: test7: -; CHECK: # %bb.0: -; CHECK-NEXT: blendps {{.*#+}} xmm0 = xmm0[0,1],xmm1[2,3] -; CHECK-NEXT: retq - %and1 = and <4 x i32> %a, - %and2 = and <4 x i32> %b, - %or = or <4 x i32> %and1, %and2 - ret <4 x i32> %or -} - - -define <2 x i64> @test8(<2 x i64> %a, <2 x i64> %b) { -; CHECK-LABEL: test8: -; CHECK: # %bb.0: -; CHECK-NEXT: blendps {{.*#+}} xmm0 = xmm0[0,1],xmm1[2,3] -; CHECK-NEXT: retq - %and1 = and <2 x i64> %a, - %and2 = and <2 x i64> %b, - %or = or <2 x i64> %and1, %and2 - ret <2 x i64> %or -} - - -define <4 x i32> @test9(<4 x i32> %a, <4 x i32> %b) { -; CHECK-LABEL: test9: -; CHECK: # %bb.0: -; CHECK-NEXT: blendps {{.*#+}} xmm0 = xmm1[0,1],xmm0[2,3] -; CHECK-NEXT: retq - %and1 = and <4 x i32> %a, - %and2 = and <4 x i32> %b, - %or = or <4 x i32> %and1, %and2 - ret <4 x i32> %or -} - - -define <2 x i64> @test10(<2 x i64> %a, <2 x i64> %b) { -; CHECK-LABEL: test10: -; CHECK: # %bb.0: -; CHECK-NEXT: blendps {{.*#+}} xmm0 = xmm1[0,1],xmm0[2,3] -; CHECK-NEXT: retq - %and1 = and <2 x i64> %a, - %and2 = and <2 x i64> %b, - %or = or <2 x i64> %and1, %and2 - ret <2 x i64> %or -} - - -define <4 x i32> @test11(<4 x i32> %a, <4 x i32> %b) { -; CHECK-LABEL: test11: -; CHECK: # %bb.0: -; CHECK-NEXT: blendps {{.*#+}} xmm0 = xmm0[0],xmm1[1,2,3] -; CHECK-NEXT: retq - %and1 = and <4 x i32> %a, - %and2 = and <4 x i32> %b, - %or = or <4 x i32> %and1, %and2 - ret <4 x i32> %or -} - - -define <4 x i32> @test12(<4 x i32> %a, <4 x i32> %b) { -; CHECK-LABEL: test12: -; CHECK: # %bb.0: -; CHECK-NEXT: blendps {{.*#+}} xmm0 = xmm1[0],xmm0[1,2,3] -; CHECK-NEXT: retq - %and1 = and <4 x i32> %a, - %and2 = and <4 x i32> %b, - %or = or <4 x i32> %and1, %and2 - ret <4 x i32> %or -} - - -; Verify that the following test cases are folded into single shuffles. - -define <4 x i32> @test13(<4 x i32> %a, <4 x i32> %b) { -; CHECK-LABEL: test13: -; CHECK: # %bb.0: -; CHECK-NEXT: shufps {{.*#+}} xmm0 = xmm0[1,1],xmm1[2,3] -; CHECK-NEXT: retq - %shuf1 = shufflevector <4 x i32> %a, <4 x i32> zeroinitializer, <4 x i32> - %shuf2 = shufflevector <4 x i32> %b, <4 x i32> zeroinitializer, <4 x i32> - %or = or <4 x i32> %shuf1, %shuf2 - ret <4 x i32> %or -} - - -define <2 x i64> @test14(<2 x i64> %a, <2 x i64> %b) { -; CHECK-LABEL: test14: -; CHECK: # %bb.0: -; CHECK-NEXT: movlhps {{.*#+}} xmm0 = xmm0[0],xmm1[0] -; CHECK-NEXT: retq - %shuf1 = shufflevector <2 x i64> %a, <2 x i64> zeroinitializer, <2 x i32> - %shuf2 = shufflevector <2 x i64> %b, <2 x i64> zeroinitializer, <2 x i32> - %or = or <2 x i64> %shuf1, %shuf2 - ret <2 x i64> %or -} - - -define <4 x i32> @test15(<4 x i32> %a, <4 x i32> %b) { -; CHECK-LABEL: test15: -; CHECK: # %bb.0: -; CHECK-NEXT: shufps {{.*#+}} xmm1 = xmm1[2,1],xmm0[2,1] -; CHECK-NEXT: movaps %xmm1, %xmm0 -; CHECK-NEXT: retq - %shuf1 = shufflevector <4 x i32> %a, <4 x i32> zeroinitializer, <4 x i32> - %shuf2 = shufflevector <4 x i32> %b, <4 x i32> zeroinitializer, <4 x i32> - %or = or <4 x i32> %shuf1, %shuf2 - ret <4 x i32> %or -} - - -define <2 x i64> @test16(<2 x i64> %a, <2 x i64> %b) { -; CHECK-LABEL: test16: -; CHECK: # %bb.0: -; CHECK-NEXT: movlhps {{.*#+}} xmm1 = xmm1[0],xmm0[0] -; CHECK-NEXT: movaps %xmm1, %xmm0 -; CHECK-NEXT: retq - %shuf1 = shufflevector <2 x i64> %a, <2 x i64> zeroinitializer, <2 x i32> - %shuf2 = shufflevector <2 x i64> %b, <2 x i64> zeroinitializer, <2 x i32> - %or = or <2 x i64> %shuf1, %shuf2 - ret <2 x i64> %or -} - - -; Verify that the dag-combiner does not fold a OR of two shuffles into a single -; shuffle instruction when the shuffle indexes are not compatible. - -define <4 x i32> @test17(<4 x i32> %a, <4 x i32> %b) { -; CHECK-LABEL: test17: -; CHECK: # %bb.0: -; CHECK-NEXT: psllq $32, %xmm0 -; CHECK-NEXT: movq {{.*#+}} xmm1 = xmm1[0],zero -; CHECK-NEXT: por %xmm1, %xmm0 -; CHECK-NEXT: retq - %shuf1 = shufflevector <4 x i32> %a, <4 x i32> zeroinitializer, <4 x i32> - %shuf2 = shufflevector <4 x i32> %b, <4 x i32> zeroinitializer, <4 x i32> - %or = or <4 x i32> %shuf1, %shuf2 - ret <4 x i32> %or -} - - -define <4 x i32> @test18(<4 x i32> %a, <4 x i32> %b) { -; CHECK-LABEL: test18: -; CHECK: # %bb.0: -; CHECK-NEXT: pxor %xmm2, %xmm2 -; CHECK-NEXT: pblendw {{.*#+}} xmm0 = xmm0[0,1],xmm2[2,3,4,5,6,7] -; CHECK-NEXT: pshufd {{.*#+}} xmm0 = xmm0[1,0,1,1] -; CHECK-NEXT: pblendw {{.*#+}} xmm2 = xmm1[0,1],xmm2[2,3,4,5,6,7] -; CHECK-NEXT: por %xmm0, %xmm2 -; CHECK-NEXT: movdqa %xmm2, %xmm0 -; CHECK-NEXT: retq - %shuf1 = shufflevector <4 x i32> %a, <4 x i32> zeroinitializer, <4 x i32> - %shuf2 = shufflevector <4 x i32> %b, <4 x i32> zeroinitializer, <4 x i32> - %or = or <4 x i32> %shuf1, %shuf2 - ret <4 x i32> %or -} - - -define <4 x i32> @test19(<4 x i32> %a, <4 x i32> %b) { -; CHECK-LABEL: test19: -; CHECK: # %bb.0: -; CHECK-NEXT: pshufd {{.*#+}} xmm2 = xmm0[0,0,2,3] -; CHECK-NEXT: pxor %xmm3, %xmm3 -; CHECK-NEXT: pblendw {{.*#+}} xmm2 = xmm3[0,1],xmm2[2,3],xmm3[4,5],xmm2[6,7] -; CHECK-NEXT: pshufd {{.*#+}} xmm0 = xmm1[0,1,2,2] -; CHECK-NEXT: pblendw {{.*#+}} xmm0 = xmm0[0,1],xmm3[2,3],xmm0[4,5,6,7] -; CHECK-NEXT: por %xmm2, %xmm0 -; CHECK-NEXT: retq - %shuf1 = shufflevector <4 x i32> %a, <4 x i32> zeroinitializer, <4 x i32> - %shuf2 = shufflevector <4 x i32> %b, <4 x i32> zeroinitializer, <4 x i32> - %or = or <4 x i32> %shuf1, %shuf2 - ret <4 x i32> %or -} - - -define <2 x i64> @test20(<2 x i64> %a, <2 x i64> %b) { -; CHECK-LABEL: test20: -; CHECK: # %bb.0: -; CHECK-NEXT: por %xmm1, %xmm0 -; CHECK-NEXT: movq {{.*#+}} xmm0 = xmm0[0],zero -; CHECK-NEXT: retq - %shuf1 = shufflevector <2 x i64> %a, <2 x i64> zeroinitializer, <2 x i32> - %shuf2 = shufflevector <2 x i64> %b, <2 x i64> zeroinitializer, <2 x i32> - %or = or <2 x i64> %shuf1, %shuf2 - ret <2 x i64> %or -} - - -define <2 x i64> @test21(<2 x i64> %a, <2 x i64> %b) { -; CHECK-LABEL: test21: -; CHECK: # %bb.0: -; CHECK-NEXT: por %xmm1, %xmm0 -; CHECK-NEXT: pslldq {{.*#+}} xmm0 = zero,zero,zero,zero,zero,zero,zero,zero,xmm0[0,1,2,3,4,5,6,7] -; CHECK-NEXT: retq - %shuf1 = shufflevector <2 x i64> %a, <2 x i64> zeroinitializer, <2 x i32> - %shuf2 = shufflevector <2 x i64> %b, <2 x i64> zeroinitializer, <2 x i32> - %or = or <2 x i64> %shuf1, %shuf2 - ret <2 x i64> %or -} - - -; Verify that the dag-combiner keeps the correct domain for float/double vectors -; bitcast to use the mask-or blend combine. - -define <2 x double> @test22(<2 x double> %a0, <2 x double> %a1) { -; CHECK-LABEL: test22: -; CHECK: # %bb.0: -; CHECK-NEXT: blendps {{.*#+}} xmm0 = xmm1[0,1],xmm0[2,3] -; CHECK-NEXT: retq - %bc1 = bitcast <2 x double> %a0 to <2 x i64> - %bc2 = bitcast <2 x double> %a1 to <2 x i64> - %and1 = and <2 x i64> %bc1, - %and2 = and <2 x i64> %bc2, - %or = or <2 x i64> %and1, %and2 - %bc3 = bitcast <2 x i64> %or to <2 x double> - ret <2 x double> %bc3 -} - - -define <4 x float> @test23(<4 x float> %a0, <4 x float> %a1) { -; CHECK-LABEL: test23: -; CHECK: # %bb.0: -; CHECK-NEXT: blendps {{.*#+}} xmm0 = xmm1[0],xmm0[1,2],xmm1[3] -; CHECK-NEXT: retq - %bc1 = bitcast <4 x float> %a0 to <4 x i32> - %bc2 = bitcast <4 x float> %a1 to <4 x i32> - %and1 = and <4 x i32> %bc1, - %and2 = and <4 x i32> %bc2, - %or = or <4 x i32> %and1, %and2 - %bc3 = bitcast <4 x i32> %or to <4 x float> - ret <4 x float> %bc3 -} - - -define <4 x float> @test24(<4 x float> %a0, <4 x float> %a1) { -; CHECK-LABEL: test24: -; CHECK: # %bb.0: -; CHECK-NEXT: blendps {{.*#+}} xmm0 = xmm1[0,1],xmm0[2,3] -; CHECK-NEXT: retq - %bc1 = bitcast <4 x float> %a0 to <2 x i64> - %bc2 = bitcast <4 x float> %a1 to <2 x i64> - %and1 = and <2 x i64> %bc1, - %and2 = and <2 x i64> %bc2, - %or = or <2 x i64> %and1, %and2 - %bc3 = bitcast <2 x i64> %or to <4 x float> - ret <4 x float> %bc3 -} - - -define <4 x float> @test25(<4 x float> %a0) { -; CHECK-LABEL: test25: -; CHECK: # %bb.0: -; CHECK-NEXT: blendps {{.*#+}} xmm0 = mem[0],xmm0[1,2],mem[3] -; CHECK-NEXT: retq - %bc1 = bitcast <4 x float> %a0 to <4 x i32> - %bc2 = bitcast <4 x float> to <4 x i32> - %and1 = and <4 x i32> %bc1, - %and2 = and <4 x i32> %bc2, - %or = or <4 x i32> %and1, %and2 - %bc3 = bitcast <4 x i32> %or to <4 x float> - ret <4 x float> %bc3 -} - - -; Verify that the DAGCombiner doesn't crash in the attempt to check if a shuffle -; with illegal type has a legal mask. Method 'isShuffleMaskLegal' only knows how to -; handle legal vector value types. -define <4 x i8> @test_crash(<4 x i8> %a, <4 x i8> %b) { -; CHECK-LABEL: test_crash: -; CHECK: # %bb.0: -; CHECK-NEXT: pblendw {{.*#+}} xmm0 = xmm1[0],xmm0[1],xmm1[2,3,4,5,6,7] -; CHECK-NEXT: retq - %shuf1 = shufflevector <4 x i8> %a, <4 x i8> zeroinitializer, <4 x i32> - %shuf2 = shufflevector <4 x i8> %b, <4 x i8> zeroinitializer, <4 x i32> - %or = or <4 x i8> %shuf1, %shuf2 - ret <4 x i8> %or -} - -; Verify that we can fold regardless of which operand is the zeroinitializer - -define <4 x i32> @test2b(<4 x i32> %a, <4 x i32> %b) { -; CHECK-LABEL: test2b: -; CHECK: # %bb.0: -; CHECK-NEXT: blendps {{.*#+}} xmm0 = xmm1[0,1],xmm0[2,3] -; CHECK-NEXT: retq - %shuf1 = shufflevector <4 x i32> zeroinitializer, <4 x i32> %a, <4 x i32> - %shuf2 = shufflevector <4 x i32> %b, <4 x i32> zeroinitializer, <4 x i32> - %or = or <4 x i32> %shuf1, %shuf2 - ret <4 x i32> %or -} - -define <4 x i32> @test2c(<4 x i32> %a, <4 x i32> %b) { -; CHECK-LABEL: test2c: -; CHECK: # %bb.0: -; CHECK-NEXT: blendps {{.*#+}} xmm0 = xmm1[0,1],xmm0[2,3] -; CHECK-NEXT: retq - %shuf1 = shufflevector <4 x i32> zeroinitializer, <4 x i32> %a, <4 x i32> - %shuf2 = shufflevector <4 x i32> zeroinitializer, <4 x i32> %b, <4 x i32> - %or = or <4 x i32> %shuf1, %shuf2 - ret <4 x i32> %or -} - - -define <4 x i32> @test2d(<4 x i32> %a, <4 x i32> %b) { -; CHECK-LABEL: test2d: -; CHECK: # %bb.0: -; CHECK-NEXT: blendps {{.*#+}} xmm0 = xmm1[0,1],xmm0[2,3] -; CHECK-NEXT: retq - %shuf1 = shufflevector <4 x i32> %a, <4 x i32> zeroinitializer, <4 x i32> - %shuf2 = shufflevector <4 x i32> zeroinitializer, <4 x i32> %b, <4 x i32> - %or = or <4 x i32> %shuf1, %shuf2 - ret <4 x i32> %or -} - -; Make sure we can have an undef where an index pointing to the zero vector should be - -define <4 x i32> @test2e(<4 x i32> %a, <4 x i32> %b) { -; CHECK-LABEL: test2e: -; CHECK: # %bb.0: -; CHECK-NEXT: blendps {{.*#+}} xmm0 = xmm1[0,1],xmm0[2,3] -; CHECK-NEXT: retq - %shuf1 = shufflevector <4 x i32> %a, <4 x i32> , <4 x i32> - %shuf2 = shufflevector <4 x i32> %b, <4 x i32> , <4 x i32> - %or = or <4 x i32> %shuf1, %shuf2 - ret <4 x i32> %or -} - -define <4 x i32> @test2f(<4 x i32> %a, <4 x i32> %b) { -; CHECK-LABEL: test2f: -; CHECK: # %bb.0: -; CHECK-NEXT: blendps {{.*#+}} xmm0 = xmm1[0,1],xmm0[2,3] -; CHECK-NEXT: retq - %shuf1 = shufflevector <4 x i32> %a, <4 x i32> , <4 x i32> - %shuf2 = shufflevector <4 x i32> %b, <4 x i32> , <4 x i32> - %or = or <4 x i32> %shuf1, %shuf2 - ret <4 x i32> %or -} - -; (or (and X, c1), c2) -> (and (or X, c2), c1|c2) iff (c1 & c2) != 0 - -define <2 x i64> @or_and_v2i64(<2 x i64> %a0) { -; CHECK-LABEL: or_and_v2i64: -; CHECK: # %bb.0: -; CHECK-NEXT: orps {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm0 -; CHECK-NEXT: andps {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm0 -; CHECK-NEXT: retq - %1 = and <2 x i64> %a0, - %2 = or <2 x i64> %1, - ret <2 x i64> %2 -} - -define <4 x i32> @or_and_v4i32(<4 x i32> %a0) { -; CHECK-LABEL: or_and_v4i32: -; CHECK: # %bb.0: -; CHECK-NEXT: orps {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm0 -; CHECK-NEXT: andps {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm0 -; CHECK-NEXT: retq - %1 = and <4 x i32> %a0, - %2 = or <4 x i32> %1, - ret <4 x i32> %2 -} - -; If all masked bits are going to be set, that's a constant fold. - -define <4 x i32> @or_and_v4i32_fold(<4 x i32> %a0) { -; CHECK-LABEL: or_and_v4i32_fold: -; CHECK: # %bb.0: -; CHECK-NEXT: movaps {{.*#+}} xmm0 = [3,3,3,3] -; CHECK-NEXT: retq - %1 = and <4 x i32> %a0, - %2 = or <4 x i32> %1, - ret <4 x i32> %2 -} - ; fold (or x, c) -> c iff (x & ~c) == 0 define <2 x i64> @or_zext_v2i32(<2 x i32> %a0) { -; CHECK-LABEL: or_zext_v2i32: -; CHECK: # %bb.0: -; CHECK-NEXT: movaps {{.*#+}} xmm0 = [4294967295,4294967295] -; CHECK-NEXT: retq +; SSE-LABEL: or_zext_v2i32: +; SSE: # %bb.0: +; SSE-NEXT: movaps {{.*#+}} xmm0 = [4294967295,4294967295] +; SSE-NEXT: retq +; +; AVX-LABEL: or_zext_v2i32: +; AVX: # %bb.0: +; AVX-NEXT: vmovddup {{.*#+}} xmm0 = [4294967295,4294967295] +; AVX-NEXT: # xmm0 = mem[0,0] +; AVX-NEXT: retq %1 = zext <2 x i32> %a0 to <2 x i64> %2 = or <2 x i64> %1, ret <2 x i64> %2 } define <4 x i32> @or_zext_v4i16(<4 x i16> %a0) { -; CHECK-LABEL: or_zext_v4i16: -; CHECK: # %bb.0: -; CHECK-NEXT: movaps {{.*#+}} xmm0 = [65535,65535,65535,65535] -; CHECK-NEXT: retq +; SSE-LABEL: or_zext_v4i16: +; SSE: # %bb.0: +; SSE-NEXT: movaps {{.*#+}} xmm0 = [65535,65535,65535,65535] +; SSE-NEXT: retq +; +; AVX-LABEL: or_zext_v4i16: +; AVX: # %bb.0: +; AVX-NEXT: vbroadcastss {{.*#+}} xmm0 = [65535,65535,65535,65535] +; AVX-NEXT: retq %1 = zext <4 x i16> %a0 to <4 x i32> %2 = or <4 x i32> %1, ret <4 x i32> %2 @@ -522,12 +86,19 @@ define i64 @or_and_and_commute_i64(i64 %x, i64 %y) { } define <4 x i32> @or_and_and_v4i32(<4 x i32> %x, <4 x i32> %y) { -; CHECK-LABEL: or_and_and_v4i32: -; CHECK: # %bb.0: -; CHECK-NEXT: andps {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm1 -; CHECK-NEXT: andps {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm0 -; CHECK-NEXT: orps %xmm1, %xmm0 -; CHECK-NEXT: retq +; SSE-LABEL: or_and_and_v4i32: +; SSE: # %bb.0: +; SSE-NEXT: andps {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm1 +; SSE-NEXT: andps {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm0 +; SSE-NEXT: orps %xmm1, %xmm0 +; SSE-NEXT: retq +; +; AVX-LABEL: or_and_and_v4i32: +; AVX: # %bb.0: +; AVX-NEXT: vandps {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm1, %xmm1 +; AVX-NEXT: vandps {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm0, %xmm0 +; AVX-NEXT: vorps %xmm1, %xmm0, %xmm0 +; AVX-NEXT: retq %xy = or <4 x i32> %x, %y %mx = and <4 x i32> %x, %mxy = and <4 x i32> %xy, @@ -611,7 +182,106 @@ define i32 @or_and_multiuse_and_multiuse_i32(i32 %x, i32 %y) nounwind { ret i32 %r } +define i64 @or_build_pair_not(i32 %a0, i32 %a1) { +; CHECK-LABEL: or_build_pair_not: +; CHECK: # %bb.0: +; CHECK-NEXT: # kill: def $esi killed $esi def $rsi +; CHECK-NEXT: shlq $32, %rsi +; CHECK-NEXT: movl %edi, %eax +; CHECK-NEXT: orq %rsi, %rax +; CHECK-NEXT: notq %rax +; CHECK-NEXT: retq + %n0 = xor i32 %a0, -1 + %n1 = xor i32 %a1, -1 + %x0 = zext i32 %n0 to i64 + %x1 = zext i32 %n1 to i64 + %hi = shl i64 %x1, 32 + %r = or i64 %hi, %x0 + ret i64 %r +} + +define i64 @PR89533(<64 x i8> %a0) { +; SSE-LABEL: PR89533: +; SSE: # %bb.0: +; SSE-NEXT: movdqa {{.*#+}} xmm4 = [95,95,95,95,95,95,95,95,95,95,95,95,95,95,95,95] +; SSE-NEXT: pcmpeqb %xmm4, %xmm0 +; SSE-NEXT: pmovmskb %xmm0, %eax +; SSE-NEXT: xorl $65535, %eax # imm = 0xFFFF +; SSE-NEXT: pcmpeqb %xmm4, %xmm1 +; SSE-NEXT: pmovmskb %xmm1, %ecx +; SSE-NEXT: notl %ecx +; SSE-NEXT: shll $16, %ecx +; SSE-NEXT: orl %eax, %ecx +; SSE-NEXT: pcmpeqb %xmm4, %xmm2 +; SSE-NEXT: pmovmskb %xmm2, %edx +; SSE-NEXT: xorl $65535, %edx # imm = 0xFFFF +; SSE-NEXT: pcmpeqb %xmm4, %xmm3 +; SSE-NEXT: pmovmskb %xmm3, %eax +; SSE-NEXT: notl %eax +; SSE-NEXT: shll $16, %eax +; SSE-NEXT: orl %edx, %eax +; SSE-NEXT: shlq $32, %rax +; SSE-NEXT: orq %rcx, %rax +; SSE-NEXT: je .LBB11_2 +; SSE-NEXT: # %bb.1: # %cond.false +; SSE-NEXT: rep bsfq %rax, %rax +; SSE-NEXT: retq +; SSE-NEXT: .LBB11_2: # %cond.end +; SSE-NEXT: movl $64, %eax +; SSE-NEXT: retq +; +; AVX1-LABEL: PR89533: +; AVX1: # %bb.0: +; AVX1-NEXT: vbroadcastss {{.*#+}} xmm2 = [95,95,95,95,95,95,95,95,95,95,95,95,95,95,95,95] +; AVX1-NEXT: vpcmpeqb %xmm2, %xmm0, %xmm3 +; AVX1-NEXT: vpmovmskb %xmm3, %eax +; AVX1-NEXT: xorl $65535, %eax # imm = 0xFFFF +; AVX1-NEXT: vextractf128 $1, %ymm0, %xmm0 +; AVX1-NEXT: vpcmpeqb %xmm2, %xmm0, %xmm0 +; AVX1-NEXT: vpmovmskb %xmm0, %ecx +; AVX1-NEXT: notl %ecx +; AVX1-NEXT: shll $16, %ecx +; AVX1-NEXT: orl %eax, %ecx +; AVX1-NEXT: vpcmpeqb %xmm2, %xmm1, %xmm0 +; AVX1-NEXT: vpmovmskb %xmm0, %edx +; AVX1-NEXT: xorl $65535, %edx # imm = 0xFFFF +; AVX1-NEXT: vextractf128 $1, %ymm1, %xmm0 +; AVX1-NEXT: vpcmpeqb %xmm2, %xmm0, %xmm0 +; AVX1-NEXT: vpmovmskb %xmm0, %eax +; AVX1-NEXT: notl %eax +; AVX1-NEXT: shll $16, %eax +; AVX1-NEXT: orl %edx, %eax +; AVX1-NEXT: shlq $32, %rax +; AVX1-NEXT: orq %rcx, %rax +; AVX1-NEXT: je .LBB11_2 +; AVX1-NEXT: # %bb.1: # %cond.false +; AVX1-NEXT: rep bsfq %rax, %rax +; AVX1-NEXT: vzeroupper +; AVX1-NEXT: retq +; AVX1-NEXT: .LBB11_2: # %cond.end +; AVX1-NEXT: movl $64, %eax +; AVX1-NEXT: vzeroupper +; AVX1-NEXT: retq +; +; AVX2-LABEL: PR89533: +; AVX2: # %bb.0: +; AVX2-NEXT: vpbroadcastb {{.*#+}} ymm2 = [95,95,95,95,95,95,95,95,95,95,95,95,95,95,95,95,95,95,95,95,95,95,95,95,95,95,95,95,95,95,95,95] +; AVX2-NEXT: vpcmpeqb %ymm2, %ymm0, %ymm0 +; AVX2-NEXT: vpmovmskb %ymm0, %eax +; AVX2-NEXT: vpcmpeqb %ymm2, %ymm1, %ymm0 +; AVX2-NEXT: vpmovmskb %ymm0, %ecx +; AVX2-NEXT: shlq $32, %rcx +; AVX2-NEXT: orq %rax, %rcx +; AVX2-NEXT: notq %rcx +; AVX2-NEXT: xorl %eax, %eax +; AVX2-NEXT: tzcntq %rcx, %rax +; AVX2-NEXT: vzeroupper +; AVX2-NEXT: retq + %cmp = icmp ne <64 x i8> %a0, + %mask = bitcast <64 x i1> %cmp to i64 + %tz = tail call i64 @llvm.cttz.i64(i64 %mask, i1 false) + ret i64 %tz +} + declare void @use_i32(i32) -;; NOTE: These prefixes are unused and the list is autogenerated. Do not add tests below this line: -; CHECK-LIS: {{.*}} -; CHECK-LV: {{.*}} + diff --git a/llvm/test/CodeGen/X86/div-rem-pair-recomposition-signed.ll b/llvm/test/CodeGen/X86/div-rem-pair-recomposition-signed.ll index e12ca56023a7f2c174a0812d1390f28f32371ec7..bf7c1c00c71df107b93866056d754d6333965795 100644 --- a/llvm/test/CodeGen/X86/div-rem-pair-recomposition-signed.ll +++ b/llvm/test/CodeGen/X86/div-rem-pair-recomposition-signed.ll @@ -178,15 +178,15 @@ define i128 @scalar_i128(i128 %x, i128 %y, ptr %divdst) nounwind { ; X86-NEXT: pushl %edi ; X86-NEXT: pushl %esi ; X86-NEXT: subl $152, %esp -; X86-NEXT: movl {{[0-9]+}}(%esp), %edx +; X86-NEXT: movl {{[0-9]+}}(%esp), %ebp ; X86-NEXT: movl {{[0-9]+}}(%esp), %ecx ; X86-NEXT: movl %ecx, %eax ; X86-NEXT: sarl $31, %eax -; X86-NEXT: movl %edx, %edi -; X86-NEXT: sarl $31, %edi +; X86-NEXT: movl %ebp, %edx +; X86-NEXT: sarl $31, %edx ; X86-NEXT: movl %eax, %esi ; X86-NEXT: xorl %ecx, %esi -; X86-NEXT: movl %esi, %ebp +; X86-NEXT: movl %esi, %edi ; X86-NEXT: movl %eax, %ecx ; X86-NEXT: xorl {{[0-9]+}}(%esp), %ecx ; X86-NEXT: movl %ecx, %ebx @@ -195,67 +195,66 @@ define i128 @scalar_i128(i128 %x, i128 %y, ptr %divdst) nounwind { ; X86-NEXT: movl %eax, %esi ; X86-NEXT: xorl {{[0-9]+}}(%esp), %esi ; X86-NEXT: subl %eax, %esi -; X86-NEXT: movl %esi, (%esp) # 4-byte Spill +; X86-NEXT: movl %esi, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill ; X86-NEXT: sbbl %eax, %ecx ; X86-NEXT: movl %ecx, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill ; X86-NEXT: sbbl %eax, %ebx -; X86-NEXT: movl %ebx, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill -; X86-NEXT: sbbl %eax, %ebp -; X86-NEXT: movl %ebp, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill -; X86-NEXT: movl %edi, %esi -; X86-NEXT: xorl %edx, %esi -; X86-NEXT: movl %edi, %edx -; X86-NEXT: xorl {{[0-9]+}}(%esp), %edx -; X86-NEXT: movl %edi, %ebx +; X86-NEXT: movl %ebx, (%esp) # 4-byte Spill +; X86-NEXT: sbbl %eax, %edi +; X86-NEXT: movl %edi, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill +; X86-NEXT: movl %edx, %edi +; X86-NEXT: xorl %ebp, %edi +; X86-NEXT: movl %edx, %ebx ; X86-NEXT: xorl {{[0-9]+}}(%esp), %ebx -; X86-NEXT: movl %edi, %ebp +; X86-NEXT: movl %edx, %esi +; X86-NEXT: xorl {{[0-9]+}}(%esp), %esi +; X86-NEXT: movl %edx, %ebp ; X86-NEXT: xorl {{[0-9]+}}(%esp), %ebp -; X86-NEXT: subl %edi, %ebp -; X86-NEXT: sbbl %edi, %ebx -; X86-NEXT: sbbl %edi, %edx -; X86-NEXT: sbbl %edi, %esi -; X86-NEXT: xorl %eax, %edi -; X86-NEXT: movl %edi, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill -; X86-NEXT: movl %ebx, %eax -; X86-NEXT: orl %esi, %eax +; X86-NEXT: subl %edx, %ebp +; X86-NEXT: sbbl %edx, %esi +; X86-NEXT: sbbl %edx, %ebx +; X86-NEXT: sbbl %edx, %edi +; X86-NEXT: xorl %eax, %edx +; X86-NEXT: movl %edx, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill +; X86-NEXT: movl %esi, %eax +; X86-NEXT: orl %edi, %eax ; X86-NEXT: movl %ebp, %ecx -; X86-NEXT: orl %edx, %ecx -; X86-NEXT: movl %edx, %edi +; X86-NEXT: orl %ebx, %ecx ; X86-NEXT: orl %eax, %ecx ; X86-NEXT: sete %cl ; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %eax # 4-byte Reload ; X86-NEXT: orl {{[-0-9]+}}(%e{{[sb]}}p), %eax # 4-byte Folded Reload -; X86-NEXT: movl (%esp), %edx # 4-byte Reload -; X86-NEXT: orl {{[-0-9]+}}(%e{{[sb]}}p), %edx # 4-byte Folded Reload +; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %edx # 4-byte Reload +; X86-NEXT: orl (%esp), %edx # 4-byte Folded Reload ; X86-NEXT: orl %eax, %edx ; X86-NEXT: sete %al ; X86-NEXT: orb %cl, %al ; X86-NEXT: movb %al, {{[-0-9]+}}(%e{{[sb]}}p) # 1-byte Spill -; X86-NEXT: bsrl %esi, %edx +; X86-NEXT: bsrl %edi, %edx ; X86-NEXT: xorl $31, %edx -; X86-NEXT: bsrl %edi, %ecx +; X86-NEXT: bsrl %ebx, %ecx ; X86-NEXT: xorl $31, %ecx ; X86-NEXT: addl $32, %ecx -; X86-NEXT: testl %esi, %esi +; X86-NEXT: testl %edi, %edi ; X86-NEXT: cmovnel %edx, %ecx -; X86-NEXT: bsrl %ebx, %edx +; X86-NEXT: bsrl %esi, %edx ; X86-NEXT: xorl $31, %edx ; X86-NEXT: movl %ebp, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill ; X86-NEXT: bsrl %ebp, %ebp ; X86-NEXT: xorl $31, %ebp ; X86-NEXT: addl $32, %ebp -; X86-NEXT: movl %ebx, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill -; X86-NEXT: testl %ebx, %ebx +; X86-NEXT: movl %esi, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill +; X86-NEXT: testl %esi, %esi ; X86-NEXT: cmovnel %edx, %ebp ; X86-NEXT: addl $64, %ebp +; X86-NEXT: movl %ebx, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill ; X86-NEXT: movl %edi, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill -; X86-NEXT: movl %esi, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill -; X86-NEXT: orl %esi, %edi +; X86-NEXT: orl %edi, %ebx ; X86-NEXT: cmovnel %ecx, %ebp ; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %edi # 4-byte Reload ; X86-NEXT: bsrl %edi, %edx ; X86-NEXT: xorl $31, %edx -; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %eax # 4-byte Reload +; X86-NEXT: movl (%esp), %eax # 4-byte Reload ; X86-NEXT: bsrl %eax, %ecx ; X86-NEXT: xorl $31, %ecx ; X86-NEXT: addl $32, %ecx @@ -264,7 +263,7 @@ define i128 @scalar_i128(i128 %x, i128 %y, ptr %divdst) nounwind { ; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %ebx # 4-byte Reload ; X86-NEXT: bsrl %ebx, %esi ; X86-NEXT: xorl $31, %esi -; X86-NEXT: bsrl (%esp), %edx # 4-byte Folded Reload +; X86-NEXT: bsrl {{[-0-9]+}}(%e{{[sb]}}p), %edx # 4-byte Folded Reload ; X86-NEXT: xorl $31, %edx ; X86-NEXT: addl $32, %edx ; X86-NEXT: testl %ebx, %ebx @@ -272,52 +271,56 @@ define i128 @scalar_i128(i128 %x, i128 %y, ptr %divdst) nounwind { ; X86-NEXT: addl $64, %edx ; X86-NEXT: movl %eax, %esi ; X86-NEXT: orl %edi, %esi +; X86-NEXT: movl %edi, %ebx ; X86-NEXT: cmovnel %ecx, %edx ; X86-NEXT: xorl %esi, %esi ; X86-NEXT: subl %edx, %ebp -; X86-NEXT: movl $0, %ebx -; X86-NEXT: sbbl %ebx, %ebx ; X86-NEXT: movl $0, %edx ; X86-NEXT: sbbl %edx, %edx ; X86-NEXT: movl $0, %eax ; X86-NEXT: sbbl %eax, %eax +; X86-NEXT: movl $0, %edi +; X86-NEXT: sbbl %edi, %edi ; X86-NEXT: movl $127, %ecx ; X86-NEXT: movl %ebp, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill ; X86-NEXT: cmpl %ebp, %ecx ; X86-NEXT: movl $0, %ecx -; X86-NEXT: sbbl %ebx, %ecx -; X86-NEXT: movl $0, %ecx ; X86-NEXT: movl %edx, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill ; X86-NEXT: sbbl %edx, %ecx ; X86-NEXT: movl $0, %ecx ; X86-NEXT: movl %eax, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill ; X86-NEXT: sbbl %eax, %ecx +; X86-NEXT: movl $0, %ecx +; X86-NEXT: movl %edi, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill +; X86-NEXT: sbbl %edi, %ecx ; X86-NEXT: setb %cl ; X86-NEXT: orb {{[-0-9]+}}(%e{{[sb]}}p), %cl # 1-byte Folded Reload +; X86-NEXT: movl %ebx, %edi ; X86-NEXT: cmovnel %esi, %edi -; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %edx # 4-byte Reload +; X86-NEXT: movl (%esp), %edx # 4-byte Reload ; X86-NEXT: cmovnel %esi, %edx ; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %eax # 4-byte Reload ; X86-NEXT: cmovnel %esi, %eax -; X86-NEXT: cmovel (%esp), %esi # 4-byte Folded Reload +; X86-NEXT: cmovel {{[-0-9]+}}(%e{{[sb]}}p), %esi # 4-byte Folded Reload ; X86-NEXT: movl {{[0-9]+}}(%esp), %ebp -; X86-NEXT: jne .LBB4_8 -; X86-NEXT: # %bb.1: # %_udiv-special-cases -; X86-NEXT: movl %ebx, %ecx -; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %ebx # 4-byte Reload -; X86-NEXT: xorl $127, %ebx -; X86-NEXT: orl {{[-0-9]+}}(%e{{[sb]}}p), %ebx # 4-byte Folded Reload -; X86-NEXT: movl %ecx, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill +; X86-NEXT: jne .LBB4_1 +; X86-NEXT: # %bb.8: # %_udiv-special-cases +; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %ebp # 4-byte Reload +; X86-NEXT: xorl $127, %ebp +; X86-NEXT: orl {{[-0-9]+}}(%e{{[sb]}}p), %ebp # 4-byte Folded Reload +; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %ecx # 4-byte Reload ; X86-NEXT: orl {{[-0-9]+}}(%e{{[sb]}}p), %ecx # 4-byte Folded Reload -; X86-NEXT: orl %ebx, %ecx -; X86-NEXT: je .LBB4_8 -; X86-NEXT: # %bb.2: # %udiv-bb1 -; X86-NEXT: movl (%esp), %eax # 4-byte Reload -; X86-NEXT: movl %eax, {{[0-9]+}}(%esp) +; X86-NEXT: orl %ebp, %ecx +; X86-NEXT: movl {{[0-9]+}}(%esp), %ebp +; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %ebx # 4-byte Reload +; X86-NEXT: je .LBB4_9 +; X86-NEXT: # %bb.5: # %udiv-bb1 ; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %eax # 4-byte Reload ; X86-NEXT: movl %eax, {{[0-9]+}}(%esp) ; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %eax # 4-byte Reload ; X86-NEXT: movl %eax, {{[0-9]+}}(%esp) +; X86-NEXT: movl (%esp), %eax # 4-byte Reload +; X86-NEXT: movl %eax, {{[0-9]+}}(%esp) ; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %eax # 4-byte Reload ; X86-NEXT: movl %eax, {{[0-9]+}}(%esp) ; X86-NEXT: movl $0, {{[0-9]+}}(%esp) @@ -332,78 +335,82 @@ define i128 @scalar_i128(i128 %x, i128 %y, ptr %divdst) nounwind { ; X86-NEXT: shrb $3, %al ; X86-NEXT: andb $15, %al ; X86-NEXT: negb %al -; X86-NEXT: movsbl %al, %ebx -; X86-NEXT: movl 144(%esp,%ebx), %edx -; X86-NEXT: movl 148(%esp,%ebx), %edi +; X86-NEXT: movsbl %al, %edi +; X86-NEXT: movl 144(%esp,%edi), %edx +; X86-NEXT: movl 148(%esp,%edi), %esi ; X86-NEXT: movb %ch, %cl -; X86-NEXT: shldl %cl, %edx, %edi +; X86-NEXT: shldl %cl, %edx, %esi +; X86-NEXT: movl %esi, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill ; X86-NEXT: shll %cl, %edx ; X86-NEXT: notb %cl -; X86-NEXT: movl 140(%esp,%ebx), %eax +; X86-NEXT: movl 140(%esp,%edi), %eax ; X86-NEXT: movl %eax, %esi ; X86-NEXT: shrl %esi ; X86-NEXT: shrl %cl, %esi ; X86-NEXT: orl %edx, %esi ; X86-NEXT: movl %esi, %edx -; X86-NEXT: movl 136(%esp,%ebx), %esi +; X86-NEXT: movl 136(%esp,%edi), %esi ; X86-NEXT: movb %ch, %cl ; X86-NEXT: shldl %cl, %esi, %eax ; X86-NEXT: shll %cl, %esi -; X86-NEXT: movl %esi, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill ; X86-NEXT: addl $1, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Folded Spill ; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %ecx # 4-byte Reload ; X86-NEXT: adcl $0, %ecx -; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %ebx # 4-byte Reload -; X86-NEXT: adcl $0, %ebx +; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %edi # 4-byte Reload +; X86-NEXT: adcl $0, %edi ; X86-NEXT: adcl $0, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Folded Spill -; X86-NEXT: jae .LBB4_3 +; X86-NEXT: jae .LBB4_2 ; X86-NEXT: # %bb.6: -; X86-NEXT: xorl %ebx, %ebx -; X86-NEXT: xorl %esi, %esi +; X86-NEXT: movl $0, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Folded Spill +; X86-NEXT: xorl %ecx, %ecx ; X86-NEXT: jmp .LBB4_7 -; X86-NEXT: .LBB4_3: # %udiv-preheader -; X86-NEXT: movl (%esp), %esi # 4-byte Reload -; X86-NEXT: movl %esi, {{[0-9]+}}(%esp) -; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %esi # 4-byte Reload -; X86-NEXT: movl %esi, {{[0-9]+}}(%esp) -; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %esi # 4-byte Reload -; X86-NEXT: movl %esi, {{[0-9]+}}(%esp) -; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %esi # 4-byte Reload -; X86-NEXT: movl %esi, {{[0-9]+}}(%esp) +; X86-NEXT: .LBB4_1: +; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %ebx # 4-byte Reload +; X86-NEXT: jmp .LBB4_9 +; X86-NEXT: .LBB4_2: # %udiv-preheader +; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %ebx # 4-byte Reload +; X86-NEXT: movl %ebx, {{[0-9]+}}(%esp) +; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %ebx # 4-byte Reload +; X86-NEXT: movl %ebx, {{[0-9]+}}(%esp) +; X86-NEXT: movl (%esp), %ebx # 4-byte Reload +; X86-NEXT: movl %ebx, {{[0-9]+}}(%esp) +; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %ebx # 4-byte Reload +; X86-NEXT: movl %ebx, {{[0-9]+}}(%esp) ; X86-NEXT: movl $0, {{[0-9]+}}(%esp) ; X86-NEXT: movl $0, {{[0-9]+}}(%esp) ; X86-NEXT: movl $0, {{[0-9]+}}(%esp) ; X86-NEXT: movl $0, {{[0-9]+}}(%esp) -; X86-NEXT: movl %ecx, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill -; X86-NEXT: movl %ebx, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill ; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %ebx # 4-byte Reload +; X86-NEXT: movl %ecx, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill ; X86-NEXT: movb %bl, %ch ; X86-NEXT: andb $7, %ch ; X86-NEXT: movb %bl, %cl ; X86-NEXT: shrb $3, %cl ; X86-NEXT: andb $15, %cl -; X86-NEXT: movzbl %cl, %ebp -; X86-NEXT: movl 100(%esp,%ebp), %esi -; X86-NEXT: movl %esi, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill -; X86-NEXT: movl %eax, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill -; X86-NEXT: movl 96(%esp,%ebp), %ebx -; X86-NEXT: movl %ebp, %eax +; X86-NEXT: movl %edi, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill +; X86-NEXT: movzbl %cl, %ebx +; X86-NEXT: movl 100(%esp,%ebx), %ebp +; X86-NEXT: movl %ebp, (%esp) # 4-byte Spill +; X86-NEXT: movl 96(%esp,%ebx), %edi ; X86-NEXT: movl %edx, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill -; X86-NEXT: movl %ebx, %edx +; X86-NEXT: movl %edi, %edx ; X86-NEXT: movb %ch, %cl -; X86-NEXT: shrdl %cl, %esi, %edx -; X86-NEXT: movl 88(%esp,%ebp), %ebp -; X86-NEXT: movl 92(%esp,%eax), %esi -; X86-NEXT: movl %esi, %eax +; X86-NEXT: shrdl %cl, %ebp, %edx +; X86-NEXT: movl %edx, %ebp +; X86-NEXT: movl %eax, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill +; X86-NEXT: movl 88(%esp,%ebx), %edx +; X86-NEXT: movl 92(%esp,%ebx), %ebx +; X86-NEXT: movl %ebx, %eax ; X86-NEXT: shrl %cl, %eax ; X86-NEXT: notb %cl -; X86-NEXT: addl %ebx, %ebx -; X86-NEXT: shll %cl, %ebx -; X86-NEXT: orl %eax, %ebx -; X86-NEXT: movl %ebx, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill +; X86-NEXT: addl %edi, %edi +; X86-NEXT: shll %cl, %edi +; X86-NEXT: orl %eax, %edi +; X86-NEXT: movl %edi, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill ; X86-NEXT: movb %ch, %cl -; X86-NEXT: shrl %cl, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Folded Spill -; X86-NEXT: shrdl %cl, %esi, %ebp +; X86-NEXT: shrl %cl, (%esp) # 4-byte Folded Spill +; X86-NEXT: shrdl %cl, %ebx, %edx +; X86-NEXT: movl %edx, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill ; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %eax # 4-byte Reload ; X86-NEXT: addl $-1, %eax ; X86-NEXT: movl %eax, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill @@ -413,113 +420,109 @@ define i128 @scalar_i128(i128 %x, i128 %y, ptr %divdst) nounwind { ; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %eax # 4-byte Reload ; X86-NEXT: adcl $-1, %eax ; X86-NEXT: movl %eax, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill -; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %ecx # 4-byte Reload -; X86-NEXT: movl %ecx, %eax +; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %eax # 4-byte Reload ; X86-NEXT: adcl $-1, %eax ; X86-NEXT: movl %eax, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill -; X86-NEXT: xorl %esi, %esi ; X86-NEXT: movl $0, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Folded Spill -; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %ebx # 4-byte Reload +; X86-NEXT: movl $0, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Folded Spill +; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %edi # 4-byte Reload +; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %edx # 4-byte Reload ; X86-NEXT: .p2align 4, 0x90 -; X86-NEXT: .LBB4_4: # %udiv-do-while +; X86-NEXT: .LBB4_3: # %udiv-do-while ; X86-NEXT: # =>This Inner Loop Header: Depth=1 -; X86-NEXT: movl %ebx, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill ; X86-NEXT: movl %edx, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill -; X86-NEXT: movl %esi, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill -; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %ebx # 4-byte Reload -; X86-NEXT: shldl $1, %edx, %ebx -; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %edx # 4-byte Reload -; X86-NEXT: shldl $1, %edx, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Folded Spill +; X86-NEXT: movl %ebp, %edx +; X86-NEXT: shldl $1, %ebp, (%esp) # 4-byte Folded Spill +; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %ebp # 4-byte Reload ; X86-NEXT: shldl $1, %ebp, %edx -; X86-NEXT: shldl $1, %edi, %ebp -; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %eax # 4-byte Reload -; X86-NEXT: shldl $1, %eax, %edi -; X86-NEXT: orl %esi, %edi -; X86-NEXT: movl %edi, (%esp) # 4-byte Spill -; X86-NEXT: movl %ecx, %edi +; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %ebx # 4-byte Reload +; X86-NEXT: shldl $1, %ebx, %ebp +; X86-NEXT: shldl $1, %edi, %ebx ; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %ecx # 4-byte Reload -; X86-NEXT: shldl $1, %ecx, %eax -; X86-NEXT: orl %esi, %eax -; X86-NEXT: movl %eax, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill +; X86-NEXT: shldl $1, %ecx, %edi ; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %eax # 4-byte Reload -; X86-NEXT: shldl $1, %eax, %ecx -; X86-NEXT: orl %esi, %ecx +; X86-NEXT: orl %eax, %edi +; X86-NEXT: movl %edi, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill +; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %edi # 4-byte Reload +; X86-NEXT: shldl $1, %edi, %ecx +; X86-NEXT: orl %eax, %ecx ; X86-NEXT: movl %ecx, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill -; X86-NEXT: addl %eax, %eax -; X86-NEXT: orl {{[-0-9]+}}(%e{{[sb]}}p), %eax # 4-byte Folded Reload -; X86-NEXT: movl %eax, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill -; X86-NEXT: cmpl %ebp, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Folded Reload +; X86-NEXT: shldl $1, %esi, %edi +; X86-NEXT: orl %eax, %edi +; X86-NEXT: movl %edi, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill +; X86-NEXT: addl %esi, %esi +; X86-NEXT: orl {{[-0-9]+}}(%e{{[sb]}}p), %esi # 4-byte Folded Reload +; X86-NEXT: movl %esi, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill +; X86-NEXT: cmpl %ebx, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Folded Reload ; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %ecx # 4-byte Reload -; X86-NEXT: sbbl %edx, %ecx +; X86-NEXT: sbbl %ebp, %ecx ; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %ecx # 4-byte Reload -; X86-NEXT: sbbl {{[-0-9]+}}(%e{{[sb]}}p), %ecx # 4-byte Folded Reload +; X86-NEXT: sbbl %edx, %ecx ; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %ecx # 4-byte Reload -; X86-NEXT: sbbl %ebx, %ecx +; X86-NEXT: sbbl (%esp), %ecx # 4-byte Folded Reload ; X86-NEXT: sarl $31, %ecx -; X86-NEXT: movl %ecx, %eax -; X86-NEXT: andl $1, %eax -; X86-NEXT: movl %eax, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill ; X86-NEXT: movl %ecx, %esi -; X86-NEXT: andl %edi, %esi +; X86-NEXT: andl $1, %esi +; X86-NEXT: movl %esi, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill +; X86-NEXT: movl %ecx, %esi +; X86-NEXT: andl {{[-0-9]+}}(%e{{[sb]}}p), %esi # 4-byte Folded Reload ; X86-NEXT: movl %ecx, %edi ; X86-NEXT: andl {{[-0-9]+}}(%e{{[sb]}}p), %edi # 4-byte Folded Reload ; X86-NEXT: movl %ecx, %eax ; X86-NEXT: andl {{[-0-9]+}}(%e{{[sb]}}p), %eax # 4-byte Folded Reload ; X86-NEXT: andl {{[-0-9]+}}(%e{{[sb]}}p), %ecx # 4-byte Folded Reload -; X86-NEXT: subl %ecx, %ebp -; X86-NEXT: sbbl %eax, %edx -; X86-NEXT: movl %edx, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill -; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %edx # 4-byte Reload -; X86-NEXT: sbbl %edi, %edx -; X86-NEXT: movl (%esp), %edi # 4-byte Reload -; X86-NEXT: sbbl %esi, %ebx +; X86-NEXT: subl %ecx, %ebx ; X86-NEXT: movl %ebx, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill -; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %ebx # 4-byte Reload +; X86-NEXT: sbbl %eax, %ebp +; X86-NEXT: movl %ebp, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill +; X86-NEXT: sbbl %edi, %edx +; X86-NEXT: movl %edx, %ebp +; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %edx # 4-byte Reload +; X86-NEXT: sbbl %esi, (%esp) # 4-byte Folded Spill +; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %esi # 4-byte Reload ; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %ecx # 4-byte Reload ; X86-NEXT: addl $-1, %ecx ; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %eax # 4-byte Reload ; X86-NEXT: adcl $-1, %eax -; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %esi # 4-byte Reload -; X86-NEXT: adcl $-1, %esi -; X86-NEXT: adcl $-1, %ebx +; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %edi # 4-byte Reload +; X86-NEXT: adcl $-1, %edi +; X86-NEXT: adcl $-1, %edx ; X86-NEXT: movl %eax, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill -; X86-NEXT: orl %ebx, %eax +; X86-NEXT: orl %edx, %eax ; X86-NEXT: movl %ecx, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill -; X86-NEXT: movl %esi, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill -; X86-NEXT: orl %esi, %ecx -; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %esi # 4-byte Reload +; X86-NEXT: movl %edi, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill +; X86-NEXT: orl %edi, %ecx +; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %edi # 4-byte Reload ; X86-NEXT: orl %eax, %ecx -; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %ecx # 4-byte Reload -; X86-NEXT: jne .LBB4_4 -; X86-NEXT: # %bb.5: +; X86-NEXT: jne .LBB4_3 +; X86-NEXT: # %bb.4: +; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %ebx # 4-byte Reload ; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %edx # 4-byte Reload ; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %eax # 4-byte Reload ; X86-NEXT: movl {{[0-9]+}}(%esp), %ebp -; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %ebx # 4-byte Reload +; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %ecx # 4-byte Reload ; X86-NEXT: .LBB4_7: # %udiv-loop-exit +; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %edi # 4-byte Reload ; X86-NEXT: shldl $1, %edx, %edi -; X86-NEXT: orl %esi, %edi +; X86-NEXT: orl %ecx, %edi ; X86-NEXT: shldl $1, %eax, %edx -; X86-NEXT: orl %esi, %edx -; X86-NEXT: movl %esi, %ecx -; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %esi # 4-byte Reload +; X86-NEXT: orl %ecx, %edx ; X86-NEXT: shldl $1, %esi, %eax ; X86-NEXT: orl %ecx, %eax ; X86-NEXT: addl %esi, %esi -; X86-NEXT: orl %ebx, %esi -; X86-NEXT: .LBB4_8: # %udiv-end -; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %ecx # 4-byte Reload -; X86-NEXT: xorl %ecx, %edi -; X86-NEXT: xorl %ecx, %edx -; X86-NEXT: xorl %ecx, %eax -; X86-NEXT: xorl %ecx, %esi -; X86-NEXT: subl %ecx, %esi +; X86-NEXT: orl {{[-0-9]+}}(%e{{[sb]}}p), %esi # 4-byte Folded Reload +; X86-NEXT: .LBB4_9: # %udiv-end +; X86-NEXT: xorl %ebx, %edi +; X86-NEXT: xorl %ebx, %edx +; X86-NEXT: xorl %ebx, %eax +; X86-NEXT: xorl %ebx, %esi +; X86-NEXT: subl %ebx, %esi ; X86-NEXT: movl %esi, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill -; X86-NEXT: sbbl %ecx, %eax +; X86-NEXT: sbbl %ebx, %eax ; X86-NEXT: movl %eax, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill -; X86-NEXT: sbbl %ecx, %edx -; X86-NEXT: sbbl %ecx, %edi -; X86-NEXT: movl %edi, (%esp) # 4-byte Spill +; X86-NEXT: sbbl %ebx, %edx +; X86-NEXT: sbbl %ebx, %edi +; X86-NEXT: movl %edi, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill ; X86-NEXT: movl %esi, (%ebp) ; X86-NEXT: movl %eax, 4(%ebp) ; X86-NEXT: movl %edx, 8(%ebp) @@ -532,7 +535,7 @@ define i128 @scalar_i128(i128 %x, i128 %y, ptr %divdst) nounwind { ; X86-NEXT: movl %eax, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill ; X86-NEXT: movl %esi, %eax ; X86-NEXT: mull %edi -; X86-NEXT: movl %eax, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill +; X86-NEXT: movl %eax, (%esp) # 4-byte Spill ; X86-NEXT: movl %edx, %edi ; X86-NEXT: addl {{[-0-9]+}}(%e{{[sb]}}p), %edi # 4-byte Folded Reload ; X86-NEXT: adcl $0, %ecx @@ -553,10 +556,10 @@ define i128 @scalar_i128(i128 %x, i128 %y, ptr %divdst) nounwind { ; X86-NEXT: adcl %eax, %edx ; X86-NEXT: movl %edx, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill ; X86-NEXT: movl {{[0-9]+}}(%esp), %eax -; X86-NEXT: movl (%esp), %ecx # 4-byte Reload +; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %ecx # 4-byte Reload ; X86-NEXT: imull %eax, %ecx ; X86-NEXT: mull %ebx -; X86-NEXT: movl %eax, (%esp) # 4-byte Spill +; X86-NEXT: movl %eax, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill ; X86-NEXT: imull {{[0-9]+}}(%esp), %ebx ; X86-NEXT: addl %edx, %ebx ; X86-NEXT: addl %ecx, %ebx @@ -568,12 +571,12 @@ define i128 @scalar_i128(i128 %x, i128 %y, ptr %divdst) nounwind { ; X86-NEXT: mull %edx ; X86-NEXT: addl %edx, %ebp ; X86-NEXT: addl %ecx, %ebp -; X86-NEXT: addl (%esp), %eax # 4-byte Folded Reload +; X86-NEXT: addl {{[-0-9]+}}(%e{{[sb]}}p), %eax # 4-byte Folded Reload ; X86-NEXT: adcl %ebx, %ebp ; X86-NEXT: addl {{[-0-9]+}}(%e{{[sb]}}p), %eax # 4-byte Folded Reload ; X86-NEXT: adcl {{[-0-9]+}}(%e{{[sb]}}p), %ebp # 4-byte Folded Reload ; X86-NEXT: movl {{[0-9]+}}(%esp), %edx -; X86-NEXT: subl {{[-0-9]+}}(%e{{[sb]}}p), %edx # 4-byte Folded Reload +; X86-NEXT: subl (%esp), %edx # 4-byte Folded Reload ; X86-NEXT: movl {{[0-9]+}}(%esp), %ecx ; X86-NEXT: sbbl {{[-0-9]+}}(%e{{[sb]}}p), %ecx # 4-byte Folded Reload ; X86-NEXT: movl {{[0-9]+}}(%esp), %esi diff --git a/llvm/test/CodeGen/X86/fold-masked-merge.ll b/llvm/test/CodeGen/X86/fold-masked-merge.ll index 135494ac25f8cb2de974322b114a80e6350a8c7d..b2614c5fe0493c07a30e8ad26fb2f07742b84ce9 100644 --- a/llvm/test/CodeGen/X86/fold-masked-merge.ll +++ b/llvm/test/CodeGen/X86/fold-masked-merge.ll @@ -56,9 +56,7 @@ define i8 @masked_merge2(i8 %a0, i8 %a1, i8 %a2) { ; NOBMI-LABEL: masked_merge2: ; NOBMI: # %bb.0: ; NOBMI-NEXT: movl %esi, %eax -; NOBMI-NEXT: xorb %sil, %al -; NOBMI-NEXT: andb %dil, %al -; NOBMI-NEXT: xorb %sil, %al +; NOBMI-NEXT: # kill: def $al killed $al killed $eax ; NOBMI-NEXT: retq ; ; BMI-LABEL: masked_merge2: diff --git a/llvm/test/CodeGen/X86/freeze-combine.ll b/llvm/test/CodeGen/X86/freeze-combine.ll index b037a6d9a1b93b937476f2293b6d0f3b182499ac..1cfb8627a4dd4579578fa0649652e6f3fe210296 100644 --- a/llvm/test/CodeGen/X86/freeze-combine.ll +++ b/llvm/test/CodeGen/X86/freeze-combine.ll @@ -3,9 +3,9 @@ define i32 @const() { ; CHECK-LABEL: name: const ; CHECK: bb.0 (%ir-block.0): - ; CHECK: [[MOV32ri:%[0-9]+]]:gr32 = MOV32ri 1 - ; CHECK: $eax = COPY [[MOV32ri]] - ; CHECK: RET 0, $eax + ; CHECK-NEXT: [[MOV32ri:%[0-9]+]]:gr32 = MOV32ri 1 + ; CHECK-NEXT: $eax = COPY [[MOV32ri]] + ; CHECK-NEXT: RET 0, $eax %y = freeze i32 1 ret i32 %y } @@ -13,11 +13,11 @@ define i32 @const() { define i32 @fold(i32 %x) { ; CHECK-LABEL: name: fold ; CHECK: bb.0 (%ir-block.0): - ; CHECK: liveins: $edi - ; CHECK: [[COPY:%[0-9]+]]:gr32 = COPY $edi - ; CHECK: [[COPY1:%[0-9]+]]:gr32 = COPY [[COPY]] - ; CHECK: $eax = COPY [[COPY1]] - ; CHECK: RET 0, $eax + ; CHECK-NEXT: liveins: $edi + ; CHECK-NEXT: {{ $}} + ; CHECK-NEXT: [[COPY:%[0-9]+]]:gr32 = COPY $edi + ; CHECK-NEXT: $eax = COPY [[COPY]] + ; CHECK-NEXT: RET 0, $eax %y = freeze i32 %x %z = freeze i32 %y ret i32 %z diff --git a/llvm/test/CodeGen/X86/gfni-funnel-shifts.ll b/llvm/test/CodeGen/X86/gfni-funnel-shifts.ll index 0c341dc63a9ecc9bdba7c806e6a8fa5487faf385..afe0ebb9dcb4f081fc8acb02c9ac1095769dc8be 100644 --- a/llvm/test/CodeGen/X86/gfni-funnel-shifts.ll +++ b/llvm/test/CodeGen/X86/gfni-funnel-shifts.ll @@ -522,17 +522,17 @@ declare <16 x i8> @llvm.fshl.v16i8(<16 x i8>, <16 x i8>, <16 x i8>) define <16 x i8> @splatconstant_fshr_v16i8(<16 x i8> %a, <16 x i8> %b) nounwind { ; GFNISSE-LABEL: splatconstant_fshr_v16i8: ; GFNISSE: # %bb.0: +; GFNISSE-NEXT: paddb %xmm0, %xmm0 ; GFNISSE-NEXT: psrlw $7, %xmm1 ; GFNISSE-NEXT: pand {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm1 -; GFNISSE-NEXT: paddb %xmm0, %xmm0 ; GFNISSE-NEXT: por %xmm1, %xmm0 ; GFNISSE-NEXT: retq ; ; GFNIAVX1OR2-LABEL: splatconstant_fshr_v16i8: ; GFNIAVX1OR2: # %bb.0: +; GFNIAVX1OR2-NEXT: vpaddb %xmm0, %xmm0, %xmm0 ; GFNIAVX1OR2-NEXT: vpsrlw $7, %xmm1, %xmm1 ; GFNIAVX1OR2-NEXT: vpand {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm1, %xmm1 -; GFNIAVX1OR2-NEXT: vpaddb %xmm0, %xmm0, %xmm0 ; GFNIAVX1OR2-NEXT: vpor %xmm1, %xmm0, %xmm0 ; GFNIAVX1OR2-NEXT: retq ; diff --git a/llvm/test/CodeGen/X86/gfni-rotates.ll b/llvm/test/CodeGen/X86/gfni-rotates.ll index 7ab8300b269a48e8fc634db49b5b059945757977..96aff5b2af31556ed7414478f0357fff08f9dd9c 100644 --- a/llvm/test/CodeGen/X86/gfni-rotates.ll +++ b/llvm/test/CodeGen/X86/gfni-rotates.ll @@ -421,18 +421,18 @@ define <16 x i8> @splatconstant_rotr_v16i8(<16 x i8> %a) nounwind { ; GFNISSE-LABEL: splatconstant_rotr_v16i8: ; GFNISSE: # %bb.0: ; GFNISSE-NEXT: movdqa %xmm0, %xmm1 -; GFNISSE-NEXT: psrlw $7, %xmm1 -; GFNISSE-NEXT: pand {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm1 -; GFNISSE-NEXT: paddb %xmm0, %xmm0 +; GFNISSE-NEXT: paddb %xmm0, %xmm1 +; GFNISSE-NEXT: psrlw $7, %xmm0 +; GFNISSE-NEXT: pand {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm0 ; GFNISSE-NEXT: por %xmm1, %xmm0 ; GFNISSE-NEXT: retq ; ; GFNIAVX1OR2-LABEL: splatconstant_rotr_v16i8: ; GFNIAVX1OR2: # %bb.0: -; GFNIAVX1OR2-NEXT: vpsrlw $7, %xmm0, %xmm1 -; GFNIAVX1OR2-NEXT: vpand {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm1, %xmm1 -; GFNIAVX1OR2-NEXT: vpaddb %xmm0, %xmm0, %xmm0 -; GFNIAVX1OR2-NEXT: vpor %xmm1, %xmm0, %xmm0 +; GFNIAVX1OR2-NEXT: vpaddb %xmm0, %xmm0, %xmm1 +; GFNIAVX1OR2-NEXT: vpsrlw $7, %xmm0, %xmm0 +; GFNIAVX1OR2-NEXT: vpand {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm0, %xmm0 +; GFNIAVX1OR2-NEXT: vpor %xmm0, %xmm1, %xmm0 ; GFNIAVX1OR2-NEXT: retq ; ; GFNIAVX512-LABEL: splatconstant_rotr_v16i8: diff --git a/llvm/test/CodeGen/X86/known-never-zero.ll b/llvm/test/CodeGen/X86/known-never-zero.ll index 39d02f9112f4fcbff8b3156b406e73664c8be6fe..2f780e3c6fe1f1edfc2bf941f0c1d648092f3b60 100644 --- a/llvm/test/CodeGen/X86/known-never-zero.ll +++ b/llvm/test/CodeGen/X86/known-never-zero.ll @@ -676,12 +676,13 @@ define i32 @rotr_known_nonzero(i32 %xx, i32 %y) { ; X64: # %bb.0: ; X64-NEXT: movl %esi, %ecx ; X64-NEXT: orl $256, %edi # imm = 0x100 +; X64-NEXT: movl %edi, %eax ; X64-NEXT: # kill: def $cl killed $cl killed $ecx -; X64-NEXT: rorl %cl, %edi +; X64-NEXT: rorl %cl, %eax ; X64-NEXT: testl %edi, %edi ; X64-NEXT: je .LBB22_1 ; X64-NEXT: # %bb.2: # %cond.false -; X64-NEXT: rep bsfl %edi, %eax +; X64-NEXT: rep bsfl %eax, %eax ; X64-NEXT: retq ; X64-NEXT: .LBB22_1: ; X64-NEXT: movl $32, %eax @@ -713,12 +714,13 @@ define i32 @rotr_maybe_zero(i32 %x, i32 %y) { ; X64-LABEL: rotr_maybe_zero: ; X64: # %bb.0: ; X64-NEXT: movl %esi, %ecx +; X64-NEXT: movl %edi, %eax ; X64-NEXT: # kill: def $cl killed $cl killed $ecx -; X64-NEXT: rorl %cl, %edi +; X64-NEXT: rorl %cl, %eax ; X64-NEXT: testl %edi, %edi ; X64-NEXT: je .LBB23_1 ; X64-NEXT: # %bb.2: # %cond.false -; X64-NEXT: rep bsfl %edi, %eax +; X64-NEXT: rep bsfl %eax, %eax ; X64-NEXT: retq ; X64-NEXT: .LBB23_1: ; X64-NEXT: movl $32, %eax @@ -773,12 +775,13 @@ define i32 @rotr_with_fshr_maybe_zero(i32 %x, i32 %y) { ; X64-LABEL: rotr_with_fshr_maybe_zero: ; X64: # %bb.0: ; X64-NEXT: movl %esi, %ecx +; X64-NEXT: movl %edi, %eax ; X64-NEXT: # kill: def $cl killed $cl killed $ecx -; X64-NEXT: rorl %cl, %edi +; X64-NEXT: rorl %cl, %eax ; X64-NEXT: testl %edi, %edi ; X64-NEXT: je .LBB25_1 ; X64-NEXT: # %bb.2: # %cond.false -; X64-NEXT: rep bsfl %edi, %eax +; X64-NEXT: rep bsfl %eax, %eax ; X64-NEXT: retq ; X64-NEXT: .LBB25_1: ; X64-NEXT: movl $32, %eax @@ -808,12 +811,13 @@ define i32 @rotl_known_nonzero(i32 %xx, i32 %y) { ; X64: # %bb.0: ; X64-NEXT: movl %esi, %ecx ; X64-NEXT: orl $256, %edi # imm = 0x100 +; X64-NEXT: movl %edi, %eax ; X64-NEXT: # kill: def $cl killed $cl killed $ecx -; X64-NEXT: roll %cl, %edi +; X64-NEXT: roll %cl, %eax ; X64-NEXT: testl %edi, %edi ; X64-NEXT: je .LBB26_1 ; X64-NEXT: # %bb.2: # %cond.false -; X64-NEXT: rep bsfl %edi, %eax +; X64-NEXT: rep bsfl %eax, %eax ; X64-NEXT: retq ; X64-NEXT: .LBB26_1: ; X64-NEXT: movl $32, %eax @@ -845,12 +849,13 @@ define i32 @rotl_maybe_zero(i32 %x, i32 %y) { ; X64-LABEL: rotl_maybe_zero: ; X64: # %bb.0: ; X64-NEXT: movl %esi, %ecx +; X64-NEXT: movl %edi, %eax ; X64-NEXT: # kill: def $cl killed $cl killed $ecx -; X64-NEXT: roll %cl, %edi +; X64-NEXT: roll %cl, %eax ; X64-NEXT: testl %edi, %edi ; X64-NEXT: je .LBB27_1 ; X64-NEXT: # %bb.2: # %cond.false -; X64-NEXT: rep bsfl %edi, %eax +; X64-NEXT: rep bsfl %eax, %eax ; X64-NEXT: retq ; X64-NEXT: .LBB27_1: ; X64-NEXT: movl $32, %eax @@ -905,12 +910,13 @@ define i32 @rotl_with_fshl_maybe_zero(i32 %x, i32 %y) { ; X64-LABEL: rotl_with_fshl_maybe_zero: ; X64: # %bb.0: ; X64-NEXT: movl %esi, %ecx +; X64-NEXT: movl %edi, %eax ; X64-NEXT: # kill: def $cl killed $cl killed $ecx -; X64-NEXT: roll %cl, %edi +; X64-NEXT: roll %cl, %eax ; X64-NEXT: testl %edi, %edi ; X64-NEXT: je .LBB29_1 ; X64-NEXT: # %bb.2: # %cond.false -; X64-NEXT: rep bsfl %edi, %eax +; X64-NEXT: rep bsfl %eax, %eax ; X64-NEXT: retq ; X64-NEXT: .LBB29_1: ; X64-NEXT: movl $32, %eax diff --git a/llvm/test/CodeGen/X86/midpoint-int-vec-128.ll b/llvm/test/CodeGen/X86/midpoint-int-vec-128.ll index d3cced3233ea65045517cfd674ced9f360c009d4..5a6375e08bcaff62c5e8a36f1ae86bc1095b591d 100644 --- a/llvm/test/CodeGen/X86/midpoint-int-vec-128.ll +++ b/llvm/test/CodeGen/X86/midpoint-int-vec-128.ll @@ -893,27 +893,26 @@ define <2 x i64> @vec128_i64_signed_reg_reg(<2 x i64> %a1, <2 x i64> %a2) nounwi ; SSE41-NEXT: pcmpeqd %xmm3, %xmm0 ; SSE41-NEXT: pshufd {{.*#+}} xmm3 = xmm0[1,1,3,3] ; SSE41-NEXT: pand %xmm5, %xmm3 -; SSE41-NEXT: pshufd {{.*#+}} xmm6 = xmm4[1,1,3,3] -; SSE41-NEXT: por %xmm3, %xmm6 -; SSE41-NEXT: por {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm6 -; SSE41-NEXT: pand %xmm5, %xmm0 -; SSE41-NEXT: por %xmm4, %xmm0 -; SSE41-NEXT: movdqa %xmm2, %xmm3 -; SSE41-NEXT: psubq %xmm1, %xmm3 +; SSE41-NEXT: pshufd {{.*#+}} xmm0 = xmm4[1,1,3,3] +; SSE41-NEXT: por %xmm3, %xmm0 +; SSE41-NEXT: pmovsxbq {{.*#+}} xmm3 = [1,1] +; SSE41-NEXT: por %xmm0, %xmm3 +; SSE41-NEXT: movdqa %xmm2, %xmm4 +; SSE41-NEXT: psubq %xmm1, %xmm4 ; SSE41-NEXT: psubq %xmm2, %xmm1 -; SSE41-NEXT: blendvpd %xmm0, %xmm3, %xmm1 +; SSE41-NEXT: blendvpd %xmm0, %xmm4, %xmm1 ; SSE41-NEXT: movapd %xmm1, %xmm0 ; SSE41-NEXT: psrlq $1, %xmm0 ; SSE41-NEXT: psrlq $33, %xmm1 -; SSE41-NEXT: pmuludq %xmm6, %xmm1 -; SSE41-NEXT: movdqa %xmm6, %xmm3 -; SSE41-NEXT: psrlq $32, %xmm3 -; SSE41-NEXT: pmuludq %xmm0, %xmm3 -; SSE41-NEXT: paddq %xmm1, %xmm3 -; SSE41-NEXT: psllq $32, %xmm3 -; SSE41-NEXT: pmuludq %xmm6, %xmm0 +; SSE41-NEXT: pmuludq %xmm3, %xmm1 +; SSE41-NEXT: movdqa %xmm3, %xmm4 +; SSE41-NEXT: psrlq $32, %xmm4 +; SSE41-NEXT: pmuludq %xmm0, %xmm4 +; SSE41-NEXT: paddq %xmm1, %xmm4 +; SSE41-NEXT: psllq $32, %xmm4 +; SSE41-NEXT: pmuludq %xmm3, %xmm0 ; SSE41-NEXT: paddq %xmm2, %xmm0 -; SSE41-NEXT: paddq %xmm3, %xmm0 +; SSE41-NEXT: paddq %xmm4, %xmm0 ; SSE41-NEXT: retq ; ; AVX-LABEL: vec128_i64_signed_reg_reg: @@ -1077,27 +1076,26 @@ define <2 x i64> @vec128_i64_unsigned_reg_reg(<2 x i64> %a1, <2 x i64> %a2) noun ; SSE41-NEXT: pcmpeqd %xmm3, %xmm0 ; SSE41-NEXT: pshufd {{.*#+}} xmm3 = xmm0[1,1,3,3] ; SSE41-NEXT: pand %xmm5, %xmm3 -; SSE41-NEXT: pshufd {{.*#+}} xmm6 = xmm4[1,1,3,3] -; SSE41-NEXT: por %xmm3, %xmm6 -; SSE41-NEXT: por {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm6 -; SSE41-NEXT: pand %xmm5, %xmm0 -; SSE41-NEXT: por %xmm4, %xmm0 -; SSE41-NEXT: movdqa %xmm2, %xmm3 -; SSE41-NEXT: psubq %xmm1, %xmm3 +; SSE41-NEXT: pshufd {{.*#+}} xmm0 = xmm4[1,1,3,3] +; SSE41-NEXT: por %xmm3, %xmm0 +; SSE41-NEXT: pmovsxbq {{.*#+}} xmm3 = [1,1] +; SSE41-NEXT: por %xmm0, %xmm3 +; SSE41-NEXT: movdqa %xmm2, %xmm4 +; SSE41-NEXT: psubq %xmm1, %xmm4 ; SSE41-NEXT: psubq %xmm2, %xmm1 -; SSE41-NEXT: blendvpd %xmm0, %xmm3, %xmm1 +; SSE41-NEXT: blendvpd %xmm0, %xmm4, %xmm1 ; SSE41-NEXT: movapd %xmm1, %xmm0 ; SSE41-NEXT: psrlq $1, %xmm0 ; SSE41-NEXT: psrlq $33, %xmm1 -; SSE41-NEXT: pmuludq %xmm6, %xmm1 -; SSE41-NEXT: movdqa %xmm6, %xmm3 -; SSE41-NEXT: psrlq $32, %xmm3 -; SSE41-NEXT: pmuludq %xmm0, %xmm3 -; SSE41-NEXT: paddq %xmm1, %xmm3 -; SSE41-NEXT: psllq $32, %xmm3 -; SSE41-NEXT: pmuludq %xmm6, %xmm0 +; SSE41-NEXT: pmuludq %xmm3, %xmm1 +; SSE41-NEXT: movdqa %xmm3, %xmm4 +; SSE41-NEXT: psrlq $32, %xmm4 +; SSE41-NEXT: pmuludq %xmm0, %xmm4 +; SSE41-NEXT: paddq %xmm1, %xmm4 +; SSE41-NEXT: psllq $32, %xmm4 +; SSE41-NEXT: pmuludq %xmm3, %xmm0 ; SSE41-NEXT: paddq %xmm2, %xmm0 -; SSE41-NEXT: paddq %xmm3, %xmm0 +; SSE41-NEXT: paddq %xmm4, %xmm0 ; SSE41-NEXT: retq ; ; AVX1-LABEL: vec128_i64_unsigned_reg_reg: @@ -1993,14 +1991,14 @@ define <8 x i16> @vec128_i16_unsigned_reg_reg(<8 x i16> %a1, <8 x i16> %a2) noun ; ; AVX512VL-FALLBACK-LABEL: vec128_i16_unsigned_reg_reg: ; AVX512VL-FALLBACK: # %bb.0: -; AVX512VL-FALLBACK-NEXT: vpminuw %xmm1, %xmm0, %xmm2 -; AVX512VL-FALLBACK-NEXT: vpmaxuw %xmm1, %xmm0, %xmm1 -; AVX512VL-FALLBACK-NEXT: vpsubw %xmm2, %xmm1, %xmm1 -; AVX512VL-FALLBACK-NEXT: vpsrlw $1, %xmm1, %xmm1 -; AVX512VL-FALLBACK-NEXT: vpcmpeqw %xmm2, %xmm0, %xmm2 -; AVX512VL-FALLBACK-NEXT: vpternlogq $15, %xmm2, %xmm2, %xmm2 -; AVX512VL-FALLBACK-NEXT: vpxor %xmm2, %xmm1, %xmm1 -; AVX512VL-FALLBACK-NEXT: vpsubw %xmm2, %xmm1, %xmm1 +; AVX512VL-FALLBACK-NEXT: vpmaxuw %xmm1, %xmm0, %xmm2 +; AVX512VL-FALLBACK-NEXT: vpminuw %xmm1, %xmm0, %xmm1 +; AVX512VL-FALLBACK-NEXT: vpsubw %xmm1, %xmm2, %xmm2 +; AVX512VL-FALLBACK-NEXT: vpsrlw $1, %xmm2, %xmm2 +; AVX512VL-FALLBACK-NEXT: vpcmpeqw %xmm1, %xmm0, %xmm1 +; AVX512VL-FALLBACK-NEXT: vpternlogq $15, %xmm1, %xmm1, %xmm1 +; AVX512VL-FALLBACK-NEXT: vpxor %xmm1, %xmm2, %xmm2 +; AVX512VL-FALLBACK-NEXT: vpsubw %xmm1, %xmm2, %xmm1 ; AVX512VL-FALLBACK-NEXT: vpaddw %xmm0, %xmm1, %xmm0 ; AVX512VL-FALLBACK-NEXT: retq ; @@ -2786,14 +2784,14 @@ define <16 x i8> @vec128_i8_unsigned_reg_reg(<16 x i8> %a1, <16 x i8> %a2) nounw ; ; AVX512VL-FALLBACK-LABEL: vec128_i8_unsigned_reg_reg: ; AVX512VL-FALLBACK: # %bb.0: -; AVX512VL-FALLBACK-NEXT: vpminub %xmm1, %xmm0, %xmm2 -; AVX512VL-FALLBACK-NEXT: vpmaxub %xmm1, %xmm0, %xmm1 -; AVX512VL-FALLBACK-NEXT: vpsubb %xmm2, %xmm1, %xmm1 -; AVX512VL-FALLBACK-NEXT: vpsrlw $1, %xmm1, %xmm1 -; AVX512VL-FALLBACK-NEXT: vpcmpeqb %xmm2, %xmm0, %xmm2 -; AVX512VL-FALLBACK-NEXT: vpternlogq $15, %xmm2, %xmm2, %xmm2 -; AVX512VL-FALLBACK-NEXT: vpternlogd $108, {{\.?LCPI[0-9]+_[0-9]+}}(%rip){1to4}, %xmm2, %xmm1 -; AVX512VL-FALLBACK-NEXT: vpsubb %xmm2, %xmm1, %xmm1 +; AVX512VL-FALLBACK-NEXT: vpmaxub %xmm1, %xmm0, %xmm2 +; AVX512VL-FALLBACK-NEXT: vpminub %xmm1, %xmm0, %xmm1 +; AVX512VL-FALLBACK-NEXT: vpsubb %xmm1, %xmm2, %xmm2 +; AVX512VL-FALLBACK-NEXT: vpsrlw $1, %xmm2, %xmm2 +; AVX512VL-FALLBACK-NEXT: vpcmpeqb %xmm1, %xmm0, %xmm1 +; AVX512VL-FALLBACK-NEXT: vpternlogq $15, %xmm1, %xmm1, %xmm1 +; AVX512VL-FALLBACK-NEXT: vpternlogd $108, {{\.?LCPI[0-9]+_[0-9]+}}(%rip){1to4}, %xmm1, %xmm2 +; AVX512VL-FALLBACK-NEXT: vpsubb %xmm1, %xmm2, %xmm1 ; AVX512VL-FALLBACK-NEXT: vpaddb %xmm0, %xmm1, %xmm0 ; AVX512VL-FALLBACK-NEXT: retq ; diff --git a/llvm/test/CodeGen/X86/midpoint-int-vec-256.ll b/llvm/test/CodeGen/X86/midpoint-int-vec-256.ll index cc08396ae8c78fe7554cc6b0200cf3708e6e441d..e880a1acc9e83fed6f1bbde8e375f656ff4543b4 100644 --- a/llvm/test/CodeGen/X86/midpoint-int-vec-256.ll +++ b/llvm/test/CodeGen/X86/midpoint-int-vec-256.ll @@ -1445,14 +1445,14 @@ define <16 x i16> @vec256_i16_unsigned_reg_reg(<16 x i16> %a1, <16 x i16> %a2) n ; ; AVX512VL-FALLBACK-LABEL: vec256_i16_unsigned_reg_reg: ; AVX512VL-FALLBACK: # %bb.0: -; AVX512VL-FALLBACK-NEXT: vpminuw %ymm1, %ymm0, %ymm2 -; AVX512VL-FALLBACK-NEXT: vpmaxuw %ymm1, %ymm0, %ymm1 -; AVX512VL-FALLBACK-NEXT: vpsubw %ymm2, %ymm1, %ymm1 -; AVX512VL-FALLBACK-NEXT: vpsrlw $1, %ymm1, %ymm1 -; AVX512VL-FALLBACK-NEXT: vpcmpeqw %ymm2, %ymm0, %ymm2 -; AVX512VL-FALLBACK-NEXT: vpternlogq $15, %ymm2, %ymm2, %ymm2 -; AVX512VL-FALLBACK-NEXT: vpxor %ymm2, %ymm1, %ymm1 -; AVX512VL-FALLBACK-NEXT: vpsubw %ymm2, %ymm1, %ymm1 +; AVX512VL-FALLBACK-NEXT: vpmaxuw %ymm1, %ymm0, %ymm2 +; AVX512VL-FALLBACK-NEXT: vpminuw %ymm1, %ymm0, %ymm1 +; AVX512VL-FALLBACK-NEXT: vpsubw %ymm1, %ymm2, %ymm2 +; AVX512VL-FALLBACK-NEXT: vpsrlw $1, %ymm2, %ymm2 +; AVX512VL-FALLBACK-NEXT: vpcmpeqw %ymm1, %ymm0, %ymm1 +; AVX512VL-FALLBACK-NEXT: vpternlogq $15, %ymm1, %ymm1, %ymm1 +; AVX512VL-FALLBACK-NEXT: vpxor %ymm1, %ymm2, %ymm2 +; AVX512VL-FALLBACK-NEXT: vpsubw %ymm1, %ymm2, %ymm1 ; AVX512VL-FALLBACK-NEXT: vpaddw %ymm0, %ymm1, %ymm0 ; AVX512VL-FALLBACK-NEXT: retq ; @@ -2210,14 +2210,14 @@ define <32 x i8> @vec256_i8_unsigned_reg_reg(<32 x i8> %a1, <32 x i8> %a2) nounw ; ; AVX512VL-FALLBACK-LABEL: vec256_i8_unsigned_reg_reg: ; AVX512VL-FALLBACK: # %bb.0: -; AVX512VL-FALLBACK-NEXT: vpminub %ymm1, %ymm0, %ymm2 -; AVX512VL-FALLBACK-NEXT: vpmaxub %ymm1, %ymm0, %ymm1 -; AVX512VL-FALLBACK-NEXT: vpsubb %ymm2, %ymm1, %ymm1 -; AVX512VL-FALLBACK-NEXT: vpsrlw $1, %ymm1, %ymm1 -; AVX512VL-FALLBACK-NEXT: vpcmpeqb %ymm2, %ymm0, %ymm2 -; AVX512VL-FALLBACK-NEXT: vpternlogq $15, %ymm2, %ymm2, %ymm2 -; AVX512VL-FALLBACK-NEXT: vpternlogd $108, {{\.?LCPI[0-9]+_[0-9]+}}(%rip){1to8}, %ymm2, %ymm1 -; AVX512VL-FALLBACK-NEXT: vpsubb %ymm2, %ymm1, %ymm1 +; AVX512VL-FALLBACK-NEXT: vpmaxub %ymm1, %ymm0, %ymm2 +; AVX512VL-FALLBACK-NEXT: vpminub %ymm1, %ymm0, %ymm1 +; AVX512VL-FALLBACK-NEXT: vpsubb %ymm1, %ymm2, %ymm2 +; AVX512VL-FALLBACK-NEXT: vpsrlw $1, %ymm2, %ymm2 +; AVX512VL-FALLBACK-NEXT: vpcmpeqb %ymm1, %ymm0, %ymm1 +; AVX512VL-FALLBACK-NEXT: vpternlogq $15, %ymm1, %ymm1, %ymm1 +; AVX512VL-FALLBACK-NEXT: vpternlogd $108, {{\.?LCPI[0-9]+_[0-9]+}}(%rip){1to8}, %ymm1, %ymm2 +; AVX512VL-FALLBACK-NEXT: vpsubb %ymm1, %ymm2, %ymm1 ; AVX512VL-FALLBACK-NEXT: vpaddb %ymm0, %ymm1, %ymm0 ; AVX512VL-FALLBACK-NEXT: retq ; diff --git a/llvm/test/CodeGen/X86/pr34592.ll b/llvm/test/CodeGen/X86/pr34592.ll index 9887dac76e20b40a1ad52454d265c2f60a2d81fd..23de746ecb35395dc861dba4eb65b6e5fc8847df 100644 --- a/llvm/test/CodeGen/X86/pr34592.ll +++ b/llvm/test/CodeGen/X86/pr34592.ll @@ -1,51 +1,76 @@ ; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py -; RUN: llc < %s -mtriple=x86_64-unknown-unknown -mattr=avx2 -O0 | FileCheck %s +; RUN: llc < %s -mtriple=x86_64-unknown-unknown -mattr=avx2 -O0 | FileCheck %s --check-prefixes=CHECK-O0 +; RUN: llc < %s -mtriple=x86_64-unknown-unknown -mattr=avx2 -O3 | FileCheck %s --check-prefixes=CHECK-O3 -define <16 x i64> @pluto(<16 x i64> %arg, <16 x i64> %arg1, <16 x i64> %arg2, <16 x i64> %arg3, <16 x i64> %arg4) { -; CHECK-LABEL: pluto: -; CHECK: # %bb.0: # %bb -; CHECK-NEXT: pushq %rbp -; CHECK-NEXT: .cfi_def_cfa_offset 16 -; CHECK-NEXT: .cfi_offset %rbp, -16 -; CHECK-NEXT: movq %rsp, %rbp -; CHECK-NEXT: .cfi_def_cfa_register %rbp -; CHECK-NEXT: andq $-32, %rsp -; CHECK-NEXT: subq $32, %rsp -; CHECK-NEXT: vmovaps %ymm4, %ymm10 -; CHECK-NEXT: vmovaps %ymm3, %ymm9 -; CHECK-NEXT: vmovaps %ymm1, %ymm8 -; CHECK-NEXT: vmovaps 240(%rbp), %ymm4 -; CHECK-NEXT: vmovaps 208(%rbp), %ymm3 -; CHECK-NEXT: vmovaps 176(%rbp), %ymm1 -; CHECK-NEXT: vmovaps 144(%rbp), %ymm1 -; CHECK-NEXT: vmovaps 112(%rbp), %ymm11 -; CHECK-NEXT: vmovaps 80(%rbp), %ymm11 -; CHECK-NEXT: vmovaps 48(%rbp), %ymm11 -; CHECK-NEXT: vmovaps 16(%rbp), %ymm11 -; CHECK-NEXT: vpblendd {{.*#+}} ymm0 = ymm6[0,1,2,3,4,5],ymm2[6,7] -; CHECK-NEXT: vpunpcklqdq {{.*#+}} ymm1 = ymm1[0],ymm3[0],ymm1[2],ymm3[2] -; CHECK-NEXT: vpermq {{.*#+}} ymm1 = ymm1[0,2,1,3] -; CHECK-NEXT: vpermq {{.*#+}} ymm0 = ymm0[3,1,2,1] -; CHECK-NEXT: vpblendd {{.*#+}} ymm0 = ymm0[0,1],ymm1[2,3,4,5],ymm0[6,7] -; CHECK-NEXT: vperm2i128 {{.*#+}} ymm1 = ymm7[2,3],ymm6[0,1] -; CHECK-NEXT: vxorps %xmm2, %xmm2, %xmm2 -; CHECK-NEXT: vpblendd {{.*#+}} ymm2 = ymm1[0,1],ymm2[2,3],ymm1[4,5,6,7] -; CHECK-NEXT: vpunpcklqdq {{.*#+}} ymm1 = ymm7[0],ymm5[0],ymm7[2],ymm5[2] -; CHECK-NEXT: vpermq {{.*#+}} ymm1 = ymm1[2,1,2,3] -; CHECK-NEXT: vpermq {{.*#+}} ymm4 = ymm4[1,1,1,1] -; CHECK-NEXT: vpblendd {{.*#+}} ymm1 = ymm1[0,1],ymm4[2,3,4,5],ymm1[6,7] -; CHECK-NEXT: vmovaps %xmm3, %xmm4 -; CHECK-NEXT: vmovaps %xmm7, %xmm3 -; CHECK-NEXT: vpblendd {{.*#+}} xmm4 = xmm3[0,1],xmm4[2,3] -; CHECK-NEXT: # implicit-def: $ymm3 -; CHECK-NEXT: vmovaps %xmm4, %xmm3 -; CHECK-NEXT: vpermq {{.*#+}} ymm4 = ymm3[0,0,1,3] -; CHECK-NEXT: vpslldq {{.*#+}} ymm3 = zero,zero,zero,zero,zero,zero,zero,zero,ymm5[0,1,2,3,4,5,6,7],zero,zero,zero,zero,zero,zero,zero,zero,ymm5[16,17,18,19,20,21,22,23] -; CHECK-NEXT: vpblendd {{.*#+}} ymm3 = ymm3[0,1],ymm4[2,3,4,5],ymm3[6,7] -; CHECK-NEXT: movq %rbp, %rsp -; CHECK-NEXT: popq %rbp -; CHECK-NEXT: .cfi_def_cfa %rsp, 8 -; CHECK-NEXT: retq +define <16 x i64> @pluto(<16 x i64> %arg, <16 x i64> %arg1, <16 x i64> %arg2, <16 x i64> %arg3, <16 x i64> %arg4) nounwind { +; CHECK-O0-LABEL: pluto: +; CHECK-O0: # %bb.0: # %bb +; CHECK-O0-NEXT: pushq %rbp +; CHECK-O0-NEXT: movq %rsp, %rbp +; CHECK-O0-NEXT: andq $-32, %rsp +; CHECK-O0-NEXT: subq $32, %rsp +; CHECK-O0-NEXT: vmovaps %ymm4, %ymm10 +; CHECK-O0-NEXT: vmovaps %ymm3, %ymm9 +; CHECK-O0-NEXT: vmovaps %ymm1, %ymm8 +; CHECK-O0-NEXT: vmovaps 240(%rbp), %ymm4 +; CHECK-O0-NEXT: vmovaps 208(%rbp), %ymm3 +; CHECK-O0-NEXT: vmovaps 176(%rbp), %ymm1 +; CHECK-O0-NEXT: vmovaps 144(%rbp), %ymm1 +; CHECK-O0-NEXT: vmovaps 112(%rbp), %ymm11 +; CHECK-O0-NEXT: vmovaps 80(%rbp), %ymm11 +; CHECK-O0-NEXT: vmovaps 48(%rbp), %ymm11 +; CHECK-O0-NEXT: vmovaps 16(%rbp), %ymm11 +; CHECK-O0-NEXT: vpblendd {{.*#+}} ymm0 = ymm6[0,1,2,3,4,5],ymm2[6,7] +; CHECK-O0-NEXT: vpunpcklqdq {{.*#+}} ymm1 = ymm1[0],ymm3[0],ymm1[2],ymm3[2] +; CHECK-O0-NEXT: vpermq {{.*#+}} ymm1 = ymm1[0,2,1,3] +; CHECK-O0-NEXT: vpermq {{.*#+}} ymm0 = ymm0[3,1,2,1] +; CHECK-O0-NEXT: vpblendd {{.*#+}} ymm0 = ymm0[0,1],ymm1[2,3,4,5],ymm0[6,7] +; CHECK-O0-NEXT: vperm2i128 {{.*#+}} ymm1 = ymm7[2,3],ymm6[0,1] +; CHECK-O0-NEXT: vxorps %xmm2, %xmm2, %xmm2 +; CHECK-O0-NEXT: vpblendd {{.*#+}} ymm2 = ymm1[0,1],ymm2[2,3],ymm1[4,5,6,7] +; CHECK-O0-NEXT: vpunpcklqdq {{.*#+}} ymm1 = ymm7[0],ymm5[0],ymm7[2],ymm5[2] +; CHECK-O0-NEXT: vpermq {{.*#+}} ymm1 = ymm1[2,1,2,3] +; CHECK-O0-NEXT: vpermq {{.*#+}} ymm4 = ymm4[1,1,1,1] +; CHECK-O0-NEXT: vpblendd {{.*#+}} ymm1 = ymm1[0,1],ymm4[2,3,4,5],ymm1[6,7] +; CHECK-O0-NEXT: vmovaps %xmm3, %xmm4 +; CHECK-O0-NEXT: vmovaps %xmm7, %xmm3 +; CHECK-O0-NEXT: vpblendd {{.*#+}} xmm4 = xmm3[0,1],xmm4[2,3] +; CHECK-O0-NEXT: # implicit-def: $ymm3 +; CHECK-O0-NEXT: vmovaps %xmm4, %xmm3 +; CHECK-O0-NEXT: vpermq {{.*#+}} ymm4 = ymm3[0,0,1,3] +; CHECK-O0-NEXT: vpslldq {{.*#+}} ymm3 = zero,zero,zero,zero,zero,zero,zero,zero,ymm5[0,1,2,3,4,5,6,7],zero,zero,zero,zero,zero,zero,zero,zero,ymm5[16,17,18,19,20,21,22,23] +; CHECK-O0-NEXT: vpblendd {{.*#+}} ymm3 = ymm3[0,1],ymm4[2,3,4,5],ymm3[6,7] +; CHECK-O0-NEXT: movq %rbp, %rsp +; CHECK-O0-NEXT: popq %rbp +; CHECK-O0-NEXT: retq +; +; CHECK-O3-LABEL: pluto: +; CHECK-O3: # %bb.0: # %bb +; CHECK-O3-NEXT: pushq %rbp +; CHECK-O3-NEXT: movq %rsp, %rbp +; CHECK-O3-NEXT: andq $-32, %rsp +; CHECK-O3-NEXT: subq $32, %rsp +; CHECK-O3-NEXT: vmovdqa 208(%rbp), %ymm3 +; CHECK-O3-NEXT: vmovdqa 144(%rbp), %ymm0 +; CHECK-O3-NEXT: vpblendd {{.*#+}} ymm1 = ymm6[0,1,2,3,4,5],ymm2[6,7] +; CHECK-O3-NEXT: vpunpcklqdq {{.*#+}} ymm0 = ymm0[0],ymm3[0],ymm0[2],ymm3[2] +; CHECK-O3-NEXT: vpermq {{.*#+}} ymm0 = ymm0[0,2,1,3] +; CHECK-O3-NEXT: vpermq {{.*#+}} ymm1 = ymm1[3,1,2,1] +; CHECK-O3-NEXT: vpblendd {{.*#+}} ymm0 = ymm1[0,1],ymm0[2,3,4,5],ymm1[6,7] +; CHECK-O3-NEXT: vperm2i128 {{.*#+}} ymm1 = ymm7[2,3],ymm6[0,1] +; CHECK-O3-NEXT: vpxor %xmm2, %xmm2, %xmm2 +; CHECK-O3-NEXT: vpblendd {{.*#+}} ymm2 = ymm1[0,1],ymm2[2,3],ymm1[4,5,6,7] +; CHECK-O3-NEXT: vpunpcklqdq {{.*#+}} ymm1 = ymm7[0],ymm5[0],ymm7[2],ymm5[2] +; CHECK-O3-NEXT: vpermq {{.*#+}} ymm1 = ymm1[2,1,2,3] +; CHECK-O3-NEXT: vpbroadcastq 248(%rbp), %ymm4 +; CHECK-O3-NEXT: vpblendd {{.*#+}} ymm1 = ymm1[0,1],ymm4[2,3,4,5],ymm1[6,7] +; CHECK-O3-NEXT: vpblendd {{.*#+}} xmm3 = xmm7[0,1],xmm3[2,3] +; CHECK-O3-NEXT: vpermq {{.*#+}} ymm3 = ymm3[0,0,1,3] +; CHECK-O3-NEXT: vpslldq {{.*#+}} ymm4 = zero,zero,zero,zero,zero,zero,zero,zero,ymm5[0,1,2,3,4,5,6,7],zero,zero,zero,zero,zero,zero,zero,zero,ymm5[16,17,18,19,20,21,22,23] +; CHECK-O3-NEXT: vpblendd {{.*#+}} ymm3 = ymm4[0,1],ymm3[2,3,4,5],ymm4[6,7] +; CHECK-O3-NEXT: movq %rbp, %rsp +; CHECK-O3-NEXT: popq %rbp +; CHECK-O3-NEXT: retq bb: %tmp = select <16 x i1> , <16 x i64> %arg, <16 x i64> %arg1 %tmp5 = select <16 x i1> , <16 x i64> %arg2, <16 x i64> zeroinitializer diff --git a/llvm/test/CodeGen/X86/pr38539.ll b/llvm/test/CodeGen/X86/pr38539.ll index 04aff9b7d2e5863a63b3f43858f466df6c5563ca..ace78b38d53edbb500a29bdd63ca82f4a7aa1bf0 100644 --- a/llvm/test/CodeGen/X86/pr38539.ll +++ b/llvm/test/CodeGen/X86/pr38539.ll @@ -22,7 +22,7 @@ define void @f() nounwind { ; X86-NEXT: pushl %edi ; X86-NEXT: pushl %esi ; X86-NEXT: andl $-16, %esp -; X86-NEXT: subl $176, %esp +; X86-NEXT: subl $160, %esp ; X86-NEXT: movzbl {{[0-9]+}}(%esp), %edx ; X86-NEXT: movl {{[0-9]+}}(%esp), %esi ; X86-NEXT: movl {{[0-9]+}}(%esp), %edi @@ -47,55 +47,54 @@ define void @f() nounwind { ; X86-NEXT: testl %edi, %edi ; X86-NEXT: jne .LBB0_1 ; X86-NEXT: # %bb.2: # %BB_udiv-special-cases -; X86-NEXT: bsrl %esi, %ecx -; X86-NEXT: xorl $31, %ecx -; X86-NEXT: addl $32, %ecx +; X86-NEXT: bsrl %esi, %eax +; X86-NEXT: xorl $31, %eax +; X86-NEXT: addl $32, %eax ; X86-NEXT: jmp .LBB0_3 ; X86-NEXT: .LBB0_1: -; X86-NEXT: bsrl %edi, %ecx -; X86-NEXT: xorl $31, %ecx +; X86-NEXT: bsrl %edi, %eax +; X86-NEXT: xorl $31, %eax ; X86-NEXT: .LBB0_3: # %BB_udiv-special-cases -; X86-NEXT: xorl %eax, %eax +; X86-NEXT: xorl %ecx, %ecx ; X86-NEXT: testl %edx, %edx -; X86-NEXT: movl %edi, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill +; X86-NEXT: movl %esi, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill ; X86-NEXT: jne .LBB0_4 ; X86-NEXT: # %bb.5: # %BB_udiv-special-cases -; X86-NEXT: addl $64, %ecx +; X86-NEXT: addl $64, %eax ; X86-NEXT: jmp .LBB0_6 ; X86-NEXT: .LBB0_4: -; X86-NEXT: bsrl %edx, %ecx -; X86-NEXT: xorl $31, %ecx -; X86-NEXT: addl $32, %ecx +; X86-NEXT: bsrl %edx, %eax +; X86-NEXT: xorl $31, %eax +; X86-NEXT: addl $32, %eax ; X86-NEXT: .LBB0_6: # %BB_udiv-special-cases -; X86-NEXT: subl $62, %ecx +; X86-NEXT: subl $62, %eax ; X86-NEXT: movl $0, %ebx ; X86-NEXT: sbbl %ebx, %ebx -; X86-NEXT: sbbl %eax, %eax -; X86-NEXT: addl $-66, %ecx +; X86-NEXT: sbbl %ecx, %ecx +; X86-NEXT: addl $-66, %eax ; X86-NEXT: adcl $-1, %ebx -; X86-NEXT: adcl $3, %eax -; X86-NEXT: movl %eax, %edi -; X86-NEXT: movb $1, %al -; X86-NEXT: testb %al, %al +; X86-NEXT: adcl $3, %ecx +; X86-NEXT: movl %ecx, %esi +; X86-NEXT: movb $1, %cl +; X86-NEXT: testb %cl, %cl ; X86-NEXT: jne .LBB0_11 ; X86-NEXT: # %bb.7: # %BB_udiv-special-cases -; X86-NEXT: andl $3, %edi -; X86-NEXT: movl %ecx, %eax -; X86-NEXT: xorl $65, %eax -; X86-NEXT: movl %edi, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill -; X86-NEXT: orl %edi, %eax -; X86-NEXT: orl %ebx, %eax +; X86-NEXT: andl $3, %esi +; X86-NEXT: movl %eax, %ecx +; X86-NEXT: xorl $65, %ecx +; X86-NEXT: movl %esi, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill +; X86-NEXT: orl %esi, %ecx +; X86-NEXT: orl %ebx, %ecx ; X86-NEXT: je .LBB0_11 ; X86-NEXT: # %bb.8: # %udiv-bb1 -; X86-NEXT: movl %esi, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill -; X86-NEXT: movl %ecx, %eax +; X86-NEXT: movl %eax, %ecx ; X86-NEXT: addl $1, %ecx ; X86-NEXT: movl %ecx, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill ; X86-NEXT: adcl $0, %ebx -; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %esi # 4-byte Reload -; X86-NEXT: adcl $0, %esi -; X86-NEXT: andl $3, %esi -; X86-NEXT: movl %esi, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill +; X86-NEXT: movl %ebx, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill +; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %ebx # 4-byte Reload +; X86-NEXT: adcl $0, %ebx +; X86-NEXT: andl $3, %ebx ; X86-NEXT: movb $65, %cl ; X86-NEXT: subb %al, %cl ; X86-NEXT: movb %cl, %ch @@ -112,29 +111,31 @@ define void @f() nounwind { ; X86-NEXT: movl $0, {{[0-9]+}}(%esp) ; X86-NEXT: movl $0, {{[0-9]+}}(%esp) ; X86-NEXT: movl $0, {{[0-9]+}}(%esp) -; X86-NEXT: movl %edx, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill -; X86-NEXT: movl 136(%esp,%eax), %edx +; X86-NEXT: movl %edi, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill +; X86-NEXT: movl 120(%esp,%eax), %edi ; X86-NEXT: movb %ch, %cl -; X86-NEXT: shll %cl, %edx +; X86-NEXT: shll %cl, %edi ; X86-NEXT: notb %cl -; X86-NEXT: movl 128(%esp,%eax), %edi -; X86-NEXT: movl 132(%esp,%eax), %esi -; X86-NEXT: movl %esi, %eax +; X86-NEXT: movl 112(%esp,%eax), %esi +; X86-NEXT: movl %edx, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill +; X86-NEXT: movl 116(%esp,%eax), %edx +; X86-NEXT: movl %edx, %eax ; X86-NEXT: shrl %eax ; X86-NEXT: shrl %cl, %eax ; X86-NEXT: movb %ch, %cl -; X86-NEXT: shldl %cl, %edi, %esi +; X86-NEXT: shldl %cl, %esi, %edx +; X86-NEXT: movl %edx, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill +; X86-NEXT: shll %cl, %esi ; X86-NEXT: movl %esi, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill -; X86-NEXT: shll %cl, %edi -; X86-NEXT: movl %edi, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill ; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %ecx # 4-byte Reload -; X86-NEXT: orl {{[-0-9]+}}(%e{{[sb]}}p), %ecx # 4-byte Folded Reload +; X86-NEXT: movl %ebx, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill ; X86-NEXT: orl %ebx, %ecx +; X86-NEXT: orl {{[-0-9]+}}(%e{{[sb]}}p), %ecx # 4-byte Folded Reload ; X86-NEXT: je .LBB0_11 ; X86-NEXT: # %bb.9: # %udiv-preheader -; X86-NEXT: orl %eax, %edx -; X86-NEXT: andl $3, %edx -; X86-NEXT: movl %edx, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill +; X86-NEXT: orl %eax, %edi +; X86-NEXT: andl $3, %edi +; X86-NEXT: movl %edi, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill ; X86-NEXT: movl $0, {{[0-9]+}}(%esp) ; X86-NEXT: movl $0, {{[0-9]+}}(%esp) ; X86-NEXT: movl $0, {{[0-9]+}}(%esp) @@ -149,20 +150,20 @@ define void @f() nounwind { ; X86-NEXT: # kill: def $al killed $al killed $eax ; X86-NEXT: shrb $3, %al ; X86-NEXT: andb $15, %al -; X86-NEXT: movzbl %al, %esi -; X86-NEXT: movl 80(%esp,%esi), %edx -; X86-NEXT: movl 84(%esp,%esi), %eax -; X86-NEXT: movl %eax, %edi +; X86-NEXT: movzbl %al, %eax +; X86-NEXT: movl 64(%esp,%eax), %edi +; X86-NEXT: movl 68(%esp,%eax), %edx +; X86-NEXT: movl %edx, %esi ; X86-NEXT: movb %ch, %cl -; X86-NEXT: shrl %cl, %edi +; X86-NEXT: shrl %cl, %esi ; X86-NEXT: notb %cl -; X86-NEXT: movl 88(%esp,%esi), %esi -; X86-NEXT: addl %esi, %esi -; X86-NEXT: shll %cl, %esi -; X86-NEXT: orl %edi, %esi +; X86-NEXT: movl 72(%esp,%eax), %ebx +; X86-NEXT: addl %ebx, %ebx +; X86-NEXT: shll %cl, %ebx +; X86-NEXT: orl %esi, %ebx ; X86-NEXT: movb %ch, %cl -; X86-NEXT: shrdl %cl, %eax, %edx -; X86-NEXT: movl %edx, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill +; X86-NEXT: shrdl %cl, %edx, %edi +; X86-NEXT: movl %edi, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill ; X86-NEXT: movl $0, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Folded Spill ; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %eax # 4-byte Reload ; X86-NEXT: addl $-1, %eax @@ -179,63 +180,62 @@ define void @f() nounwind { ; X86-NEXT: .p2align 4, 0x90 ; X86-NEXT: .LBB0_10: # %udiv-do-while ; X86-NEXT: # =>This Inner Loop Header: Depth=1 -; X86-NEXT: movl %ebx, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill -; X86-NEXT: shldl $1, %esi, %ecx -; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %edx # 4-byte Reload -; X86-NEXT: shldl $1, %edx, %esi -; X86-NEXT: movl %esi, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill +; X86-NEXT: movl %ebx, %edi +; X86-NEXT: shldl $1, %ebx, %ecx ; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %ebx # 4-byte Reload -; X86-NEXT: movl %ebx, %eax -; X86-NEXT: andl $2, %eax -; X86-NEXT: shrl %eax -; X86-NEXT: leal (%eax,%edx,2), %edx -; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %edi # 4-byte Reload -; X86-NEXT: shldl $1, %edi, %ebx +; X86-NEXT: shldl $1, %ebx, %edi ; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %esi # 4-byte Reload -; X86-NEXT: orl %esi, %ebx +; X86-NEXT: movl %esi, %edx +; X86-NEXT: andl $2, %edx +; X86-NEXT: shrl %edx +; X86-NEXT: leal (%edx,%ebx,2), %ebx +; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %edx # 4-byte Reload +; X86-NEXT: shldl $1, %edx, %esi +; X86-NEXT: orl {{[-0-9]+}}(%e{{[sb]}}p), %esi # 4-byte Folded Reload ; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %eax # 4-byte Reload -; X86-NEXT: shldl $1, %eax, %edi -; X86-NEXT: orl %esi, %edi -; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %esi # 4-byte Reload -; X86-NEXT: movl %edi, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill +; X86-NEXT: shldl $1, %eax, %edx +; X86-NEXT: orl {{[-0-9]+}}(%e{{[sb]}}p), %edx # 4-byte Folded Reload +; X86-NEXT: movl %edx, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill ; X86-NEXT: addl %eax, %eax ; X86-NEXT: orl {{[-0-9]+}}(%e{{[sb]}}p), %eax # 4-byte Folded Reload ; X86-NEXT: movl %eax, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill -; X86-NEXT: andl $3, %ebx -; X86-NEXT: movl %ebx, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill -; X86-NEXT: cmpl %edx, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Folded Reload -; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %eax # 4-byte Reload -; X86-NEXT: sbbl %esi, %eax -; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %ebx # 4-byte Reload -; X86-NEXT: sbbl %ecx, %ebx -; X86-NEXT: shll $30, %ebx -; X86-NEXT: movl %ebx, %eax -; X86-NEXT: sarl $30, %eax -; X86-NEXT: sarl $31, %ebx -; X86-NEXT: shrdl $1, %ebx, %eax -; X86-NEXT: movl %eax, %edi -; X86-NEXT: andl $1, %edi -; X86-NEXT: movl %edi, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill +; X86-NEXT: andl $3, %esi +; X86-NEXT: movl %esi, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill +; X86-NEXT: cmpl %ebx, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Folded Reload +; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %edx # 4-byte Reload +; X86-NEXT: sbbl %edi, %edx +; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %esi # 4-byte Reload +; X86-NEXT: sbbl %ecx, %esi +; X86-NEXT: shll $30, %esi +; X86-NEXT: movl %esi, %edx +; X86-NEXT: sarl $30, %edx +; X86-NEXT: sarl $31, %esi +; X86-NEXT: shrdl $1, %esi, %edx +; X86-NEXT: movl %edx, %eax +; X86-NEXT: andl $1, %eax +; X86-NEXT: movl %eax, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill +; X86-NEXT: andl {{[-0-9]+}}(%e{{[sb]}}p), %edx # 4-byte Folded Reload +; X86-NEXT: movl %esi, %eax ; X86-NEXT: andl {{[-0-9]+}}(%e{{[sb]}}p), %eax # 4-byte Folded Reload -; X86-NEXT: movl %ebx, %edi -; X86-NEXT: andl {{[-0-9]+}}(%e{{[sb]}}p), %edi # 4-byte Folded Reload -; X86-NEXT: andl {{[-0-9]+}}(%e{{[sb]}}p), %ebx # 4-byte Folded Reload -; X86-NEXT: subl %eax, %edx -; X86-NEXT: movl %edx, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill -; X86-NEXT: sbbl %ebx, %esi -; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %ebx # 4-byte Reload -; X86-NEXT: sbbl %edi, %ecx +; X86-NEXT: andl {{[-0-9]+}}(%e{{[sb]}}p), %esi # 4-byte Folded Reload +; X86-NEXT: subl %edx, %ebx +; X86-NEXT: movl %ebx, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill +; X86-NEXT: sbbl %esi, %edi +; X86-NEXT: movl %edi, %ebx +; X86-NEXT: sbbl %eax, %ecx ; X86-NEXT: andl $3, %ecx ; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %eax # 4-byte Reload ; X86-NEXT: addl $-1, %eax -; X86-NEXT: adcl $-1, %ebx -; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %edi # 4-byte Reload -; X86-NEXT: adcl $3, %edi -; X86-NEXT: andl $3, %edi +; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %edx # 4-byte Reload +; X86-NEXT: adcl $-1, %edx +; X86-NEXT: movl {{[-0-9]+}}(%e{{[sb]}}p), %esi # 4-byte Reload +; X86-NEXT: adcl $3, %esi +; X86-NEXT: andl $3, %esi ; X86-NEXT: movl %eax, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill -; X86-NEXT: movl %edi, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill -; X86-NEXT: orl %edi, %eax -; X86-NEXT: orl %ebx, %eax +; X86-NEXT: movl %esi, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill +; X86-NEXT: orl %esi, %eax +; X86-NEXT: movl %edx, {{[-0-9]+}}(%e{{[sb]}}p) # 4-byte Spill +; X86-NEXT: orl %edx, %eax ; X86-NEXT: jne .LBB0_10 ; X86-NEXT: .LBB0_11: # %udiv-end ; X86-NEXT: cmpb $0, {{[-0-9]+}}(%e{{[sb]}}p) # 1-byte Folded Reload diff --git a/llvm/test/CodeGen/X86/pr62286.ll b/llvm/test/CodeGen/X86/pr62286.ll index 782c84408f25abcdcbecd815bb1311a9337c40b7..1b13cee628df676da621b51828ded31d5a3a105c 100644 --- a/llvm/test/CodeGen/X86/pr62286.ll +++ b/llvm/test/CodeGen/X86/pr62286.ll @@ -8,21 +8,20 @@ define i64 @PR62286(i32 %a) { ; SSE-LABEL: PR62286: ; SSE: # %bb.0: ; SSE-NEXT: movd %edi, %xmm0 -; SSE-NEXT: pshufd {{.*#+}} xmm1 = xmm0[0,1,1,0] -; SSE-NEXT: paddd %xmm1, %xmm1 +; SSE-NEXT: pshufd {{.*#+}} xmm1 = xmm0[1,0,1,0] +; SSE-NEXT: paddd %xmm0, %xmm0 ; SSE-NEXT: pxor %xmm2, %xmm2 -; SSE-NEXT: punpckldq {{.*#+}} xmm1 = xmm1[0],xmm2[0],xmm1[1],xmm2[1] -; SSE-NEXT: pxor %xmm3, %xmm3 -; SSE-NEXT: pcmpgtd %xmm1, %xmm3 -; SSE-NEXT: punpckldq {{.*#+}} xmm1 = xmm1[0],xmm3[0],xmm1[1],xmm3[1] -; SSE-NEXT: pshufd {{.*#+}} xmm0 = xmm0[1,0,1,0] -; SSE-NEXT: pand {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm0 -; SSE-NEXT: pcmpgtd %xmm0, %xmm2 ; SSE-NEXT: punpckldq {{.*#+}} xmm0 = xmm0[0],xmm2[0],xmm0[1],xmm2[1] -; SSE-NEXT: paddq %xmm1, %xmm0 -; SSE-NEXT: pshufd {{.*#+}} xmm1 = xmm0[2,3,2,3] +; SSE-NEXT: pxor %xmm3, %xmm3 +; SSE-NEXT: pcmpgtd %xmm0, %xmm3 +; SSE-NEXT: punpckldq {{.*#+}} xmm0 = xmm0[0],xmm3[0],xmm0[1],xmm3[1] +; SSE-NEXT: pand {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm1 +; SSE-NEXT: pcmpgtd %xmm1, %xmm2 +; SSE-NEXT: punpckldq {{.*#+}} xmm1 = xmm1[0],xmm2[0],xmm1[1],xmm2[1] ; SSE-NEXT: paddq %xmm0, %xmm1 -; SSE-NEXT: movq %xmm1, %rax +; SSE-NEXT: pshufd {{.*#+}} xmm0 = xmm1[2,3,2,3] +; SSE-NEXT: paddq %xmm1, %xmm0 +; SSE-NEXT: movq %xmm0, %rax ; SSE-NEXT: retq ; ; AVX1-LABEL: PR62286: @@ -47,10 +46,10 @@ define i64 @PR62286(i32 %a) { ; AVX2-LABEL: PR62286: ; AVX2: # %bb.0: ; AVX2-NEXT: vmovd %edi, %xmm0 -; AVX2-NEXT: vpslldq {{.*#+}} xmm1 = zero,zero,zero,zero,zero,zero,zero,zero,zero,zero,zero,zero,xmm0[0,1,2,3] -; AVX2-NEXT: vpaddd %xmm0, %xmm0, %xmm0 -; AVX2-NEXT: vpand {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm1, %xmm1 -; AVX2-NEXT: vpor %xmm0, %xmm1, %xmm0 +; AVX2-NEXT: vpaddd %xmm0, %xmm0, %xmm1 +; AVX2-NEXT: vpslldq {{.*#+}} xmm0 = zero,zero,zero,zero,zero,zero,zero,zero,zero,zero,zero,zero,xmm0[0,1,2,3] +; AVX2-NEXT: vpand {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm0, %xmm0 +; AVX2-NEXT: vpblendd {{.*#+}} xmm0 = xmm1[0],xmm0[1,2,3] ; AVX2-NEXT: vpmovsxdq %xmm0, %ymm0 ; AVX2-NEXT: vextracti128 $1, %ymm0, %xmm1 ; AVX2-NEXT: vpaddq %xmm1, %xmm0, %xmm0 diff --git a/llvm/test/CodeGen/X86/scheduler-backtracking.ll b/llvm/test/CodeGen/X86/scheduler-backtracking.ll index a9f3e8b22fb69eda76603bb340dd9008667ab666..785b97d8c24027cc56aee49ed2ef7deb2932c2ee 100644 --- a/llvm/test/CodeGen/X86/scheduler-backtracking.ll +++ b/llvm/test/CodeGen/X86/scheduler-backtracking.ll @@ -14,7 +14,6 @@ define i256 @test1(i256 %a) nounwind { ; ILP: # %bb.0: ; ILP-NEXT: movq %rdi, %rax ; ILP-NEXT: leal (%rsi,%rsi), %ecx -; ILP-NEXT: addb $3, %cl ; ILP-NEXT: movq $0, -{{[0-9]+}}(%rsp) ; ILP-NEXT: movq $0, -{{[0-9]+}}(%rsp) ; ILP-NEXT: movq $0, -{{[0-9]+}}(%rsp) @@ -23,6 +22,7 @@ define i256 @test1(i256 %a) nounwind { ; ILP-NEXT: movq $0, -{{[0-9]+}}(%rsp) ; ILP-NEXT: movq $0, -{{[0-9]+}}(%rsp) ; ILP-NEXT: movq $0, -{{[0-9]+}}(%rsp) +; ILP-NEXT: addb $3, %cl ; ILP-NEXT: movl %ecx, %edx ; ILP-NEXT: shrb $3, %dl ; ILP-NEXT: andb $7, %cl diff --git a/llvm/test/CodeGen/X86/sdiv_fix_sat.ll b/llvm/test/CodeGen/X86/sdiv_fix_sat.ll index 31297a06f809935a3d1d4ab4c80b4dda65a8c565..a1cabb433d879bc52dd1a8278ef363a2f6d10e6b 100644 --- a/llvm/test/CodeGen/X86/sdiv_fix_sat.ll +++ b/llvm/test/CodeGen/X86/sdiv_fix_sat.ll @@ -563,18 +563,20 @@ define <4 x i32> @vec(<4 x i32> %x, <4 x i32> %y) nounwind { ; X64-NEXT: subq $120, %rsp ; X64-NEXT: movdqa %xmm1, {{[-0-9]+}}(%r{{[sb]}}p) # 16-byte Spill ; X64-NEXT: movdqa %xmm0, {{[-0-9]+}}(%r{{[sb]}}p) # 16-byte Spill -; X64-NEXT: pshufd {{.*#+}} xmm3 = xmm0[2,1,3,3] -; X64-NEXT: psllq $32, %xmm3 +; X64-NEXT: pxor %xmm3, %xmm3 +; X64-NEXT: punpckhdq {{.*#+}} xmm3 = xmm3[2],xmm0[2],xmm3[3],xmm0[3] ; X64-NEXT: pshufd {{.*#+}} xmm2 = xmm3[1,3,2,3] ; X64-NEXT: psrad $31, %xmm2 ; X64-NEXT: psrlq $31, %xmm3 ; X64-NEXT: pshufd {{.*#+}} xmm0 = xmm3[0,2,2,3] ; X64-NEXT: punpckldq {{.*#+}} xmm0 = xmm0[0],xmm2[0],xmm0[1],xmm2[1] ; X64-NEXT: movdqa %xmm0, {{[-0-9]+}}(%r{{[sb]}}p) # 16-byte Spill -; X64-NEXT: movq %xmm0, %rbx -; X64-NEXT: movq %rbx, %r13 -; X64-NEXT: sarq $63, %r13 -; X64-NEXT: shldq $31, %rbx, %r13 +; X64-NEXT: movq %xmm0, %rbp +; X64-NEXT: movq %rbp, %r14 +; X64-NEXT: sarq $63, %r14 +; X64-NEXT: shldq $31, %rbp, %r14 +; X64-NEXT: movq %rbp, %r15 +; X64-NEXT: shlq $31, %r15 ; X64-NEXT: pshufd {{.*#+}} xmm1 = xmm1[2,3,2,3] ; X64-NEXT: pxor %xmm0, %xmm0 ; X64-NEXT: pcmpgtd %xmm1, %xmm0 @@ -582,113 +584,113 @@ define <4 x i32> @vec(<4 x i32> %x, <4 x i32> %y) nounwind { ; X64-NEXT: movdqa %xmm1, {{[-0-9]+}}(%r{{[sb]}}p) # 16-byte Spill ; X64-NEXT: movq %xmm1, %rdx ; X64-NEXT: movq %rdx, {{[-0-9]+}}(%r{{[sb]}}p) # 8-byte Spill -; X64-NEXT: movq %rdx, %r15 -; X64-NEXT: sarq $63, %r15 -; X64-NEXT: movq %rbx, %r12 -; X64-NEXT: shlq $31, %r12 -; X64-NEXT: movq %r12, %rdi -; X64-NEXT: movq %r13, %rsi -; X64-NEXT: movq %r15, %rcx +; X64-NEXT: movq %rdx, %rbx +; X64-NEXT: sarq $63, %rbx +; X64-NEXT: movq %r15, %rdi +; X64-NEXT: movq %r14, %rsi +; X64-NEXT: movq %rbx, %rcx ; X64-NEXT: callq __divti3@PLT -; X64-NEXT: movq %rax, %rbp +; X64-NEXT: movq %rax, %r13 ; X64-NEXT: movq %rax, {{[-0-9]+}}(%r{{[sb]}}p) # 8-byte Spill -; X64-NEXT: movq %rdx, %r14 +; X64-NEXT: movq %rdx, %r12 ; X64-NEXT: movq %rdx, {{[-0-9]+}}(%r{{[sb]}}p) # 8-byte Spill -; X64-NEXT: subq $1, %rbp -; X64-NEXT: sbbq $0, %r14 -; X64-NEXT: shrq $63, %rbx -; X64-NEXT: xorl %r15d, %ebx -; X64-NEXT: movq %r12, %rdi -; X64-NEXT: movq %r13, %rsi +; X64-NEXT: subq $1, %r13 +; X64-NEXT: sbbq $0, %r12 +; X64-NEXT: movq %r15, %rdi +; X64-NEXT: movq %r14, %rsi ; X64-NEXT: movq {{[-0-9]+}}(%r{{[sb]}}p), %rdx # 8-byte Reload -; X64-NEXT: movq %r15, %rcx +; X64-NEXT: movq %rbx, %rcx ; X64-NEXT: callq __modti3@PLT ; X64-NEXT: orq %rax, %rdx ; X64-NEXT: setne %al +; X64-NEXT: shrq $63, %rbp +; X64-NEXT: xorl %ebp, %ebx ; X64-NEXT: testb %bl, %al -; X64-NEXT: cmoveq {{[-0-9]+}}(%r{{[sb]}}p), %r14 # 8-byte Folded Reload -; X64-NEXT: cmoveq {{[-0-9]+}}(%r{{[sb]}}p), %rbp # 8-byte Folded Reload +; X64-NEXT: cmoveq {{[-0-9]+}}(%r{{[sb]}}p), %r13 # 8-byte Folded Reload +; X64-NEXT: cmoveq {{[-0-9]+}}(%r{{[sb]}}p), %r12 # 8-byte Folded Reload ; X64-NEXT: xorl %ecx, %ecx ; X64-NEXT: movl $4294967295, %edx # imm = 0xFFFFFFFF -; X64-NEXT: cmpq %rdx, %rbp -; X64-NEXT: movq %r14, %rax +; X64-NEXT: cmpq %rdx, %r13 +; X64-NEXT: movq %r12, %rax ; X64-NEXT: sbbq $0, %rax -; X64-NEXT: cmovgeq %rcx, %r14 -; X64-NEXT: cmovgeq %rdx, %rbp +; X64-NEXT: cmovgeq %rdx, %r13 +; X64-NEXT: cmovgeq %rcx, %r12 ; X64-NEXT: movabsq $-4294967296, %rcx # imm = 0xFFFFFFFF00000000 -; X64-NEXT: cmpq %rbp, %rcx +; X64-NEXT: cmpq %r13, %rcx ; X64-NEXT: movq $-1, {{[-0-9]+}}(%r{{[sb]}}p) # 8-byte Folded Spill ; X64-NEXT: movq $-1, %rax -; X64-NEXT: sbbq %r14, %rax -; X64-NEXT: cmovgeq %rcx, %rbp -; X64-NEXT: movq %rbp, %xmm0 +; X64-NEXT: sbbq %r12, %rax +; X64-NEXT: cmovgeq %rcx, %r13 +; X64-NEXT: movq %r13, %xmm0 ; X64-NEXT: movdqa %xmm0, {{[-0-9]+}}(%r{{[sb]}}p) # 16-byte Spill ; X64-NEXT: pshufd $238, {{[-0-9]+}}(%r{{[sb]}}p), %xmm0 # 16-byte Folded Reload ; X64-NEXT: # xmm0 = mem[2,3,2,3] -; X64-NEXT: movq %xmm0, %rbx -; X64-NEXT: movq %rbx, %r13 -; X64-NEXT: sarq $63, %r13 -; X64-NEXT: shldq $31, %rbx, %r13 +; X64-NEXT: movq %xmm0, %rbp +; X64-NEXT: movq %rbp, %r14 +; X64-NEXT: sarq $63, %r14 +; X64-NEXT: shldq $31, %rbp, %r14 +; X64-NEXT: movq %rbp, %r15 +; X64-NEXT: shlq $31, %r15 ; X64-NEXT: pshufd $238, {{[-0-9]+}}(%r{{[sb]}}p), %xmm0 # 16-byte Folded Reload ; X64-NEXT: # xmm0 = mem[2,3,2,3] ; X64-NEXT: movq %xmm0, %rdx ; X64-NEXT: movq %rdx, {{[-0-9]+}}(%r{{[sb]}}p) # 8-byte Spill -; X64-NEXT: movq %rdx, %r15 -; X64-NEXT: sarq $63, %r15 -; X64-NEXT: movq %rbx, %r12 -; X64-NEXT: shlq $31, %r12 -; X64-NEXT: movq %r12, %rdi -; X64-NEXT: movq %r13, %rsi -; X64-NEXT: movq %r15, %rcx +; X64-NEXT: movq %rdx, %rbx +; X64-NEXT: sarq $63, %rbx +; X64-NEXT: movq %r15, %rdi +; X64-NEXT: movq %r14, %rsi +; X64-NEXT: movq %rbx, %rcx ; X64-NEXT: callq __divti3@PLT -; X64-NEXT: movq %rax, %rbp +; X64-NEXT: movq %rax, %r13 ; X64-NEXT: movq %rax, {{[-0-9]+}}(%r{{[sb]}}p) # 8-byte Spill -; X64-NEXT: movq %rdx, %r14 +; X64-NEXT: movq %rdx, %r12 ; X64-NEXT: movq %rdx, {{[-0-9]+}}(%r{{[sb]}}p) # 8-byte Spill -; X64-NEXT: subq $1, %rbp -; X64-NEXT: sbbq $0, %r14 -; X64-NEXT: shrq $63, %rbx -; X64-NEXT: xorl %r15d, %ebx -; X64-NEXT: movq %r12, %rdi -; X64-NEXT: movq %r13, %rsi +; X64-NEXT: subq $1, %r13 +; X64-NEXT: sbbq $0, %r12 +; X64-NEXT: movq %r15, %rdi +; X64-NEXT: movq %r14, %rsi ; X64-NEXT: movq {{[-0-9]+}}(%r{{[sb]}}p), %rdx # 8-byte Reload -; X64-NEXT: movq %r15, %rcx +; X64-NEXT: movq %rbx, %rcx ; X64-NEXT: callq __modti3@PLT ; X64-NEXT: orq %rax, %rdx ; X64-NEXT: setne %al +; X64-NEXT: shrq $63, %rbp +; X64-NEXT: xorl %ebp, %ebx ; X64-NEXT: testb %bl, %al -; X64-NEXT: cmoveq {{[-0-9]+}}(%r{{[sb]}}p), %r14 # 8-byte Folded Reload -; X64-NEXT: cmoveq {{[-0-9]+}}(%r{{[sb]}}p), %rbp # 8-byte Folded Reload +; X64-NEXT: cmoveq {{[-0-9]+}}(%r{{[sb]}}p), %r13 # 8-byte Folded Reload +; X64-NEXT: cmoveq {{[-0-9]+}}(%r{{[sb]}}p), %r12 # 8-byte Folded Reload ; X64-NEXT: movl $4294967295, %ecx # imm = 0xFFFFFFFF -; X64-NEXT: cmpq %rcx, %rbp -; X64-NEXT: movq %r14, %rax +; X64-NEXT: cmpq %rcx, %r13 +; X64-NEXT: movq %r12, %rax ; X64-NEXT: sbbq $0, %rax +; X64-NEXT: cmovgeq %rcx, %r13 ; X64-NEXT: movl $0, %eax -; X64-NEXT: cmovgeq %rax, %r14 -; X64-NEXT: cmovgeq %rcx, %rbp +; X64-NEXT: cmovgeq %rax, %r12 ; X64-NEXT: movabsq $-4294967296, %rcx # imm = 0xFFFFFFFF00000000 -; X64-NEXT: cmpq %rbp, %rcx +; X64-NEXT: cmpq %r13, %rcx ; X64-NEXT: movq $-1, %rax -; X64-NEXT: sbbq %r14, %rax -; X64-NEXT: cmovgeq %rcx, %rbp -; X64-NEXT: movq %rbp, %xmm0 +; X64-NEXT: sbbq %r12, %rax +; X64-NEXT: cmovgeq %rcx, %r13 +; X64-NEXT: movq %r13, %xmm0 ; X64-NEXT: movdqa {{[-0-9]+}}(%r{{[sb]}}p), %xmm1 # 16-byte Reload ; X64-NEXT: punpcklqdq {{.*#+}} xmm1 = xmm1[0],xmm0[0] ; X64-NEXT: psrlq $1, %xmm1 ; X64-NEXT: movdqa %xmm1, {{[-0-9]+}}(%r{{[sb]}}p) # 16-byte Spill -; X64-NEXT: pshufd $212, {{[-0-9]+}}(%r{{[sb]}}p), %xmm0 # 16-byte Folded Reload -; X64-NEXT: # xmm0 = mem[0,1,1,3] -; X64-NEXT: psllq $32, %xmm0 +; X64-NEXT: pxor %xmm0, %xmm0 +; X64-NEXT: punpckldq {{[-0-9]+}}(%r{{[sb]}}p), %xmm0 # 16-byte Folded Reload +; X64-NEXT: # xmm0 = xmm0[0],mem[0],xmm0[1],mem[1] ; X64-NEXT: pshufd {{.*#+}} xmm1 = xmm0[1,3,2,3] ; X64-NEXT: psrad $31, %xmm1 ; X64-NEXT: psrlq $31, %xmm0 ; X64-NEXT: pshufd {{.*#+}} xmm0 = xmm0[0,2,2,3] ; X64-NEXT: punpckldq {{.*#+}} xmm0 = xmm0[0],xmm1[0],xmm0[1],xmm1[1] ; X64-NEXT: movdqa %xmm0, {{[-0-9]+}}(%r{{[sb]}}p) # 16-byte Spill -; X64-NEXT: movq %xmm0, %rbx -; X64-NEXT: movq %rbx, %r13 -; X64-NEXT: sarq $63, %r13 -; X64-NEXT: shldq $31, %rbx, %r13 +; X64-NEXT: movq %xmm0, %rbp +; X64-NEXT: movq %rbp, %r14 +; X64-NEXT: sarq $63, %r14 +; X64-NEXT: shldq $31, %rbp, %r14 +; X64-NEXT: movq %rbp, %r15 +; X64-NEXT: shlq $31, %r15 ; X64-NEXT: movdqa {{[-0-9]+}}(%r{{[sb]}}p), %xmm0 # 16-byte Reload ; X64-NEXT: pxor %xmm1, %xmm1 ; X64-NEXT: pcmpgtd %xmm0, %xmm1 @@ -696,94 +698,92 @@ define <4 x i32> @vec(<4 x i32> %x, <4 x i32> %y) nounwind { ; X64-NEXT: movdqa %xmm0, {{[-0-9]+}}(%r{{[sb]}}p) # 16-byte Spill ; X64-NEXT: movq %xmm0, %rdx ; X64-NEXT: movq %rdx, {{[-0-9]+}}(%r{{[sb]}}p) # 8-byte Spill -; X64-NEXT: movq %rdx, %r15 -; X64-NEXT: sarq $63, %r15 -; X64-NEXT: movq %rbx, %r12 -; X64-NEXT: shlq $31, %r12 -; X64-NEXT: movq %r12, %rdi -; X64-NEXT: movq %r13, %rsi -; X64-NEXT: movq %r15, %rcx +; X64-NEXT: movq %rdx, %rbx +; X64-NEXT: sarq $63, %rbx +; X64-NEXT: movq %r15, %rdi +; X64-NEXT: movq %r14, %rsi +; X64-NEXT: movq %rbx, %rcx ; X64-NEXT: callq __divti3@PLT -; X64-NEXT: movq %rax, %rbp +; X64-NEXT: movq %rax, %r13 ; X64-NEXT: movq %rax, {{[-0-9]+}}(%r{{[sb]}}p) # 8-byte Spill -; X64-NEXT: movq %rdx, %r14 +; X64-NEXT: movq %rdx, %r12 ; X64-NEXT: movq %rdx, {{[-0-9]+}}(%r{{[sb]}}p) # 8-byte Spill -; X64-NEXT: subq $1, %rbp -; X64-NEXT: sbbq $0, %r14 -; X64-NEXT: shrq $63, %rbx -; X64-NEXT: xorl %r15d, %ebx -; X64-NEXT: movq %r12, %rdi -; X64-NEXT: movq %r13, %rsi +; X64-NEXT: subq $1, %r13 +; X64-NEXT: sbbq $0, %r12 +; X64-NEXT: movq %r15, %rdi +; X64-NEXT: movq %r14, %rsi ; X64-NEXT: movq {{[-0-9]+}}(%r{{[sb]}}p), %rdx # 8-byte Reload -; X64-NEXT: movq %r15, %rcx +; X64-NEXT: movq %rbx, %rcx ; X64-NEXT: callq __modti3@PLT ; X64-NEXT: orq %rax, %rdx ; X64-NEXT: setne %al +; X64-NEXT: shrq $63, %rbp +; X64-NEXT: xorl %ebp, %ebx ; X64-NEXT: testb %bl, %al -; X64-NEXT: cmoveq {{[-0-9]+}}(%r{{[sb]}}p), %r14 # 8-byte Folded Reload -; X64-NEXT: cmoveq {{[-0-9]+}}(%r{{[sb]}}p), %rbp # 8-byte Folded Reload +; X64-NEXT: cmoveq {{[-0-9]+}}(%r{{[sb]}}p), %r13 # 8-byte Folded Reload +; X64-NEXT: cmoveq {{[-0-9]+}}(%r{{[sb]}}p), %r12 # 8-byte Folded Reload ; X64-NEXT: movl $4294967295, %ecx # imm = 0xFFFFFFFF -; X64-NEXT: cmpq %rcx, %rbp -; X64-NEXT: movq %r14, %rax +; X64-NEXT: cmpq %rcx, %r13 +; X64-NEXT: movq %r12, %rax ; X64-NEXT: sbbq $0, %rax +; X64-NEXT: cmovgeq %rcx, %r13 ; X64-NEXT: movl $0, %eax -; X64-NEXT: cmovgeq %rax, %r14 -; X64-NEXT: cmovgeq %rcx, %rbp +; X64-NEXT: cmovgeq %rax, %r12 ; X64-NEXT: movabsq $-4294967296, %rcx # imm = 0xFFFFFFFF00000000 -; X64-NEXT: cmpq %rbp, %rcx +; X64-NEXT: cmpq %r13, %rcx ; X64-NEXT: movq $-1, %rax -; X64-NEXT: sbbq %r14, %rax -; X64-NEXT: cmovgeq %rcx, %rbp -; X64-NEXT: movq %rbp, %xmm0 +; X64-NEXT: sbbq %r12, %rax +; X64-NEXT: cmovgeq %rcx, %r13 +; X64-NEXT: movq %r13, %xmm0 ; X64-NEXT: movdqa %xmm0, {{[-0-9]+}}(%r{{[sb]}}p) # 16-byte Spill ; X64-NEXT: pshufd $238, {{[-0-9]+}}(%r{{[sb]}}p), %xmm0 # 16-byte Folded Reload ; X64-NEXT: # xmm0 = mem[2,3,2,3] -; X64-NEXT: movq %xmm0, %rbx -; X64-NEXT: movq %rbx, %r13 -; X64-NEXT: sarq $63, %r13 -; X64-NEXT: shldq $31, %rbx, %r13 +; X64-NEXT: movq %xmm0, %rbp +; X64-NEXT: movq %rbp, %r14 +; X64-NEXT: sarq $63, %r14 +; X64-NEXT: shldq $31, %rbp, %r14 +; X64-NEXT: movq %rbp, %r15 +; X64-NEXT: shlq $31, %r15 ; X64-NEXT: pshufd $238, {{[-0-9]+}}(%r{{[sb]}}p), %xmm0 # 16-byte Folded Reload ; X64-NEXT: # xmm0 = mem[2,3,2,3] ; X64-NEXT: movq %xmm0, %rdx ; X64-NEXT: movq %rdx, {{[-0-9]+}}(%r{{[sb]}}p) # 8-byte Spill -; X64-NEXT: movq %rdx, %r15 -; X64-NEXT: sarq $63, %r15 -; X64-NEXT: movq %rbx, %r12 -; X64-NEXT: shlq $31, %r12 -; X64-NEXT: movq %r12, %rdi -; X64-NEXT: movq %r13, %rsi -; X64-NEXT: movq %r15, %rcx +; X64-NEXT: movq %rdx, %rbx +; X64-NEXT: sarq $63, %rbx +; X64-NEXT: movq %r15, %rdi +; X64-NEXT: movq %r14, %rsi +; X64-NEXT: movq %rbx, %rcx ; X64-NEXT: callq __divti3@PLT -; X64-NEXT: movq %rax, %rbp +; X64-NEXT: movq %rax, %r13 ; X64-NEXT: movq %rax, {{[-0-9]+}}(%r{{[sb]}}p) # 8-byte Spill -; X64-NEXT: movq %rdx, %r14 +; X64-NEXT: movq %rdx, %r12 ; X64-NEXT: movq %rdx, {{[-0-9]+}}(%r{{[sb]}}p) # 8-byte Spill -; X64-NEXT: subq $1, %rbp -; X64-NEXT: sbbq $0, %r14 -; X64-NEXT: shrq $63, %rbx -; X64-NEXT: xorl %r15d, %ebx -; X64-NEXT: movq %r12, %rdi -; X64-NEXT: movq %r13, %rsi +; X64-NEXT: subq $1, %r13 +; X64-NEXT: sbbq $0, %r12 +; X64-NEXT: movq %r15, %rdi +; X64-NEXT: movq %r14, %rsi ; X64-NEXT: movq {{[-0-9]+}}(%r{{[sb]}}p), %rdx # 8-byte Reload -; X64-NEXT: movq %r15, %rcx +; X64-NEXT: movq %rbx, %rcx ; X64-NEXT: callq __modti3@PLT ; X64-NEXT: orq %rax, %rdx ; X64-NEXT: setne %al +; X64-NEXT: shrq $63, %rbp +; X64-NEXT: xorl %ebp, %ebx ; X64-NEXT: testb %bl, %al -; X64-NEXT: cmoveq {{[-0-9]+}}(%r{{[sb]}}p), %r14 # 8-byte Folded Reload -; X64-NEXT: cmoveq {{[-0-9]+}}(%r{{[sb]}}p), %rbp # 8-byte Folded Reload +; X64-NEXT: cmoveq {{[-0-9]+}}(%r{{[sb]}}p), %r13 # 8-byte Folded Reload +; X64-NEXT: cmoveq {{[-0-9]+}}(%r{{[sb]}}p), %r12 # 8-byte Folded Reload ; X64-NEXT: movl $4294967295, %ecx # imm = 0xFFFFFFFF -; X64-NEXT: cmpq %rcx, %rbp -; X64-NEXT: movq %r14, %rax +; X64-NEXT: cmpq %rcx, %r13 +; X64-NEXT: movq %r12, %rax ; X64-NEXT: sbbq $0, %rax +; X64-NEXT: cmovgeq %rcx, %r13 ; X64-NEXT: movl $0, %eax -; X64-NEXT: cmovgeq %rax, %r14 -; X64-NEXT: cmovgeq %rcx, %rbp +; X64-NEXT: cmovgeq %rax, %r12 ; X64-NEXT: movabsq $-4294967296, %rax # imm = 0xFFFFFFFF00000000 -; X64-NEXT: cmpq %rbp, %rax -; X64-NEXT: sbbq %r14, {{[-0-9]+}}(%r{{[sb]}}p) # 8-byte Folded Spill -; X64-NEXT: cmovgeq %rax, %rbp -; X64-NEXT: movq %rbp, %xmm1 +; X64-NEXT: cmpq %r13, %rax +; X64-NEXT: sbbq %r12, {{[-0-9]+}}(%r{{[sb]}}p) # 8-byte Folded Spill +; X64-NEXT: cmovgeq %rax, %r13 +; X64-NEXT: movq %r13, %xmm1 ; X64-NEXT: movdqa {{[-0-9]+}}(%r{{[sb]}}p), %xmm0 # 16-byte Reload ; X64-NEXT: punpcklqdq {{.*#+}} xmm0 = xmm0[0],xmm1[0] ; X64-NEXT: psrlq $1, %xmm0 diff --git a/llvm/test/CodeGen/X86/setcc-non-simple-type.ll b/llvm/test/CodeGen/X86/setcc-non-simple-type.ll index 97c3c2040b2914cfe75e3827d6a0dc33882a4968..a80d8d8cd01b8536189396f46b3cccdda48f3804 100644 --- a/llvm/test/CodeGen/X86/setcc-non-simple-type.ll +++ b/llvm/test/CodeGen/X86/setcc-non-simple-type.ll @@ -46,7 +46,6 @@ define void @failing(ptr %0, ptr %1) nounwind { ; CHECK-NEXT: movq 24(%rsi), %rcx ; CHECK-NEXT: movq 32(%rsi), %rdx ; CHECK-NEXT: movdqa {{.*#+}} xmm0 = [0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0] -; CHECK-NEXT: xorl %esi, %esi ; CHECK-NEXT: movdqa {{.*#+}} xmm1 = [1,1] ; CHECK-NEXT: movdqa {{.*#+}} xmm2 = [2,2] ; CHECK-NEXT: .p2align 4, 0x90 @@ -54,39 +53,45 @@ define void @failing(ptr %0, ptr %1) nounwind { ; CHECK-NEXT: # =>This Loop Header: Depth=1 ; CHECK-NEXT: # Child Loop BB0_2 Depth 2 ; CHECK-NEXT: xorpd %xmm3, %xmm3 -; CHECK-NEXT: movq $-1024, %rdi # imm = 0xFC00 +; CHECK-NEXT: movq $-1024, %rsi # imm = 0xFC00 ; CHECK-NEXT: movdqa %xmm0, %xmm4 ; CHECK-NEXT: .p2align 4, 0x90 ; CHECK-NEXT: .LBB0_2: # %vector.body ; CHECK-NEXT: # Parent Loop BB0_1 Depth=1 ; CHECK-NEXT: # => This Inner Loop Header: Depth=2 -; CHECK-NEXT: cmpq 1024(%rdx,%rdi), %rsi -; CHECK-NEXT: movq %rcx, %r8 -; CHECK-NEXT: sbbq 1032(%rdx,%rdi), %r8 -; CHECK-NEXT: setge %r8b -; CHECK-NEXT: movzbl %r8b, %r8d -; CHECK-NEXT: andl $1, %r8d +; CHECK-NEXT: movdqu 1024(%rdx,%rsi), %xmm5 +; CHECK-NEXT: movdqu 1040(%rdx,%rsi), %xmm6 +; CHECK-NEXT: movq %xmm5, %rdi +; CHECK-NEXT: movq %xmm6, %r8 +; CHECK-NEXT: pshufd {{.*#+}} xmm5 = xmm5[2,3,2,3] +; CHECK-NEXT: movq %xmm5, %r9 +; CHECK-NEXT: pshufd {{.*#+}} xmm5 = xmm6[2,3,2,3] +; CHECK-NEXT: movq %xmm5, %r10 ; CHECK-NEXT: negq %r8 -; CHECK-NEXT: movq %r8, %xmm5 -; CHECK-NEXT: cmpq 1040(%rdx,%rdi), %rsi ; CHECK-NEXT: movq %rcx, %r8 -; CHECK-NEXT: sbbq 1048(%rdx,%rdi), %r8 +; CHECK-NEXT: sbbq %r10, %r8 ; CHECK-NEXT: setge %r8b ; CHECK-NEXT: movzbl %r8b, %r8d -; CHECK-NEXT: andl $1, %r8d ; CHECK-NEXT: negq %r8 -; CHECK-NEXT: movq %r8, %xmm6 -; CHECK-NEXT: punpcklqdq {{.*#+}} xmm5 = xmm5[0],xmm6[0] -; CHECK-NEXT: movdqa %xmm1, %xmm6 -; CHECK-NEXT: psllq %xmm4, %xmm6 +; CHECK-NEXT: movq %r8, %xmm5 +; CHECK-NEXT: negq %rdi +; CHECK-NEXT: movq %rcx, %rdi +; CHECK-NEXT: sbbq %r9, %rdi +; CHECK-NEXT: setge %dil +; CHECK-NEXT: movzbl %dil, %edi +; CHECK-NEXT: negq %rdi +; CHECK-NEXT: movq %rdi, %xmm6 +; CHECK-NEXT: punpcklqdq {{.*#+}} xmm6 = xmm6[0],xmm5[0] +; CHECK-NEXT: movdqa %xmm1, %xmm5 +; CHECK-NEXT: psllq %xmm4, %xmm5 ; CHECK-NEXT: pshufd {{.*#+}} xmm7 = xmm4[2,3,2,3] ; CHECK-NEXT: movdqa %xmm1, %xmm8 ; CHECK-NEXT: psllq %xmm7, %xmm8 -; CHECK-NEXT: movsd {{.*#+}} xmm8 = xmm6[0],xmm8[1] -; CHECK-NEXT: andpd %xmm5, %xmm8 +; CHECK-NEXT: movsd {{.*#+}} xmm8 = xmm5[0],xmm8[1] +; CHECK-NEXT: andpd %xmm6, %xmm8 ; CHECK-NEXT: orpd %xmm8, %xmm3 ; CHECK-NEXT: paddq %xmm2, %xmm4 -; CHECK-NEXT: addq $32, %rdi +; CHECK-NEXT: addq $32, %rsi ; CHECK-NEXT: jne .LBB0_2 ; CHECK-NEXT: # %bb.3: # %middle.block ; CHECK-NEXT: # in Loop: Header=BB0_1 Depth=1 @@ -101,7 +106,6 @@ define void @failing(ptr %0, ptr %1) nounwind { ; CHECK-AVX2-NEXT: movq 24(%rsi), %rcx ; CHECK-AVX2-NEXT: movq 32(%rsi), %rdx ; CHECK-AVX2-NEXT: vpmovsxbq {{.*#+}} xmm0 = [0,1] -; CHECK-AVX2-NEXT: xorl %esi, %esi ; CHECK-AVX2-NEXT: vpmovsxbq {{.*#+}} xmm1 = [1,1] ; CHECK-AVX2-NEXT: vpmovsxbq {{.*#+}} xmm2 = [2,2] ; CHECK-AVX2-NEXT: .p2align 4, 0x90 @@ -109,34 +113,40 @@ define void @failing(ptr %0, ptr %1) nounwind { ; CHECK-AVX2-NEXT: # =>This Loop Header: Depth=1 ; CHECK-AVX2-NEXT: # Child Loop BB0_2 Depth 2 ; CHECK-AVX2-NEXT: vpxor %xmm3, %xmm3, %xmm3 -; CHECK-AVX2-NEXT: movq $-1024, %rdi # imm = 0xFC00 +; CHECK-AVX2-NEXT: movq $-1024, %rsi # imm = 0xFC00 ; CHECK-AVX2-NEXT: vmovdqa %xmm0, %xmm4 ; CHECK-AVX2-NEXT: .p2align 4, 0x90 ; CHECK-AVX2-NEXT: .LBB0_2: # %vector.body ; CHECK-AVX2-NEXT: # Parent Loop BB0_1 Depth=1 ; CHECK-AVX2-NEXT: # => This Inner Loop Header: Depth=2 -; CHECK-AVX2-NEXT: cmpq 1024(%rdx,%rdi), %rsi -; CHECK-AVX2-NEXT: movq %rcx, %r8 -; CHECK-AVX2-NEXT: sbbq 1032(%rdx,%rdi), %r8 +; CHECK-AVX2-NEXT: vmovdqu 1024(%rdx,%rsi), %xmm5 +; CHECK-AVX2-NEXT: vmovdqu 1040(%rdx,%rsi), %xmm6 +; CHECK-AVX2-NEXT: vpunpcklqdq {{.*#+}} xmm7 = xmm5[0],xmm6[0] +; CHECK-AVX2-NEXT: vpunpckhqdq {{.*#+}} xmm5 = xmm5[1],xmm6[1] +; CHECK-AVX2-NEXT: vmovq %xmm5, %rdi +; CHECK-AVX2-NEXT: vpextrq $1, %xmm5, %r8 +; CHECK-AVX2-NEXT: vmovq %xmm7, %r9 +; CHECK-AVX2-NEXT: vpextrq $1, %xmm7, %r10 +; CHECK-AVX2-NEXT: negq %r10 +; CHECK-AVX2-NEXT: movq %rcx, %r10 +; CHECK-AVX2-NEXT: sbbq %r8, %r10 ; CHECK-AVX2-NEXT: setge %r8b ; CHECK-AVX2-NEXT: movzbl %r8b, %r8d -; CHECK-AVX2-NEXT: andl $1, %r8d ; CHECK-AVX2-NEXT: negq %r8 ; CHECK-AVX2-NEXT: vmovq %r8, %xmm5 -; CHECK-AVX2-NEXT: cmpq 1040(%rdx,%rdi), %rsi +; CHECK-AVX2-NEXT: negq %r9 ; CHECK-AVX2-NEXT: movq %rcx, %r8 -; CHECK-AVX2-NEXT: sbbq 1048(%rdx,%rdi), %r8 -; CHECK-AVX2-NEXT: setge %r8b -; CHECK-AVX2-NEXT: movzbl %r8b, %r8d -; CHECK-AVX2-NEXT: andl $1, %r8d -; CHECK-AVX2-NEXT: negq %r8 -; CHECK-AVX2-NEXT: vmovq %r8, %xmm6 -; CHECK-AVX2-NEXT: vpunpcklqdq {{.*#+}} xmm5 = xmm5[0],xmm6[0] +; CHECK-AVX2-NEXT: sbbq %rdi, %r8 +; CHECK-AVX2-NEXT: setge %dil +; CHECK-AVX2-NEXT: movzbl %dil, %edi +; CHECK-AVX2-NEXT: negq %rdi +; CHECK-AVX2-NEXT: vmovq %rdi, %xmm6 +; CHECK-AVX2-NEXT: vpunpcklqdq {{.*#+}} xmm5 = xmm6[0],xmm5[0] ; CHECK-AVX2-NEXT: vpsllvq %xmm4, %xmm1, %xmm6 ; CHECK-AVX2-NEXT: vpand %xmm6, %xmm5, %xmm5 ; CHECK-AVX2-NEXT: vpor %xmm3, %xmm5, %xmm3 ; CHECK-AVX2-NEXT: vpaddq %xmm2, %xmm4, %xmm4 -; CHECK-AVX2-NEXT: addq $32, %rdi +; CHECK-AVX2-NEXT: addq $32, %rsi ; CHECK-AVX2-NEXT: jne .LBB0_2 ; CHECK-AVX2-NEXT: # %bb.3: # %middle.block ; CHECK-AVX2-NEXT: # in Loop: Header=BB0_1 Depth=1 diff --git a/llvm/test/CodeGen/X86/subvectorwise-store-of-vector-splat.ll b/llvm/test/CodeGen/X86/subvectorwise-store-of-vector-splat.ll index e0f438eb7cc8f7169c8ea9dcf099f1c137d46298..ae66c5420638bcb1dd80feef5906c7ed0a439232 100644 --- a/llvm/test/CodeGen/X86/subvectorwise-store-of-vector-splat.ll +++ b/llvm/test/CodeGen/X86/subvectorwise-store-of-vector-splat.ll @@ -3060,12 +3060,7 @@ define void @vec384_v3i32(ptr %in.subvec.ptr, ptr %out.subvec.ptr, ptr %out.vec. ; SCALAR: # %bb.0: ; SCALAR-NEXT: movl 8(%rdi), %eax ; SCALAR-NEXT: movq (%rdi), %rcx -; SCALAR-NEXT: movq %rcx, %rdi -; SCALAR-NEXT: shrq $32, %rdi -; SCALAR-NEXT: notl %edi -; SCALAR-NEXT: shlq $32, %rdi -; SCALAR-NEXT: notl %ecx -; SCALAR-NEXT: orq %rdi, %rcx +; SCALAR-NEXT: notq %rcx ; SCALAR-NEXT: notl %eax ; SCALAR-NEXT: movl %eax, 8(%rsi) ; SCALAR-NEXT: movq %rcx, (%rsi) @@ -3196,12 +3191,7 @@ define void @vec384_v3f32(ptr %in.subvec.ptr, ptr %out.subvec.ptr, ptr %out.vec. ; SCALAR: # %bb.0: ; SCALAR-NEXT: movl 8(%rdi), %eax ; SCALAR-NEXT: movq (%rdi), %rcx -; SCALAR-NEXT: movq %rcx, %rdi -; SCALAR-NEXT: shrq $32, %rdi -; SCALAR-NEXT: notl %edi -; SCALAR-NEXT: shlq $32, %rdi -; SCALAR-NEXT: notl %ecx -; SCALAR-NEXT: orq %rdi, %rcx +; SCALAR-NEXT: notq %rcx ; SCALAR-NEXT: notl %eax ; SCALAR-NEXT: movl %eax, 8(%rsi) ; SCALAR-NEXT: movq %rcx, (%rsi) @@ -4216,25 +4206,10 @@ define void @vec384_v6i32(ptr %in.subvec.ptr, ptr %out.subvec.ptr, ptr %out.vec. ; SCALAR: # %bb.0: ; SCALAR-NEXT: movq (%rdi), %rax ; SCALAR-NEXT: movq 8(%rdi), %rcx -; SCALAR-NEXT: movq %rax, %r8 -; SCALAR-NEXT: shrq $32, %r8 -; SCALAR-NEXT: movq %rcx, %r9 -; SCALAR-NEXT: shrq $32, %r9 ; SCALAR-NEXT: movq 16(%rdi), %rdi -; SCALAR-NEXT: movq %rdi, %r10 -; SCALAR-NEXT: shrq $32, %r10 -; SCALAR-NEXT: notl %r10d -; SCALAR-NEXT: shlq $32, %r10 -; SCALAR-NEXT: notl %edi -; SCALAR-NEXT: orq %r10, %rdi -; SCALAR-NEXT: notl %r9d -; SCALAR-NEXT: shlq $32, %r9 -; SCALAR-NEXT: notl %ecx -; SCALAR-NEXT: orq %r9, %rcx -; SCALAR-NEXT: notl %r8d -; SCALAR-NEXT: shlq $32, %r8 -; SCALAR-NEXT: notl %eax -; SCALAR-NEXT: orq %r8, %rax +; SCALAR-NEXT: notq %rdi +; SCALAR-NEXT: notq %rcx +; SCALAR-NEXT: notq %rax ; SCALAR-NEXT: movq %rax, (%rsi) ; SCALAR-NEXT: movq %rcx, 8(%rsi) ; SCALAR-NEXT: movq %rdi, 16(%rsi) @@ -4303,25 +4278,10 @@ define void @vec384_v6f32(ptr %in.subvec.ptr, ptr %out.subvec.ptr, ptr %out.vec. ; SCALAR: # %bb.0: ; SCALAR-NEXT: movq (%rdi), %rax ; SCALAR-NEXT: movq 8(%rdi), %rcx -; SCALAR-NEXT: movq %rax, %r8 -; SCALAR-NEXT: shrq $32, %r8 -; SCALAR-NEXT: movq %rcx, %r9 -; SCALAR-NEXT: shrq $32, %r9 ; SCALAR-NEXT: movq 16(%rdi), %rdi -; SCALAR-NEXT: movq %rdi, %r10 -; SCALAR-NEXT: shrq $32, %r10 -; SCALAR-NEXT: notl %r10d -; SCALAR-NEXT: shlq $32, %r10 -; SCALAR-NEXT: notl %edi -; SCALAR-NEXT: orq %r10, %rdi -; SCALAR-NEXT: notl %r9d -; SCALAR-NEXT: shlq $32, %r9 -; SCALAR-NEXT: notl %ecx -; SCALAR-NEXT: orq %r9, %rcx -; SCALAR-NEXT: notl %r8d -; SCALAR-NEXT: shlq $32, %r8 -; SCALAR-NEXT: notl %eax -; SCALAR-NEXT: orq %r8, %rax +; SCALAR-NEXT: notq %rdi +; SCALAR-NEXT: notq %rcx +; SCALAR-NEXT: notq %rax ; SCALAR-NEXT: movq %rax, (%rsi) ; SCALAR-NEXT: movq %rcx, 8(%rsi) ; SCALAR-NEXT: movq %rdi, 16(%rsi) diff --git a/llvm/test/CodeGen/X86/vec_saddo.ll b/llvm/test/CodeGen/X86/vec_saddo.ll index cee30f5fe5da9e933fe4bd9545fd2caa0d1e0d60..460c5fe11f82a519aea2bc0d8cb8914faf7d2cd2 100644 --- a/llvm/test/CodeGen/X86/vec_saddo.ll +++ b/llvm/test/CodeGen/X86/vec_saddo.ll @@ -1045,16 +1045,12 @@ define <4 x i32> @saddo_v4i1(<4 x i1> %a0, <4 x i1> %a1, ptr %p2) nounwind { ; ; AVX512-LABEL: saddo_v4i1: ; AVX512: # %bb.0: +; AVX512-NEXT: vpxor %xmm1, %xmm0, %xmm2 +; AVX512-NEXT: vpslld $31, %xmm2, %xmm2 +; AVX512-NEXT: vptestmd %xmm2, %xmm2, %k0 +; AVX512-NEXT: vpand %xmm1, %xmm0, %xmm0 ; AVX512-NEXT: vpslld $31, %xmm0, %xmm0 -; AVX512-NEXT: vptestmd %xmm0, %xmm0, %k0 -; AVX512-NEXT: vpslld $31, %xmm1, %xmm0 -; AVX512-NEXT: vptestmd %xmm0, %xmm0, %k1 -; AVX512-NEXT: kxorw %k1, %k0, %k2 -; AVX512-NEXT: kandw %k1, %k0, %k1 -; AVX512-NEXT: vpcmpeqd %xmm0, %xmm0, %xmm0 -; AVX512-NEXT: vmovdqa32 %xmm0, %xmm0 {%k1} {z} -; AVX512-NEXT: kshiftlw $12, %k2, %k0 -; AVX512-NEXT: kshiftrw $12, %k0, %k0 +; AVX512-NEXT: vpsrad $31, %xmm0, %xmm0 ; AVX512-NEXT: kmovd %k0, %eax ; AVX512-NEXT: movb %al, (%rdi) ; AVX512-NEXT: retq diff --git a/llvm/test/CodeGen/X86/vec_ssubo.ll b/llvm/test/CodeGen/X86/vec_ssubo.ll index 64ed081048851bd2d08bc92aeba8ef06a0f05193..d06993da6365d8e6295cf49d7060313b88447278 100644 --- a/llvm/test/CodeGen/X86/vec_ssubo.ll +++ b/llvm/test/CodeGen/X86/vec_ssubo.ll @@ -1062,16 +1062,12 @@ define <4 x i32> @ssubo_v4i1(<4 x i1> %a0, <4 x i1> %a1, ptr %p2) nounwind { ; ; AVX512-LABEL: ssubo_v4i1: ; AVX512: # %bb.0: +; AVX512-NEXT: vpxor %xmm1, %xmm0, %xmm2 +; AVX512-NEXT: vpslld $31, %xmm2, %xmm2 +; AVX512-NEXT: vptestmd %xmm2, %xmm2, %k0 +; AVX512-NEXT: vpandn %xmm1, %xmm0, %xmm0 ; AVX512-NEXT: vpslld $31, %xmm0, %xmm0 -; AVX512-NEXT: vptestmd %xmm0, %xmm0, %k0 -; AVX512-NEXT: vpslld $31, %xmm1, %xmm1 -; AVX512-NEXT: vptestmd %xmm1, %xmm1, %k1 -; AVX512-NEXT: kxorw %k1, %k0, %k0 -; AVX512-NEXT: vptestnmd %xmm0, %xmm0, %k1 {%k1} -; AVX512-NEXT: vpcmpeqd %xmm0, %xmm0, %xmm0 -; AVX512-NEXT: vmovdqa32 %xmm0, %xmm0 {%k1} {z} -; AVX512-NEXT: kshiftlw $12, %k0, %k0 -; AVX512-NEXT: kshiftrw $12, %k0, %k0 +; AVX512-NEXT: vpsrad $31, %xmm0, %xmm0 ; AVX512-NEXT: kmovd %k0, %eax ; AVX512-NEXT: movb %al, (%rdi) ; AVX512-NEXT: retq diff --git a/llvm/test/CodeGen/X86/vec_uaddo.ll b/llvm/test/CodeGen/X86/vec_uaddo.ll index 950e943bd90201397542b34e17f20900c2b7922e..bac118095331ca55e9a0edb3452a5a304e4b01b8 100644 --- a/llvm/test/CodeGen/X86/vec_uaddo.ll +++ b/llvm/test/CodeGen/X86/vec_uaddo.ll @@ -1098,16 +1098,12 @@ define <4 x i32> @uaddo_v4i1(<4 x i1> %a0, <4 x i1> %a1, ptr %p2) nounwind { ; ; AVX512-LABEL: uaddo_v4i1: ; AVX512: # %bb.0: +; AVX512-NEXT: vpxor %xmm1, %xmm0, %xmm2 +; AVX512-NEXT: vpslld $31, %xmm2, %xmm2 +; AVX512-NEXT: vptestmd %xmm2, %xmm2, %k0 +; AVX512-NEXT: vpand %xmm1, %xmm0, %xmm0 ; AVX512-NEXT: vpslld $31, %xmm0, %xmm0 -; AVX512-NEXT: vptestmd %xmm0, %xmm0, %k0 -; AVX512-NEXT: vpslld $31, %xmm1, %xmm0 -; AVX512-NEXT: vptestmd %xmm0, %xmm0, %k1 -; AVX512-NEXT: kxorw %k1, %k0, %k2 -; AVX512-NEXT: kandw %k1, %k0, %k1 -; AVX512-NEXT: vpcmpeqd %xmm0, %xmm0, %xmm0 -; AVX512-NEXT: vmovdqa32 %xmm0, %xmm0 {%k1} {z} -; AVX512-NEXT: kshiftlw $12, %k2, %k0 -; AVX512-NEXT: kshiftrw $12, %k0, %k0 +; AVX512-NEXT: vpsrad $31, %xmm0, %xmm0 ; AVX512-NEXT: kmovd %k0, %eax ; AVX512-NEXT: movb %al, (%rdi) ; AVX512-NEXT: retq diff --git a/llvm/test/CodeGen/X86/vec_usubo.ll b/llvm/test/CodeGen/X86/vec_usubo.ll index 7de972770d8da4ffcb5b1da5a37c26cf117db2bd..ab75ada72f256520fff44310a9b2452114fa3931 100644 --- a/llvm/test/CodeGen/X86/vec_usubo.ll +++ b/llvm/test/CodeGen/X86/vec_usubo.ll @@ -1145,16 +1145,12 @@ define <4 x i32> @usubo_v4i1(<4 x i1> %a0, <4 x i1> %a1, ptr %p2) nounwind { ; ; AVX512-LABEL: usubo_v4i1: ; AVX512: # %bb.0: +; AVX512-NEXT: vpxor %xmm1, %xmm0, %xmm2 +; AVX512-NEXT: vpslld $31, %xmm2, %xmm2 +; AVX512-NEXT: vptestmd %xmm2, %xmm2, %k0 +; AVX512-NEXT: vpandn %xmm1, %xmm0, %xmm0 ; AVX512-NEXT: vpslld $31, %xmm0, %xmm0 -; AVX512-NEXT: vptestmd %xmm0, %xmm0, %k0 -; AVX512-NEXT: vpslld $31, %xmm1, %xmm1 -; AVX512-NEXT: vptestmd %xmm1, %xmm1, %k1 -; AVX512-NEXT: kxorw %k1, %k0, %k0 -; AVX512-NEXT: vptestnmd %xmm0, %xmm0, %k1 {%k1} -; AVX512-NEXT: vpcmpeqd %xmm0, %xmm0, %xmm0 -; AVX512-NEXT: vmovdqa32 %xmm0, %xmm0 {%k1} {z} -; AVX512-NEXT: kshiftlw $12, %k0, %k0 -; AVX512-NEXT: kshiftrw $12, %k0, %k0 +; AVX512-NEXT: vpsrad $31, %xmm0, %xmm0 ; AVX512-NEXT: kmovd %k0, %eax ; AVX512-NEXT: movb %al, (%rdi) ; AVX512-NEXT: retq diff --git a/llvm/test/CodeGen/X86/vector-bo-select.ll b/llvm/test/CodeGen/X86/vector-bo-select.ll index 78797b9acc2e6ec1191d6616f44f888388eaa665..27aaad6353ed68782a62be9ba8aafc35966d92aa 100644 --- a/llvm/test/CodeGen/X86/vector-bo-select.ll +++ b/llvm/test/CodeGen/X86/vector-bo-select.ll @@ -3137,11 +3137,11 @@ define <8 x i64> @mul_v8i64_cast_cond(i8 noundef zeroext %pb, <8 x i64> noundef ; AVX512-LABEL: mul_v8i64_cast_cond: ; AVX512: # %bb.0: ; AVX512-NEXT: kmovw %edi, %k1 -; AVX512-NEXT: vpsrlq $32, %zmm1, %zmm2 -; AVX512-NEXT: vpmuludq %zmm2, %zmm0, %zmm2 -; AVX512-NEXT: vpsrlq $32, %zmm0, %zmm3 -; AVX512-NEXT: vpmuludq %zmm1, %zmm3, %zmm3 -; AVX512-NEXT: vpaddq %zmm3, %zmm2, %zmm2 +; AVX512-NEXT: vpsrlq $32, %zmm0, %zmm2 +; AVX512-NEXT: vpmuludq %zmm1, %zmm2, %zmm2 +; AVX512-NEXT: vpsrlq $32, %zmm1, %zmm3 +; AVX512-NEXT: vpmuludq %zmm3, %zmm0, %zmm3 +; AVX512-NEXT: vpaddq %zmm2, %zmm3, %zmm2 ; AVX512-NEXT: vpsllq $32, %zmm2, %zmm2 ; AVX512-NEXT: vpmuludq %zmm1, %zmm0, %zmm1 ; AVX512-NEXT: vpaddq %zmm2, %zmm1, %zmm0 {%k1} diff --git a/llvm/test/CodeGen/X86/vector-fshr-128.ll b/llvm/test/CodeGen/X86/vector-fshr-128.ll index b839452725a95f46788ac100f82485e5212eb132..3aaa9268a8d8880592073b4bfd467b8b961f046f 100644 --- a/llvm/test/CodeGen/X86/vector-fshr-128.ll +++ b/llvm/test/CodeGen/X86/vector-fshr-128.ll @@ -58,12 +58,12 @@ define <2 x i64> @var_funnnel_v2i64(<2 x i64> %x, <2 x i64> %y, <2 x i64> %amt) ; SSE41-NEXT: psrlq %xmm4, %xmm1 ; SSE41-NEXT: pblendw {{.*#+}} xmm5 = xmm5[0,1,2,3],xmm1[4,5,6,7] ; SSE41-NEXT: pandn %xmm3, %xmm2 -; SSE41-NEXT: pshufd {{.*#+}} xmm1 = xmm2[2,3,2,3] ; SSE41-NEXT: paddq %xmm0, %xmm0 -; SSE41-NEXT: movdqa %xmm0, %xmm3 -; SSE41-NEXT: psllq %xmm1, %xmm3 +; SSE41-NEXT: movdqa %xmm0, %xmm1 +; SSE41-NEXT: psllq %xmm2, %xmm1 +; SSE41-NEXT: pshufd {{.*#+}} xmm2 = xmm2[2,3,2,3] ; SSE41-NEXT: psllq %xmm2, %xmm0 -; SSE41-NEXT: pblendw {{.*#+}} xmm0 = xmm0[0,1,2,3],xmm3[4,5,6,7] +; SSE41-NEXT: pblendw {{.*#+}} xmm0 = xmm1[0,1,2,3],xmm0[4,5,6,7] ; SSE41-NEXT: por %xmm5, %xmm0 ; SSE41-NEXT: retq ; @@ -76,11 +76,11 @@ define <2 x i64> @var_funnnel_v2i64(<2 x i64> %x, <2 x i64> %y, <2 x i64> %amt) ; AVX1-NEXT: vpsrlq %xmm4, %xmm1, %xmm1 ; AVX1-NEXT: vpblendw {{.*#+}} xmm1 = xmm5[0,1,2,3],xmm1[4,5,6,7] ; AVX1-NEXT: vpandn %xmm3, %xmm2, %xmm2 -; AVX1-NEXT: vpshufd {{.*#+}} xmm3 = xmm2[2,3,2,3] ; AVX1-NEXT: vpaddq %xmm0, %xmm0, %xmm0 -; AVX1-NEXT: vpsllq %xmm3, %xmm0, %xmm3 +; AVX1-NEXT: vpsllq %xmm2, %xmm0, %xmm3 +; AVX1-NEXT: vpshufd {{.*#+}} xmm2 = xmm2[2,3,2,3] ; AVX1-NEXT: vpsllq %xmm2, %xmm0, %xmm0 -; AVX1-NEXT: vpblendw {{.*#+}} xmm0 = xmm0[0,1,2,3],xmm3[4,5,6,7] +; AVX1-NEXT: vpblendw {{.*#+}} xmm0 = xmm3[0,1,2,3],xmm0[4,5,6,7] ; AVX1-NEXT: vpor %xmm1, %xmm0, %xmm0 ; AVX1-NEXT: retq ; @@ -158,13 +158,13 @@ define <2 x i64> @var_funnnel_v2i64(<2 x i64> %x, <2 x i64> %y, <2 x i64> %amt) ; XOPAVX1-LABEL: var_funnnel_v2i64: ; XOPAVX1: # %bb.0: ; XOPAVX1-NEXT: vpmovsxbq {{.*#+}} xmm3 = [63,63] -; XOPAVX1-NEXT: vpand %xmm3, %xmm2, %xmm4 -; XOPAVX1-NEXT: vpxor %xmm5, %xmm5, %xmm5 -; XOPAVX1-NEXT: vpsubq %xmm4, %xmm5, %xmm4 -; XOPAVX1-NEXT: vpshlq %xmm4, %xmm1, %xmm1 -; XOPAVX1-NEXT: vpandn %xmm3, %xmm2, %xmm2 +; XOPAVX1-NEXT: vpandn %xmm3, %xmm2, %xmm4 ; XOPAVX1-NEXT: vpaddq %xmm0, %xmm0, %xmm0 -; XOPAVX1-NEXT: vpshlq %xmm2, %xmm0, %xmm0 +; XOPAVX1-NEXT: vpshlq %xmm4, %xmm0, %xmm0 +; XOPAVX1-NEXT: vpand %xmm3, %xmm2, %xmm2 +; XOPAVX1-NEXT: vpxor %xmm3, %xmm3, %xmm3 +; XOPAVX1-NEXT: vpsubq %xmm2, %xmm3, %xmm2 +; XOPAVX1-NEXT: vpshlq %xmm2, %xmm1, %xmm1 ; XOPAVX1-NEXT: vpor %xmm1, %xmm0, %xmm0 ; XOPAVX1-NEXT: retq ; @@ -366,13 +366,13 @@ define <4 x i32> @var_funnnel_v4i32(<4 x i32> %x, <4 x i32> %y, <4 x i32> %amt) ; XOPAVX1-LABEL: var_funnnel_v4i32: ; XOPAVX1: # %bb.0: ; XOPAVX1-NEXT: vbroadcastss {{.*#+}} xmm3 = [31,31,31,31] -; XOPAVX1-NEXT: vpand %xmm3, %xmm2, %xmm4 -; XOPAVX1-NEXT: vpxor %xmm5, %xmm5, %xmm5 -; XOPAVX1-NEXT: vpsubd %xmm4, %xmm5, %xmm4 -; XOPAVX1-NEXT: vpshld %xmm4, %xmm1, %xmm1 -; XOPAVX1-NEXT: vpandn %xmm3, %xmm2, %xmm2 +; XOPAVX1-NEXT: vpandn %xmm3, %xmm2, %xmm4 ; XOPAVX1-NEXT: vpaddd %xmm0, %xmm0, %xmm0 -; XOPAVX1-NEXT: vpshld %xmm2, %xmm0, %xmm0 +; XOPAVX1-NEXT: vpshld %xmm4, %xmm0, %xmm0 +; XOPAVX1-NEXT: vpand %xmm3, %xmm2, %xmm2 +; XOPAVX1-NEXT: vpxor %xmm3, %xmm3, %xmm3 +; XOPAVX1-NEXT: vpsubd %xmm2, %xmm3, %xmm2 +; XOPAVX1-NEXT: vpshld %xmm2, %xmm1, %xmm1 ; XOPAVX1-NEXT: vpor %xmm1, %xmm0, %xmm0 ; XOPAVX1-NEXT: retq ; @@ -646,26 +646,26 @@ define <8 x i16> @var_funnnel_v8i16(<8 x i16> %x, <8 x i16> %y, <8 x i16> %amt) ; XOPAVX1-LABEL: var_funnnel_v8i16: ; XOPAVX1: # %bb.0: ; XOPAVX1-NEXT: vbroadcastss {{.*#+}} xmm3 = [15,15,15,15,15,15,15,15] -; XOPAVX1-NEXT: vpand %xmm3, %xmm2, %xmm4 -; XOPAVX1-NEXT: vpxor %xmm5, %xmm5, %xmm5 -; XOPAVX1-NEXT: vpsubw %xmm4, %xmm5, %xmm4 -; XOPAVX1-NEXT: vpshlw %xmm4, %xmm1, %xmm1 -; XOPAVX1-NEXT: vpandn %xmm3, %xmm2, %xmm2 +; XOPAVX1-NEXT: vpandn %xmm3, %xmm2, %xmm4 ; XOPAVX1-NEXT: vpaddw %xmm0, %xmm0, %xmm0 -; XOPAVX1-NEXT: vpshlw %xmm2, %xmm0, %xmm0 +; XOPAVX1-NEXT: vpshlw %xmm4, %xmm0, %xmm0 +; XOPAVX1-NEXT: vpand %xmm3, %xmm2, %xmm2 +; XOPAVX1-NEXT: vpxor %xmm3, %xmm3, %xmm3 +; XOPAVX1-NEXT: vpsubw %xmm2, %xmm3, %xmm2 +; XOPAVX1-NEXT: vpshlw %xmm2, %xmm1, %xmm1 ; XOPAVX1-NEXT: vpor %xmm1, %xmm0, %xmm0 ; XOPAVX1-NEXT: retq ; ; XOPAVX2-LABEL: var_funnnel_v8i16: ; XOPAVX2: # %bb.0: ; XOPAVX2-NEXT: vpbroadcastw {{.*#+}} xmm3 = [15,15,15,15,15,15,15,15] -; XOPAVX2-NEXT: vpand %xmm3, %xmm2, %xmm4 -; XOPAVX2-NEXT: vpxor %xmm5, %xmm5, %xmm5 -; XOPAVX2-NEXT: vpsubw %xmm4, %xmm5, %xmm4 -; XOPAVX2-NEXT: vpshlw %xmm4, %xmm1, %xmm1 -; XOPAVX2-NEXT: vpandn %xmm3, %xmm2, %xmm2 +; XOPAVX2-NEXT: vpandn %xmm3, %xmm2, %xmm4 ; XOPAVX2-NEXT: vpaddw %xmm0, %xmm0, %xmm0 -; XOPAVX2-NEXT: vpshlw %xmm2, %xmm0, %xmm0 +; XOPAVX2-NEXT: vpshlw %xmm4, %xmm0, %xmm0 +; XOPAVX2-NEXT: vpand %xmm3, %xmm2, %xmm2 +; XOPAVX2-NEXT: vpxor %xmm3, %xmm3, %xmm3 +; XOPAVX2-NEXT: vpsubw %xmm2, %xmm3, %xmm2 +; XOPAVX2-NEXT: vpshlw %xmm2, %xmm1, %xmm1 ; XOPAVX2-NEXT: vpor %xmm1, %xmm0, %xmm0 ; XOPAVX2-NEXT: retq ; @@ -995,26 +995,26 @@ define <16 x i8> @var_funnnel_v16i8(<16 x i8> %x, <16 x i8> %y, <16 x i8> %amt) ; XOPAVX1-LABEL: var_funnnel_v16i8: ; XOPAVX1: # %bb.0: ; XOPAVX1-NEXT: vbroadcastss {{.*#+}} xmm3 = [7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7] -; XOPAVX1-NEXT: vpand %xmm3, %xmm2, %xmm4 -; XOPAVX1-NEXT: vpxor %xmm5, %xmm5, %xmm5 -; XOPAVX1-NEXT: vpsubb %xmm4, %xmm5, %xmm4 -; XOPAVX1-NEXT: vpshlb %xmm4, %xmm1, %xmm1 -; XOPAVX1-NEXT: vpandn %xmm3, %xmm2, %xmm2 +; XOPAVX1-NEXT: vpandn %xmm3, %xmm2, %xmm4 ; XOPAVX1-NEXT: vpaddb %xmm0, %xmm0, %xmm0 -; XOPAVX1-NEXT: vpshlb %xmm2, %xmm0, %xmm0 +; XOPAVX1-NEXT: vpshlb %xmm4, %xmm0, %xmm0 +; XOPAVX1-NEXT: vpand %xmm3, %xmm2, %xmm2 +; XOPAVX1-NEXT: vpxor %xmm3, %xmm3, %xmm3 +; XOPAVX1-NEXT: vpsubb %xmm2, %xmm3, %xmm2 +; XOPAVX1-NEXT: vpshlb %xmm2, %xmm1, %xmm1 ; XOPAVX1-NEXT: vpor %xmm1, %xmm0, %xmm0 ; XOPAVX1-NEXT: retq ; ; XOPAVX2-LABEL: var_funnnel_v16i8: ; XOPAVX2: # %bb.0: ; XOPAVX2-NEXT: vpbroadcastb {{.*#+}} xmm3 = [7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7] -; XOPAVX2-NEXT: vpand %xmm3, %xmm2, %xmm4 -; XOPAVX2-NEXT: vpxor %xmm5, %xmm5, %xmm5 -; XOPAVX2-NEXT: vpsubb %xmm4, %xmm5, %xmm4 -; XOPAVX2-NEXT: vpshlb %xmm4, %xmm1, %xmm1 -; XOPAVX2-NEXT: vpandn %xmm3, %xmm2, %xmm2 +; XOPAVX2-NEXT: vpandn %xmm3, %xmm2, %xmm4 ; XOPAVX2-NEXT: vpaddb %xmm0, %xmm0, %xmm0 -; XOPAVX2-NEXT: vpshlb %xmm2, %xmm0, %xmm0 +; XOPAVX2-NEXT: vpshlb %xmm4, %xmm0, %xmm0 +; XOPAVX2-NEXT: vpand %xmm3, %xmm2, %xmm2 +; XOPAVX2-NEXT: vpxor %xmm3, %xmm3, %xmm3 +; XOPAVX2-NEXT: vpsubb %xmm2, %xmm3, %xmm2 +; XOPAVX2-NEXT: vpshlb %xmm2, %xmm1, %xmm1 ; XOPAVX2-NEXT: vpor %xmm1, %xmm0, %xmm0 ; XOPAVX2-NEXT: retq ; diff --git a/llvm/test/CodeGen/X86/vector-fshr-256.ll b/llvm/test/CodeGen/X86/vector-fshr-256.ll index 7b6b0ea83c7eea3f5d9507b3ea9a310cb07eded3..fc65f759f5fbed608288b418fdc4a21acbe0a0a6 100644 --- a/llvm/test/CodeGen/X86/vector-fshr-256.ll +++ b/llvm/test/CodeGen/X86/vector-fshr-256.ll @@ -486,22 +486,22 @@ define <16 x i16> @var_funnnel_v16i16(<16 x i16> %x, <16 x i16> %y, <16 x i16> % ; XOPAVX2-LABEL: var_funnnel_v16i16: ; XOPAVX2: # %bb.0: ; XOPAVX2-NEXT: vpbroadcastw {{.*#+}} ymm3 = [15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15] -; XOPAVX2-NEXT: vpand %ymm3, %ymm2, %ymm4 +; XOPAVX2-NEXT: vpandn %ymm3, %ymm2, %ymm4 ; XOPAVX2-NEXT: vextracti128 $1, %ymm4, %xmm5 -; XOPAVX2-NEXT: vpxor %xmm6, %xmm6, %xmm6 -; XOPAVX2-NEXT: vpsubw %xmm5, %xmm6, %xmm5 -; XOPAVX2-NEXT: vextracti128 $1, %ymm1, %xmm7 -; XOPAVX2-NEXT: vpshlw %xmm5, %xmm7, %xmm5 -; XOPAVX2-NEXT: vpsubw %xmm4, %xmm6, %xmm4 -; XOPAVX2-NEXT: vpshlw %xmm4, %xmm1, %xmm1 -; XOPAVX2-NEXT: vinserti128 $1, %xmm5, %ymm1, %ymm1 -; XOPAVX2-NEXT: vpandn %ymm3, %ymm2, %ymm2 -; XOPAVX2-NEXT: vextracti128 $1, %ymm2, %xmm3 ; XOPAVX2-NEXT: vpaddw %ymm0, %ymm0, %ymm0 -; XOPAVX2-NEXT: vextracti128 $1, %ymm0, %xmm4 -; XOPAVX2-NEXT: vpshlw %xmm3, %xmm4, %xmm3 -; XOPAVX2-NEXT: vpshlw %xmm2, %xmm0, %xmm0 -; XOPAVX2-NEXT: vinserti128 $1, %xmm3, %ymm0, %ymm0 +; XOPAVX2-NEXT: vextracti128 $1, %ymm0, %xmm6 +; XOPAVX2-NEXT: vpshlw %xmm5, %xmm6, %xmm5 +; XOPAVX2-NEXT: vpshlw %xmm4, %xmm0, %xmm0 +; XOPAVX2-NEXT: vinserti128 $1, %xmm5, %ymm0, %ymm0 +; XOPAVX2-NEXT: vpand %ymm3, %ymm2, %ymm2 +; XOPAVX2-NEXT: vextracti128 $1, %ymm2, %xmm3 +; XOPAVX2-NEXT: vpxor %xmm4, %xmm4, %xmm4 +; XOPAVX2-NEXT: vpsubw %xmm3, %xmm4, %xmm3 +; XOPAVX2-NEXT: vextracti128 $1, %ymm1, %xmm5 +; XOPAVX2-NEXT: vpshlw %xmm3, %xmm5, %xmm3 +; XOPAVX2-NEXT: vpsubw %xmm2, %xmm4, %xmm2 +; XOPAVX2-NEXT: vpshlw %xmm2, %xmm1, %xmm1 +; XOPAVX2-NEXT: vinserti128 $1, %xmm3, %ymm1, %ymm1 ; XOPAVX2-NEXT: vpor %ymm1, %ymm0, %ymm0 ; XOPAVX2-NEXT: retq %res = call <16 x i16> @llvm.fshr.v16i16(<16 x i16> %x, <16 x i16> %y, <16 x i16> %amt) diff --git a/llvm/test/CodeGen/X86/vector-fshr-sub128.ll b/llvm/test/CodeGen/X86/vector-fshr-sub128.ll index 0426c48aecfcffc4094fd2f2d07a0c2fbd3f3197..a6067a960fc0d63a4560d061116e74697d393c0f 100644 --- a/llvm/test/CodeGen/X86/vector-fshr-sub128.ll +++ b/llvm/test/CodeGen/X86/vector-fshr-sub128.ll @@ -185,13 +185,13 @@ define <2 x i32> @var_funnnel_v2i32(<2 x i32> %x, <2 x i32> %y, <2 x i32> %amt) ; XOPAVX1-LABEL: var_funnnel_v2i32: ; XOPAVX1: # %bb.0: ; XOPAVX1-NEXT: vbroadcastss {{.*#+}} xmm3 = [31,31,31,31] -; XOPAVX1-NEXT: vpand %xmm3, %xmm2, %xmm4 -; XOPAVX1-NEXT: vpxor %xmm5, %xmm5, %xmm5 -; XOPAVX1-NEXT: vpsubd %xmm4, %xmm5, %xmm4 -; XOPAVX1-NEXT: vpshld %xmm4, %xmm1, %xmm1 -; XOPAVX1-NEXT: vpandn %xmm3, %xmm2, %xmm2 +; XOPAVX1-NEXT: vpandn %xmm3, %xmm2, %xmm4 ; XOPAVX1-NEXT: vpaddd %xmm0, %xmm0, %xmm0 -; XOPAVX1-NEXT: vpshld %xmm2, %xmm0, %xmm0 +; XOPAVX1-NEXT: vpshld %xmm4, %xmm0, %xmm0 +; XOPAVX1-NEXT: vpand %xmm3, %xmm2, %xmm2 +; XOPAVX1-NEXT: vpxor %xmm3, %xmm3, %xmm3 +; XOPAVX1-NEXT: vpsubd %xmm2, %xmm3, %xmm2 +; XOPAVX1-NEXT: vpshld %xmm2, %xmm1, %xmm1 ; XOPAVX1-NEXT: vpor %xmm1, %xmm0, %xmm0 ; XOPAVX1-NEXT: retq ; diff --git a/llvm/test/CodeGen/X86/vector-shift-shl-128.ll b/llvm/test/CodeGen/X86/vector-shift-shl-128.ll index c54da38ef10cc18414c613229468586a27477446..75baba5f35f792cade7e86f9537aebae78c51975 100644 --- a/llvm/test/CodeGen/X86/vector-shift-shl-128.ll +++ b/llvm/test/CodeGen/X86/vector-shift-shl-128.ll @@ -927,9 +927,9 @@ define <2 x i64> @constant_shift_v2i64(<2 x i64> %a) nounwind { ; SSE2-LABEL: constant_shift_v2i64: ; SSE2: # %bb.0: ; SSE2-NEXT: movdqa %xmm0, %xmm1 -; SSE2-NEXT: psllq $7, %xmm1 -; SSE2-NEXT: paddq %xmm0, %xmm0 -; SSE2-NEXT: shufps {{.*#+}} xmm0 = xmm0[0,1],xmm1[2,3] +; SSE2-NEXT: paddq %xmm0, %xmm1 +; SSE2-NEXT: psllq $7, %xmm0 +; SSE2-NEXT: movsd {{.*#+}} xmm0 = xmm1[0],xmm0[1] ; SSE2-NEXT: retq ; ; SSE41-LABEL: constant_shift_v2i64: @@ -975,9 +975,9 @@ define <2 x i64> @constant_shift_v2i64(<2 x i64> %a) nounwind { ; X86-SSE-LABEL: constant_shift_v2i64: ; X86-SSE: # %bb.0: ; X86-SSE-NEXT: movdqa %xmm0, %xmm1 -; X86-SSE-NEXT: psllq $7, %xmm1 -; X86-SSE-NEXT: paddq %xmm0, %xmm0 -; X86-SSE-NEXT: shufps {{.*#+}} xmm0 = xmm0[0,1],xmm1[2,3] +; X86-SSE-NEXT: paddq %xmm0, %xmm1 +; X86-SSE-NEXT: psllq $7, %xmm0 +; X86-SSE-NEXT: movsd {{.*#+}} xmm0 = xmm1[0],xmm0[1] ; X86-SSE-NEXT: retl %shift = shl <2 x i64> %a, ret <2 x i64> %shift diff --git a/llvm/test/CodeGen/Xtensa/call.ll b/llvm/test/CodeGen/Xtensa/call.ll new file mode 100644 index 0000000000000000000000000000000000000000..24c7c4f558e1388be7b3596cdcbce2f3ba222748 --- /dev/null +++ b/llvm/test/CodeGen/Xtensa/call.ll @@ -0,0 +1,49 @@ +; RUN: llc --mtriple=xtensa < %s | FileCheck %s + +declare i32 @external_function(i32) + +define i32 @test_call_external(i32 %a) nounwind { +; CHECK-LABEL: test_call_external: +; CHECK: # %bb.0: +; CHECK-NEXT: s32i a0, a1, 0 +; CHECK-NEXT: l32r a8, .LCPI0_0 +; CHECK-NEXT: callx0 a8 +; CHECK-NEXT: l32i a0, a1, 0 +; CHECK-NEXT: ret + %1 = call i32 @external_function(i32 %a) + ret i32 %1 +} + +define i32 @defined_function(i32 %a) nounwind { +; CHECK-LABEL: defined_function: +; CHECK: # %bb.0: +; CHECK-NEXT: addi a2, a2, 1 +; CHECK-NEXT: ret + %1 = add i32 %a, 1 + ret i32 %1 +} + +define i32 @test_call_defined(i32 %a) nounwind { +; CHECK-LABEL: test_call_defined: +; CHECK: # %bb.0: +; CHECK-NEXT: s32i a0, a1, 0 +; CHECK-NEXT: l32r a8, .LCPI2_0 +; CHECK-NEXT: callx0 a8 +; CHECK-NEXT: l32i a0, a1, 0 +; CHECK-NEXT: ret + %1 = call i32 @defined_function(i32 %a) nounwind + ret i32 %1 +} + +define i32 @test_call_indirect(ptr %a, i32 %b) nounwind { +; CHECK-LABEL: test_call_indirect: +; CHECK: # %bb.0: +; CHECK-NEXT: s32i a0, a1, 0 +; CHECK-NEXT: or a8, a2, a2 +; CHECK-NEXT: or a2, a3, a3 +; CHECK-NEXT: callx0 a8 +; CHECK-NEXT: l32i a0, a1, 0 +; CHECK-NEXT: ret + %1 = call i32 %a(i32 %b) + ret i32 %1 +} diff --git a/llvm/test/CodeGen/Xtensa/calling-conv.ll b/llvm/test/CodeGen/Xtensa/calling-conv.ll new file mode 100644 index 0000000000000000000000000000000000000000..41ae4220145c27c6e44bc4a56cca72490d898328 --- /dev/null +++ b/llvm/test/CodeGen/Xtensa/calling-conv.ll @@ -0,0 +1,78 @@ +; RUN: llc -mtriple=xtensa -O1 -verify-machineinstrs < %s \ +; RUN: | FileCheck %s -check-prefix=XTENSA + +; Check placement of first 6 arguments in registers and 7th argument on stack +define dso_local i32 @test1(i32 noundef %0, i32 noundef %1, i32 noundef %2, i32 noundef %3, i32 noundef %4, i32 noundef %5, ptr nocapture noundef readonly byval(i32) align 4 %6) { +; XTENSA-LABEL: @test1 +; XTENSA: add a8, a7, a2 +; XTENSA: l32i a9, a1, 0 +; XTENSA: add a2, a8, a9 +; XTENSA: ret + %8 = load i32, ptr %6, align 4 + %9 = add nsw i32 %5, %0 + %10 = add nsw i32 %9, %8 + ret i32 %10 +} + +; Check placement of second i64 argument in registers +define dso_local i32 @test2(i32 noundef %0, i64 noundef %1, i32 noundef %2) { +; XTENSA-LABEL: @test2 +; XTENSA: add a8, a6, a2 +; XTENSA: add a2, a8, a4 +; XTENSA: ret + %4 = trunc i64 %1 to i32 + %5 = add nsw i32 %2, %0 + %6 = add nsw i32 %5, %4 + ret i32 %6 +} + +; Check placement of first argument typeof i8 in register +define dso_local i32 @test3(i8 noundef signext %0, i64 noundef %1, i32 noundef %2) { +; XTENSA-LABEL: @test3 +; XTENSA: add a8, a2, a6 +; XTENSA: add a2, a8, a4 +; XTENSA: ret + %4 = trunc i64 %1 to i32 + %5 = sext i8 %0 to i32 + %6 = add nsw i32 %5, %2 + %7 = add nsw i32 %6, %4 + ret i32 %7 +} + +; Check placement of 4th argument typeof i64 on stack +define dso_local i32 @test4(i8 noundef signext %0, i64 noundef %1, i32 noundef %2, ptr nocapture noundef readonly byval(i64) align 8 %3) { +; XTENSA-LABEL: @test4 +; XTENSA: add a8, a2, a6 +; XTENSA: add a8, a8, a4 +; XTENSA: l32i a9, a1, 0 +; XTENSA: add a2, a8, a9 +; XTENSA: ret + %5 = load i64, ptr %3, align 8 + %6 = trunc i64 %1 to i32 + %7 = trunc i64 %5 to i32 + %8 = sext i8 %0 to i32 + %9 = add nsw i32 %8, %2 + %10 = add nsw i32 %9, %6 + %11 = add nsw i32 %10, %7 + ret i32 %11 +} + +; Check placement of 128 bit structure on registers +define dso_local i32 @test5([4 x i32] %0, i32 noundef %1) { +; XTENSA-LABEL: @test5 +; XTENSA: add a2, a2, a6 +; XTENSA: ret + %3 = extractvalue [4 x i32] %0, 0 + %4 = add nsw i32 %3, %1 + ret i32 %4 +} + +; Check placement of 128 bit structure on stack +define dso_local i32 @test6(i32 noundef %0, [4 x i32] %1) { +; XTENSA-LABEL: @test6 +; XTENSA: add a2, a3, a2 +; XTENSA: ret + %3 = extractvalue [4 x i32] %1, 0 + %4 = add nsw i32 %3, %0 + ret i32 %4 +} diff --git a/llvm/test/CodeGen/Xtensa/constantpool.ll b/llvm/test/CodeGen/Xtensa/constantpool.ll new file mode 100644 index 0000000000000000000000000000000000000000..9b380d2c37b9e0012d3767e85ec7f40ac408b043 --- /dev/null +++ b/llvm/test/CodeGen/Xtensa/constantpool.ll @@ -0,0 +1,28 @@ +; RUN: llc -mtriple=xtensa -verify-machineinstrs < %s \ +; RUN: | FileCheck %s + +; Test placement of the i32,i64, float and double constants in constantpool + +define dso_local i32 @const_i32() #0 { +; CHECK: .literal_position +; CHECK-NEXT: .literal .LCPI0_0, 74565 +; CHECK-LABEL: const_i32: +; CHECK: l32r a2, .LCPI0_0 + %1 = alloca i32, align 4 + store i32 74565, ptr %1, align 4 + %2 = load i32, ptr %1, align 4 + ret i32 %2 +} + +define dso_local i64 @const_int64() #0 { +; CHECK: .literal_position +; CHECK-NEXT: .literal .LCPI1_0, 305419896 +; CHECK-NEXT: .literal .LCPI1_1, -1859959449 +; CHECK-LABEL: const_int64: +; CHECK: l32r a3, .LCPI1_0 +; CHECK: l32r a2, .LCPI1_1 + %1 = alloca i64, align 8 + store i64 1311768467302729063, ptr %1, align 8 + %2 = load i64, ptr %1, align 8 + ret i64 %2 +} diff --git a/llvm/test/CodeGen/Xtensa/stack-access.ll b/llvm/test/CodeGen/Xtensa/stack-access.ll new file mode 100644 index 0000000000000000000000000000000000000000..1590d24f228f2e1636e8e007f3becebc3fc80c5e --- /dev/null +++ b/llvm/test/CodeGen/Xtensa/stack-access.ll @@ -0,0 +1,35 @@ +; RUN: llc -mtriple=xtensa -O0 -verify-machineinstrs < %s \ +; RUN: | FileCheck %s -check-prefix=XTENSA + +define i8 @loadi8(i8 %a) { +; XTENSA-LABEL: loadi8: +; XTENSA: s8i a2, a1, 3 +; XTENSA: l8ui a2, a1, 3 +; XTENSA: ret + %b = alloca i8, align 1 + store i8 %a, ptr %b, align 1 + %1 = load i8, ptr %b, align 1 + ret i8 %1 +} + +define i16 @loadi16(i16 %a) { +; XTENSA-LABEL: loadi16: +; XTENSA: s16i a2, a1, 2 +; XTENSA: l16ui a2, a1, 2 +; XTENSA: ret + %b = alloca i16, align 2 + store i16 %a, ptr %b, align 2 + %1 = load i16, ptr %b, align 2 + ret i16 %1 +} + +define i32 @loadi32(i32 %a) { +; XTENSA-LABEL: loadi32: +; XTENSA: s32i a2, a1, 0 +; XTENSA: l32i a2, a1, 0 +; XTENSA: ret + %b = alloca i32, align 4 + store i32 %a, ptr %b, align 4 + %1 = load i32, ptr %b, align 4 + ret i32 %1 +} diff --git a/llvm/test/DebugInfo/X86/invalid-cu-abbrev-contribution-dwp.s b/llvm/test/DebugInfo/X86/invalid-cu-abbrev-contribution-dwp.s new file mode 100644 index 0000000000000000000000000000000000000000..6cc539cf8594f2e474c2ce377fae4630bf8be299 --- /dev/null +++ b/llvm/test/DebugInfo/X86/invalid-cu-abbrev-contribution-dwp.s @@ -0,0 +1,58 @@ +# RUN: llvm-mc -triple x86_64-unknown-linux %s -filetype=obj -o - | \ +# RUN: llvm-dwarfdump -debug-info - 2>&1 | FileCheck %s + +# CHECK: warning: DWARF package unit at offset 0x00000000 missing abbreviation column + + .section .debug_abbrev.dwo, "e", @progbits +.LAbbrBegin: + .uleb128 1 # Abbreviation Code + .uleb128 17 # DW_TAG_compile_unit + .byte 0 # DW_CHILDREN_no + .uleb128 3 # DW_AT_name + .uleb128 8 # DW_FORM_string + .uleb128 0x2131 # DW_AT_GNU_dwo_id + .uleb128 7 # DW_FORM_data8 + .byte 0 # EOM(1) + .byte 0 # EOM(2) + .byte 0 # EOM(3) +.LAbbrEnd: + + .section .debug_info.dwo, "e", @progbits +.LCUBegin: + .long .LCUEnd-.LCUVersion # Length +.LCUVersion: + .short 4 # Version + .long 0 # Abbrev offset + .byte 4 # Address size + .uleb128 1 # Abbrev [1] DW_TAG_compile_unit + .asciz "a.c" # DW_AT_name + .quad 0x1100001122222222 # DW_AT_GNU_dwo_id +.LCUEnd: + + .section .debug_cu_index, "", @progbits +## Header: + .short 2 # Version + .space 2 # Padding + .long 1 # Section count (Invalid, should be 2) + .long 1 # Unit count + .long 4 # Slot count +## Hash Table of Signatures: + .quad 0 + .quad 0 + .quad 0x1100001122222222 + .quad 0 +## Parallel Table of Indexes: + .long 0 + .long 0 + .long 1 + .long 0 +## Table of Section Offsets: +## Row 0: + .long 1 # DW_SECT_INFO +# .long 3 # DW_SECT_ABBREV (Intentionally omitted) +## Row 1: + .long .LCUBegin-.debug_info.dwo # Offset in .debug_info.dwo +# .long .LAbbrBegin-.debug_abbrev.dwo # Offset in .debug_abbrev.dwo (Intentionally omitted) +## Table of Section Sizes: + .long .LCUEnd-.LCUBegin # Size of the contribution in .debug_info.dwo + .long .LAbbrEnd-.LAbbrBegin # Size of the contribution in .debug_abbrev.dwo (Intentionally omitted) diff --git a/llvm/test/DebugInfo/X86/invalid-cu-abbrev-offset-dwp.s b/llvm/test/DebugInfo/X86/invalid-cu-abbrev-offset-dwp.s new file mode 100644 index 0000000000000000000000000000000000000000..b9e769e3ed4a5baa87c0d709c395ce8255958913 --- /dev/null +++ b/llvm/test/DebugInfo/X86/invalid-cu-abbrev-offset-dwp.s @@ -0,0 +1,58 @@ +# RUN: llvm-mc -triple x86_64-unknown-linux %s -filetype=obj -o - | \ +# RUN: llvm-dwarfdump -debug-info - 2>&1 | FileCheck %s + +# CHECK: warning: DWARF package unit at offset 0x00000000 has a non-zero abbreviation offset + + .section .debug_abbrev.dwo, "e", @progbits +.LAbbrBegin: + .uleb128 1 # Abbreviation Code + .uleb128 17 # DW_TAG_compile_unit + .byte 0 # DW_CHILDREN_no + .uleb128 3 # DW_AT_name + .uleb128 8 # DW_FORM_string + .uleb128 0x2131 # DW_AT_GNU_dwo_id + .uleb128 7 # DW_FORM_data8 + .byte 0 # EOM(1) + .byte 0 # EOM(2) + .byte 0 # EOM(3) +.LAbbrEnd: + + .section .debug_info.dwo, "e", @progbits +.LCUBegin: + .long .LCUEnd-.LCUVersion # Length +.LCUVersion: + .short 4 # Version + .long 1 # Abbrev offset (Invalid, should be 0) + .byte 4 # Address size + .uleb128 1 # Abbrev [1] DW_TAG_compile_unit + .asciz "a.c" # DW_AT_name + .quad 0x1100001122222222 # DW_AT_GNU_dwo_id +.LCUEnd: + + .section .debug_cu_index, "", @progbits +## Header: + .short 2 # Version + .space 2 # Padding + .long 2 # Section count + .long 1 # Unit count + .long 4 # Slot count +## Hash Table of Signatures: + .quad 0 + .quad 0 + .quad 0x1100001122222222 + .quad 0 +## Parallel Table of Indexes: + .long 0 + .long 0 + .long 1 + .long 0 +## Table of Section Offsets: +## Row 0: + .long 1 # DW_SECT_INFO + .long 3 # DW_SECT_ABBREV +## Row 1: + .long .LCUBegin-.debug_info.dwo # Offset in .debug_info.dwo + .long .LAbbrBegin-.debug_abbrev.dwo # Offset in .debug_abbrev.dwo +## Table of Section Sizes: + .long .LCUEnd-.LCUBegin + .long .LAbbrEnd-.LAbbrBegin diff --git a/llvm/test/DebugInfo/X86/invalid-cu-length-dwp.s b/llvm/test/DebugInfo/X86/invalid-cu-length-dwp.s index 299bea1bf1a708821e539e4385ec4539c26649a7..d67416736093b4177f7d55f0e512d1f9e71479ce 100644 --- a/llvm/test/DebugInfo/X86/invalid-cu-length-dwp.s +++ b/llvm/test/DebugInfo/X86/invalid-cu-length-dwp.s @@ -1,9 +1,11 @@ # RUN: llvm-mc -triple x86_64-unknown-linux %s -filetype=obj -o - | \ -# RUN: llvm-dwarfdump -debug-info - +# RUN: llvm-dwarfdump -debug-info - 2>&1 | FileCheck %s ## llvm-dwarfdump used to crash with this input because of an invalid size ## of the compilation unit contribution in the .debug_cu_index section. +# CHECK: warning: DWARF package unit at offset 0x00000000 has an inconsistent index (expected: 23, actual: 24) + .section .debug_abbrev.dwo, "e", @progbits .LAbbrBegin: .uleb128 1 # Abbreviation Code diff --git a/llvm/test/Instrumentation/HWAddressSanitizer/basic.ll b/llvm/test/Instrumentation/HWAddressSanitizer/basic.ll index 5dededaccaad0d1e24b8c5db56470a0206559006..4212293f42545e22bbfdf75865c2cb6d6fdb2a8c 100644 --- a/llvm/test/Instrumentation/HWAddressSanitizer/basic.ll +++ b/llvm/test/Instrumentation/HWAddressSanitizer/basic.ll @@ -9,8 +9,6 @@ ; RUN: opt < %s -passes=hwasan -hwasan-recover=0 -hwasan-mapping-offset=0 -S | FileCheck %s --check-prefixes=ABORT-ZERO-BASED-SHADOW ; RUN: opt < %s -passes=hwasan -hwasan-recover=1 -hwasan-mapping-offset=0 -S | FileCheck %s --check-prefixes=RECOVER-ZERO-BASED-SHADOW -; CHECK: @llvm.used = appending global [1 x ptr] [ptr @hwasan.module_ctor] -; CHECK: @llvm.global_ctors = appending global [1 x { i32, ptr, ptr }] [{ i32, ptr, ptr } { i32 0, ptr @hwasan.module_ctor, ptr @hwasan.module_ctor }] target datalayout = "e-m:e-i8:8:32-i16:16:32-i64:64-i128:128-n32:64-S128" target triple = "aarch64--linux-android10000" @@ -101,7 +99,7 @@ define i8 @test_load8(ptr %a) sanitize_hwaddress { ; ABORT-ZERO-BASED-SHADOW-SAME: (ptr [[A:%.*]]) #[[ATTR0:[0-9]+]] { ; ABORT-ZERO-BASED-SHADOW-NEXT: entry: ; ABORT-ZERO-BASED-SHADOW-NEXT: [[DOTHWASAN_SHADOW:%.*]] = call ptr asm "", "=r,0"(ptr null) -; ABORT-ZERO-BASED-SHADOW-NEXT: call void @llvm.hwasan.check.memaccess.shortgranules(ptr [[DOTHWASAN_SHADOW]], ptr [[A]], i32 0) +; ABORT-ZERO-BASED-SHADOW-NEXT: call void @llvm.hwasan.check.memaccess.shortgranules.fixedshadow(ptr [[A]], i32 0, i64 0) ; ABORT-ZERO-BASED-SHADOW-NEXT: [[B:%.*]] = load i8, ptr [[A]], align 4 ; ABORT-ZERO-BASED-SHADOW-NEXT: ret i8 [[B]] ; @@ -233,7 +231,7 @@ define i16 @test_load16(ptr %a) sanitize_hwaddress { ; ABORT-ZERO-BASED-SHADOW-SAME: (ptr [[A:%.*]]) #[[ATTR0]] { ; ABORT-ZERO-BASED-SHADOW-NEXT: entry: ; ABORT-ZERO-BASED-SHADOW-NEXT: [[DOTHWASAN_SHADOW:%.*]] = call ptr asm "", "=r,0"(ptr null) -; ABORT-ZERO-BASED-SHADOW-NEXT: call void @llvm.hwasan.check.memaccess.shortgranules(ptr [[DOTHWASAN_SHADOW]], ptr [[A]], i32 1) +; ABORT-ZERO-BASED-SHADOW-NEXT: call void @llvm.hwasan.check.memaccess.shortgranules.fixedshadow(ptr [[A]], i32 1, i64 0) ; ABORT-ZERO-BASED-SHADOW-NEXT: [[B:%.*]] = load i16, ptr [[A]], align 4 ; ABORT-ZERO-BASED-SHADOW-NEXT: ret i16 [[B]] ; @@ -365,7 +363,7 @@ define i32 @test_load32(ptr %a) sanitize_hwaddress { ; ABORT-ZERO-BASED-SHADOW-SAME: (ptr [[A:%.*]]) #[[ATTR0]] { ; ABORT-ZERO-BASED-SHADOW-NEXT: entry: ; ABORT-ZERO-BASED-SHADOW-NEXT: [[DOTHWASAN_SHADOW:%.*]] = call ptr asm "", "=r,0"(ptr null) -; ABORT-ZERO-BASED-SHADOW-NEXT: call void @llvm.hwasan.check.memaccess.shortgranules(ptr [[DOTHWASAN_SHADOW]], ptr [[A]], i32 2) +; ABORT-ZERO-BASED-SHADOW-NEXT: call void @llvm.hwasan.check.memaccess.shortgranules.fixedshadow(ptr [[A]], i32 2, i64 0) ; ABORT-ZERO-BASED-SHADOW-NEXT: [[B:%.*]] = load i32, ptr [[A]], align 4 ; ABORT-ZERO-BASED-SHADOW-NEXT: ret i32 [[B]] ; @@ -497,7 +495,7 @@ define i64 @test_load64(ptr %a) sanitize_hwaddress { ; ABORT-ZERO-BASED-SHADOW-SAME: (ptr [[A:%.*]]) #[[ATTR0]] { ; ABORT-ZERO-BASED-SHADOW-NEXT: entry: ; ABORT-ZERO-BASED-SHADOW-NEXT: [[DOTHWASAN_SHADOW:%.*]] = call ptr asm "", "=r,0"(ptr null) -; ABORT-ZERO-BASED-SHADOW-NEXT: call void @llvm.hwasan.check.memaccess.shortgranules(ptr [[DOTHWASAN_SHADOW]], ptr [[A]], i32 3) +; ABORT-ZERO-BASED-SHADOW-NEXT: call void @llvm.hwasan.check.memaccess.shortgranules.fixedshadow(ptr [[A]], i32 3, i64 0) ; ABORT-ZERO-BASED-SHADOW-NEXT: [[B:%.*]] = load i64, ptr [[A]], align 8 ; ABORT-ZERO-BASED-SHADOW-NEXT: ret i64 [[B]] ; @@ -629,7 +627,7 @@ define i128 @test_load128(ptr %a) sanitize_hwaddress { ; ABORT-ZERO-BASED-SHADOW-SAME: (ptr [[A:%.*]]) #[[ATTR0]] { ; ABORT-ZERO-BASED-SHADOW-NEXT: entry: ; ABORT-ZERO-BASED-SHADOW-NEXT: [[DOTHWASAN_SHADOW:%.*]] = call ptr asm "", "=r,0"(ptr null) -; ABORT-ZERO-BASED-SHADOW-NEXT: call void @llvm.hwasan.check.memaccess.shortgranules(ptr [[DOTHWASAN_SHADOW]], ptr [[A]], i32 4) +; ABORT-ZERO-BASED-SHADOW-NEXT: call void @llvm.hwasan.check.memaccess.shortgranules.fixedshadow(ptr [[A]], i32 4, i64 0) ; ABORT-ZERO-BASED-SHADOW-NEXT: [[B:%.*]] = load i128, ptr [[A]], align 16 ; ABORT-ZERO-BASED-SHADOW-NEXT: ret i128 [[B]] ; @@ -830,7 +828,7 @@ define void @test_store8(ptr %a, i8 %b) sanitize_hwaddress { ; ABORT-ZERO-BASED-SHADOW-SAME: (ptr [[A:%.*]], i8 [[B:%.*]]) #[[ATTR0]] { ; ABORT-ZERO-BASED-SHADOW-NEXT: entry: ; ABORT-ZERO-BASED-SHADOW-NEXT: [[DOTHWASAN_SHADOW:%.*]] = call ptr asm "", "=r,0"(ptr null) -; ABORT-ZERO-BASED-SHADOW-NEXT: call void @llvm.hwasan.check.memaccess.shortgranules(ptr [[DOTHWASAN_SHADOW]], ptr [[A]], i32 16) +; ABORT-ZERO-BASED-SHADOW-NEXT: call void @llvm.hwasan.check.memaccess.shortgranules.fixedshadow(ptr [[A]], i32 16, i64 0) ; ABORT-ZERO-BASED-SHADOW-NEXT: store i8 [[B]], ptr [[A]], align 4 ; ABORT-ZERO-BASED-SHADOW-NEXT: ret void ; @@ -962,7 +960,7 @@ define void @test_store16(ptr %a, i16 %b) sanitize_hwaddress { ; ABORT-ZERO-BASED-SHADOW-SAME: (ptr [[A:%.*]], i16 [[B:%.*]]) #[[ATTR0]] { ; ABORT-ZERO-BASED-SHADOW-NEXT: entry: ; ABORT-ZERO-BASED-SHADOW-NEXT: [[DOTHWASAN_SHADOW:%.*]] = call ptr asm "", "=r,0"(ptr null) -; ABORT-ZERO-BASED-SHADOW-NEXT: call void @llvm.hwasan.check.memaccess.shortgranules(ptr [[DOTHWASAN_SHADOW]], ptr [[A]], i32 17) +; ABORT-ZERO-BASED-SHADOW-NEXT: call void @llvm.hwasan.check.memaccess.shortgranules.fixedshadow(ptr [[A]], i32 17, i64 0) ; ABORT-ZERO-BASED-SHADOW-NEXT: store i16 [[B]], ptr [[A]], align 4 ; ABORT-ZERO-BASED-SHADOW-NEXT: ret void ; @@ -1094,7 +1092,7 @@ define void @test_store32(ptr %a, i32 %b) sanitize_hwaddress { ; ABORT-ZERO-BASED-SHADOW-SAME: (ptr [[A:%.*]], i32 [[B:%.*]]) #[[ATTR0]] { ; ABORT-ZERO-BASED-SHADOW-NEXT: entry: ; ABORT-ZERO-BASED-SHADOW-NEXT: [[DOTHWASAN_SHADOW:%.*]] = call ptr asm "", "=r,0"(ptr null) -; ABORT-ZERO-BASED-SHADOW-NEXT: call void @llvm.hwasan.check.memaccess.shortgranules(ptr [[DOTHWASAN_SHADOW]], ptr [[A]], i32 18) +; ABORT-ZERO-BASED-SHADOW-NEXT: call void @llvm.hwasan.check.memaccess.shortgranules.fixedshadow(ptr [[A]], i32 18, i64 0) ; ABORT-ZERO-BASED-SHADOW-NEXT: store i32 [[B]], ptr [[A]], align 4 ; ABORT-ZERO-BASED-SHADOW-NEXT: ret void ; @@ -1226,7 +1224,7 @@ define void @test_store64(ptr %a, i64 %b) sanitize_hwaddress { ; ABORT-ZERO-BASED-SHADOW-SAME: (ptr [[A:%.*]], i64 [[B:%.*]]) #[[ATTR0]] { ; ABORT-ZERO-BASED-SHADOW-NEXT: entry: ; ABORT-ZERO-BASED-SHADOW-NEXT: [[DOTHWASAN_SHADOW:%.*]] = call ptr asm "", "=r,0"(ptr null) -; ABORT-ZERO-BASED-SHADOW-NEXT: call void @llvm.hwasan.check.memaccess.shortgranules(ptr [[DOTHWASAN_SHADOW]], ptr [[A]], i32 19) +; ABORT-ZERO-BASED-SHADOW-NEXT: call void @llvm.hwasan.check.memaccess.shortgranules.fixedshadow(ptr [[A]], i32 19, i64 0) ; ABORT-ZERO-BASED-SHADOW-NEXT: store i64 [[B]], ptr [[A]], align 8 ; ABORT-ZERO-BASED-SHADOW-NEXT: ret void ; @@ -1358,7 +1356,7 @@ define void @test_store128(ptr %a, i128 %b) sanitize_hwaddress { ; ABORT-ZERO-BASED-SHADOW-SAME: (ptr [[A:%.*]], i128 [[B:%.*]]) #[[ATTR0]] { ; ABORT-ZERO-BASED-SHADOW-NEXT: entry: ; ABORT-ZERO-BASED-SHADOW-NEXT: [[DOTHWASAN_SHADOW:%.*]] = call ptr asm "", "=r,0"(ptr null) -; ABORT-ZERO-BASED-SHADOW-NEXT: call void @llvm.hwasan.check.memaccess.shortgranules(ptr [[DOTHWASAN_SHADOW]], ptr [[A]], i32 20) +; ABORT-ZERO-BASED-SHADOW-NEXT: call void @llvm.hwasan.check.memaccess.shortgranules.fixedshadow(ptr [[A]], i32 20, i64 0) ; ABORT-ZERO-BASED-SHADOW-NEXT: store i128 [[B]], ptr [[A]], align 16 ; ABORT-ZERO-BASED-SHADOW-NEXT: ret void ; diff --git a/llvm/test/Instrumentation/HWAddressSanitizer/fixed-shadow.ll b/llvm/test/Instrumentation/HWAddressSanitizer/fixed-shadow.ll new file mode 100644 index 0000000000000000000000000000000000000000..980189c5607f31ea9e96d25f5c4e2bf521232b9d --- /dev/null +++ b/llvm/test/Instrumentation/HWAddressSanitizer/fixed-shadow.ll @@ -0,0 +1,229 @@ +; NOTE: Assertions have been autogenerated by utils/update_test_checks.py UTC_ARGS: --version 2 +; Test basic address sanitizer instrumentation. +; +; RUN: opt < %s -passes=hwasan -hwasan-mapping-offset=4398046511104 -S | FileCheck %s + + +target datalayout = "e-m:e-i8:8:32-i16:16:32-i64:64-i128:128-n32:64-S128" +target triple = "aarch64--linux-android9001" + +define i8 @test_load8(ptr %a) sanitize_hwaddress { +; CHECK-LABEL: define i8 @test_load8 +; CHECK-SAME: (ptr [[A:%.*]]) #[[ATTR0:[0-9]+]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[DOTHWASAN_SHADOW:%.*]] = call ptr asm "", "=r,0"(ptr inttoptr (i64 4398046511104 to ptr)) +; CHECK-NEXT: call void @llvm.hwasan.check.memaccess.shortgranules.fixedshadow(ptr [[A]], i32 0, i64 4398046511104) +; CHECK-NEXT: [[B:%.*]] = load i8, ptr [[A]], align 4 +; CHECK-NEXT: ret i8 [[B]] +; +entry: + %b = load i8, ptr %a, align 4 + ret i8 %b +} + +define i16 @test_load16(ptr %a) sanitize_hwaddress { +; CHECK-LABEL: define i16 @test_load16 +; CHECK-SAME: (ptr [[A:%.*]]) #[[ATTR0]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[DOTHWASAN_SHADOW:%.*]] = call ptr asm "", "=r,0"(ptr inttoptr (i64 4398046511104 to ptr)) +; CHECK-NEXT: call void @llvm.hwasan.check.memaccess.shortgranules.fixedshadow(ptr [[A]], i32 1, i64 4398046511104) +; CHECK-NEXT: [[B:%.*]] = load i16, ptr [[A]], align 4 +; CHECK-NEXT: ret i16 [[B]] +; +entry: + %b = load i16, ptr %a, align 4 + ret i16 %b +} + +define i32 @test_load32(ptr %a) sanitize_hwaddress { +; CHECK-LABEL: define i32 @test_load32 +; CHECK-SAME: (ptr [[A:%.*]]) #[[ATTR0]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[DOTHWASAN_SHADOW:%.*]] = call ptr asm "", "=r,0"(ptr inttoptr (i64 4398046511104 to ptr)) +; CHECK-NEXT: call void @llvm.hwasan.check.memaccess.shortgranules.fixedshadow(ptr [[A]], i32 2, i64 4398046511104) +; CHECK-NEXT: [[B:%.*]] = load i32, ptr [[A]], align 4 +; CHECK-NEXT: ret i32 [[B]] +; +entry: + %b = load i32, ptr %a, align 4 + ret i32 %b +} + +define i64 @test_load64(ptr %a) sanitize_hwaddress { +; CHECK-LABEL: define i64 @test_load64 +; CHECK-SAME: (ptr [[A:%.*]]) #[[ATTR0]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[DOTHWASAN_SHADOW:%.*]] = call ptr asm "", "=r,0"(ptr inttoptr (i64 4398046511104 to ptr)) +; CHECK-NEXT: call void @llvm.hwasan.check.memaccess.shortgranules.fixedshadow(ptr [[A]], i32 3, i64 4398046511104) +; CHECK-NEXT: [[B:%.*]] = load i64, ptr [[A]], align 8 +; CHECK-NEXT: ret i64 [[B]] +; +entry: + %b = load i64, ptr %a, align 8 + ret i64 %b +} + +define i128 @test_load128(ptr %a) sanitize_hwaddress { +; CHECK-LABEL: define i128 @test_load128 +; CHECK-SAME: (ptr [[A:%.*]]) #[[ATTR0]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[DOTHWASAN_SHADOW:%.*]] = call ptr asm "", "=r,0"(ptr inttoptr (i64 4398046511104 to ptr)) +; CHECK-NEXT: call void @llvm.hwasan.check.memaccess.shortgranules.fixedshadow(ptr [[A]], i32 4, i64 4398046511104) +; CHECK-NEXT: [[B:%.*]] = load i128, ptr [[A]], align 16 +; CHECK-NEXT: ret i128 [[B]] +; +entry: + %b = load i128, ptr %a, align 16 + ret i128 %b +} + +define i40 @test_load40(ptr %a) sanitize_hwaddress { +; CHECK-LABEL: define i40 @test_load40 +; CHECK-SAME: (ptr [[A:%.*]]) #[[ATTR0]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[DOTHWASAN_SHADOW:%.*]] = call ptr asm "", "=r,0"(ptr inttoptr (i64 4398046511104 to ptr)) +; CHECK-NEXT: [[TMP0:%.*]] = ptrtoint ptr [[A]] to i64 +; CHECK-NEXT: call void @__hwasan_loadN(i64 [[TMP0]], i64 5) +; CHECK-NEXT: [[B:%.*]] = load i40, ptr [[A]], align 4 +; CHECK-NEXT: ret i40 [[B]] +; +entry: + %b = load i40, ptr %a, align 4 + ret i40 %b +} + +define void @test_store8(ptr %a, i8 %b) sanitize_hwaddress { +; CHECK-LABEL: define void @test_store8 +; CHECK-SAME: (ptr [[A:%.*]], i8 [[B:%.*]]) #[[ATTR0]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[DOTHWASAN_SHADOW:%.*]] = call ptr asm "", "=r,0"(ptr inttoptr (i64 4398046511104 to ptr)) +; CHECK-NEXT: call void @llvm.hwasan.check.memaccess.shortgranules.fixedshadow(ptr [[A]], i32 16, i64 4398046511104) +; CHECK-NEXT: store i8 [[B]], ptr [[A]], align 4 +; CHECK-NEXT: ret void +; +entry: + store i8 %b, ptr %a, align 4 + ret void +} + +define void @test_store16(ptr %a, i16 %b) sanitize_hwaddress { +; CHECK-LABEL: define void @test_store16 +; CHECK-SAME: (ptr [[A:%.*]], i16 [[B:%.*]]) #[[ATTR0]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[DOTHWASAN_SHADOW:%.*]] = call ptr asm "", "=r,0"(ptr inttoptr (i64 4398046511104 to ptr)) +; CHECK-NEXT: call void @llvm.hwasan.check.memaccess.shortgranules.fixedshadow(ptr [[A]], i32 17, i64 4398046511104) +; CHECK-NEXT: store i16 [[B]], ptr [[A]], align 4 +; CHECK-NEXT: ret void +; +entry: + store i16 %b, ptr %a, align 4 + ret void +} + +define void @test_store32(ptr %a, i32 %b) sanitize_hwaddress { +; CHECK-LABEL: define void @test_store32 +; CHECK-SAME: (ptr [[A:%.*]], i32 [[B:%.*]]) #[[ATTR0]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[DOTHWASAN_SHADOW:%.*]] = call ptr asm "", "=r,0"(ptr inttoptr (i64 4398046511104 to ptr)) +; CHECK-NEXT: call void @llvm.hwasan.check.memaccess.shortgranules.fixedshadow(ptr [[A]], i32 18, i64 4398046511104) +; CHECK-NEXT: store i32 [[B]], ptr [[A]], align 4 +; CHECK-NEXT: ret void +; +entry: + store i32 %b, ptr %a, align 4 + ret void +} + +define void @test_store64(ptr %a, i64 %b) sanitize_hwaddress { +; CHECK-LABEL: define void @test_store64 +; CHECK-SAME: (ptr [[A:%.*]], i64 [[B:%.*]]) #[[ATTR0]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[DOTHWASAN_SHADOW:%.*]] = call ptr asm "", "=r,0"(ptr inttoptr (i64 4398046511104 to ptr)) +; CHECK-NEXT: call void @llvm.hwasan.check.memaccess.shortgranules.fixedshadow(ptr [[A]], i32 19, i64 4398046511104) +; CHECK-NEXT: store i64 [[B]], ptr [[A]], align 8 +; CHECK-NEXT: ret void +; +entry: + store i64 %b, ptr %a, align 8 + ret void +} + +define void @test_store128(ptr %a, i128 %b) sanitize_hwaddress { +; CHECK-LABEL: define void @test_store128 +; CHECK-SAME: (ptr [[A:%.*]], i128 [[B:%.*]]) #[[ATTR0]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[DOTHWASAN_SHADOW:%.*]] = call ptr asm "", "=r,0"(ptr inttoptr (i64 4398046511104 to ptr)) +; CHECK-NEXT: call void @llvm.hwasan.check.memaccess.shortgranules.fixedshadow(ptr [[A]], i32 20, i64 4398046511104) +; CHECK-NEXT: store i128 [[B]], ptr [[A]], align 16 +; CHECK-NEXT: ret void +; +entry: + store i128 %b, ptr %a, align 16 + ret void +} + +define void @test_store40(ptr %a, i40 %b) sanitize_hwaddress { +; CHECK-LABEL: define void @test_store40 +; CHECK-SAME: (ptr [[A:%.*]], i40 [[B:%.*]]) #[[ATTR0]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[DOTHWASAN_SHADOW:%.*]] = call ptr asm "", "=r,0"(ptr inttoptr (i64 4398046511104 to ptr)) +; CHECK-NEXT: [[TMP0:%.*]] = ptrtoint ptr [[A]] to i64 +; CHECK-NEXT: call void @__hwasan_storeN(i64 [[TMP0]], i64 5) +; CHECK-NEXT: store i40 [[B]], ptr [[A]], align 4 +; CHECK-NEXT: ret void +; +entry: + store i40 %b, ptr %a, align 4 + ret void +} + +define void @test_store_unaligned(ptr %a, i64 %b) sanitize_hwaddress { +; CHECK-LABEL: define void @test_store_unaligned +; CHECK-SAME: (ptr [[A:%.*]], i64 [[B:%.*]]) #[[ATTR0]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[DOTHWASAN_SHADOW:%.*]] = call ptr asm "", "=r,0"(ptr inttoptr (i64 4398046511104 to ptr)) +; CHECK-NEXT: [[TMP0:%.*]] = ptrtoint ptr [[A]] to i64 +; CHECK-NEXT: call void @__hwasan_storeN(i64 [[TMP0]], i64 8) +; CHECK-NEXT: store i64 [[B]], ptr [[A]], align 4 +; CHECK-NEXT: ret void +; +entry: + store i64 %b, ptr %a, align 4 + ret void +} + +define i8 @test_load_noattr(ptr %a) { +; CHECK-LABEL: define i8 @test_load_noattr +; CHECK-SAME: (ptr [[A:%.*]]) { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[B:%.*]] = load i8, ptr [[A]], align 4 +; CHECK-NEXT: ret i8 [[B]] +; +entry: + %b = load i8, ptr %a, align 4 + ret i8 %b +} + +define i8 @test_load_notmyattr(ptr %a) sanitize_address { +; CHECK-LABEL: define i8 @test_load_notmyattr +; CHECK-SAME: (ptr [[A:%.*]]) #[[ATTR1:[0-9]+]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[B:%.*]] = load i8, ptr [[A]], align 4 +; CHECK-NEXT: ret i8 [[B]] +; +entry: + %b = load i8, ptr %a, align 4 + ret i8 %b +} + +define i8 @test_load_addrspace(ptr addrspace(256) %a) sanitize_hwaddress { +; CHECK-LABEL: define i8 @test_load_addrspace +; CHECK-SAME: (ptr addrspace(256) [[A:%.*]]) #[[ATTR0]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[B:%.*]] = load i8, ptr addrspace(256) [[A]], align 4 +; CHECK-NEXT: ret i8 [[B]] +; +entry: + %b = load i8, ptr addrspace(256) %a, align 4 + ret i8 %b +} diff --git a/llvm/test/Instrumentation/HWAddressSanitizer/prologue.ll b/llvm/test/Instrumentation/HWAddressSanitizer/prologue.ll index f8e0364ba19f4625e72a2a6fae9964786a3b41b8..49f0bf739cb6925a98aca749e34180303686f795 100644 --- a/llvm/test/Instrumentation/HWAddressSanitizer/prologue.ll +++ b/llvm/test/Instrumentation/HWAddressSanitizer/prologue.ll @@ -69,7 +69,7 @@ define i32 @test_load(ptr %a) sanitize_hwaddress { ; FUCHSIA-SAME: (ptr [[A:%.*]]) #[[ATTR0:[0-9]+]] { ; FUCHSIA-NEXT: entry: ; FUCHSIA-NEXT: [[DOTHWASAN_SHADOW:%.*]] = call ptr asm "", "=r,0"(ptr null) -; FUCHSIA-NEXT: call void @llvm.hwasan.check.memaccess.shortgranules(ptr [[DOTHWASAN_SHADOW]], ptr [[A]], i32 2) +; FUCHSIA-NEXT: call void @llvm.hwasan.check.memaccess.shortgranules.fixedshadow(ptr [[A]], i32 2, i64 0) ; FUCHSIA-NEXT: [[X:%.*]] = load i32, ptr [[A]], align 4 ; FUCHSIA-NEXT: ret i32 [[X]] ; @@ -77,7 +77,7 @@ define i32 @test_load(ptr %a) sanitize_hwaddress { ; FUCHSIA-LIBCALL-SAME: (ptr [[A:%.*]]) #[[ATTR0:[0-9]+]] { ; FUCHSIA-LIBCALL-NEXT: entry: ; FUCHSIA-LIBCALL-NEXT: [[DOTHWASAN_SHADOW:%.*]] = call ptr asm "", "=r,0"(ptr null) -; FUCHSIA-LIBCALL-NEXT: call void @llvm.hwasan.check.memaccess.shortgranules(ptr [[DOTHWASAN_SHADOW]], ptr [[A]], i32 2) +; FUCHSIA-LIBCALL-NEXT: call void @llvm.hwasan.check.memaccess.shortgranules.fixedshadow(ptr [[A]], i32 2, i64 0) ; FUCHSIA-LIBCALL-NEXT: [[X:%.*]] = load i32, ptr [[A]], align 4 ; FUCHSIA-LIBCALL-NEXT: ret i32 [[X]] ; diff --git a/llvm/test/Instrumentation/InstrProfiling/Coro/coro-split-musttail.ll b/llvm/test/Instrumentation/InstrProfiling/Coro/coro-split-musttail.ll deleted file mode 100644 index a7321833d74843ba5cc1af09deb7cab7347a2d7f..0000000000000000000000000000000000000000 --- a/llvm/test/Instrumentation/InstrProfiling/Coro/coro-split-musttail.ll +++ /dev/null @@ -1,63 +0,0 @@ -; Tests that instrumentation doesn't interfere with lowering (coro-split). -; It should convert coro.resume followed by a suspend to a musttail call. - -; RUN: opt < %s -passes='pgo-instr-gen,cgscc(coro-split),simplifycfg,early-cse' -S | FileCheck %s - -define void @f() #0 { -entry: - %id = call token @llvm.coro.id(i32 0, ptr null, ptr null, ptr null) - %alloc = call ptr @malloc(i64 16) #3 - %vFrame = call noalias nonnull ptr @llvm.coro.begin(token %id, ptr %alloc) - - %save = call token @llvm.coro.save(ptr null) - %addr1 = call ptr @llvm.coro.subfn.addr(ptr null, i8 0) - call fastcc void %addr1(ptr null) - - %suspend = call i8 @llvm.coro.suspend(token %save, i1 false) - switch i8 %suspend, label %exit [ - i8 0, label %await.ready - i8 1, label %exit - ] -await.ready: - %save2 = call token @llvm.coro.save(ptr null) - %addr2 = call ptr @llvm.coro.subfn.addr(ptr null, i8 0) - call fastcc void %addr2(ptr null) - - %suspend2 = call i8 @llvm.coro.suspend(token %save2, i1 false) - switch i8 %suspend2, label %exit [ - i8 0, label %exit - i8 1, label %exit - ] -exit: - call i1 @llvm.coro.end(ptr null, i1 false, token none) - ret void -} - -; Verify that in the initial function resume is not marked with musttail. -; CHECK-LABEL: @f( -; CHECK: %[[addr1:.+]] = call ptr @llvm.coro.subfn.addr(ptr null, i8 0) -; CHECK-NOT: musttail call fastcc void %[[addr1]](ptr null) - -; Verify that in the resume part resume call is marked with musttail. -; CHECK-LABEL: @f.resume( -; CHECK: %[[addr2:.+]] = call ptr @llvm.coro.subfn.addr(ptr null, i8 0) -; CHECK: call void @llvm.instrprof -; CHECK-NEXT: musttail call fastcc void %[[addr2]](ptr null) -; CHECK-NEXT: ret void - -declare token @llvm.coro.id(i32, ptr readnone, ptr nocapture readonly, ptr) #1 -declare i1 @llvm.coro.alloc(token) #2 -declare i64 @llvm.coro.size.i64() #3 -declare ptr @llvm.coro.begin(token, ptr writeonly) #2 -declare token @llvm.coro.save(ptr) #2 -declare ptr @llvm.coro.frame() #3 -declare i8 @llvm.coro.suspend(token, i1) #2 -declare ptr @llvm.coro.free(token, ptr nocapture readonly) #1 -declare i1 @llvm.coro.end(ptr, i1, token) #2 -declare ptr @llvm.coro.subfn.addr(ptr nocapture readonly, i8) #1 -declare ptr @malloc(i64) - -attributes #0 = { presplitcoroutine } -attributes #1 = { argmemonly nounwind readonly } -attributes #2 = { nounwind } -attributes #3 = { nounwind readnone } diff --git a/llvm/test/Instrumentation/InstrProfiling/Coro/coro-split-musttail1.ll b/llvm/test/Instrumentation/InstrProfiling/Coro/coro-split-musttail1.ll deleted file mode 100644 index 6098dee9a58035a9bdda368e57f0d6e6a86700cc..0000000000000000000000000000000000000000 --- a/llvm/test/Instrumentation/InstrProfiling/Coro/coro-split-musttail1.ll +++ /dev/null @@ -1,97 +0,0 @@ -; Tests that instrumentation doesn't interfere with lowering (coro-split). -; It should convert coro.resume followed by a suspend to a musttail call. - -; RUN: opt < %s -passes='pgo-instr-gen,cgscc(coro-split),simplifycfg,early-cse' -S | FileCheck %s - -define void @f() #0 { -entry: - %id = call token @llvm.coro.id(i32 0, ptr null, ptr null, ptr null) - %alloc = call ptr @malloc(i64 16) #3 - %vFrame = call noalias nonnull ptr @llvm.coro.begin(token %id, ptr %alloc) - - %save = call token @llvm.coro.save(ptr null) - %addr1 = call ptr @llvm.coro.subfn.addr(ptr null, i8 0) - call fastcc void %addr1(ptr null) - - %suspend = call i8 @llvm.coro.suspend(token %save, i1 false) - switch i8 %suspend, label %exit [ - i8 0, label %await.suspend - i8 1, label %exit - ] -await.suspend: - %save2 = call token @llvm.coro.save(ptr null) - %br0 = call i8 @switch_result() - switch i8 %br0, label %unreach [ - i8 0, label %await.resume3 - i8 1, label %await.resume1 - i8 2, label %await.resume2 - ] -await.resume1: - %hdl = call ptr @g() - %addr2 = call ptr @llvm.coro.subfn.addr(ptr %hdl, i8 0) - call fastcc void %addr2(ptr %hdl) - br label %final.suspend -await.resume2: - %hdl2 = call ptr @h() - %addr3 = call ptr @llvm.coro.subfn.addr(ptr %hdl2, i8 0) - call fastcc void %addr3(ptr %hdl2) - br label %final.suspend -await.resume3: - %addr4 = call ptr @llvm.coro.subfn.addr(ptr null, i8 0) - call fastcc void %addr4(ptr null) - br label %final.suspend -final.suspend: - %suspend2 = call i8 @llvm.coro.suspend(token %save2, i1 false) - switch i8 %suspend2, label %exit [ - i8 0, label %pre.exit - i8 1, label %exit - ] -pre.exit: - br label %exit -exit: - call i1 @llvm.coro.end(ptr null, i1 false, token none) - ret void -unreach: - unreachable -} - -; Verify that in the initial function resume is not marked with musttail. -; CHECK-LABEL: @f( -; CHECK: %[[addr1:.+]] = call ptr @llvm.coro.subfn.addr(ptr null, i8 0) -; CHECK-NOT: musttail call fastcc void %[[addr1]](ptr null) - -; Verify that in the resume part resume call is marked with musttail. -; CHECK-LABEL: @f.resume( -; CHECK: %[[hdl:.+]] = call ptr @g() -; CHECK-NEXT: %[[addr2:.+]] = call ptr @llvm.coro.subfn.addr(ptr %[[hdl]], i8 0) -; CHECK: musttail call fastcc void %[[addr2]](ptr %[[hdl]]) -; CHECK-NEXT: ret void -; CHECK: %[[hdl2:.+]] = call ptr @h() -; CHECK-NEXT: %[[addr3:.+]] = call ptr @llvm.coro.subfn.addr(ptr %[[hdl2]], i8 0) -; CHECK: musttail call fastcc void %[[addr3]](ptr %[[hdl2]]) -; CHECK-NEXT: ret void -; CHECK: %[[addr4:.+]] = call ptr @llvm.coro.subfn.addr(ptr null, i8 0) -; CHECK: musttail call fastcc void %[[addr4]](ptr null) -; CHECK-NEXT: ret void - - - -declare token @llvm.coro.id(i32, ptr readnone, ptr nocapture readonly, ptr) #1 -declare i1 @llvm.coro.alloc(token) #2 -declare i64 @llvm.coro.size.i64() #3 -declare ptr @llvm.coro.begin(token, ptr writeonly) #2 -declare token @llvm.coro.save(ptr) #2 -declare ptr @llvm.coro.frame() #3 -declare i8 @llvm.coro.suspend(token, i1) #2 -declare ptr @llvm.coro.free(token, ptr nocapture readonly) #1 -declare i1 @llvm.coro.end(ptr, i1, token) #2 -declare ptr @llvm.coro.subfn.addr(ptr nocapture readonly, i8) #1 -declare ptr @malloc(i64) -declare i8 @switch_result() -declare ptr @g() -declare ptr @h() - -attributes #0 = { presplitcoroutine } -attributes #1 = { argmemonly nounwind readonly } -attributes #2 = { nounwind } -attributes #3 = { nounwind readnone } diff --git a/llvm/test/Instrumentation/InstrProfiling/Coro/coro-split-musttail10.ll b/llvm/test/Instrumentation/InstrProfiling/Coro/coro-split-musttail10.ll deleted file mode 100644 index f43b10ebf42e5a3fdb1b47494606cb2cfa02f15b..0000000000000000000000000000000000000000 --- a/llvm/test/Instrumentation/InstrProfiling/Coro/coro-split-musttail10.ll +++ /dev/null @@ -1,55 +0,0 @@ -; Tests that instrumentation doesn't interfere with lowering (coro-split). -; It should convert coro.resume followed by a suspend to a musttail call. - -; RUN: opt < %s -passes='pgo-instr-gen,cgscc(coro-split),simplifycfg,early-cse' -S | FileCheck %s - -target triple = "wasm64-unknown-unknown" - -define void @f() #0 { -entry: - %id = call token @llvm.coro.id(i32 0, ptr null, ptr null, ptr null) - %alloc = call ptr @malloc(i64 16) #3 - %vFrame = call noalias nonnull ptr @llvm.coro.begin(token %id, ptr %alloc) - - %save = call token @llvm.coro.save(ptr null) - %addr1 = call ptr @llvm.coro.subfn.addr(ptr null, i8 0) - call fastcc void %addr1(ptr null) - - %suspend = call i8 @llvm.coro.suspend(token %save, i1 false) - switch i8 %suspend, label %exit [ - i8 0, label %await.ready - i8 1, label %exit - ] -await.ready: - %save2 = call token @llvm.coro.save(ptr null) - %addr2 = call ptr @llvm.coro.subfn.addr(ptr null, i8 0) - call fastcc void %addr2(ptr null) - - %suspend2 = call i8 @llvm.coro.suspend(token %save2, i1 false) - switch i8 %suspend2, label %exit [ - i8 0, label %exit - i8 1, label %exit - ] -exit: - call i1 @llvm.coro.end(ptr null, i1 false, token none) - ret void -} - -; CHECK: musttail call - -declare token @llvm.coro.id(i32, ptr readnone, ptr nocapture readonly, ptr) #1 -declare i1 @llvm.coro.alloc(token) #2 -declare i64 @llvm.coro.size.i64() #3 -declare ptr @llvm.coro.begin(token, ptr writeonly) #2 -declare token @llvm.coro.save(ptr) #2 -declare ptr @llvm.coro.frame() #3 -declare i8 @llvm.coro.suspend(token, i1) #2 -declare ptr @llvm.coro.free(token, ptr nocapture readonly) #1 -declare i1 @llvm.coro.end(ptr, i1, token) #2 -declare ptr @llvm.coro.subfn.addr(ptr nocapture readonly, i8) #1 -declare ptr @malloc(i64) - -attributes #0 = { presplitcoroutine "target-features"="+tail-call" } -attributes #1 = { argmemonly nounwind readonly } -attributes #2 = { nounwind } -attributes #3 = { nounwind readnone } diff --git a/llvm/test/Instrumentation/InstrProfiling/Coro/coro-split-musttail11.ll b/llvm/test/Instrumentation/InstrProfiling/Coro/coro-split-musttail11.ll deleted file mode 100644 index fc5bb9a1b20b3de11762870d05662bd44cf4b356..0000000000000000000000000000000000000000 --- a/llvm/test/Instrumentation/InstrProfiling/Coro/coro-split-musttail11.ll +++ /dev/null @@ -1,55 +0,0 @@ -; Tests that instrumentation doesn't interfere with lowering (coro-split). -; It should convert coro.resume followed by a suspend to a musttail call. - -; RUN: opt < %s -passes='pgo-instr-gen,cgscc(coro-split),simplifycfg,early-cse' -S | FileCheck %s - -target triple = "wasm32-unknown-unknown" - -define void @f() #0 { -entry: - %id = call token @llvm.coro.id(i32 0, ptr null, ptr null, ptr null) - %alloc = call ptr @malloc(i64 16) #3 - %vFrame = call noalias nonnull ptr @llvm.coro.begin(token %id, ptr %alloc) - - %save = call token @llvm.coro.save(ptr null) - %addr1 = call ptr @llvm.coro.subfn.addr(ptr null, i8 0) - call fastcc void %addr1(ptr null) - - %suspend = call i8 @llvm.coro.suspend(token %save, i1 false) - switch i8 %suspend, label %exit [ - i8 0, label %await.ready - i8 1, label %exit - ] -await.ready: - %save2 = call token @llvm.coro.save(ptr null) - %addr2 = call ptr @llvm.coro.subfn.addr(ptr null, i8 0) - call fastcc void %addr2(ptr null) - - %suspend2 = call i8 @llvm.coro.suspend(token %save2, i1 false) - switch i8 %suspend2, label %exit [ - i8 0, label %exit - i8 1, label %exit - ] -exit: - call i1 @llvm.coro.end(ptr null, i1 false, token none) - ret void -} - -; CHECK: musttail call - -declare token @llvm.coro.id(i32, ptr readnone, ptr nocapture readonly, ptr) #1 -declare i1 @llvm.coro.alloc(token) #2 -declare i64 @llvm.coro.size.i64() #3 -declare ptr @llvm.coro.begin(token, ptr writeonly) #2 -declare token @llvm.coro.save(ptr) #2 -declare ptr @llvm.coro.frame() #3 -declare i8 @llvm.coro.suspend(token, i1) #2 -declare ptr @llvm.coro.free(token, ptr nocapture readonly) #1 -declare i1 @llvm.coro.end(ptr, i1, token) #2 -declare ptr @llvm.coro.subfn.addr(ptr nocapture readonly, i8) #1 -declare ptr @malloc(i64) - -attributes #0 = { presplitcoroutine "target-features"="+tail-call" } -attributes #1 = { argmemonly nounwind readonly } -attributes #2 = { nounwind } -attributes #3 = { nounwind readnone } diff --git a/llvm/test/Instrumentation/InstrProfiling/Coro/coro-split-musttail12.ll b/llvm/test/Instrumentation/InstrProfiling/Coro/coro-split-musttail12.ll deleted file mode 100644 index 634d0106a2e6aea662112080ea0c8dd05e43969a..0000000000000000000000000000000000000000 --- a/llvm/test/Instrumentation/InstrProfiling/Coro/coro-split-musttail12.ll +++ /dev/null @@ -1,85 +0,0 @@ -; Tests that instrumentation doesn't interfere with lowering (coro-split). -; It should convert coro.resume followed by a suspend to a musttail call. - -; RUN: opt < %s -passes='pgo-instr-gen,cgscc(coro-split),simplifycfg,early-cse' -S | FileCheck %s - -declare void @fakeresume1(ptr) -declare void @print() - -define void @f(i1 %cond) #0 { -entry: - %id = call token @llvm.coro.id(i32 0, ptr null, ptr null, ptr null) - %alloc = call ptr @malloc(i64 16) #3 - %vFrame = call noalias nonnull ptr @llvm.coro.begin(token %id, ptr %alloc) - - %save = call token @llvm.coro.save(ptr null) - - %init_suspend = call i8 @llvm.coro.suspend(token %save, i1 false) - switch i8 %init_suspend, label %coro.end [ - i8 0, label %await.ready - i8 1, label %coro.end - ] -await.ready: - %save2 = call token @llvm.coro.save(ptr null) - br i1 %cond, label %then, label %else - -then: - call fastcc void @fakeresume1(ptr align 8 null) - br label %merge - -else: - br label %merge - -merge: - %v0 = phi i1 [0, %then], [1, %else] - br label %compare - -compare: - %cond.cmp = icmp eq i1 %v0, 0 - br i1 %cond.cmp, label %ready, label %prepare - -prepare: - call void @print() - br label %ready - -ready: - %suspend = call i8 @llvm.coro.suspend(token %save2, i1 true) - %switch = icmp ult i8 %suspend, 2 - br i1 %switch, label %cleanup, label %coro.end - -cleanup: - %free.handle = call ptr @llvm.coro.free(token %id, ptr %vFrame) - %.not = icmp eq ptr %free.handle, null - br i1 %.not, label %coro.end, label %coro.free - -coro.free: - call void @delete(ptr nonnull %free.handle) #2 - br label %coro.end - -coro.end: - call i1 @llvm.coro.end(ptr null, i1 false, token none) - ret void -} - -; CHECK-LABEL: @f.resume( -; CHECK-NOT: } -; CHECK: call void @print() - - -declare token @llvm.coro.id(i32, ptr readnone, ptr nocapture readonly, ptr) #1 -declare i1 @llvm.coro.alloc(token) #2 -declare i64 @llvm.coro.size.i64() #3 -declare ptr @llvm.coro.begin(token, ptr writeonly) #2 -declare token @llvm.coro.save(ptr) #2 -declare ptr @llvm.coro.frame() #3 -declare i8 @llvm.coro.suspend(token, i1) #2 -declare ptr @llvm.coro.free(token, ptr nocapture readonly) #1 -declare i1 @llvm.coro.end(ptr, i1, token) #2 -declare ptr @llvm.coro.subfn.addr(ptr nocapture readonly, i8) #1 -declare ptr @malloc(i64) -declare void @delete(ptr nonnull) #2 - -attributes #0 = { presplitcoroutine } -attributes #1 = { argmemonly nounwind readonly } -attributes #2 = { nounwind } -attributes #3 = { nounwind readnone } diff --git a/llvm/test/Instrumentation/InstrProfiling/Coro/coro-split-musttail13.ll b/llvm/test/Instrumentation/InstrProfiling/Coro/coro-split-musttail13.ll deleted file mode 100644 index 2f9a14c901071950e31d3d186d39bfdd34578a36..0000000000000000000000000000000000000000 --- a/llvm/test/Instrumentation/InstrProfiling/Coro/coro-split-musttail13.ll +++ /dev/null @@ -1,76 +0,0 @@ -; Tests that instrumentation doesn't interfere with lowering (coro-split). -; It should convert coro.resume followed by a suspend to a musttail call. - -; RUN: opt < %s -passes='pgo-instr-gen,cgscc(coro-split),simplifycfg,early-cse' -S | FileCheck %s - -declare void @fakeresume1(ptr) -declare void @may_throw(ptr) -declare void @print() - -define void @f(i1 %cond) #0 personality i32 3 { -entry: - %id = call token @llvm.coro.id(i32 0, ptr null, ptr null, ptr null) - %alloc = call ptr @malloc(i64 16) #3 - %vFrame = call noalias nonnull ptr @llvm.coro.begin(token %id, ptr %alloc) - - %save = call token @llvm.coro.save(ptr null) - - %init_suspend = call i8 @llvm.coro.suspend(token %save, i1 false) - switch i8 %init_suspend, label %coro.end [ - i8 0, label %await.ready - i8 1, label %coro.end - ] -await.ready: - call fastcc void @fakeresume1(ptr align 8 null) - invoke void @may_throw(ptr null) - to label %ready unwind label %lpad - -ready: - %save2 = call token @llvm.coro.save(ptr null) - %suspend = call i8 @llvm.coro.suspend(token %save2, i1 true) - %switch = icmp ult i8 %suspend, 2 - br i1 %switch, label %cleanup, label %coro.end - -cleanup: - %free.handle = call ptr @llvm.coro.free(token %id, ptr %vFrame) - %.not = icmp eq ptr %free.handle, null - br i1 %.not, label %coro.end, label %coro.free - -lpad: - %lpval = landingpad { ptr, i32 } - cleanup - - %need.resume = call i1 @llvm.coro.end(ptr null, i1 true, token none) - resume { ptr, i32 } %lpval - -coro.free: - call void @delete(ptr nonnull %free.handle) #2 - br label %coro.end - -coro.end: - call i1 @llvm.coro.end(ptr null, i1 false, token none) - ret void -} - -; CHECK-LABEL: @f.resume( -; CHECK-NOT: musttail call fastcc void @fakeresume1( -; CHECK: } - - -declare token @llvm.coro.id(i32, ptr readnone, ptr nocapture readonly, ptr) #1 -declare i1 @llvm.coro.alloc(token) #2 -declare i64 @llvm.coro.size.i64() #3 -declare ptr @llvm.coro.begin(token, ptr writeonly) #2 -declare token @llvm.coro.save(ptr) #2 -declare ptr @llvm.coro.frame() #3 -declare i8 @llvm.coro.suspend(token, i1) #2 -declare ptr @llvm.coro.free(token, ptr nocapture readonly) #1 -declare i1 @llvm.coro.end(ptr, i1, token) #2 -declare ptr @llvm.coro.subfn.addr(ptr nocapture readonly, i8) #1 -declare ptr @malloc(i64) -declare void @delete(ptr nonnull) #2 - -attributes #0 = { presplitcoroutine } -attributes #1 = { argmemonly nounwind readonly } -attributes #2 = { nounwind } -attributes #3 = { nounwind readnone } diff --git a/llvm/test/Instrumentation/InstrProfiling/Coro/coro-split-musttail2.ll b/llvm/test/Instrumentation/InstrProfiling/Coro/coro-split-musttail2.ll deleted file mode 100644 index 61b61a200e704d5303332d988494dd64fe35e80f..0000000000000000000000000000000000000000 --- a/llvm/test/Instrumentation/InstrProfiling/Coro/coro-split-musttail2.ll +++ /dev/null @@ -1,68 +0,0 @@ -; Tests that instrumentation doesn't interfere with lowering (coro-split). -; It should convert coro.resume followed by a suspend to a musttail call. - -; RUN: opt < %s -passes='pgo-instr-gen,cgscc(coro-split),simplifycfg,early-cse' -S | FileCheck %s - -define void @fakeresume1(ptr) { -entry: - ret void; -} - -define void @fakeresume2(ptr align 8) { -entry: - ret void; -} - -define void @g() #0 { -entry: - %id = call token @llvm.coro.id(i32 0, ptr null, ptr null, ptr null) - %alloc = call ptr @malloc(i64 16) #3 - %vFrame = call noalias nonnull ptr @llvm.coro.begin(token %id, ptr %alloc) - - %save = call token @llvm.coro.save(ptr null) - call fastcc void @fakeresume1(ptr null) - - %suspend = call i8 @llvm.coro.suspend(token %save, i1 false) - switch i8 %suspend, label %exit [ - i8 0, label %await.ready - i8 1, label %exit - ] -await.ready: - %save2 = call token @llvm.coro.save(ptr null) - call fastcc void @fakeresume2(ptr align 8 null) - - %suspend2 = call i8 @llvm.coro.suspend(token %save2, i1 false) - switch i8 %suspend2, label %exit [ - i8 0, label %exit - i8 1, label %exit - ] -exit: - call i1 @llvm.coro.end(ptr null, i1 false, token none) - ret void -} - -; Verify that in the initial function resume is not marked with musttail. -; CHECK-LABEL: @g( -; CHECK-NOT: musttail call fastcc void @fakeresume1(ptr null) - -; Verify that in the resume part resume call is marked with musttail. -; CHECK-LABEL: @g.resume( -; CHECK: musttail call fastcc void @fakeresume2(ptr align 8 null) -; CHECK-NEXT: ret void - -declare token @llvm.coro.id(i32, ptr readnone, ptr nocapture readonly, ptr) #1 -declare i1 @llvm.coro.alloc(token) #2 -declare i64 @llvm.coro.size.i64() #3 -declare ptr @llvm.coro.begin(token, ptr writeonly) #2 -declare token @llvm.coro.save(ptr) #2 -declare ptr @llvm.coro.frame() #3 -declare i8 @llvm.coro.suspend(token, i1) #2 -declare ptr @llvm.coro.free(token, ptr nocapture readonly) #1 -declare i1 @llvm.coro.end(ptr, i1, token) #2 -declare ptr @llvm.coro.subfn.addr(ptr nocapture readonly, i8) #1 -declare ptr @malloc(i64) - -attributes #0 = { presplitcoroutine } -attributes #1 = { argmemonly nounwind readonly } -attributes #2 = { nounwind } -attributes #3 = { nounwind readnone } diff --git a/llvm/test/Instrumentation/InstrProfiling/Coro/coro-split-musttail3.ll b/llvm/test/Instrumentation/InstrProfiling/Coro/coro-split-musttail3.ll deleted file mode 100644 index 82176b8085e6c7bac75bd1b446e0fb8f04104242..0000000000000000000000000000000000000000 --- a/llvm/test/Instrumentation/InstrProfiling/Coro/coro-split-musttail3.ll +++ /dev/null @@ -1,91 +0,0 @@ -; Tests that instrumentation doesn't interfere with lowering (coro-split). -; It should convert coro.resume followed by a suspend to a musttail call. - -; RUN: opt < %s -passes='pgo-instr-gen,cgscc(coro-split),simplifycfg,early-cse' -S | FileCheck %s - -define void @f() #0 { -entry: - %id = call token @llvm.coro.id(i32 0, ptr null, ptr null, ptr null) - %alloc = call ptr @malloc(i64 16) #3 - %vFrame = call noalias nonnull ptr @llvm.coro.begin(token %id, ptr %alloc) - - %save = call token @llvm.coro.save(ptr null) - %addr1 = call ptr @llvm.coro.subfn.addr(ptr null, i8 0) - call fastcc void %addr1(ptr null) - - %suspend = call i8 @llvm.coro.suspend(token %save, i1 false) - %cmp = icmp eq i8 %suspend, 0 - br i1 %cmp, label %await.suspend, label %exit -await.suspend: - %save2 = call token @llvm.coro.save(ptr null) - %br0 = call i8 @switch_result() - switch i8 %br0, label %unreach [ - i8 0, label %await.resume3 - i8 1, label %await.resume1 - i8 2, label %await.resume2 - ] -await.resume1: - %hdl = call ptr @g() - %addr2 = call ptr @llvm.coro.subfn.addr(ptr %hdl, i8 0) - call fastcc void %addr2(ptr %hdl) - br label %final.suspend -await.resume2: - %hdl2 = call ptr @h() - %addr3 = call ptr @llvm.coro.subfn.addr(ptr %hdl2, i8 0) - call fastcc void %addr3(ptr %hdl2) - br label %final.suspend -await.resume3: - %addr4 = call ptr @llvm.coro.subfn.addr(ptr null, i8 0) - call fastcc void %addr4(ptr null) - br label %final.suspend -final.suspend: - %suspend2 = call i8 @llvm.coro.suspend(token %save2, i1 false) - %cmp2 = icmp eq i8 %suspend2, 0 - br i1 %cmp2, label %pre.exit, label %exit -pre.exit: - br label %exit -exit: - call i1 @llvm.coro.end(ptr null, i1 false, token none) - ret void -unreach: - unreachable -} - -; Verify that in the initial function resume is not marked with musttail. -; CHECK-LABEL: @f( -; CHECK: %[[addr1:.+]] = call ptr @llvm.coro.subfn.addr(ptr null, i8 0) -; CHECK-NOT: musttail call fastcc void %[[addr1]](ptr null) - -; Verify that in the resume part resume call is marked with musttail. -; CHECK-LABEL: @f.resume( -; CHECK: %[[hdl:.+]] = call ptr @g() -; CHECK-NEXT: %[[addr2:.+]] = call ptr @llvm.coro.subfn.addr(ptr %[[hdl]], i8 0) -; CHECK: musttail call fastcc void %[[addr2]](ptr %[[hdl]]) -; CHECK-NEXT: ret void -; CHECK: %[[hdl2:.+]] = call ptr @h() -; CHECK-NEXT: %[[addr3:.+]] = call ptr @llvm.coro.subfn.addr(ptr %[[hdl2]], i8 0) -; CHECK: musttail call fastcc void %[[addr3]](ptr %[[hdl2]]) -; CHECK-NEXT: ret void -; CHECK: %[[addr4:.+]] = call ptr @llvm.coro.subfn.addr(ptr null, i8 0) -; CHECK: musttail call fastcc void %[[addr4]](ptr null) -; CHECK-NEXT: ret void - -declare token @llvm.coro.id(i32, ptr readnone, ptr nocapture readonly, ptr) #1 -declare i1 @llvm.coro.alloc(token) #2 -declare i64 @llvm.coro.size.i64() #3 -declare ptr @llvm.coro.begin(token, ptr writeonly) #2 -declare token @llvm.coro.save(ptr) #2 -declare ptr @llvm.coro.frame() #3 -declare i8 @llvm.coro.suspend(token, i1) #2 -declare ptr @llvm.coro.free(token, ptr nocapture readonly) #1 -declare i1 @llvm.coro.end(ptr, i1, token) #2 -declare ptr @llvm.coro.subfn.addr(ptr nocapture readonly, i8) #1 -declare ptr @malloc(i64) -declare i8 @switch_result() -declare ptr @g() -declare ptr @h() - -attributes #0 = { presplitcoroutine } -attributes #1 = { argmemonly nounwind readonly } -attributes #2 = { nounwind } -attributes #3 = { nounwind readnone } diff --git a/llvm/test/Instrumentation/InstrProfiling/Coro/coro-split-musttail4.ll b/llvm/test/Instrumentation/InstrProfiling/Coro/coro-split-musttail4.ll deleted file mode 100644 index be70fc4b51f1db4eb50b2c55bb6f1f3e3c558022..0000000000000000000000000000000000000000 --- a/llvm/test/Instrumentation/InstrProfiling/Coro/coro-split-musttail4.ll +++ /dev/null @@ -1,66 +0,0 @@ -; Tests that instrumentation doesn't interfere with lowering (coro-split). -; It should convert coro.resume followed by a suspend to a musttail call. - -; RUN: opt < %s -passes='pgo-instr-gen,cgscc(coro-split),simplifycfg,early-cse' -S | FileCheck %s - -define void @fakeresume1(ptr) { -entry: - ret void; -} - -define void @f() #0 { -entry: - %id = call token @llvm.coro.id(i32 0, ptr null, ptr null, ptr null) - %alloc = call ptr @malloc(i64 16) #3 - %vFrame = call noalias nonnull ptr @llvm.coro.begin(token %id, ptr %alloc) - - %save = call token @llvm.coro.save(ptr null) - - %init_suspend = call i8 @llvm.coro.suspend(token %save, i1 false) - switch i8 %init_suspend, label %coro.end [ - i8 0, label %await.ready - i8 1, label %coro.end - ] -await.ready: - %save2 = call token @llvm.coro.save(ptr null) - - call fastcc void @fakeresume1(ptr align 8 null) - %suspend = call i8 @llvm.coro.suspend(token %save2, i1 true) - %switch = icmp ult i8 %suspend, 2 - br i1 %switch, label %cleanup, label %coro.end - -cleanup: - %free.handle = call ptr @llvm.coro.free(token %id, ptr %vFrame) - %.not = icmp eq ptr %free.handle, null - br i1 %.not, label %coro.end, label %coro.free - -coro.free: - call void @delete(ptr nonnull %free.handle) #2 - br label %coro.end - -coro.end: - call i1 @llvm.coro.end(ptr null, i1 false, token none) - ret void -} - -; CHECK-LABEL: @f.resume( -; CHECK: musttail call fastcc void @fakeresume1( -; CHECK-NEXT: ret void - -declare token @llvm.coro.id(i32, ptr readnone, ptr nocapture readonly, ptr) #1 -declare i1 @llvm.coro.alloc(token) #2 -declare i64 @llvm.coro.size.i64() #3 -declare ptr @llvm.coro.begin(token, ptr writeonly) #2 -declare token @llvm.coro.save(ptr) #2 -declare ptr @llvm.coro.frame() #3 -declare i8 @llvm.coro.suspend(token, i1) #2 -declare ptr @llvm.coro.free(token, ptr nocapture readonly) #1 -declare i1 @llvm.coro.end(ptr, i1, token) #2 -declare ptr @llvm.coro.subfn.addr(ptr nocapture readonly, i8) #1 -declare ptr @malloc(i64) -declare void @delete(ptr nonnull) #2 - -attributes #0 = { presplitcoroutine } -attributes #1 = { argmemonly nounwind readonly } -attributes #2 = { nounwind } -attributes #3 = { nounwind readnone } diff --git a/llvm/test/Instrumentation/InstrProfiling/Coro/coro-split-musttail5.ll b/llvm/test/Instrumentation/InstrProfiling/Coro/coro-split-musttail5.ll deleted file mode 100644 index 3e5bddd8e13112db495881bd28b3d8450b9281f6..0000000000000000000000000000000000000000 --- a/llvm/test/Instrumentation/InstrProfiling/Coro/coro-split-musttail5.ll +++ /dev/null @@ -1,63 +0,0 @@ -; Tests that instrumentation doesn't interfere with lowering (coro-split). -; It should convert coro.resume followed by a suspend to a musttail call. - -; RUN: opt < %s -passes='pgo-instr-gen,cgscc(coro-split),simplifycfg,early-cse' -S | FileCheck %s - -declare void @fakeresume1(ptr align 8) - -define void @g() #0 { -entry: - %id = call token @llvm.coro.id(i32 0, ptr null, ptr null, ptr null) - %alloc = call ptr @malloc(i64 16) #3 - %alloc.var = alloca i8 - call void @llvm.lifetime.start.p0(i64 1, ptr %alloc.var) - %vFrame = call noalias nonnull ptr @llvm.coro.begin(token %id, ptr %alloc) - - %save = call token @llvm.coro.save(ptr null) - %suspend = call i8 @llvm.coro.suspend(token %save, i1 false) - - switch i8 %suspend, label %exit [ - i8 0, label %await.suspend - i8 1, label %exit - ] -await.suspend: - %save2 = call token @llvm.coro.save(ptr null) - call fastcc void @fakeresume1(ptr align 8 null) - %suspend2 = call i8 @llvm.coro.suspend(token %save2, i1 false) - switch i8 %suspend2, label %exit [ - i8 0, label %await.ready - i8 1, label %exit - ] -await.ready: - call void @consume(ptr %alloc.var) - call void @llvm.lifetime.end.p0(i64 1, ptr %alloc.var) - br label %exit -exit: - call i1 @llvm.coro.end(ptr null, i1 false, token none) - ret void -} - -; Verify that in the resume part resume call is marked with musttail. -; CHECK-LABEL: @g.resume( -; CHECK: musttail call fastcc void @fakeresume1(ptr align 8 null) -; CHECK-NEXT: ret void - -declare token @llvm.coro.id(i32, ptr readnone, ptr nocapture readonly, ptr) #1 -declare i1 @llvm.coro.alloc(token) #2 -declare i64 @llvm.coro.size.i64() #3 -declare ptr @llvm.coro.begin(token, ptr writeonly) #2 -declare token @llvm.coro.save(ptr) #2 -declare ptr @llvm.coro.frame() #3 -declare i8 @llvm.coro.suspend(token, i1) #2 -declare ptr @llvm.coro.free(token, ptr nocapture readonly) #1 -declare i1 @llvm.coro.end(ptr, i1, token) #2 -declare ptr @llvm.coro.subfn.addr(ptr nocapture readonly, i8) #1 -declare ptr @malloc(i64) -declare void @consume(ptr) -declare void @llvm.lifetime.start.p0(i64, ptr nocapture) -declare void @llvm.lifetime.end.p0(i64, ptr nocapture) - -attributes #0 = { presplitcoroutine } -attributes #1 = { argmemonly nounwind readonly } -attributes #2 = { nounwind } -attributes #3 = { nounwind readnone } diff --git a/llvm/test/Instrumentation/InstrProfiling/Coro/coro-split-musttail6.ll b/llvm/test/Instrumentation/InstrProfiling/Coro/coro-split-musttail6.ll deleted file mode 100644 index 4359d5305d4d91cdb8a55bfd39faff9203507f87..0000000000000000000000000000000000000000 --- a/llvm/test/Instrumentation/InstrProfiling/Coro/coro-split-musttail6.ll +++ /dev/null @@ -1,112 +0,0 @@ -; Tests that instrumentation doesn't interfere with lowering (coro-split). -; It should convert coro.resume followed by a suspend to a musttail call. - -; RUN: opt < %s -passes='pgo-instr-gen,cgscc(coro-split),simplifycfg,early-cse' -S | FileCheck %s - -declare void @fakeresume1(ptr align 8) - -define void @g() #0 { -entry: - %id = call token @llvm.coro.id(i32 0, ptr null, ptr null, ptr null) - %alloc = call ptr @malloc(i64 16) #3 - %alloc.var = alloca i64 - call void @llvm.lifetime.start.p0(i64 1, ptr %alloc.var) - %vFrame = call noalias nonnull ptr @llvm.coro.begin(token %id, ptr %alloc) - - %save = call token @llvm.coro.save(ptr null) - %suspend = call i8 @llvm.coro.suspend(token %save, i1 false) - - switch i8 %suspend, label %exit [ - i8 0, label %await.suspend - i8 1, label %exit - ] -await.suspend: - %save2 = call token @llvm.coro.save(ptr null) - call fastcc void @fakeresume1(ptr align 8 null) - %suspend2 = call i8 @llvm.coro.suspend(token %save2, i1 false) - switch i8 %suspend2, label %exit [ - i8 0, label %await.ready - i8 1, label %exit - ] -await.ready: - call void @consume(ptr %alloc.var) - call void @llvm.lifetime.end.p0(i64 1, ptr %alloc.var) - br label %exit -exit: - call i1 @llvm.coro.end(ptr null, i1 false, token none) - ret void -} - -; Verify that in the resume part resume call is marked with musttail. -; CHECK-LABEL: @g.resume( -; CHECK: musttail call fastcc void @fakeresume1(ptr align 8 null) -; CHECK-NEXT: ret void - -; It has a cleanup bb. -define void @f() #0 { -entry: - %id = call token @llvm.coro.id(i32 0, ptr null, ptr null, ptr null) - %alloc = call ptr @malloc(i64 16) #3 - %alloc.var = alloca i64 - call void @llvm.lifetime.start.p0(i64 1, ptr %alloc.var) - %vFrame = call noalias nonnull ptr @llvm.coro.begin(token %id, ptr %alloc) - - %save = call token @llvm.coro.save(ptr null) - %suspend = call i8 @llvm.coro.suspend(token %save, i1 false) - - switch i8 %suspend, label %exit [ - i8 0, label %await.suspend - i8 1, label %exit - ] -await.suspend: - %save2 = call token @llvm.coro.save(ptr null) - call fastcc void @fakeresume1(ptr align 8 null) - %suspend2 = call i8 @llvm.coro.suspend(token %save2, i1 false) - switch i8 %suspend2, label %exit [ - i8 0, label %await.ready - i8 1, label %cleanup - ] -await.ready: - call void @consume(ptr %alloc.var) - call void @llvm.lifetime.end.p0(i64 1, ptr %alloc.var) - br label %exit - -cleanup: - %free.handle = call ptr @llvm.coro.free(token %id, ptr %vFrame) - %.not = icmp eq ptr %free.handle, null - br i1 %.not, label %exit, label %coro.free - -coro.free: - call void @delete(ptr nonnull %free.handle) #2 - br label %exit - -exit: - call i1 @llvm.coro.end(ptr null, i1 false, token none) - ret void -} - -; Verify that in the resume part resume call is marked with musttail. -; CHECK-LABEL: @f.resume( -; CHECK: musttail call fastcc void @fakeresume1(ptr align 8 null) -; CHECK-NEXT: ret void - -declare token @llvm.coro.id(i32, ptr readnone, ptr nocapture readonly, ptr) #1 -declare i1 @llvm.coro.alloc(token) #2 -declare i64 @llvm.coro.size.i64() #3 -declare ptr @llvm.coro.begin(token, ptr writeonly) #2 -declare token @llvm.coro.save(ptr) #2 -declare ptr @llvm.coro.frame() #3 -declare i8 @llvm.coro.suspend(token, i1) #2 -declare ptr @llvm.coro.free(token, ptr nocapture readonly) #1 -declare i1 @llvm.coro.end(ptr, i1, token) #2 -declare ptr @llvm.coro.subfn.addr(ptr nocapture readonly, i8) #1 -declare ptr @malloc(i64) -declare void @delete(ptr nonnull) #2 -declare void @consume(ptr) -declare void @llvm.lifetime.start.p0(i64, ptr nocapture) -declare void @llvm.lifetime.end.p0(i64, ptr nocapture) - -attributes #0 = { presplitcoroutine } -attributes #1 = { argmemonly nounwind readonly } -attributes #2 = { nounwind } -attributes #3 = { nounwind readnone } diff --git a/llvm/test/Instrumentation/InstrProfiling/Coro/coro-split-musttail7.ll b/llvm/test/Instrumentation/InstrProfiling/Coro/coro-split-musttail7.ll deleted file mode 100644 index 2a14be0f921806e7c380f9cb4f3d30f170df15f5..0000000000000000000000000000000000000000 --- a/llvm/test/Instrumentation/InstrProfiling/Coro/coro-split-musttail7.ll +++ /dev/null @@ -1,115 +0,0 @@ -; Tests that instrumentation doesn't interfere with lowering (coro-split). -; It should convert coro.resume followed by a suspend to a musttail call. - -; The difference between this and coro-split-musttail5.ll and coro-split-musttail5.ll -; is that this contains dead instruction generated during the transformation, -; which makes the optimization harder. -; RUN: opt < %s -passes='pgo-instr-gen,cgscc(coro-split),simplifycfg,early-cse' -S | FileCheck %s - -declare void @fakeresume1(ptr align 8) - -define void @g() #0 { -entry: - %id = call token @llvm.coro.id(i32 0, ptr null, ptr null, ptr null) - %alloc = call ptr @malloc(i64 16) #3 - %alloc.var = alloca i64 - call void @llvm.lifetime.start.p0(i64 1, ptr %alloc.var) - %vFrame = call noalias nonnull ptr @llvm.coro.begin(token %id, ptr %alloc) - - %save = call token @llvm.coro.save(ptr null) - %suspend = call i8 @llvm.coro.suspend(token %save, i1 false) - - switch i8 %suspend, label %exit [ - i8 0, label %await.suspend - i8 1, label %exit - ] -await.suspend: - %save2 = call token @llvm.coro.save(ptr null) - call fastcc void @fakeresume1(ptr align 8 null) - %suspend2 = call i8 @llvm.coro.suspend(token %save2, i1 false) - switch i8 %suspend2, label %exit [ - i8 0, label %await.ready - i8 1, label %exit - ] -await.ready: - call void @consume(ptr %alloc.var) - call void @llvm.lifetime.end.p0(i64 1, ptr %alloc.var) - br label %exit -exit: - call i1 @llvm.coro.end(ptr null, i1 false, token none) - ret void -} - -; Verify that in the resume part resume call is marked with musttail. -; CHECK-LABEL: @g.resume( -; CHECK: musttail call fastcc void @fakeresume1(ptr align 8 null) -; CHECK-NEXT: ret void - -; It has a cleanup bb. -define void @f() #0 { -entry: - %id = call token @llvm.coro.id(i32 0, ptr null, ptr null, ptr null) - %alloc = call ptr @malloc(i64 16) #3 - %alloc.var = alloca i64 - call void @llvm.lifetime.start.p0(i64 1, ptr %alloc.var) - %vFrame = call noalias nonnull ptr @llvm.coro.begin(token %id, ptr %alloc) - - %save = call token @llvm.coro.save(ptr null) - %suspend = call i8 @llvm.coro.suspend(token %save, i1 false) - - switch i8 %suspend, label %exit [ - i8 0, label %await.suspend - i8 1, label %exit - ] -await.suspend: - %save2 = call token @llvm.coro.save(ptr null) - call fastcc void @fakeresume1(ptr align 8 null) - %suspend2 = call i8 @llvm.coro.suspend(token %save2, i1 false) - switch i8 %suspend2, label %exit [ - i8 0, label %await.ready - i8 1, label %cleanup - ] -await.ready: - call void @consume(ptr %alloc.var) - call void @llvm.lifetime.end.p0(i64 1, ptr %alloc.var) - br label %exit - -cleanup: - %free.handle = call ptr @llvm.coro.free(token %id, ptr %vFrame) - %.not = icmp eq ptr %free.handle, null - br i1 %.not, label %exit, label %coro.free - -coro.free: - call void @delete(ptr nonnull %free.handle) #2 - br label %exit - -exit: - call i1 @llvm.coro.end(ptr null, i1 false, token none) - ret void -} - -; Verify that in the resume part resume call is marked with musttail. -; CHECK-LABEL: @f.resume( -; CHECK: musttail call fastcc void @fakeresume1(ptr align 8 null) -; CHECK-NEXT: ret void - -declare token @llvm.coro.id(i32, ptr readnone, ptr nocapture readonly, ptr) #1 -declare i1 @llvm.coro.alloc(token) #2 -declare i64 @llvm.coro.size.i64() #3 -declare ptr @llvm.coro.begin(token, ptr writeonly) #2 -declare token @llvm.coro.save(ptr) #2 -declare ptr @llvm.coro.frame() #3 -declare i8 @llvm.coro.suspend(token, i1) #2 -declare ptr @llvm.coro.free(token, ptr nocapture readonly) #1 -declare i1 @llvm.coro.end(ptr, i1, token) #2 -declare ptr @llvm.coro.subfn.addr(ptr nocapture readonly, i8) #1 -declare ptr @malloc(i64) -declare void @delete(ptr nonnull) #2 -declare void @consume(ptr) -declare void @llvm.lifetime.start.p0(i64, ptr nocapture) -declare void @llvm.lifetime.end.p0(i64, ptr nocapture) - -attributes #0 = { presplitcoroutine } -attributes #1 = { argmemonly nounwind readonly } -attributes #2 = { nounwind } -attributes #3 = { nounwind readnone } diff --git a/llvm/test/Instrumentation/MemorySanitizer/X86/mmx-intrinsics.ll b/llvm/test/Instrumentation/MemorySanitizer/X86/mmx-intrinsics.ll new file mode 100644 index 0000000000000000000000000000000000000000..39b2b6225d8b102d3337d17a8e726c155094bc70 --- /dev/null +++ b/llvm/test/Instrumentation/MemorySanitizer/X86/mmx-intrinsics.ll @@ -0,0 +1,3617 @@ +; NOTE: Assertions have been autogenerated by utils/update_test_checks.py UTC_ARGS: --version 4 +; RUN: opt %s -S -passes=msan 2>&1 | FileCheck %s + +target datalayout = "e-m:o-p270:32:32-p271:32:32-p272:64:64-i64:64-f80:128-n8:16:32:64-S128" +target triple = "x86_64-unknown-linux-gnu" + +declare x86_mmx @llvm.x86.ssse3.phadd.w(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test1(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test1( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1:[0-9]+]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP9:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <1 x i64> [[TMP9]] to <4 x i16> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <4 x i16> +; CHECK-NEXT: [[TMP13:%.*]] = bitcast <1 x i64> [[TMP10]] to <4 x i16> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <4 x i16> +; CHECK-NEXT: [[TMP16:%.*]] = bitcast <4 x i16> [[TMP13]] to i64 +; CHECK-NEXT: [[TMP2:%.*]] = bitcast <4 x i16> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP8:%.*]] = bitcast <4 x i16> [[TMP12]] to i64 +; CHECK-NEXT: [[TMP3:%.*]] = bitcast <4 x i16> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP16]], [[TMP8]] +; CHECK-NEXT: [[TMP4:%.*]] = tail call x86_mmx @llvm.x86.ssse3.phadd.w(x86_mmx [[TMP2]], x86_mmx [[TMP3]]) #[[ATTR5:[0-9]+]] +; CHECK-NEXT: [[TMP11:%.*]] = bitcast i64 [[_MSPROP]] to <4 x i16> +; CHECK-NEXT: [[TMP5:%.*]] = bitcast x86_mmx [[TMP4]] to <4 x i16> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <4 x i16> [[TMP11]] to <1 x i64> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <4 x i16> [[TMP5]] to <1 x i64> +; CHECK-NEXT: [[TMP7:%.*]] = extractelement <1 x i64> [[TMP6]], i32 0 +; CHECK-NEXT: [[TMP15:%.*]] = extractelement <1 x i64> [[TMP14]], i32 0 +; CHECK-NEXT: store i64 [[TMP7]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP15]] +; +entry: + %0 = bitcast <1 x i64> %b to <4 x i16> + %1 = bitcast <1 x i64> %a to <4 x i16> + %2 = bitcast <4 x i16> %1 to x86_mmx + %3 = bitcast <4 x i16> %0 to x86_mmx + %4 = tail call x86_mmx @llvm.x86.ssse3.phadd.w(x86_mmx %2, x86_mmx %3) nounwind readnone + %5 = bitcast x86_mmx %4 to <4 x i16> + %6 = bitcast <4 x i16> %5 to <1 x i64> + %7 = extractelement <1 x i64> %6, i32 0 + ret i64 %7 +} + +declare x86_mmx @llvm.x86.mmx.pcmpgt.d(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test88(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test88( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP8:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP11:%.*]] = bitcast <1 x i64> [[TMP8]] to <2 x i32> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <2 x i32> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <1 x i64> [[TMP10]] to <2 x i32> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <2 x i32> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <2 x i32> [[TMP14]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <2 x i32> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP7:%.*]] = bitcast <2 x i32> [[TMP11]] to i64 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast <2 x i32> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP6]], [[TMP7]] +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.mmx.pcmpgt.d(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2:[0-9]+]] +; CHECK-NEXT: [[TMP9:%.*]] = bitcast i64 [[_MSPROP]] to <2 x i32> +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to <2 x i32> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast <2 x i32> [[TMP9]] to <1 x i64> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <2 x i32> [[TMP3]] to <1 x i64> +; CHECK-NEXT: [[TMP5:%.*]] = extractelement <1 x i64> [[TMP4]], i32 0 +; CHECK-NEXT: [[TMP13:%.*]] = extractelement <1 x i64> [[TMP12]], i32 0 +; CHECK-NEXT: store i64 [[TMP5]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP13]] +; +entry: + %0 = bitcast <1 x i64> %b to <2 x i32> + %1 = bitcast <1 x i64> %a to <2 x i32> + %mmx_var.i = bitcast <2 x i32> %1 to x86_mmx + %mmx_var1.i = bitcast <2 x i32> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.pcmpgt.d(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <2 x i32> + %4 = bitcast <2 x i32> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.mmx.pcmpgt.w(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test87(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test87( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP8:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP11:%.*]] = bitcast <1 x i64> [[TMP8]] to <4 x i16> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <4 x i16> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <1 x i64> [[TMP10]] to <4 x i16> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <4 x i16> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <4 x i16> [[TMP14]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <4 x i16> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP7:%.*]] = bitcast <4 x i16> [[TMP11]] to i64 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast <4 x i16> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP6]], [[TMP7]] +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.mmx.pcmpgt.w(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP9:%.*]] = bitcast i64 [[_MSPROP]] to <4 x i16> +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to <4 x i16> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast <4 x i16> [[TMP9]] to <1 x i64> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <4 x i16> [[TMP3]] to <1 x i64> +; CHECK-NEXT: [[TMP5:%.*]] = extractelement <1 x i64> [[TMP4]], i32 0 +; CHECK-NEXT: [[TMP13:%.*]] = extractelement <1 x i64> [[TMP12]], i32 0 +; CHECK-NEXT: store i64 [[TMP5]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP13]] +; +entry: + %0 = bitcast <1 x i64> %b to <4 x i16> + %1 = bitcast <1 x i64> %a to <4 x i16> + %mmx_var.i = bitcast <4 x i16> %1 to x86_mmx + %mmx_var1.i = bitcast <4 x i16> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.pcmpgt.w(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <4 x i16> + %4 = bitcast <4 x i16> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.mmx.pcmpgt.b(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test86(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test86( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP8:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP11:%.*]] = bitcast <1 x i64> [[TMP8]] to <8 x i8> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <8 x i8> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <1 x i64> [[TMP10]] to <8 x i8> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <8 x i8> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <8 x i8> [[TMP14]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <8 x i8> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP7:%.*]] = bitcast <8 x i8> [[TMP11]] to i64 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast <8 x i8> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP6]], [[TMP7]] +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.mmx.pcmpgt.b(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP9:%.*]] = bitcast i64 [[_MSPROP]] to <8 x i8> +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to <8 x i8> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast <8 x i8> [[TMP9]] to <1 x i64> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <8 x i8> [[TMP3]] to <1 x i64> +; CHECK-NEXT: [[TMP5:%.*]] = extractelement <1 x i64> [[TMP4]], i32 0 +; CHECK-NEXT: [[TMP13:%.*]] = extractelement <1 x i64> [[TMP12]], i32 0 +; CHECK-NEXT: store i64 [[TMP5]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP13]] +; +entry: + %0 = bitcast <1 x i64> %b to <8 x i8> + %1 = bitcast <1 x i64> %a to <8 x i8> + %mmx_var.i = bitcast <8 x i8> %1 to x86_mmx + %mmx_var1.i = bitcast <8 x i8> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.pcmpgt.b(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <8 x i8> + %4 = bitcast <8 x i8> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.mmx.pcmpeq.d(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test85(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test85( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP8:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP11:%.*]] = bitcast <1 x i64> [[TMP8]] to <2 x i32> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <2 x i32> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <1 x i64> [[TMP10]] to <2 x i32> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <2 x i32> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <2 x i32> [[TMP14]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <2 x i32> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP7:%.*]] = bitcast <2 x i32> [[TMP11]] to i64 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast <2 x i32> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP6]], [[TMP7]] +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.mmx.pcmpeq.d(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP9:%.*]] = bitcast i64 [[_MSPROP]] to <2 x i32> +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to <2 x i32> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast <2 x i32> [[TMP9]] to <1 x i64> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <2 x i32> [[TMP3]] to <1 x i64> +; CHECK-NEXT: [[TMP5:%.*]] = extractelement <1 x i64> [[TMP4]], i32 0 +; CHECK-NEXT: [[TMP13:%.*]] = extractelement <1 x i64> [[TMP12]], i32 0 +; CHECK-NEXT: store i64 [[TMP5]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP13]] +; +entry: + %0 = bitcast <1 x i64> %b to <2 x i32> + %1 = bitcast <1 x i64> %a to <2 x i32> + %mmx_var.i = bitcast <2 x i32> %1 to x86_mmx + %mmx_var1.i = bitcast <2 x i32> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.pcmpeq.d(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <2 x i32> + %4 = bitcast <2 x i32> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.mmx.pcmpeq.w(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test84(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test84( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP8:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP11:%.*]] = bitcast <1 x i64> [[TMP8]] to <4 x i16> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <4 x i16> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <1 x i64> [[TMP10]] to <4 x i16> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <4 x i16> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <4 x i16> [[TMP14]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <4 x i16> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP7:%.*]] = bitcast <4 x i16> [[TMP11]] to i64 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast <4 x i16> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP6]], [[TMP7]] +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.mmx.pcmpeq.w(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP9:%.*]] = bitcast i64 [[_MSPROP]] to <4 x i16> +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to <4 x i16> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast <4 x i16> [[TMP9]] to <1 x i64> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <4 x i16> [[TMP3]] to <1 x i64> +; CHECK-NEXT: [[TMP5:%.*]] = extractelement <1 x i64> [[TMP4]], i32 0 +; CHECK-NEXT: [[TMP13:%.*]] = extractelement <1 x i64> [[TMP12]], i32 0 +; CHECK-NEXT: store i64 [[TMP5]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP13]] +; +entry: + %0 = bitcast <1 x i64> %b to <4 x i16> + %1 = bitcast <1 x i64> %a to <4 x i16> + %mmx_var.i = bitcast <4 x i16> %1 to x86_mmx + %mmx_var1.i = bitcast <4 x i16> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.pcmpeq.w(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <4 x i16> + %4 = bitcast <4 x i16> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.mmx.pcmpeq.b(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test83(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test83( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP8:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP11:%.*]] = bitcast <1 x i64> [[TMP8]] to <8 x i8> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <8 x i8> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <1 x i64> [[TMP10]] to <8 x i8> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <8 x i8> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <8 x i8> [[TMP14]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <8 x i8> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP7:%.*]] = bitcast <8 x i8> [[TMP11]] to i64 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast <8 x i8> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP6]], [[TMP7]] +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.mmx.pcmpeq.b(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP9:%.*]] = bitcast i64 [[_MSPROP]] to <8 x i8> +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to <8 x i8> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast <8 x i8> [[TMP9]] to <1 x i64> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <8 x i8> [[TMP3]] to <1 x i64> +; CHECK-NEXT: [[TMP5:%.*]] = extractelement <1 x i64> [[TMP4]], i32 0 +; CHECK-NEXT: [[TMP13:%.*]] = extractelement <1 x i64> [[TMP12]], i32 0 +; CHECK-NEXT: store i64 [[TMP5]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP13]] +; +entry: + %0 = bitcast <1 x i64> %b to <8 x i8> + %1 = bitcast <1 x i64> %a to <8 x i8> + %mmx_var.i = bitcast <8 x i8> %1 to x86_mmx + %mmx_var1.i = bitcast <8 x i8> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.pcmpeq.b(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <8 x i8> + %4 = bitcast <8 x i8> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.mmx.punpckldq(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test82(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test82( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP8:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP11:%.*]] = bitcast <1 x i64> [[TMP8]] to <2 x i32> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <2 x i32> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <1 x i64> [[TMP10]] to <2 x i32> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <2 x i32> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <2 x i32> [[TMP14]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <2 x i32> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP7:%.*]] = bitcast <2 x i32> [[TMP11]] to i64 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast <2 x i32> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP6]], [[TMP7]] +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.mmx.punpckldq(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP9:%.*]] = bitcast i64 [[_MSPROP]] to <2 x i32> +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to <2 x i32> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast <2 x i32> [[TMP9]] to <1 x i64> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <2 x i32> [[TMP3]] to <1 x i64> +; CHECK-NEXT: [[TMP5:%.*]] = extractelement <1 x i64> [[TMP4]], i32 0 +; CHECK-NEXT: [[TMP13:%.*]] = extractelement <1 x i64> [[TMP12]], i32 0 +; CHECK-NEXT: store i64 [[TMP5]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP13]] +; +entry: + %0 = bitcast <1 x i64> %b to <2 x i32> + %1 = bitcast <1 x i64> %a to <2 x i32> + %mmx_var.i = bitcast <2 x i32> %1 to x86_mmx + %mmx_var1.i = bitcast <2 x i32> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.punpckldq(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <2 x i32> + %4 = bitcast <2 x i32> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.mmx.punpcklwd(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test81(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test81( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP8:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP11:%.*]] = bitcast <1 x i64> [[TMP8]] to <4 x i16> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <4 x i16> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <1 x i64> [[TMP10]] to <4 x i16> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <4 x i16> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <4 x i16> [[TMP14]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <4 x i16> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP7:%.*]] = bitcast <4 x i16> [[TMP11]] to i64 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast <4 x i16> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP6]], [[TMP7]] +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.mmx.punpcklwd(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP9:%.*]] = bitcast i64 [[_MSPROP]] to <4 x i16> +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to <4 x i16> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast <4 x i16> [[TMP9]] to <1 x i64> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <4 x i16> [[TMP3]] to <1 x i64> +; CHECK-NEXT: [[TMP5:%.*]] = extractelement <1 x i64> [[TMP4]], i32 0 +; CHECK-NEXT: [[TMP13:%.*]] = extractelement <1 x i64> [[TMP12]], i32 0 +; CHECK-NEXT: store i64 [[TMP5]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP13]] +; +entry: + %0 = bitcast <1 x i64> %b to <4 x i16> + %1 = bitcast <1 x i64> %a to <4 x i16> + %mmx_var.i = bitcast <4 x i16> %1 to x86_mmx + %mmx_var1.i = bitcast <4 x i16> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.punpcklwd(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <4 x i16> + %4 = bitcast <4 x i16> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.mmx.punpcklbw(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test80(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test80( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP8:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP11:%.*]] = bitcast <1 x i64> [[TMP8]] to <8 x i8> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <8 x i8> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <1 x i64> [[TMP10]] to <8 x i8> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <8 x i8> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <8 x i8> [[TMP14]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <8 x i8> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP7:%.*]] = bitcast <8 x i8> [[TMP11]] to i64 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast <8 x i8> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP6]], [[TMP7]] +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.mmx.punpcklbw(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP9:%.*]] = bitcast i64 [[_MSPROP]] to <8 x i8> +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to <8 x i8> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast <8 x i8> [[TMP9]] to <1 x i64> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <8 x i8> [[TMP3]] to <1 x i64> +; CHECK-NEXT: [[TMP5:%.*]] = extractelement <1 x i64> [[TMP4]], i32 0 +; CHECK-NEXT: [[TMP13:%.*]] = extractelement <1 x i64> [[TMP12]], i32 0 +; CHECK-NEXT: store i64 [[TMP5]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP13]] +; +entry: + %0 = bitcast <1 x i64> %b to <8 x i8> + %1 = bitcast <1 x i64> %a to <8 x i8> + %mmx_var.i = bitcast <8 x i8> %1 to x86_mmx + %mmx_var1.i = bitcast <8 x i8> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.punpcklbw(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <8 x i8> + %4 = bitcast <8 x i8> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.mmx.punpckhdq(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test79(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test79( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP8:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP11:%.*]] = bitcast <1 x i64> [[TMP8]] to <2 x i32> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <2 x i32> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <1 x i64> [[TMP10]] to <2 x i32> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <2 x i32> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <2 x i32> [[TMP14]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <2 x i32> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP7:%.*]] = bitcast <2 x i32> [[TMP11]] to i64 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast <2 x i32> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP6]], [[TMP7]] +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.mmx.punpckhdq(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP9:%.*]] = bitcast i64 [[_MSPROP]] to <2 x i32> +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to <2 x i32> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast <2 x i32> [[TMP9]] to <1 x i64> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <2 x i32> [[TMP3]] to <1 x i64> +; CHECK-NEXT: [[TMP5:%.*]] = extractelement <1 x i64> [[TMP4]], i32 0 +; CHECK-NEXT: [[TMP13:%.*]] = extractelement <1 x i64> [[TMP12]], i32 0 +; CHECK-NEXT: store i64 [[TMP5]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP13]] +; +entry: + %0 = bitcast <1 x i64> %b to <2 x i32> + %1 = bitcast <1 x i64> %a to <2 x i32> + %mmx_var.i = bitcast <2 x i32> %1 to x86_mmx + %mmx_var1.i = bitcast <2 x i32> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.punpckhdq(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <2 x i32> + %4 = bitcast <2 x i32> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.mmx.punpckhwd(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test78(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test78( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP8:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP11:%.*]] = bitcast <1 x i64> [[TMP8]] to <4 x i16> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <4 x i16> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <1 x i64> [[TMP10]] to <4 x i16> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <4 x i16> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <4 x i16> [[TMP14]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <4 x i16> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP7:%.*]] = bitcast <4 x i16> [[TMP11]] to i64 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast <4 x i16> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP6]], [[TMP7]] +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.mmx.punpckhwd(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP9:%.*]] = bitcast i64 [[_MSPROP]] to <4 x i16> +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to <4 x i16> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast <4 x i16> [[TMP9]] to <1 x i64> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <4 x i16> [[TMP3]] to <1 x i64> +; CHECK-NEXT: [[TMP5:%.*]] = extractelement <1 x i64> [[TMP4]], i32 0 +; CHECK-NEXT: [[TMP13:%.*]] = extractelement <1 x i64> [[TMP12]], i32 0 +; CHECK-NEXT: store i64 [[TMP5]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP13]] +; +entry: + %0 = bitcast <1 x i64> %b to <4 x i16> + %1 = bitcast <1 x i64> %a to <4 x i16> + %mmx_var.i = bitcast <4 x i16> %1 to x86_mmx + %mmx_var1.i = bitcast <4 x i16> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.punpckhwd(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <4 x i16> + %4 = bitcast <4 x i16> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.mmx.punpckhbw(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test77(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test77( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP8:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP11:%.*]] = bitcast <1 x i64> [[TMP8]] to <8 x i8> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <8 x i8> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <1 x i64> [[TMP10]] to <8 x i8> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <8 x i8> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <8 x i8> [[TMP14]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <8 x i8> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP7:%.*]] = bitcast <8 x i8> [[TMP11]] to i64 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast <8 x i8> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP6]], [[TMP7]] +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.mmx.punpckhbw(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP9:%.*]] = bitcast i64 [[_MSPROP]] to <8 x i8> +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to <8 x i8> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast <8 x i8> [[TMP9]] to <1 x i64> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <8 x i8> [[TMP3]] to <1 x i64> +; CHECK-NEXT: [[TMP5:%.*]] = extractelement <1 x i64> [[TMP4]], i32 0 +; CHECK-NEXT: [[TMP13:%.*]] = extractelement <1 x i64> [[TMP12]], i32 0 +; CHECK-NEXT: store i64 [[TMP5]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP13]] +; +entry: + %0 = bitcast <1 x i64> %b to <8 x i8> + %1 = bitcast <1 x i64> %a to <8 x i8> + %mmx_var.i = bitcast <8 x i8> %1 to x86_mmx + %mmx_var1.i = bitcast <8 x i8> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.punpckhbw(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <8 x i8> + %4 = bitcast <8 x i8> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.mmx.packuswb(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test76(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test76( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP16:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP17:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP19:%.*]] = bitcast <1 x i64> [[TMP16]] to <4 x i16> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <4 x i16> +; CHECK-NEXT: [[TMP20:%.*]] = bitcast <1 x i64> [[TMP17]] to <4 x i16> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <4 x i16> +; CHECK-NEXT: [[TMP23:%.*]] = bitcast <4 x i16> [[TMP20]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <4 x i16> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP7:%.*]] = bitcast <4 x i16> [[TMP19]] to i64 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast <4 x i16> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[TMP8:%.*]] = bitcast i64 [[TMP23]] to <4 x i16> +; CHECK-NEXT: [[TMP9:%.*]] = bitcast i64 [[TMP7]] to <4 x i16> +; CHECK-NEXT: [[TMP10:%.*]] = icmp ne <4 x i16> [[TMP8]], zeroinitializer +; CHECK-NEXT: [[TMP11:%.*]] = sext <4 x i1> [[TMP10]] to <4 x i16> +; CHECK-NEXT: [[TMP12:%.*]] = icmp ne <4 x i16> [[TMP9]], zeroinitializer +; CHECK-NEXT: [[TMP13:%.*]] = sext <4 x i1> [[TMP12]] to <4 x i16> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <4 x i16> [[TMP11]] to x86_mmx +; CHECK-NEXT: [[TMP15:%.*]] = bitcast <4 x i16> [[TMP13]] to x86_mmx +; CHECK-NEXT: [[_MSPROP_VECTOR_PACK:%.*]] = call x86_mmx @llvm.x86.mmx.packsswb(x86_mmx [[TMP14]], x86_mmx [[TMP15]]) +; CHECK-NEXT: [[TMP2:%.*]] = bitcast x86_mmx [[_MSPROP_VECTOR_PACK]] to i64 +; CHECK-NEXT: [[TMP3:%.*]] = tail call x86_mmx @llvm.x86.mmx.packuswb(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP18:%.*]] = bitcast i64 [[TMP2]] to <8 x i8> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast x86_mmx [[TMP3]] to <8 x i8> +; CHECK-NEXT: [[TMP5:%.*]] = bitcast <8 x i8> [[TMP18]] to <1 x i64> +; CHECK-NEXT: [[TMP21:%.*]] = bitcast <8 x i8> [[TMP4]] to <1 x i64> +; CHECK-NEXT: [[TMP6:%.*]] = extractelement <1 x i64> [[TMP5]], i32 0 +; CHECK-NEXT: [[TMP22:%.*]] = extractelement <1 x i64> [[TMP21]], i32 0 +; CHECK-NEXT: store i64 [[TMP6]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP22]] +; +entry: + %0 = bitcast <1 x i64> %b to <4 x i16> + %1 = bitcast <1 x i64> %a to <4 x i16> + %mmx_var.i = bitcast <4 x i16> %1 to x86_mmx + %mmx_var1.i = bitcast <4 x i16> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.packuswb(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <8 x i8> + %4 = bitcast <8 x i8> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.mmx.packssdw(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test75(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test75( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP16:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP17:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP19:%.*]] = bitcast <1 x i64> [[TMP16]] to <2 x i32> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <2 x i32> +; CHECK-NEXT: [[TMP20:%.*]] = bitcast <1 x i64> [[TMP17]] to <2 x i32> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <2 x i32> +; CHECK-NEXT: [[TMP23:%.*]] = bitcast <2 x i32> [[TMP20]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <2 x i32> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP7:%.*]] = bitcast <2 x i32> [[TMP19]] to i64 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast <2 x i32> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[TMP8:%.*]] = bitcast i64 [[TMP23]] to <2 x i32> +; CHECK-NEXT: [[TMP9:%.*]] = bitcast i64 [[TMP7]] to <2 x i32> +; CHECK-NEXT: [[TMP10:%.*]] = icmp ne <2 x i32> [[TMP8]], zeroinitializer +; CHECK-NEXT: [[TMP11:%.*]] = sext <2 x i1> [[TMP10]] to <2 x i32> +; CHECK-NEXT: [[TMP12:%.*]] = icmp ne <2 x i32> [[TMP9]], zeroinitializer +; CHECK-NEXT: [[TMP13:%.*]] = sext <2 x i1> [[TMP12]] to <2 x i32> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <2 x i32> [[TMP11]] to x86_mmx +; CHECK-NEXT: [[TMP15:%.*]] = bitcast <2 x i32> [[TMP13]] to x86_mmx +; CHECK-NEXT: [[_MSPROP_VECTOR_PACK:%.*]] = call x86_mmx @llvm.x86.mmx.packssdw(x86_mmx [[TMP14]], x86_mmx [[TMP15]]) +; CHECK-NEXT: [[TMP2:%.*]] = bitcast x86_mmx [[_MSPROP_VECTOR_PACK]] to i64 +; CHECK-NEXT: [[TMP3:%.*]] = tail call x86_mmx @llvm.x86.mmx.packssdw(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP18:%.*]] = bitcast i64 [[TMP2]] to <4 x i16> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast x86_mmx [[TMP3]] to <4 x i16> +; CHECK-NEXT: [[TMP5:%.*]] = bitcast <4 x i16> [[TMP18]] to <1 x i64> +; CHECK-NEXT: [[TMP21:%.*]] = bitcast <4 x i16> [[TMP4]] to <1 x i64> +; CHECK-NEXT: [[TMP6:%.*]] = extractelement <1 x i64> [[TMP5]], i32 0 +; CHECK-NEXT: [[TMP22:%.*]] = extractelement <1 x i64> [[TMP21]], i32 0 +; CHECK-NEXT: store i64 [[TMP6]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP22]] +; +entry: + %0 = bitcast <1 x i64> %b to <2 x i32> + %1 = bitcast <1 x i64> %a to <2 x i32> + %mmx_var.i = bitcast <2 x i32> %1 to x86_mmx + %mmx_var1.i = bitcast <2 x i32> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.packssdw(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <4 x i16> + %4 = bitcast <4 x i16> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.mmx.packsswb(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test74(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test74( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP16:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP17:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP19:%.*]] = bitcast <1 x i64> [[TMP16]] to <4 x i16> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <4 x i16> +; CHECK-NEXT: [[TMP20:%.*]] = bitcast <1 x i64> [[TMP17]] to <4 x i16> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <4 x i16> +; CHECK-NEXT: [[TMP23:%.*]] = bitcast <4 x i16> [[TMP20]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <4 x i16> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP7:%.*]] = bitcast <4 x i16> [[TMP19]] to i64 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast <4 x i16> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[TMP8:%.*]] = bitcast i64 [[TMP23]] to <4 x i16> +; CHECK-NEXT: [[TMP9:%.*]] = bitcast i64 [[TMP7]] to <4 x i16> +; CHECK-NEXT: [[TMP10:%.*]] = icmp ne <4 x i16> [[TMP8]], zeroinitializer +; CHECK-NEXT: [[TMP11:%.*]] = sext <4 x i1> [[TMP10]] to <4 x i16> +; CHECK-NEXT: [[TMP12:%.*]] = icmp ne <4 x i16> [[TMP9]], zeroinitializer +; CHECK-NEXT: [[TMP13:%.*]] = sext <4 x i1> [[TMP12]] to <4 x i16> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <4 x i16> [[TMP11]] to x86_mmx +; CHECK-NEXT: [[TMP15:%.*]] = bitcast <4 x i16> [[TMP13]] to x86_mmx +; CHECK-NEXT: [[_MSPROP_VECTOR_PACK:%.*]] = call x86_mmx @llvm.x86.mmx.packsswb(x86_mmx [[TMP14]], x86_mmx [[TMP15]]) +; CHECK-NEXT: [[TMP2:%.*]] = bitcast x86_mmx [[_MSPROP_VECTOR_PACK]] to i64 +; CHECK-NEXT: [[TMP3:%.*]] = tail call x86_mmx @llvm.x86.mmx.packsswb(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP18:%.*]] = bitcast i64 [[TMP2]] to <8 x i8> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast x86_mmx [[TMP3]] to <8 x i8> +; CHECK-NEXT: [[TMP5:%.*]] = bitcast <8 x i8> [[TMP18]] to <1 x i64> +; CHECK-NEXT: [[TMP21:%.*]] = bitcast <8 x i8> [[TMP4]] to <1 x i64> +; CHECK-NEXT: [[TMP6:%.*]] = extractelement <1 x i64> [[TMP5]], i32 0 +; CHECK-NEXT: [[TMP22:%.*]] = extractelement <1 x i64> [[TMP21]], i32 0 +; CHECK-NEXT: store i64 [[TMP6]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP22]] +; +entry: + %0 = bitcast <1 x i64> %b to <4 x i16> + %1 = bitcast <1 x i64> %a to <4 x i16> + %mmx_var.i = bitcast <4 x i16> %1 to x86_mmx + %mmx_var1.i = bitcast <4 x i16> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.packsswb(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <8 x i8> + %4 = bitcast <8 x i8> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.mmx.psrai.d(x86_mmx, i32) nounwind readnone + +define i64 @test73(<1 x i64> %a) #0 { +; CHECK-LABEL: define i64 @test73( +; CHECK-SAME: <1 x i64> [[A:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP7:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP8:%.*]] = bitcast <1 x i64> [[TMP7]] to <2 x i32> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[A]] to <2 x i32> +; CHECK-NEXT: [[TMP9:%.*]] = bitcast <2 x i32> [[TMP8]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <2 x i32> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[TMP10:%.*]] = bitcast i64 [[TMP9]] to x86_mmx +; CHECK-NEXT: [[TMP1:%.*]] = call x86_mmx @llvm.x86.mmx.psrai.d(x86_mmx [[TMP10]], i32 3) +; CHECK-NEXT: [[TMP2:%.*]] = bitcast x86_mmx [[TMP1]] to i64 +; CHECK-NEXT: [[TMP11:%.*]] = or i64 [[TMP2]], 0 +; CHECK-NEXT: [[TMP3:%.*]] = tail call x86_mmx @llvm.x86.mmx.psrai.d(x86_mmx [[MMX_VAR_I]], i32 3) #[[ATTR2]] +; CHECK-NEXT: [[TMP14:%.*]] = bitcast i64 [[TMP11]] to <2 x i32> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast x86_mmx [[TMP3]] to <2 x i32> +; CHECK-NEXT: [[TMP5:%.*]] = bitcast <2 x i32> [[TMP14]] to <1 x i64> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <2 x i32> [[TMP4]] to <1 x i64> +; CHECK-NEXT: [[TMP6:%.*]] = extractelement <1 x i64> [[TMP5]], i32 0 +; CHECK-NEXT: [[TMP13:%.*]] = extractelement <1 x i64> [[TMP12]], i32 0 +; CHECK-NEXT: store i64 [[TMP6]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP13]] +; +entry: + %0 = bitcast <1 x i64> %a to <2 x i32> + %mmx_var.i = bitcast <2 x i32> %0 to x86_mmx + %1 = tail call x86_mmx @llvm.x86.mmx.psrai.d(x86_mmx %mmx_var.i, i32 3) nounwind + %2 = bitcast x86_mmx %1 to <2 x i32> + %3 = bitcast <2 x i32> %2 to <1 x i64> + %4 = extractelement <1 x i64> %3, i32 0 + ret i64 %4 +} + +declare x86_mmx @llvm.x86.mmx.psrai.w(x86_mmx, i32) nounwind readnone + +define i64 @test72(<1 x i64> %a) #0 { +; CHECK-LABEL: define i64 @test72( +; CHECK-SAME: <1 x i64> [[A:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP7:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP8:%.*]] = bitcast <1 x i64> [[TMP7]] to <4 x i16> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[A]] to <4 x i16> +; CHECK-NEXT: [[TMP9:%.*]] = bitcast <4 x i16> [[TMP8]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <4 x i16> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[TMP10:%.*]] = bitcast i64 [[TMP9]] to x86_mmx +; CHECK-NEXT: [[TMP1:%.*]] = call x86_mmx @llvm.x86.mmx.psrai.w(x86_mmx [[TMP10]], i32 3) +; CHECK-NEXT: [[TMP2:%.*]] = bitcast x86_mmx [[TMP1]] to i64 +; CHECK-NEXT: [[TMP11:%.*]] = or i64 [[TMP2]], 0 +; CHECK-NEXT: [[TMP3:%.*]] = tail call x86_mmx @llvm.x86.mmx.psrai.w(x86_mmx [[MMX_VAR_I]], i32 3) #[[ATTR2]] +; CHECK-NEXT: [[TMP14:%.*]] = bitcast i64 [[TMP11]] to <4 x i16> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast x86_mmx [[TMP3]] to <4 x i16> +; CHECK-NEXT: [[TMP5:%.*]] = bitcast <4 x i16> [[TMP14]] to <1 x i64> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <4 x i16> [[TMP4]] to <1 x i64> +; CHECK-NEXT: [[TMP6:%.*]] = extractelement <1 x i64> [[TMP5]], i32 0 +; CHECK-NEXT: [[TMP13:%.*]] = extractelement <1 x i64> [[TMP12]], i32 0 +; CHECK-NEXT: store i64 [[TMP6]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP13]] +; +entry: + %0 = bitcast <1 x i64> %a to <4 x i16> + %mmx_var.i = bitcast <4 x i16> %0 to x86_mmx + %1 = tail call x86_mmx @llvm.x86.mmx.psrai.w(x86_mmx %mmx_var.i, i32 3) nounwind + %2 = bitcast x86_mmx %1 to <4 x i16> + %3 = bitcast <4 x i16> %2 to <1 x i64> + %4 = extractelement <1 x i64> %3, i32 0 + ret i64 %4 +} + +define i64 @test72_2(<1 x i64> %a) #0 { +; CHECK-LABEL: define i64 @test72_2( +; CHECK-SAME: <1 x i64> [[A:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP7:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP8:%.*]] = bitcast <1 x i64> [[TMP7]] to <4 x i16> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[A]] to <4 x i16> +; CHECK-NEXT: [[TMP9:%.*]] = bitcast <4 x i16> [[TMP8]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <4 x i16> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[TMP10:%.*]] = bitcast i64 [[TMP9]] to x86_mmx +; CHECK-NEXT: [[TMP1:%.*]] = call x86_mmx @llvm.x86.mmx.psrai.w(x86_mmx [[TMP10]], i32 0) +; CHECK-NEXT: [[TMP2:%.*]] = bitcast x86_mmx [[TMP1]] to i64 +; CHECK-NEXT: [[TMP11:%.*]] = or i64 [[TMP2]], 0 +; CHECK-NEXT: [[TMP3:%.*]] = tail call x86_mmx @llvm.x86.mmx.psrai.w(x86_mmx [[MMX_VAR_I]], i32 0) #[[ATTR2]] +; CHECK-NEXT: [[TMP14:%.*]] = bitcast i64 [[TMP11]] to <4 x i16> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast x86_mmx [[TMP3]] to <4 x i16> +; CHECK-NEXT: [[TMP5:%.*]] = bitcast <4 x i16> [[TMP14]] to <1 x i64> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <4 x i16> [[TMP4]] to <1 x i64> +; CHECK-NEXT: [[TMP6:%.*]] = extractelement <1 x i64> [[TMP5]], i32 0 +; CHECK-NEXT: [[TMP13:%.*]] = extractelement <1 x i64> [[TMP12]], i32 0 +; CHECK-NEXT: store i64 [[TMP6]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP13]] +; +entry: + %0 = bitcast <1 x i64> %a to <4 x i16> + %mmx_var.i = bitcast <4 x i16> %0 to x86_mmx + %1 = tail call x86_mmx @llvm.x86.mmx.psrai.w(x86_mmx %mmx_var.i, i32 0) nounwind + %2 = bitcast x86_mmx %1 to <4 x i16> + %3 = bitcast <4 x i16> %2 to <1 x i64> + %4 = extractelement <1 x i64> %3, i32 0 + ret i64 %4 +} + +declare x86_mmx @llvm.x86.mmx.psrli.q(x86_mmx, i32) nounwind readnone + +define i64 @test71(<1 x i64> %a) #0 { +; CHECK-LABEL: define i64 @test71( +; CHECK-SAME: <1 x i64> [[A:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP5:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[_MSPROP:%.*]] = extractelement <1 x i64> [[TMP5]], i32 0 +; CHECK-NEXT: [[TMP0:%.*]] = extractelement <1 x i64> [[A]], i32 0 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast i64 [[TMP0]] to x86_mmx +; CHECK-NEXT: [[TMP6:%.*]] = bitcast i64 [[_MSPROP]] to x86_mmx +; CHECK-NEXT: [[TMP1:%.*]] = call x86_mmx @llvm.x86.mmx.psrli.q(x86_mmx [[TMP6]], i32 3) +; CHECK-NEXT: [[TMP2:%.*]] = bitcast x86_mmx [[TMP1]] to i64 +; CHECK-NEXT: [[TMP7:%.*]] = or i64 [[TMP2]], 0 +; CHECK-NEXT: [[TMP3:%.*]] = tail call x86_mmx @llvm.x86.mmx.psrli.q(x86_mmx [[MMX_VAR_I]], i32 3) #[[ATTR2]] +; CHECK-NEXT: [[TMP4:%.*]] = bitcast x86_mmx [[TMP3]] to i64 +; CHECK-NEXT: store i64 [[TMP7]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP4]] +; +entry: + %0 = extractelement <1 x i64> %a, i32 0 + %mmx_var.i = bitcast i64 %0 to x86_mmx + %1 = tail call x86_mmx @llvm.x86.mmx.psrli.q(x86_mmx %mmx_var.i, i32 3) nounwind + %2 = bitcast x86_mmx %1 to i64 + ret i64 %2 +} + +declare x86_mmx @llvm.x86.mmx.psrli.d(x86_mmx, i32) nounwind readnone + +define i64 @test70(<1 x i64> %a) #0 { +; CHECK-LABEL: define i64 @test70( +; CHECK-SAME: <1 x i64> [[A:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP7:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP8:%.*]] = bitcast <1 x i64> [[TMP7]] to <2 x i32> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[A]] to <2 x i32> +; CHECK-NEXT: [[TMP9:%.*]] = bitcast <2 x i32> [[TMP8]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <2 x i32> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[TMP10:%.*]] = bitcast i64 [[TMP9]] to x86_mmx +; CHECK-NEXT: [[TMP1:%.*]] = call x86_mmx @llvm.x86.mmx.psrli.d(x86_mmx [[TMP10]], i32 3) +; CHECK-NEXT: [[TMP2:%.*]] = bitcast x86_mmx [[TMP1]] to i64 +; CHECK-NEXT: [[TMP11:%.*]] = or i64 [[TMP2]], 0 +; CHECK-NEXT: [[TMP3:%.*]] = tail call x86_mmx @llvm.x86.mmx.psrli.d(x86_mmx [[MMX_VAR_I]], i32 3) #[[ATTR2]] +; CHECK-NEXT: [[TMP14:%.*]] = bitcast i64 [[TMP11]] to <2 x i32> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast x86_mmx [[TMP3]] to <2 x i32> +; CHECK-NEXT: [[TMP5:%.*]] = bitcast <2 x i32> [[TMP14]] to <1 x i64> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <2 x i32> [[TMP4]] to <1 x i64> +; CHECK-NEXT: [[TMP6:%.*]] = extractelement <1 x i64> [[TMP5]], i32 0 +; CHECK-NEXT: [[TMP13:%.*]] = extractelement <1 x i64> [[TMP12]], i32 0 +; CHECK-NEXT: store i64 [[TMP6]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP13]] +; +entry: + %0 = bitcast <1 x i64> %a to <2 x i32> + %mmx_var.i = bitcast <2 x i32> %0 to x86_mmx + %1 = tail call x86_mmx @llvm.x86.mmx.psrli.d(x86_mmx %mmx_var.i, i32 3) nounwind + %2 = bitcast x86_mmx %1 to <2 x i32> + %3 = bitcast <2 x i32> %2 to <1 x i64> + %4 = extractelement <1 x i64> %3, i32 0 + ret i64 %4 +} + +define i64 @test70_2(<1 x i64> %a) #0 { +; CHECK-LABEL: define i64 @test70_2( +; CHECK-SAME: <1 x i64> [[A:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP7:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP8:%.*]] = bitcast <1 x i64> [[TMP7]] to <2 x i32> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[A]] to <2 x i32> +; CHECK-NEXT: [[TMP9:%.*]] = bitcast <2 x i32> [[TMP8]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <2 x i32> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[TMP10:%.*]] = bitcast i64 [[TMP9]] to x86_mmx +; CHECK-NEXT: [[TMP1:%.*]] = call x86_mmx @llvm.x86.mmx.psrli.d(x86_mmx [[TMP10]], i32 0) +; CHECK-NEXT: [[TMP2:%.*]] = bitcast x86_mmx [[TMP1]] to i64 +; CHECK-NEXT: [[TMP11:%.*]] = or i64 [[TMP2]], 0 +; CHECK-NEXT: [[TMP3:%.*]] = tail call x86_mmx @llvm.x86.mmx.psrli.d(x86_mmx [[MMX_VAR_I]], i32 0) #[[ATTR2]] +; CHECK-NEXT: [[TMP14:%.*]] = bitcast i64 [[TMP11]] to <2 x i32> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast x86_mmx [[TMP3]] to <2 x i32> +; CHECK-NEXT: [[TMP5:%.*]] = bitcast <2 x i32> [[TMP14]] to <1 x i64> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <2 x i32> [[TMP4]] to <1 x i64> +; CHECK-NEXT: [[TMP6:%.*]] = extractelement <1 x i64> [[TMP5]], i32 0 +; CHECK-NEXT: [[TMP13:%.*]] = extractelement <1 x i64> [[TMP12]], i32 0 +; CHECK-NEXT: store i64 [[TMP6]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP13]] +; +entry: + %0 = bitcast <1 x i64> %a to <2 x i32> + %mmx_var.i = bitcast <2 x i32> %0 to x86_mmx + %1 = tail call x86_mmx @llvm.x86.mmx.psrli.d(x86_mmx %mmx_var.i, i32 0) nounwind + %2 = bitcast x86_mmx %1 to <2 x i32> + %3 = bitcast <2 x i32> %2 to <1 x i64> + %4 = extractelement <1 x i64> %3, i32 0 + ret i64 %4 +} + +declare x86_mmx @llvm.x86.mmx.psrli.w(x86_mmx, i32) nounwind readnone + +define i64 @test69(<1 x i64> %a) #0 { +; CHECK-LABEL: define i64 @test69( +; CHECK-SAME: <1 x i64> [[A:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP7:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP8:%.*]] = bitcast <1 x i64> [[TMP7]] to <4 x i16> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[A]] to <4 x i16> +; CHECK-NEXT: [[TMP9:%.*]] = bitcast <4 x i16> [[TMP8]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <4 x i16> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[TMP10:%.*]] = bitcast i64 [[TMP9]] to x86_mmx +; CHECK-NEXT: [[TMP1:%.*]] = call x86_mmx @llvm.x86.mmx.psrli.w(x86_mmx [[TMP10]], i32 3) +; CHECK-NEXT: [[TMP2:%.*]] = bitcast x86_mmx [[TMP1]] to i64 +; CHECK-NEXT: [[TMP11:%.*]] = or i64 [[TMP2]], 0 +; CHECK-NEXT: [[TMP3:%.*]] = tail call x86_mmx @llvm.x86.mmx.psrli.w(x86_mmx [[MMX_VAR_I]], i32 3) #[[ATTR2]] +; CHECK-NEXT: [[TMP14:%.*]] = bitcast i64 [[TMP11]] to <4 x i16> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast x86_mmx [[TMP3]] to <4 x i16> +; CHECK-NEXT: [[TMP5:%.*]] = bitcast <4 x i16> [[TMP14]] to <1 x i64> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <4 x i16> [[TMP4]] to <1 x i64> +; CHECK-NEXT: [[TMP6:%.*]] = extractelement <1 x i64> [[TMP5]], i32 0 +; CHECK-NEXT: [[TMP13:%.*]] = extractelement <1 x i64> [[TMP12]], i32 0 +; CHECK-NEXT: store i64 [[TMP6]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP13]] +; +entry: + %0 = bitcast <1 x i64> %a to <4 x i16> + %mmx_var.i = bitcast <4 x i16> %0 to x86_mmx + %1 = tail call x86_mmx @llvm.x86.mmx.psrli.w(x86_mmx %mmx_var.i, i32 3) nounwind + %2 = bitcast x86_mmx %1 to <4 x i16> + %3 = bitcast <4 x i16> %2 to <1 x i64> + %4 = extractelement <1 x i64> %3, i32 0 + ret i64 %4 +} + +declare x86_mmx @llvm.x86.mmx.pslli.q(x86_mmx, i32) nounwind readnone + +define i64 @test68(<1 x i64> %a) #0 { +; CHECK-LABEL: define i64 @test68( +; CHECK-SAME: <1 x i64> [[A:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP5:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[_MSPROP:%.*]] = extractelement <1 x i64> [[TMP5]], i32 0 +; CHECK-NEXT: [[TMP0:%.*]] = extractelement <1 x i64> [[A]], i32 0 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast i64 [[TMP0]] to x86_mmx +; CHECK-NEXT: [[TMP6:%.*]] = bitcast i64 [[_MSPROP]] to x86_mmx +; CHECK-NEXT: [[TMP1:%.*]] = call x86_mmx @llvm.x86.mmx.pslli.q(x86_mmx [[TMP6]], i32 3) +; CHECK-NEXT: [[TMP2:%.*]] = bitcast x86_mmx [[TMP1]] to i64 +; CHECK-NEXT: [[TMP7:%.*]] = or i64 [[TMP2]], 0 +; CHECK-NEXT: [[TMP3:%.*]] = tail call x86_mmx @llvm.x86.mmx.pslli.q(x86_mmx [[MMX_VAR_I]], i32 3) #[[ATTR2]] +; CHECK-NEXT: [[TMP4:%.*]] = bitcast x86_mmx [[TMP3]] to i64 +; CHECK-NEXT: store i64 [[TMP7]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP4]] +; +entry: + %0 = extractelement <1 x i64> %a, i32 0 + %mmx_var.i = bitcast i64 %0 to x86_mmx + %1 = tail call x86_mmx @llvm.x86.mmx.pslli.q(x86_mmx %mmx_var.i, i32 3) nounwind + %2 = bitcast x86_mmx %1 to i64 + ret i64 %2 +} + +declare x86_mmx @llvm.x86.mmx.pslli.d(x86_mmx, i32) nounwind readnone + +define i64 @test67(<1 x i64> %a) #0 { +; CHECK-LABEL: define i64 @test67( +; CHECK-SAME: <1 x i64> [[A:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP7:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP8:%.*]] = bitcast <1 x i64> [[TMP7]] to <2 x i32> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[A]] to <2 x i32> +; CHECK-NEXT: [[TMP9:%.*]] = bitcast <2 x i32> [[TMP8]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <2 x i32> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[TMP10:%.*]] = bitcast i64 [[TMP9]] to x86_mmx +; CHECK-NEXT: [[TMP1:%.*]] = call x86_mmx @llvm.x86.mmx.pslli.d(x86_mmx [[TMP10]], i32 3) +; CHECK-NEXT: [[TMP2:%.*]] = bitcast x86_mmx [[TMP1]] to i64 +; CHECK-NEXT: [[TMP11:%.*]] = or i64 [[TMP2]], 0 +; CHECK-NEXT: [[TMP3:%.*]] = tail call x86_mmx @llvm.x86.mmx.pslli.d(x86_mmx [[MMX_VAR_I]], i32 3) #[[ATTR2]] +; CHECK-NEXT: [[TMP14:%.*]] = bitcast i64 [[TMP11]] to <2 x i32> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast x86_mmx [[TMP3]] to <2 x i32> +; CHECK-NEXT: [[TMP5:%.*]] = bitcast <2 x i32> [[TMP14]] to <1 x i64> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <2 x i32> [[TMP4]] to <1 x i64> +; CHECK-NEXT: [[TMP6:%.*]] = extractelement <1 x i64> [[TMP5]], i32 0 +; CHECK-NEXT: [[TMP13:%.*]] = extractelement <1 x i64> [[TMP12]], i32 0 +; CHECK-NEXT: store i64 [[TMP6]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP13]] +; +entry: + %0 = bitcast <1 x i64> %a to <2 x i32> + %mmx_var.i = bitcast <2 x i32> %0 to x86_mmx + %1 = tail call x86_mmx @llvm.x86.mmx.pslli.d(x86_mmx %mmx_var.i, i32 3) nounwind + %2 = bitcast x86_mmx %1 to <2 x i32> + %3 = bitcast <2 x i32> %2 to <1 x i64> + %4 = extractelement <1 x i64> %3, i32 0 + ret i64 %4 +} + +declare x86_mmx @llvm.x86.mmx.pslli.w(x86_mmx, i32) nounwind readnone + +define i64 @test66(<1 x i64> %a) #0 { +; CHECK-LABEL: define i64 @test66( +; CHECK-SAME: <1 x i64> [[A:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP7:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP8:%.*]] = bitcast <1 x i64> [[TMP7]] to <4 x i16> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[A]] to <4 x i16> +; CHECK-NEXT: [[TMP9:%.*]] = bitcast <4 x i16> [[TMP8]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <4 x i16> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[TMP10:%.*]] = bitcast i64 [[TMP9]] to x86_mmx +; CHECK-NEXT: [[TMP1:%.*]] = call x86_mmx @llvm.x86.mmx.pslli.w(x86_mmx [[TMP10]], i32 3) +; CHECK-NEXT: [[TMP2:%.*]] = bitcast x86_mmx [[TMP1]] to i64 +; CHECK-NEXT: [[TMP11:%.*]] = or i64 [[TMP2]], 0 +; CHECK-NEXT: [[TMP3:%.*]] = tail call x86_mmx @llvm.x86.mmx.pslli.w(x86_mmx [[MMX_VAR_I]], i32 3) #[[ATTR2]] +; CHECK-NEXT: [[TMP14:%.*]] = bitcast i64 [[TMP11]] to <4 x i16> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast x86_mmx [[TMP3]] to <4 x i16> +; CHECK-NEXT: [[TMP5:%.*]] = bitcast <4 x i16> [[TMP14]] to <1 x i64> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <4 x i16> [[TMP4]] to <1 x i64> +; CHECK-NEXT: [[TMP6:%.*]] = extractelement <1 x i64> [[TMP5]], i32 0 +; CHECK-NEXT: [[TMP13:%.*]] = extractelement <1 x i64> [[TMP12]], i32 0 +; CHECK-NEXT: store i64 [[TMP6]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP13]] +; +entry: + %0 = bitcast <1 x i64> %a to <4 x i16> + %mmx_var.i = bitcast <4 x i16> %0 to x86_mmx + %1 = tail call x86_mmx @llvm.x86.mmx.pslli.w(x86_mmx %mmx_var.i, i32 3) nounwind + %2 = bitcast x86_mmx %1 to <4 x i16> + %3 = bitcast <4 x i16> %2 to <1 x i64> + %4 = extractelement <1 x i64> %3, i32 0 + ret i64 %4 +} + +define i64 @test66_2(<1 x i64> %a) #0 { +; CHECK-LABEL: define i64 @test66_2( +; CHECK-SAME: <1 x i64> [[A:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP7:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP8:%.*]] = bitcast <1 x i64> [[TMP7]] to <4 x i16> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[A]] to <4 x i16> +; CHECK-NEXT: [[TMP9:%.*]] = bitcast <4 x i16> [[TMP8]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <4 x i16> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[TMP10:%.*]] = bitcast i64 [[TMP9]] to x86_mmx +; CHECK-NEXT: [[TMP1:%.*]] = call x86_mmx @llvm.x86.mmx.pslli.w(x86_mmx [[TMP10]], i32 0) +; CHECK-NEXT: [[TMP2:%.*]] = bitcast x86_mmx [[TMP1]] to i64 +; CHECK-NEXT: [[TMP11:%.*]] = or i64 [[TMP2]], 0 +; CHECK-NEXT: [[TMP3:%.*]] = tail call x86_mmx @llvm.x86.mmx.pslli.w(x86_mmx [[MMX_VAR_I]], i32 0) #[[ATTR2]] +; CHECK-NEXT: [[TMP14:%.*]] = bitcast i64 [[TMP11]] to <4 x i16> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast x86_mmx [[TMP3]] to <4 x i16> +; CHECK-NEXT: [[TMP5:%.*]] = bitcast <4 x i16> [[TMP14]] to <1 x i64> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <4 x i16> [[TMP4]] to <1 x i64> +; CHECK-NEXT: [[TMP6:%.*]] = extractelement <1 x i64> [[TMP5]], i32 0 +; CHECK-NEXT: [[TMP13:%.*]] = extractelement <1 x i64> [[TMP12]], i32 0 +; CHECK-NEXT: store i64 [[TMP6]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP13]] +; +entry: + %0 = bitcast <1 x i64> %a to <4 x i16> + %mmx_var.i = bitcast <4 x i16> %0 to x86_mmx + %1 = tail call x86_mmx @llvm.x86.mmx.pslli.w(x86_mmx %mmx_var.i, i32 0) nounwind + %2 = bitcast x86_mmx %1 to <4 x i16> + %3 = bitcast <4 x i16> %2 to <1 x i64> + %4 = extractelement <1 x i64> %3, i32 0 + ret i64 %4 +} + +declare x86_mmx @llvm.x86.mmx.psra.d(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test65(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test65( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP9:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP11:%.*]] = bitcast <1 x i64> [[TMP9]] to <2 x i32> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[A]] to <2 x i32> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <2 x i32> [[TMP11]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <2 x i32> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = extractelement <1 x i64> [[TMP10]], i32 0 +; CHECK-NEXT: [[TMP1:%.*]] = extractelement <1 x i64> [[B]], i32 0 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast i64 [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP13:%.*]] = icmp ne i64 [[_MSPROP]], 0 +; CHECK-NEXT: [[TMP14:%.*]] = sext i1 [[TMP13]] to i64 +; CHECK-NEXT: [[TMP8:%.*]] = bitcast i64 [[TMP12]] to x86_mmx +; CHECK-NEXT: [[TMP2:%.*]] = call x86_mmx @llvm.x86.mmx.psra.d(x86_mmx [[TMP8]], x86_mmx [[MMX_VAR1_I]]) +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to i64 +; CHECK-NEXT: [[TMP15:%.*]] = or i64 [[TMP3]], [[TMP14]] +; CHECK-NEXT: [[TMP4:%.*]] = tail call x86_mmx @llvm.x86.mmx.psra.d(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP18:%.*]] = bitcast i64 [[TMP15]] to <2 x i32> +; CHECK-NEXT: [[TMP5:%.*]] = bitcast x86_mmx [[TMP4]] to <2 x i32> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <2 x i32> [[TMP18]] to <1 x i64> +; CHECK-NEXT: [[TMP16:%.*]] = bitcast <2 x i32> [[TMP5]] to <1 x i64> +; CHECK-NEXT: [[TMP7:%.*]] = extractelement <1 x i64> [[TMP6]], i32 0 +; CHECK-NEXT: [[TMP17:%.*]] = extractelement <1 x i64> [[TMP16]], i32 0 +; CHECK-NEXT: store i64 [[TMP7]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP17]] +; +entry: + %0 = bitcast <1 x i64> %a to <2 x i32> + %mmx_var.i = bitcast <2 x i32> %0 to x86_mmx + %1 = extractelement <1 x i64> %b, i32 0 + %mmx_var1.i = bitcast i64 %1 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.psra.d(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <2 x i32> + %4 = bitcast <2 x i32> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.mmx.psra.w(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test64(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test64( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP9:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP11:%.*]] = bitcast <1 x i64> [[TMP9]] to <4 x i16> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[A]] to <4 x i16> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <4 x i16> [[TMP11]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <4 x i16> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = extractelement <1 x i64> [[TMP10]], i32 0 +; CHECK-NEXT: [[TMP1:%.*]] = extractelement <1 x i64> [[B]], i32 0 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast i64 [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP13:%.*]] = icmp ne i64 [[_MSPROP]], 0 +; CHECK-NEXT: [[TMP14:%.*]] = sext i1 [[TMP13]] to i64 +; CHECK-NEXT: [[TMP8:%.*]] = bitcast i64 [[TMP12]] to x86_mmx +; CHECK-NEXT: [[TMP2:%.*]] = call x86_mmx @llvm.x86.mmx.psra.w(x86_mmx [[TMP8]], x86_mmx [[MMX_VAR1_I]]) +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to i64 +; CHECK-NEXT: [[TMP15:%.*]] = or i64 [[TMP3]], [[TMP14]] +; CHECK-NEXT: [[TMP4:%.*]] = tail call x86_mmx @llvm.x86.mmx.psra.w(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP18:%.*]] = bitcast i64 [[TMP15]] to <4 x i16> +; CHECK-NEXT: [[TMP5:%.*]] = bitcast x86_mmx [[TMP4]] to <4 x i16> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <4 x i16> [[TMP18]] to <1 x i64> +; CHECK-NEXT: [[TMP16:%.*]] = bitcast <4 x i16> [[TMP5]] to <1 x i64> +; CHECK-NEXT: [[TMP7:%.*]] = extractelement <1 x i64> [[TMP6]], i32 0 +; CHECK-NEXT: [[TMP17:%.*]] = extractelement <1 x i64> [[TMP16]], i32 0 +; CHECK-NEXT: store i64 [[TMP7]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP17]] +; +entry: + %0 = bitcast <1 x i64> %a to <4 x i16> + %mmx_var.i = bitcast <4 x i16> %0 to x86_mmx + %1 = extractelement <1 x i64> %b, i32 0 + %mmx_var1.i = bitcast i64 %1 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.psra.w(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <4 x i16> + %4 = bitcast <4 x i16> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.mmx.psrl.q(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test63(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test63( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP7:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: [[TMP8:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[_MSPROP:%.*]] = extractelement <1 x i64> [[TMP7]], i32 0 +; CHECK-NEXT: [[TMP0:%.*]] = extractelement <1 x i64> [[A]], i32 0 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast i64 [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP1:%.*]] = extractelement <1 x i64> [[TMP8]], i32 0 +; CHECK-NEXT: [[TMP1:%.*]] = extractelement <1 x i64> [[B]], i32 0 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast i64 [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP9:%.*]] = icmp ne i64 [[_MSPROP1]], 0 +; CHECK-NEXT: [[TMP10:%.*]] = sext i1 [[TMP9]] to i64 +; CHECK-NEXT: [[TMP6:%.*]] = bitcast i64 [[_MSPROP]] to x86_mmx +; CHECK-NEXT: [[TMP2:%.*]] = call x86_mmx @llvm.x86.mmx.psrl.q(x86_mmx [[TMP6]], x86_mmx [[MMX_VAR1_I]]) +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to i64 +; CHECK-NEXT: [[TMP11:%.*]] = or i64 [[TMP3]], [[TMP10]] +; CHECK-NEXT: [[TMP4:%.*]] = tail call x86_mmx @llvm.x86.mmx.psrl.q(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP5:%.*]] = bitcast x86_mmx [[TMP4]] to i64 +; CHECK-NEXT: store i64 [[TMP11]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP5]] +; +entry: + %0 = extractelement <1 x i64> %a, i32 0 + %mmx_var.i = bitcast i64 %0 to x86_mmx + %1 = extractelement <1 x i64> %b, i32 0 + %mmx_var1.i = bitcast i64 %1 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.psrl.q(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to i64 + ret i64 %3 +} + +declare x86_mmx @llvm.x86.mmx.psrl.d(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test62(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test62( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP9:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP11:%.*]] = bitcast <1 x i64> [[TMP9]] to <2 x i32> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[A]] to <2 x i32> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <2 x i32> [[TMP11]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <2 x i32> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = extractelement <1 x i64> [[TMP10]], i32 0 +; CHECK-NEXT: [[TMP1:%.*]] = extractelement <1 x i64> [[B]], i32 0 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast i64 [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP13:%.*]] = icmp ne i64 [[_MSPROP]], 0 +; CHECK-NEXT: [[TMP14:%.*]] = sext i1 [[TMP13]] to i64 +; CHECK-NEXT: [[TMP8:%.*]] = bitcast i64 [[TMP12]] to x86_mmx +; CHECK-NEXT: [[TMP2:%.*]] = call x86_mmx @llvm.x86.mmx.psrl.d(x86_mmx [[TMP8]], x86_mmx [[MMX_VAR1_I]]) +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to i64 +; CHECK-NEXT: [[TMP15:%.*]] = or i64 [[TMP3]], [[TMP14]] +; CHECK-NEXT: [[TMP4:%.*]] = tail call x86_mmx @llvm.x86.mmx.psrl.d(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP18:%.*]] = bitcast i64 [[TMP15]] to <2 x i32> +; CHECK-NEXT: [[TMP5:%.*]] = bitcast x86_mmx [[TMP4]] to <2 x i32> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <2 x i32> [[TMP18]] to <1 x i64> +; CHECK-NEXT: [[TMP16:%.*]] = bitcast <2 x i32> [[TMP5]] to <1 x i64> +; CHECK-NEXT: [[TMP7:%.*]] = extractelement <1 x i64> [[TMP6]], i32 0 +; CHECK-NEXT: [[TMP17:%.*]] = extractelement <1 x i64> [[TMP16]], i32 0 +; CHECK-NEXT: store i64 [[TMP7]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP17]] +; +entry: + %0 = bitcast <1 x i64> %a to <2 x i32> + %mmx_var.i = bitcast <2 x i32> %0 to x86_mmx + %1 = extractelement <1 x i64> %b, i32 0 + %mmx_var1.i = bitcast i64 %1 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.psrl.d(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <2 x i32> + %4 = bitcast <2 x i32> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.mmx.psrl.w(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test61(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test61( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP9:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP11:%.*]] = bitcast <1 x i64> [[TMP9]] to <4 x i16> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[A]] to <4 x i16> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <4 x i16> [[TMP11]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <4 x i16> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = extractelement <1 x i64> [[TMP10]], i32 0 +; CHECK-NEXT: [[TMP1:%.*]] = extractelement <1 x i64> [[B]], i32 0 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast i64 [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP13:%.*]] = icmp ne i64 [[_MSPROP]], 0 +; CHECK-NEXT: [[TMP14:%.*]] = sext i1 [[TMP13]] to i64 +; CHECK-NEXT: [[TMP8:%.*]] = bitcast i64 [[TMP12]] to x86_mmx +; CHECK-NEXT: [[TMP2:%.*]] = call x86_mmx @llvm.x86.mmx.psrl.w(x86_mmx [[TMP8]], x86_mmx [[MMX_VAR1_I]]) +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to i64 +; CHECK-NEXT: [[TMP15:%.*]] = or i64 [[TMP3]], [[TMP14]] +; CHECK-NEXT: [[TMP4:%.*]] = tail call x86_mmx @llvm.x86.mmx.psrl.w(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP18:%.*]] = bitcast i64 [[TMP15]] to <4 x i16> +; CHECK-NEXT: [[TMP5:%.*]] = bitcast x86_mmx [[TMP4]] to <4 x i16> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <4 x i16> [[TMP18]] to <1 x i64> +; CHECK-NEXT: [[TMP16:%.*]] = bitcast <4 x i16> [[TMP5]] to <1 x i64> +; CHECK-NEXT: [[TMP7:%.*]] = extractelement <1 x i64> [[TMP6]], i32 0 +; CHECK-NEXT: [[TMP17:%.*]] = extractelement <1 x i64> [[TMP16]], i32 0 +; CHECK-NEXT: store i64 [[TMP7]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP17]] +; +entry: + %0 = bitcast <1 x i64> %a to <4 x i16> + %mmx_var.i = bitcast <4 x i16> %0 to x86_mmx + %1 = extractelement <1 x i64> %b, i32 0 + %mmx_var1.i = bitcast i64 %1 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.psrl.w(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <4 x i16> + %4 = bitcast <4 x i16> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.mmx.psll.q(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test60(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test60( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP7:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: [[TMP8:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[_MSPROP:%.*]] = extractelement <1 x i64> [[TMP7]], i32 0 +; CHECK-NEXT: [[TMP0:%.*]] = extractelement <1 x i64> [[A]], i32 0 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast i64 [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP1:%.*]] = extractelement <1 x i64> [[TMP8]], i32 0 +; CHECK-NEXT: [[TMP1:%.*]] = extractelement <1 x i64> [[B]], i32 0 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast i64 [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP9:%.*]] = icmp ne i64 [[_MSPROP1]], 0 +; CHECK-NEXT: [[TMP10:%.*]] = sext i1 [[TMP9]] to i64 +; CHECK-NEXT: [[TMP6:%.*]] = bitcast i64 [[_MSPROP]] to x86_mmx +; CHECK-NEXT: [[TMP2:%.*]] = call x86_mmx @llvm.x86.mmx.psll.q(x86_mmx [[TMP6]], x86_mmx [[MMX_VAR1_I]]) +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to i64 +; CHECK-NEXT: [[TMP11:%.*]] = or i64 [[TMP3]], [[TMP10]] +; CHECK-NEXT: [[TMP4:%.*]] = tail call x86_mmx @llvm.x86.mmx.psll.q(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP5:%.*]] = bitcast x86_mmx [[TMP4]] to i64 +; CHECK-NEXT: store i64 [[TMP11]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP5]] +; +entry: + %0 = extractelement <1 x i64> %a, i32 0 + %mmx_var.i = bitcast i64 %0 to x86_mmx + %1 = extractelement <1 x i64> %b, i32 0 + %mmx_var1.i = bitcast i64 %1 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.psll.q(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to i64 + ret i64 %3 +} + +declare x86_mmx @llvm.x86.mmx.psll.d(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test59(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test59( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP9:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP11:%.*]] = bitcast <1 x i64> [[TMP9]] to <2 x i32> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[A]] to <2 x i32> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <2 x i32> [[TMP11]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <2 x i32> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = extractelement <1 x i64> [[TMP10]], i32 0 +; CHECK-NEXT: [[TMP1:%.*]] = extractelement <1 x i64> [[B]], i32 0 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast i64 [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP13:%.*]] = icmp ne i64 [[_MSPROP]], 0 +; CHECK-NEXT: [[TMP14:%.*]] = sext i1 [[TMP13]] to i64 +; CHECK-NEXT: [[TMP8:%.*]] = bitcast i64 [[TMP12]] to x86_mmx +; CHECK-NEXT: [[TMP2:%.*]] = call x86_mmx @llvm.x86.mmx.psll.d(x86_mmx [[TMP8]], x86_mmx [[MMX_VAR1_I]]) +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to i64 +; CHECK-NEXT: [[TMP15:%.*]] = or i64 [[TMP3]], [[TMP14]] +; CHECK-NEXT: [[TMP4:%.*]] = tail call x86_mmx @llvm.x86.mmx.psll.d(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP18:%.*]] = bitcast i64 [[TMP15]] to <2 x i32> +; CHECK-NEXT: [[TMP5:%.*]] = bitcast x86_mmx [[TMP4]] to <2 x i32> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <2 x i32> [[TMP18]] to <1 x i64> +; CHECK-NEXT: [[TMP16:%.*]] = bitcast <2 x i32> [[TMP5]] to <1 x i64> +; CHECK-NEXT: [[TMP7:%.*]] = extractelement <1 x i64> [[TMP6]], i32 0 +; CHECK-NEXT: [[TMP17:%.*]] = extractelement <1 x i64> [[TMP16]], i32 0 +; CHECK-NEXT: store i64 [[TMP7]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP17]] +; +entry: + %0 = bitcast <1 x i64> %a to <2 x i32> + %mmx_var.i = bitcast <2 x i32> %0 to x86_mmx + %1 = extractelement <1 x i64> %b, i32 0 + %mmx_var1.i = bitcast i64 %1 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.psll.d(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <2 x i32> + %4 = bitcast <2 x i32> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.mmx.psll.w(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test58(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test58( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP9:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP11:%.*]] = bitcast <1 x i64> [[TMP9]] to <4 x i16> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[A]] to <4 x i16> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <4 x i16> [[TMP11]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <4 x i16> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = extractelement <1 x i64> [[TMP10]], i32 0 +; CHECK-NEXT: [[TMP1:%.*]] = extractelement <1 x i64> [[B]], i32 0 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast i64 [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP13:%.*]] = icmp ne i64 [[_MSPROP]], 0 +; CHECK-NEXT: [[TMP14:%.*]] = sext i1 [[TMP13]] to i64 +; CHECK-NEXT: [[TMP8:%.*]] = bitcast i64 [[TMP12]] to x86_mmx +; CHECK-NEXT: [[TMP2:%.*]] = call x86_mmx @llvm.x86.mmx.psll.w(x86_mmx [[TMP8]], x86_mmx [[MMX_VAR1_I]]) +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to i64 +; CHECK-NEXT: [[TMP15:%.*]] = or i64 [[TMP3]], [[TMP14]] +; CHECK-NEXT: [[TMP4:%.*]] = tail call x86_mmx @llvm.x86.mmx.psll.w(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP18:%.*]] = bitcast i64 [[TMP15]] to <4 x i16> +; CHECK-NEXT: [[TMP5:%.*]] = bitcast x86_mmx [[TMP4]] to <4 x i16> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <4 x i16> [[TMP18]] to <1 x i64> +; CHECK-NEXT: [[TMP16:%.*]] = bitcast <4 x i16> [[TMP5]] to <1 x i64> +; CHECK-NEXT: [[TMP7:%.*]] = extractelement <1 x i64> [[TMP6]], i32 0 +; CHECK-NEXT: [[TMP17:%.*]] = extractelement <1 x i64> [[TMP16]], i32 0 +; CHECK-NEXT: store i64 [[TMP7]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP17]] +; +entry: + %0 = bitcast <1 x i64> %a to <4 x i16> + %mmx_var.i = bitcast <4 x i16> %0 to x86_mmx + %1 = extractelement <1 x i64> %b, i32 0 + %mmx_var1.i = bitcast i64 %1 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.psll.w(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <4 x i16> + %4 = bitcast <4 x i16> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.mmx.pxor(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test56(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test56( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP8:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP11:%.*]] = bitcast <1 x i64> [[TMP8]] to <2 x i32> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <2 x i32> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <1 x i64> [[TMP10]] to <2 x i32> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <2 x i32> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <2 x i32> [[TMP14]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <2 x i32> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP7:%.*]] = bitcast <2 x i32> [[TMP11]] to i64 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast <2 x i32> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP6]], [[TMP7]] +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.mmx.pxor(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP9:%.*]] = bitcast i64 [[_MSPROP]] to <2 x i32> +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to <2 x i32> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast <2 x i32> [[TMP9]] to <1 x i64> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <2 x i32> [[TMP3]] to <1 x i64> +; CHECK-NEXT: [[TMP5:%.*]] = extractelement <1 x i64> [[TMP4]], i32 0 +; CHECK-NEXT: [[TMP13:%.*]] = extractelement <1 x i64> [[TMP12]], i32 0 +; CHECK-NEXT: store i64 [[TMP5]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP13]] +; +entry: + %0 = bitcast <1 x i64> %b to <2 x i32> + %1 = bitcast <1 x i64> %a to <2 x i32> + %mmx_var.i = bitcast <2 x i32> %1 to x86_mmx + %mmx_var1.i = bitcast <2 x i32> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.pxor(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <2 x i32> + %4 = bitcast <2 x i32> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.mmx.por(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test55(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test55( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP8:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP11:%.*]] = bitcast <1 x i64> [[TMP8]] to <2 x i32> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <2 x i32> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <1 x i64> [[TMP10]] to <2 x i32> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <2 x i32> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <2 x i32> [[TMP14]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <2 x i32> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP7:%.*]] = bitcast <2 x i32> [[TMP11]] to i64 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast <2 x i32> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP6]], [[TMP7]] +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.mmx.por(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP9:%.*]] = bitcast i64 [[_MSPROP]] to <2 x i32> +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to <2 x i32> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast <2 x i32> [[TMP9]] to <1 x i64> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <2 x i32> [[TMP3]] to <1 x i64> +; CHECK-NEXT: [[TMP5:%.*]] = extractelement <1 x i64> [[TMP4]], i32 0 +; CHECK-NEXT: [[TMP13:%.*]] = extractelement <1 x i64> [[TMP12]], i32 0 +; CHECK-NEXT: store i64 [[TMP5]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP13]] +; +entry: + %0 = bitcast <1 x i64> %b to <2 x i32> + %1 = bitcast <1 x i64> %a to <2 x i32> + %mmx_var.i = bitcast <2 x i32> %1 to x86_mmx + %mmx_var1.i = bitcast <2 x i32> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.por(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <2 x i32> + %4 = bitcast <2 x i32> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.mmx.pandn(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test54(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test54( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP8:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP11:%.*]] = bitcast <1 x i64> [[TMP8]] to <2 x i32> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <2 x i32> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <1 x i64> [[TMP10]] to <2 x i32> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <2 x i32> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <2 x i32> [[TMP14]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <2 x i32> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP7:%.*]] = bitcast <2 x i32> [[TMP11]] to i64 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast <2 x i32> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP6]], [[TMP7]] +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.mmx.pandn(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP9:%.*]] = bitcast i64 [[_MSPROP]] to <2 x i32> +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to <2 x i32> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast <2 x i32> [[TMP9]] to <1 x i64> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <2 x i32> [[TMP3]] to <1 x i64> +; CHECK-NEXT: [[TMP5:%.*]] = extractelement <1 x i64> [[TMP4]], i32 0 +; CHECK-NEXT: [[TMP13:%.*]] = extractelement <1 x i64> [[TMP12]], i32 0 +; CHECK-NEXT: store i64 [[TMP5]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP13]] +; +entry: + %0 = bitcast <1 x i64> %b to <2 x i32> + %1 = bitcast <1 x i64> %a to <2 x i32> + %mmx_var.i = bitcast <2 x i32> %1 to x86_mmx + %mmx_var1.i = bitcast <2 x i32> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.pandn(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <2 x i32> + %4 = bitcast <2 x i32> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.mmx.pand(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test53(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test53( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP8:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP11:%.*]] = bitcast <1 x i64> [[TMP8]] to <2 x i32> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <2 x i32> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <1 x i64> [[TMP10]] to <2 x i32> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <2 x i32> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <2 x i32> [[TMP14]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <2 x i32> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP7:%.*]] = bitcast <2 x i32> [[TMP11]] to i64 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast <2 x i32> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP6]], [[TMP7]] +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.mmx.pand(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP9:%.*]] = bitcast i64 [[_MSPROP]] to <2 x i32> +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to <2 x i32> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast <2 x i32> [[TMP9]] to <1 x i64> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <2 x i32> [[TMP3]] to <1 x i64> +; CHECK-NEXT: [[TMP5:%.*]] = extractelement <1 x i64> [[TMP4]], i32 0 +; CHECK-NEXT: [[TMP13:%.*]] = extractelement <1 x i64> [[TMP12]], i32 0 +; CHECK-NEXT: store i64 [[TMP5]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP13]] +; +entry: + %0 = bitcast <1 x i64> %b to <2 x i32> + %1 = bitcast <1 x i64> %a to <2 x i32> + %mmx_var.i = bitcast <2 x i32> %1 to x86_mmx + %mmx_var1.i = bitcast <2 x i32> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.pand(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <2 x i32> + %4 = bitcast <2 x i32> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.mmx.pmull.w(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test52(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test52( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP8:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP11:%.*]] = bitcast <1 x i64> [[TMP8]] to <4 x i16> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <4 x i16> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <1 x i64> [[TMP10]] to <4 x i16> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <4 x i16> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <4 x i16> [[TMP14]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <4 x i16> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP7:%.*]] = bitcast <4 x i16> [[TMP11]] to i64 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast <4 x i16> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP6]], [[TMP7]] +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.mmx.pmull.w(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP9:%.*]] = bitcast i64 [[_MSPROP]] to <4 x i16> +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to <4 x i16> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast <4 x i16> [[TMP9]] to <1 x i64> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <4 x i16> [[TMP3]] to <1 x i64> +; CHECK-NEXT: [[TMP5:%.*]] = extractelement <1 x i64> [[TMP4]], i32 0 +; CHECK-NEXT: [[TMP13:%.*]] = extractelement <1 x i64> [[TMP12]], i32 0 +; CHECK-NEXT: store i64 [[TMP5]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP13]] +; +entry: + %0 = bitcast <1 x i64> %b to <4 x i16> + %1 = bitcast <1 x i64> %a to <4 x i16> + %mmx_var.i = bitcast <4 x i16> %1 to x86_mmx + %mmx_var1.i = bitcast <4 x i16> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.pmull.w(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <4 x i16> + %4 = bitcast <4 x i16> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +define i64 @test51(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test51( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP8:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP11:%.*]] = bitcast <1 x i64> [[TMP8]] to <4 x i16> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <4 x i16> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <1 x i64> [[TMP10]] to <4 x i16> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <4 x i16> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <4 x i16> [[TMP14]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <4 x i16> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP7:%.*]] = bitcast <4 x i16> [[TMP11]] to i64 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast <4 x i16> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP6]], [[TMP7]] +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.mmx.pmull.w(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP9:%.*]] = bitcast i64 [[_MSPROP]] to <4 x i16> +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to <4 x i16> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast <4 x i16> [[TMP9]] to <1 x i64> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <4 x i16> [[TMP3]] to <1 x i64> +; CHECK-NEXT: [[TMP5:%.*]] = extractelement <1 x i64> [[TMP4]], i32 0 +; CHECK-NEXT: [[TMP13:%.*]] = extractelement <1 x i64> [[TMP12]], i32 0 +; CHECK-NEXT: store i64 [[TMP5]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP13]] +; +entry: + %0 = bitcast <1 x i64> %b to <4 x i16> + %1 = bitcast <1 x i64> %a to <4 x i16> + %mmx_var.i = bitcast <4 x i16> %1 to x86_mmx + %mmx_var1.i = bitcast <4 x i16> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.pmull.w(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <4 x i16> + %4 = bitcast <4 x i16> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.mmx.pmulh.w(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test50(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test50( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP8:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP11:%.*]] = bitcast <1 x i64> [[TMP8]] to <4 x i16> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <4 x i16> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <1 x i64> [[TMP10]] to <4 x i16> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <4 x i16> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <4 x i16> [[TMP14]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <4 x i16> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP7:%.*]] = bitcast <4 x i16> [[TMP11]] to i64 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast <4 x i16> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP6]], [[TMP7]] +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.mmx.pmulh.w(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP9:%.*]] = bitcast i64 [[_MSPROP]] to <4 x i16> +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to <4 x i16> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast <4 x i16> [[TMP9]] to <1 x i64> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <4 x i16> [[TMP3]] to <1 x i64> +; CHECK-NEXT: [[TMP5:%.*]] = extractelement <1 x i64> [[TMP4]], i32 0 +; CHECK-NEXT: [[TMP13:%.*]] = extractelement <1 x i64> [[TMP12]], i32 0 +; CHECK-NEXT: store i64 [[TMP5]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP13]] +; +entry: + %0 = bitcast <1 x i64> %b to <4 x i16> + %1 = bitcast <1 x i64> %a to <4 x i16> + %mmx_var.i = bitcast <4 x i16> %1 to x86_mmx + %mmx_var1.i = bitcast <4 x i16> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.pmulh.w(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <4 x i16> + %4 = bitcast <4 x i16> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.mmx.pmadd.wd(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test49(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test49( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP13:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP15:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP16:%.*]] = bitcast <1 x i64> [[TMP13]] to <4 x i16> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <4 x i16> +; CHECK-NEXT: [[TMP19:%.*]] = bitcast <1 x i64> [[TMP15]] to <4 x i16> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <4 x i16> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <4 x i16> [[TMP19]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <4 x i16> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP7:%.*]] = bitcast <4 x i16> [[TMP16]] to i64 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast <4 x i16> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[TMP8:%.*]] = or i64 [[TMP6]], [[TMP7]] +; CHECK-NEXT: [[TMP9:%.*]] = bitcast i64 [[TMP8]] to <2 x i32> +; CHECK-NEXT: [[TMP10:%.*]] = icmp ne <2 x i32> [[TMP9]], zeroinitializer +; CHECK-NEXT: [[TMP11:%.*]] = sext <2 x i1> [[TMP10]] to <2 x i32> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <2 x i32> [[TMP11]] to i64 +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.mmx.pmadd.wd(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP14:%.*]] = bitcast i64 [[TMP12]] to <2 x i32> +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to <2 x i32> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast <2 x i32> [[TMP14]] to <1 x i64> +; CHECK-NEXT: [[TMP17:%.*]] = bitcast <2 x i32> [[TMP3]] to <1 x i64> +; CHECK-NEXT: [[TMP5:%.*]] = extractelement <1 x i64> [[TMP4]], i32 0 +; CHECK-NEXT: [[TMP18:%.*]] = extractelement <1 x i64> [[TMP17]], i32 0 +; CHECK-NEXT: store i64 [[TMP5]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP18]] +; +entry: + %0 = bitcast <1 x i64> %b to <4 x i16> + %1 = bitcast <1 x i64> %a to <4 x i16> + %mmx_var.i = bitcast <4 x i16> %1 to x86_mmx + %mmx_var1.i = bitcast <4 x i16> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.pmadd.wd(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <2 x i32> + %4 = bitcast <2 x i32> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.mmx.psubus.w(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test48(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test48( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP8:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP11:%.*]] = bitcast <1 x i64> [[TMP8]] to <4 x i16> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <4 x i16> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <1 x i64> [[TMP10]] to <4 x i16> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <4 x i16> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <4 x i16> [[TMP14]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <4 x i16> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP7:%.*]] = bitcast <4 x i16> [[TMP11]] to i64 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast <4 x i16> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP6]], [[TMP7]] +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.mmx.psubus.w(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP9:%.*]] = bitcast i64 [[_MSPROP]] to <4 x i16> +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to <4 x i16> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast <4 x i16> [[TMP9]] to <1 x i64> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <4 x i16> [[TMP3]] to <1 x i64> +; CHECK-NEXT: [[TMP5:%.*]] = extractelement <1 x i64> [[TMP4]], i32 0 +; CHECK-NEXT: [[TMP13:%.*]] = extractelement <1 x i64> [[TMP12]], i32 0 +; CHECK-NEXT: store i64 [[TMP5]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP13]] +; +entry: + %0 = bitcast <1 x i64> %b to <4 x i16> + %1 = bitcast <1 x i64> %a to <4 x i16> + %mmx_var.i = bitcast <4 x i16> %1 to x86_mmx + %mmx_var1.i = bitcast <4 x i16> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.psubus.w(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <4 x i16> + %4 = bitcast <4 x i16> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.mmx.psubus.b(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test47(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test47( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP8:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP11:%.*]] = bitcast <1 x i64> [[TMP8]] to <8 x i8> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <8 x i8> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <1 x i64> [[TMP10]] to <8 x i8> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <8 x i8> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <8 x i8> [[TMP14]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <8 x i8> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP7:%.*]] = bitcast <8 x i8> [[TMP11]] to i64 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast <8 x i8> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP6]], [[TMP7]] +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.mmx.psubus.b(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP9:%.*]] = bitcast i64 [[_MSPROP]] to <8 x i8> +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to <8 x i8> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast <8 x i8> [[TMP9]] to <1 x i64> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <8 x i8> [[TMP3]] to <1 x i64> +; CHECK-NEXT: [[TMP5:%.*]] = extractelement <1 x i64> [[TMP4]], i32 0 +; CHECK-NEXT: [[TMP13:%.*]] = extractelement <1 x i64> [[TMP12]], i32 0 +; CHECK-NEXT: store i64 [[TMP5]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP13]] +; +entry: + %0 = bitcast <1 x i64> %b to <8 x i8> + %1 = bitcast <1 x i64> %a to <8 x i8> + %mmx_var.i = bitcast <8 x i8> %1 to x86_mmx + %mmx_var1.i = bitcast <8 x i8> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.psubus.b(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <8 x i8> + %4 = bitcast <8 x i8> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.mmx.psubs.w(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test46(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test46( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP8:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP11:%.*]] = bitcast <1 x i64> [[TMP8]] to <4 x i16> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <4 x i16> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <1 x i64> [[TMP10]] to <4 x i16> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <4 x i16> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <4 x i16> [[TMP14]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <4 x i16> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP7:%.*]] = bitcast <4 x i16> [[TMP11]] to i64 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast <4 x i16> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP6]], [[TMP7]] +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.mmx.psubs.w(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP9:%.*]] = bitcast i64 [[_MSPROP]] to <4 x i16> +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to <4 x i16> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast <4 x i16> [[TMP9]] to <1 x i64> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <4 x i16> [[TMP3]] to <1 x i64> +; CHECK-NEXT: [[TMP5:%.*]] = extractelement <1 x i64> [[TMP4]], i32 0 +; CHECK-NEXT: [[TMP13:%.*]] = extractelement <1 x i64> [[TMP12]], i32 0 +; CHECK-NEXT: store i64 [[TMP5]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP13]] +; +entry: + %0 = bitcast <1 x i64> %b to <4 x i16> + %1 = bitcast <1 x i64> %a to <4 x i16> + %mmx_var.i = bitcast <4 x i16> %1 to x86_mmx + %mmx_var1.i = bitcast <4 x i16> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.psubs.w(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <4 x i16> + %4 = bitcast <4 x i16> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.mmx.psubs.b(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test45(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test45( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP8:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP11:%.*]] = bitcast <1 x i64> [[TMP8]] to <8 x i8> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <8 x i8> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <1 x i64> [[TMP10]] to <8 x i8> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <8 x i8> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <8 x i8> [[TMP14]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <8 x i8> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP7:%.*]] = bitcast <8 x i8> [[TMP11]] to i64 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast <8 x i8> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP6]], [[TMP7]] +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.mmx.psubs.b(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP9:%.*]] = bitcast i64 [[_MSPROP]] to <8 x i8> +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to <8 x i8> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast <8 x i8> [[TMP9]] to <1 x i64> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <8 x i8> [[TMP3]] to <1 x i64> +; CHECK-NEXT: [[TMP5:%.*]] = extractelement <1 x i64> [[TMP4]], i32 0 +; CHECK-NEXT: [[TMP13:%.*]] = extractelement <1 x i64> [[TMP12]], i32 0 +; CHECK-NEXT: store i64 [[TMP5]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP13]] +; +entry: + %0 = bitcast <1 x i64> %b to <8 x i8> + %1 = bitcast <1 x i64> %a to <8 x i8> + %mmx_var.i = bitcast <8 x i8> %1 to x86_mmx + %mmx_var1.i = bitcast <8 x i8> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.psubs.b(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <8 x i8> + %4 = bitcast <8 x i8> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +define i64 @test44(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test44( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP4:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: [[TMP5:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[_MSPROP:%.*]] = extractelement <1 x i64> [[TMP4]], i32 0 +; CHECK-NEXT: [[TMP0:%.*]] = extractelement <1 x i64> [[A]], i32 0 +; CHECK-NEXT: [[MMX_VAR:%.*]] = bitcast i64 [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP1:%.*]] = extractelement <1 x i64> [[TMP5]], i32 0 +; CHECK-NEXT: [[TMP1:%.*]] = extractelement <1 x i64> [[B]], i32 0 +; CHECK-NEXT: [[MMX_VAR1:%.*]] = bitcast i64 [[TMP1]] to x86_mmx +; CHECK-NEXT: [[_MSPROP2:%.*]] = or i64 [[_MSPROP]], [[_MSPROP1]] +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.mmx.psub.q(x86_mmx [[MMX_VAR]], x86_mmx [[MMX_VAR1]]) +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to i64 +; CHECK-NEXT: store i64 [[_MSPROP2]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP3]] +; +entry: + %0 = extractelement <1 x i64> %a, i32 0 + %mmx_var = bitcast i64 %0 to x86_mmx + %1 = extractelement <1 x i64> %b, i32 0 + %mmx_var1 = bitcast i64 %1 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.psub.q(x86_mmx %mmx_var, x86_mmx %mmx_var1) + %3 = bitcast x86_mmx %2 to i64 + ret i64 %3 +} + +declare x86_mmx @llvm.x86.mmx.psub.q(x86_mmx, x86_mmx) nounwind readnone + +declare x86_mmx @llvm.x86.mmx.psub.d(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test43(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test43( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP8:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP11:%.*]] = bitcast <1 x i64> [[TMP8]] to <2 x i32> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <2 x i32> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <1 x i64> [[TMP10]] to <2 x i32> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <2 x i32> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <2 x i32> [[TMP14]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <2 x i32> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP7:%.*]] = bitcast <2 x i32> [[TMP11]] to i64 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast <2 x i32> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP6]], [[TMP7]] +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.mmx.psub.d(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP9:%.*]] = bitcast i64 [[_MSPROP]] to <2 x i32> +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to <2 x i32> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast <2 x i32> [[TMP9]] to <1 x i64> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <2 x i32> [[TMP3]] to <1 x i64> +; CHECK-NEXT: [[TMP5:%.*]] = extractelement <1 x i64> [[TMP4]], i32 0 +; CHECK-NEXT: [[TMP13:%.*]] = extractelement <1 x i64> [[TMP12]], i32 0 +; CHECK-NEXT: store i64 [[TMP5]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP13]] +; +entry: + %0 = bitcast <1 x i64> %b to <2 x i32> + %1 = bitcast <1 x i64> %a to <2 x i32> + %mmx_var.i = bitcast <2 x i32> %1 to x86_mmx + %mmx_var1.i = bitcast <2 x i32> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.psub.d(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <2 x i32> + %4 = bitcast <2 x i32> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.mmx.psub.w(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test42(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test42( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP8:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP11:%.*]] = bitcast <1 x i64> [[TMP8]] to <4 x i16> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <4 x i16> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <1 x i64> [[TMP10]] to <4 x i16> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <4 x i16> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <4 x i16> [[TMP14]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <4 x i16> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP7:%.*]] = bitcast <4 x i16> [[TMP11]] to i64 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast <4 x i16> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP6]], [[TMP7]] +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.mmx.psub.w(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP9:%.*]] = bitcast i64 [[_MSPROP]] to <4 x i16> +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to <4 x i16> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast <4 x i16> [[TMP9]] to <1 x i64> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <4 x i16> [[TMP3]] to <1 x i64> +; CHECK-NEXT: [[TMP5:%.*]] = extractelement <1 x i64> [[TMP4]], i32 0 +; CHECK-NEXT: [[TMP13:%.*]] = extractelement <1 x i64> [[TMP12]], i32 0 +; CHECK-NEXT: store i64 [[TMP5]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP13]] +; +entry: + %0 = bitcast <1 x i64> %b to <4 x i16> + %1 = bitcast <1 x i64> %a to <4 x i16> + %mmx_var.i = bitcast <4 x i16> %1 to x86_mmx + %mmx_var1.i = bitcast <4 x i16> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.psub.w(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <4 x i16> + %4 = bitcast <4 x i16> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.mmx.psub.b(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test41(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test41( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP8:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP11:%.*]] = bitcast <1 x i64> [[TMP8]] to <8 x i8> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <8 x i8> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <1 x i64> [[TMP10]] to <8 x i8> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <8 x i8> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <8 x i8> [[TMP14]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <8 x i8> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP7:%.*]] = bitcast <8 x i8> [[TMP11]] to i64 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast <8 x i8> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP6]], [[TMP7]] +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.mmx.psub.b(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP9:%.*]] = bitcast i64 [[_MSPROP]] to <8 x i8> +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to <8 x i8> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast <8 x i8> [[TMP9]] to <1 x i64> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <8 x i8> [[TMP3]] to <1 x i64> +; CHECK-NEXT: [[TMP5:%.*]] = extractelement <1 x i64> [[TMP4]], i32 0 +; CHECK-NEXT: [[TMP13:%.*]] = extractelement <1 x i64> [[TMP12]], i32 0 +; CHECK-NEXT: store i64 [[TMP5]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP13]] +; +entry: + %0 = bitcast <1 x i64> %b to <8 x i8> + %1 = bitcast <1 x i64> %a to <8 x i8> + %mmx_var.i = bitcast <8 x i8> %1 to x86_mmx + %mmx_var1.i = bitcast <8 x i8> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.psub.b(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <8 x i8> + %4 = bitcast <8 x i8> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.mmx.paddus.w(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test40(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test40( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP8:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP11:%.*]] = bitcast <1 x i64> [[TMP8]] to <4 x i16> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <4 x i16> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <1 x i64> [[TMP10]] to <4 x i16> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <4 x i16> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <4 x i16> [[TMP14]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <4 x i16> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP7:%.*]] = bitcast <4 x i16> [[TMP11]] to i64 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast <4 x i16> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP6]], [[TMP7]] +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.mmx.paddus.w(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP9:%.*]] = bitcast i64 [[_MSPROP]] to <4 x i16> +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to <4 x i16> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast <4 x i16> [[TMP9]] to <1 x i64> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <4 x i16> [[TMP3]] to <1 x i64> +; CHECK-NEXT: [[TMP5:%.*]] = extractelement <1 x i64> [[TMP4]], i32 0 +; CHECK-NEXT: [[TMP13:%.*]] = extractelement <1 x i64> [[TMP12]], i32 0 +; CHECK-NEXT: store i64 [[TMP5]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP13]] +; +entry: + %0 = bitcast <1 x i64> %b to <4 x i16> + %1 = bitcast <1 x i64> %a to <4 x i16> + %mmx_var.i = bitcast <4 x i16> %1 to x86_mmx + %mmx_var1.i = bitcast <4 x i16> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.paddus.w(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <4 x i16> + %4 = bitcast <4 x i16> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.mmx.paddus.b(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test39(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test39( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP8:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP11:%.*]] = bitcast <1 x i64> [[TMP8]] to <8 x i8> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <8 x i8> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <1 x i64> [[TMP10]] to <8 x i8> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <8 x i8> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <8 x i8> [[TMP14]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <8 x i8> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP7:%.*]] = bitcast <8 x i8> [[TMP11]] to i64 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast <8 x i8> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP6]], [[TMP7]] +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.mmx.paddus.b(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP9:%.*]] = bitcast i64 [[_MSPROP]] to <8 x i8> +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to <8 x i8> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast <8 x i8> [[TMP9]] to <1 x i64> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <8 x i8> [[TMP3]] to <1 x i64> +; CHECK-NEXT: [[TMP5:%.*]] = extractelement <1 x i64> [[TMP4]], i32 0 +; CHECK-NEXT: [[TMP13:%.*]] = extractelement <1 x i64> [[TMP12]], i32 0 +; CHECK-NEXT: store i64 [[TMP5]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP13]] +; +entry: + %0 = bitcast <1 x i64> %b to <8 x i8> + %1 = bitcast <1 x i64> %a to <8 x i8> + %mmx_var.i = bitcast <8 x i8> %1 to x86_mmx + %mmx_var1.i = bitcast <8 x i8> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.paddus.b(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <8 x i8> + %4 = bitcast <8 x i8> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.mmx.padds.w(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test38(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test38( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP8:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP11:%.*]] = bitcast <1 x i64> [[TMP8]] to <4 x i16> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <4 x i16> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <1 x i64> [[TMP10]] to <4 x i16> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <4 x i16> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <4 x i16> [[TMP14]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <4 x i16> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP7:%.*]] = bitcast <4 x i16> [[TMP11]] to i64 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast <4 x i16> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP6]], [[TMP7]] +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.mmx.padds.w(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP9:%.*]] = bitcast i64 [[_MSPROP]] to <4 x i16> +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to <4 x i16> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast <4 x i16> [[TMP9]] to <1 x i64> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <4 x i16> [[TMP3]] to <1 x i64> +; CHECK-NEXT: [[TMP5:%.*]] = extractelement <1 x i64> [[TMP4]], i32 0 +; CHECK-NEXT: [[TMP13:%.*]] = extractelement <1 x i64> [[TMP12]], i32 0 +; CHECK-NEXT: store i64 [[TMP5]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP13]] +; +entry: + %0 = bitcast <1 x i64> %b to <4 x i16> + %1 = bitcast <1 x i64> %a to <4 x i16> + %mmx_var.i = bitcast <4 x i16> %1 to x86_mmx + %mmx_var1.i = bitcast <4 x i16> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.padds.w(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <4 x i16> + %4 = bitcast <4 x i16> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.mmx.padds.b(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test37(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test37( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP8:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP11:%.*]] = bitcast <1 x i64> [[TMP8]] to <8 x i8> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <8 x i8> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <1 x i64> [[TMP10]] to <8 x i8> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <8 x i8> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <8 x i8> [[TMP14]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <8 x i8> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP7:%.*]] = bitcast <8 x i8> [[TMP11]] to i64 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast <8 x i8> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP6]], [[TMP7]] +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.mmx.padds.b(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP9:%.*]] = bitcast i64 [[_MSPROP]] to <8 x i8> +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to <8 x i8> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast <8 x i8> [[TMP9]] to <1 x i64> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <8 x i8> [[TMP3]] to <1 x i64> +; CHECK-NEXT: [[TMP5:%.*]] = extractelement <1 x i64> [[TMP4]], i32 0 +; CHECK-NEXT: [[TMP13:%.*]] = extractelement <1 x i64> [[TMP12]], i32 0 +; CHECK-NEXT: store i64 [[TMP5]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP13]] +; +entry: + %0 = bitcast <1 x i64> %b to <8 x i8> + %1 = bitcast <1 x i64> %a to <8 x i8> + %mmx_var.i = bitcast <8 x i8> %1 to x86_mmx + %mmx_var1.i = bitcast <8 x i8> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.padds.b(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <8 x i8> + %4 = bitcast <8 x i8> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.mmx.padd.q(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test36(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test36( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP4:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: [[TMP5:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[_MSPROP:%.*]] = extractelement <1 x i64> [[TMP4]], i32 0 +; CHECK-NEXT: [[TMP0:%.*]] = extractelement <1 x i64> [[A]], i32 0 +; CHECK-NEXT: [[MMX_VAR:%.*]] = bitcast i64 [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP1:%.*]] = extractelement <1 x i64> [[TMP5]], i32 0 +; CHECK-NEXT: [[TMP1:%.*]] = extractelement <1 x i64> [[B]], i32 0 +; CHECK-NEXT: [[MMX_VAR1:%.*]] = bitcast i64 [[TMP1]] to x86_mmx +; CHECK-NEXT: [[_MSPROP2:%.*]] = or i64 [[_MSPROP]], [[_MSPROP1]] +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.mmx.padd.q(x86_mmx [[MMX_VAR]], x86_mmx [[MMX_VAR1]]) +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to i64 +; CHECK-NEXT: store i64 [[_MSPROP2]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP3]] +; +entry: + %0 = extractelement <1 x i64> %a, i32 0 + %mmx_var = bitcast i64 %0 to x86_mmx + %1 = extractelement <1 x i64> %b, i32 0 + %mmx_var1 = bitcast i64 %1 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.padd.q(x86_mmx %mmx_var, x86_mmx %mmx_var1) + %3 = bitcast x86_mmx %2 to i64 + ret i64 %3 +} + +declare x86_mmx @llvm.x86.mmx.padd.d(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test35(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test35( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP8:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP11:%.*]] = bitcast <1 x i64> [[TMP8]] to <2 x i32> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <2 x i32> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <1 x i64> [[TMP10]] to <2 x i32> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <2 x i32> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <2 x i32> [[TMP14]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <2 x i32> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP7:%.*]] = bitcast <2 x i32> [[TMP11]] to i64 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast <2 x i32> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP6]], [[TMP7]] +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.mmx.padd.d(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP9:%.*]] = bitcast i64 [[_MSPROP]] to <2 x i32> +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to <2 x i32> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast <2 x i32> [[TMP9]] to <1 x i64> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <2 x i32> [[TMP3]] to <1 x i64> +; CHECK-NEXT: [[TMP5:%.*]] = extractelement <1 x i64> [[TMP4]], i32 0 +; CHECK-NEXT: [[TMP13:%.*]] = extractelement <1 x i64> [[TMP12]], i32 0 +; CHECK-NEXT: store i64 [[TMP5]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP13]] +; +entry: + %0 = bitcast <1 x i64> %b to <2 x i32> + %1 = bitcast <1 x i64> %a to <2 x i32> + %mmx_var.i = bitcast <2 x i32> %1 to x86_mmx + %mmx_var1.i = bitcast <2 x i32> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.padd.d(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <2 x i32> + %4 = bitcast <2 x i32> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.mmx.padd.w(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test34(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test34( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP8:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP11:%.*]] = bitcast <1 x i64> [[TMP8]] to <4 x i16> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <4 x i16> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <1 x i64> [[TMP10]] to <4 x i16> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <4 x i16> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <4 x i16> [[TMP14]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <4 x i16> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP7:%.*]] = bitcast <4 x i16> [[TMP11]] to i64 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast <4 x i16> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP6]], [[TMP7]] +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.mmx.padd.w(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP9:%.*]] = bitcast i64 [[_MSPROP]] to <4 x i16> +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to <4 x i16> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast <4 x i16> [[TMP9]] to <1 x i64> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <4 x i16> [[TMP3]] to <1 x i64> +; CHECK-NEXT: [[TMP5:%.*]] = extractelement <1 x i64> [[TMP4]], i32 0 +; CHECK-NEXT: [[TMP13:%.*]] = extractelement <1 x i64> [[TMP12]], i32 0 +; CHECK-NEXT: store i64 [[TMP5]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP13]] +; +entry: + %0 = bitcast <1 x i64> %b to <4 x i16> + %1 = bitcast <1 x i64> %a to <4 x i16> + %mmx_var.i = bitcast <4 x i16> %1 to x86_mmx + %mmx_var1.i = bitcast <4 x i16> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.padd.w(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <4 x i16> + %4 = bitcast <4 x i16> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.mmx.padd.b(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test33(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test33( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP8:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP11:%.*]] = bitcast <1 x i64> [[TMP8]] to <8 x i8> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <8 x i8> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <1 x i64> [[TMP10]] to <8 x i8> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <8 x i8> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <8 x i8> [[TMP14]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <8 x i8> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP7:%.*]] = bitcast <8 x i8> [[TMP11]] to i64 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast <8 x i8> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP6]], [[TMP7]] +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.mmx.padd.b(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP9:%.*]] = bitcast i64 [[_MSPROP]] to <8 x i8> +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to <8 x i8> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast <8 x i8> [[TMP9]] to <1 x i64> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <8 x i8> [[TMP3]] to <1 x i64> +; CHECK-NEXT: [[TMP5:%.*]] = extractelement <1 x i64> [[TMP4]], i32 0 +; CHECK-NEXT: [[TMP13:%.*]] = extractelement <1 x i64> [[TMP12]], i32 0 +; CHECK-NEXT: store i64 [[TMP5]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP13]] +; +entry: + %0 = bitcast <1 x i64> %b to <8 x i8> + %1 = bitcast <1 x i64> %a to <8 x i8> + %mmx_var.i = bitcast <8 x i8> %1 to x86_mmx + %mmx_var1.i = bitcast <8 x i8> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.padd.b(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <8 x i8> + %4 = bitcast <8 x i8> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.mmx.psad.bw(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test32(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test32( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP5:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP12:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP13:%.*]] = bitcast <1 x i64> [[TMP5]] to <8 x i8> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <8 x i8> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast <1 x i64> [[TMP12]] to <8 x i8> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <8 x i8> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <8 x i8> [[TMP4]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <8 x i8> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP7:%.*]] = bitcast <8 x i8> [[TMP13]] to i64 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast <8 x i8> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[TMP8:%.*]] = or i64 [[TMP6]], [[TMP7]] +; CHECK-NEXT: [[TMP9:%.*]] = icmp ne i64 [[TMP8]], 0 +; CHECK-NEXT: [[TMP10:%.*]] = sext i1 [[TMP9]] to i64 +; CHECK-NEXT: [[TMP11:%.*]] = lshr i64 [[TMP10]], 48 +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.mmx.psad.bw(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to i64 +; CHECK-NEXT: store i64 [[TMP11]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP3]] +; +entry: + %0 = bitcast <1 x i64> %b to <8 x i8> + %1 = bitcast <1 x i64> %a to <8 x i8> + %mmx_var.i = bitcast <8 x i8> %1 to x86_mmx + %mmx_var1.i = bitcast <8 x i8> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.psad.bw(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to i64 + ret i64 %3 +} + +declare x86_mmx @llvm.x86.mmx.pmins.w(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test31(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test31( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP8:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP11:%.*]] = bitcast <1 x i64> [[TMP8]] to <4 x i16> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <4 x i16> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <1 x i64> [[TMP10]] to <4 x i16> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <4 x i16> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <4 x i16> [[TMP14]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <4 x i16> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP7:%.*]] = bitcast <4 x i16> [[TMP11]] to i64 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast <4 x i16> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP6]], [[TMP7]] +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.mmx.pmins.w(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP9:%.*]] = bitcast i64 [[_MSPROP]] to <4 x i16> +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to <4 x i16> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast <4 x i16> [[TMP9]] to <1 x i64> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <4 x i16> [[TMP3]] to <1 x i64> +; CHECK-NEXT: [[TMP5:%.*]] = extractelement <1 x i64> [[TMP4]], i32 0 +; CHECK-NEXT: [[TMP13:%.*]] = extractelement <1 x i64> [[TMP12]], i32 0 +; CHECK-NEXT: store i64 [[TMP5]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP13]] +; +entry: + %0 = bitcast <1 x i64> %b to <4 x i16> + %1 = bitcast <1 x i64> %a to <4 x i16> + %mmx_var.i = bitcast <4 x i16> %1 to x86_mmx + %mmx_var1.i = bitcast <4 x i16> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.pmins.w(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <4 x i16> + %4 = bitcast <4 x i16> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.mmx.pminu.b(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test30(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test30( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP8:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP11:%.*]] = bitcast <1 x i64> [[TMP8]] to <8 x i8> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <8 x i8> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <1 x i64> [[TMP10]] to <8 x i8> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <8 x i8> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <8 x i8> [[TMP14]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <8 x i8> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP7:%.*]] = bitcast <8 x i8> [[TMP11]] to i64 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast <8 x i8> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP6]], [[TMP7]] +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.mmx.pminu.b(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP9:%.*]] = bitcast i64 [[_MSPROP]] to <8 x i8> +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to <8 x i8> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast <8 x i8> [[TMP9]] to <1 x i64> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <8 x i8> [[TMP3]] to <1 x i64> +; CHECK-NEXT: [[TMP5:%.*]] = extractelement <1 x i64> [[TMP4]], i32 0 +; CHECK-NEXT: [[TMP13:%.*]] = extractelement <1 x i64> [[TMP12]], i32 0 +; CHECK-NEXT: store i64 [[TMP5]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP13]] +; +entry: + %0 = bitcast <1 x i64> %b to <8 x i8> + %1 = bitcast <1 x i64> %a to <8 x i8> + %mmx_var.i = bitcast <8 x i8> %1 to x86_mmx + %mmx_var1.i = bitcast <8 x i8> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.pminu.b(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <8 x i8> + %4 = bitcast <8 x i8> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.mmx.pmaxs.w(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test29(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test29( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP8:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP11:%.*]] = bitcast <1 x i64> [[TMP8]] to <4 x i16> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <4 x i16> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <1 x i64> [[TMP10]] to <4 x i16> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <4 x i16> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <4 x i16> [[TMP14]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <4 x i16> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP7:%.*]] = bitcast <4 x i16> [[TMP11]] to i64 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast <4 x i16> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP6]], [[TMP7]] +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.mmx.pmaxs.w(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP9:%.*]] = bitcast i64 [[_MSPROP]] to <4 x i16> +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to <4 x i16> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast <4 x i16> [[TMP9]] to <1 x i64> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <4 x i16> [[TMP3]] to <1 x i64> +; CHECK-NEXT: [[TMP5:%.*]] = extractelement <1 x i64> [[TMP4]], i32 0 +; CHECK-NEXT: [[TMP13:%.*]] = extractelement <1 x i64> [[TMP12]], i32 0 +; CHECK-NEXT: store i64 [[TMP5]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP13]] +; +entry: + %0 = bitcast <1 x i64> %b to <4 x i16> + %1 = bitcast <1 x i64> %a to <4 x i16> + %mmx_var.i = bitcast <4 x i16> %1 to x86_mmx + %mmx_var1.i = bitcast <4 x i16> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.pmaxs.w(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <4 x i16> + %4 = bitcast <4 x i16> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.mmx.pmaxu.b(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test28(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test28( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP8:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP11:%.*]] = bitcast <1 x i64> [[TMP8]] to <8 x i8> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <8 x i8> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <1 x i64> [[TMP10]] to <8 x i8> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <8 x i8> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <8 x i8> [[TMP14]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <8 x i8> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP7:%.*]] = bitcast <8 x i8> [[TMP11]] to i64 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast <8 x i8> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP6]], [[TMP7]] +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.mmx.pmaxu.b(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP9:%.*]] = bitcast i64 [[_MSPROP]] to <8 x i8> +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to <8 x i8> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast <8 x i8> [[TMP9]] to <1 x i64> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <8 x i8> [[TMP3]] to <1 x i64> +; CHECK-NEXT: [[TMP5:%.*]] = extractelement <1 x i64> [[TMP4]], i32 0 +; CHECK-NEXT: [[TMP13:%.*]] = extractelement <1 x i64> [[TMP12]], i32 0 +; CHECK-NEXT: store i64 [[TMP5]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP13]] +; +entry: + %0 = bitcast <1 x i64> %b to <8 x i8> + %1 = bitcast <1 x i64> %a to <8 x i8> + %mmx_var.i = bitcast <8 x i8> %1 to x86_mmx + %mmx_var1.i = bitcast <8 x i8> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.pmaxu.b(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <8 x i8> + %4 = bitcast <8 x i8> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.mmx.pavg.w(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test27(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test27( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP8:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP11:%.*]] = bitcast <1 x i64> [[TMP8]] to <4 x i16> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <4 x i16> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <1 x i64> [[TMP10]] to <4 x i16> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <4 x i16> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <4 x i16> [[TMP14]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <4 x i16> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP7:%.*]] = bitcast <4 x i16> [[TMP11]] to i64 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast <4 x i16> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP6]], [[TMP7]] +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.mmx.pavg.w(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP9:%.*]] = bitcast i64 [[_MSPROP]] to <4 x i16> +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to <4 x i16> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast <4 x i16> [[TMP9]] to <1 x i64> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <4 x i16> [[TMP3]] to <1 x i64> +; CHECK-NEXT: [[TMP5:%.*]] = extractelement <1 x i64> [[TMP4]], i32 0 +; CHECK-NEXT: [[TMP13:%.*]] = extractelement <1 x i64> [[TMP12]], i32 0 +; CHECK-NEXT: store i64 [[TMP5]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP13]] +; +entry: + %0 = bitcast <1 x i64> %b to <4 x i16> + %1 = bitcast <1 x i64> %a to <4 x i16> + %mmx_var.i = bitcast <4 x i16> %1 to x86_mmx + %mmx_var1.i = bitcast <4 x i16> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.pavg.w(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <4 x i16> + %4 = bitcast <4 x i16> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.mmx.pavg.b(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test26(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test26( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP8:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP11:%.*]] = bitcast <1 x i64> [[TMP8]] to <8 x i8> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <8 x i8> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <1 x i64> [[TMP10]] to <8 x i8> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <8 x i8> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <8 x i8> [[TMP14]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <8 x i8> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP7:%.*]] = bitcast <8 x i8> [[TMP11]] to i64 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast <8 x i8> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP6]], [[TMP7]] +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.mmx.pavg.b(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP9:%.*]] = bitcast i64 [[_MSPROP]] to <8 x i8> +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to <8 x i8> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast <8 x i8> [[TMP9]] to <1 x i64> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <8 x i8> [[TMP3]] to <1 x i64> +; CHECK-NEXT: [[TMP5:%.*]] = extractelement <1 x i64> [[TMP4]], i32 0 +; CHECK-NEXT: [[TMP13:%.*]] = extractelement <1 x i64> [[TMP12]], i32 0 +; CHECK-NEXT: store i64 [[TMP5]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP13]] +; +entry: + %0 = bitcast <1 x i64> %b to <8 x i8> + %1 = bitcast <1 x i64> %a to <8 x i8> + %mmx_var.i = bitcast <8 x i8> %1 to x86_mmx + %mmx_var1.i = bitcast <8 x i8> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.pavg.b(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <8 x i8> + %4 = bitcast <8 x i8> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare void @llvm.x86.mmx.movnt.dq(ptr, x86_mmx) nounwind + +define void @test25(ptr %p, <1 x i64> %a) nounwind optsize ssp #0 { +; CHECK-LABEL: define void @test25( +; CHECK-SAME: ptr [[P:%.*]], <1 x i64> [[A:%.*]]) #[[ATTR3:[0-9]+]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP2:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP1:%.*]] = load i64, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[_MSPROP:%.*]] = extractelement <1 x i64> [[TMP2]], i32 0 +; CHECK-NEXT: [[TMP0:%.*]] = extractelement <1 x i64> [[A]], i32 0 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast i64 [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSCMP:%.*]] = icmp ne i64 [[TMP1]], 0 +; CHECK-NEXT: [[_MSCMP1:%.*]] = icmp ne i64 [[_MSPROP]], 0 +; CHECK-NEXT: [[_MSOR:%.*]] = or i1 [[_MSCMP]], [[_MSCMP1]] +; CHECK-NEXT: br i1 [[_MSOR]], label [[TMP3:%.*]], label [[TMP4:%.*]], !prof [[PROF0:![0-9]+]] +; CHECK: 3: +; CHECK-NEXT: call void @__msan_warning_noreturn() #[[ATTR6:[0-9]+]] +; CHECK-NEXT: unreachable +; CHECK: 4: +; CHECK-NEXT: tail call void @llvm.x86.mmx.movnt.dq(ptr [[P]], x86_mmx [[MMX_VAR_I]]) #[[ATTR2]] +; CHECK-NEXT: ret void +; +entry: + %0 = extractelement <1 x i64> %a, i32 0 + %mmx_var.i = bitcast i64 %0 to x86_mmx + tail call void @llvm.x86.mmx.movnt.dq(ptr %p, x86_mmx %mmx_var.i) nounwind + ret void +} + +declare i32 @llvm.x86.mmx.pmovmskb(x86_mmx) nounwind readnone + +define i32 @test24(<1 x i64> %a) #0 { +; CHECK-LABEL: define i32 @test24( +; CHECK-SAME: <1 x i64> [[A:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP2:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <1 x i64> [[TMP2]] to <8 x i8> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[A]] to <8 x i8> +; CHECK-NEXT: [[TMP3:%.*]] = bitcast <8 x i8> [[TMP6]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <8 x i8> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSCMP:%.*]] = icmp ne i64 [[TMP3]], 0 +; CHECK-NEXT: br i1 [[_MSCMP]], label [[TMP4:%.*]], label [[TMP5:%.*]], !prof [[PROF0]] +; CHECK: 4: +; CHECK-NEXT: call void @__msan_warning_noreturn() #[[ATTR6]] +; CHECK-NEXT: unreachable +; CHECK: 5: +; CHECK-NEXT: [[TMP1:%.*]] = tail call i32 @llvm.x86.mmx.pmovmskb(x86_mmx [[MMX_VAR_I]]) #[[ATTR2]] +; CHECK-NEXT: store i32 0, ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i32 [[TMP1]] +; +entry: + %0 = bitcast <1 x i64> %a to <8 x i8> + %mmx_var.i = bitcast <8 x i8> %0 to x86_mmx + %1 = tail call i32 @llvm.x86.mmx.pmovmskb(x86_mmx %mmx_var.i) nounwind + ret i32 %1 +} + +declare void @llvm.x86.mmx.maskmovq(x86_mmx, x86_mmx, ptr) nounwind + +define void @test23(<1 x i64> %d, <1 x i64> %n, ptr %p) nounwind optsize ssp #0 { +; CHECK-LABEL: define void @test23( +; CHECK-SAME: <1 x i64> [[D:%.*]], <1 x i64> [[N:%.*]], ptr [[P:%.*]]) #[[ATTR3]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP4:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP6:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: [[TMP2:%.*]] = load i64, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 16) to ptr), align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP3:%.*]] = bitcast <1 x i64> [[TMP4]] to <8 x i8> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[N]] to <8 x i8> +; CHECK-NEXT: [[TMP5:%.*]] = bitcast <1 x i64> [[TMP6]] to <8 x i8> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[D]] to <8 x i8> +; CHECK-NEXT: [[TMP7:%.*]] = bitcast <8 x i8> [[TMP5]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <8 x i8> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP8:%.*]] = bitcast <8 x i8> [[TMP3]] to i64 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast <8 x i8> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSCMP:%.*]] = icmp ne i64 [[TMP7]], 0 +; CHECK-NEXT: [[_MSCMP1:%.*]] = icmp ne i64 [[TMP8]], 0 +; CHECK-NEXT: [[_MSOR:%.*]] = or i1 [[_MSCMP]], [[_MSCMP1]] +; CHECK-NEXT: [[_MSCMP2:%.*]] = icmp ne i64 [[TMP2]], 0 +; CHECK-NEXT: [[_MSOR3:%.*]] = or i1 [[_MSOR]], [[_MSCMP2]] +; CHECK-NEXT: br i1 [[_MSOR3]], label [[TMP9:%.*]], label [[TMP10:%.*]], !prof [[PROF0]] +; CHECK: 9: +; CHECK-NEXT: call void @__msan_warning_noreturn() #[[ATTR6]] +; CHECK-NEXT: unreachable +; CHECK: 10: +; CHECK-NEXT: tail call void @llvm.x86.mmx.maskmovq(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]], ptr [[P]]) #[[ATTR2]] +; CHECK-NEXT: ret void +; +entry: + %0 = bitcast <1 x i64> %n to <8 x i8> + %1 = bitcast <1 x i64> %d to <8 x i8> + %mmx_var.i = bitcast <8 x i8> %1 to x86_mmx + %mmx_var1.i = bitcast <8 x i8> %0 to x86_mmx + tail call void @llvm.x86.mmx.maskmovq(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i, ptr %p) nounwind + ret void +} + +declare x86_mmx @llvm.x86.mmx.pmulhu.w(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test22(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test22( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP8:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP11:%.*]] = bitcast <1 x i64> [[TMP8]] to <4 x i16> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <4 x i16> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <1 x i64> [[TMP10]] to <4 x i16> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <4 x i16> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <4 x i16> [[TMP14]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <4 x i16> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP7:%.*]] = bitcast <4 x i16> [[TMP11]] to i64 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast <4 x i16> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP6]], [[TMP7]] +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.mmx.pmulhu.w(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP9:%.*]] = bitcast i64 [[_MSPROP]] to <4 x i16> +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to <4 x i16> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast <4 x i16> [[TMP9]] to <1 x i64> +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <4 x i16> [[TMP3]] to <1 x i64> +; CHECK-NEXT: [[TMP5:%.*]] = extractelement <1 x i64> [[TMP4]], i32 0 +; CHECK-NEXT: [[TMP13:%.*]] = extractelement <1 x i64> [[TMP12]], i32 0 +; CHECK-NEXT: store i64 [[TMP5]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP13]] +; +entry: + %0 = bitcast <1 x i64> %b to <4 x i16> + %1 = bitcast <1 x i64> %a to <4 x i16> + %mmx_var.i = bitcast <4 x i16> %1 to x86_mmx + %mmx_var1.i = bitcast <4 x i16> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.pmulhu.w(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to <4 x i16> + %4 = bitcast <4 x i16> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.sse.pshuf.w(x86_mmx, i8) nounwind readnone + +define i64 @test21(<1 x i64> %a) #0 { +; CHECK-LABEL: define i64 @test21( +; CHECK-SAME: <1 x i64> [[A:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP7:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP8:%.*]] = bitcast <1 x i64> [[TMP7]] to <4 x i16> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[A]] to <4 x i16> +; CHECK-NEXT: [[TMP9:%.*]] = bitcast <4 x i16> [[TMP8]] to i64 +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <4 x i16> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSCMP:%.*]] = icmp ne i64 [[TMP9]], 0 +; CHECK-NEXT: br i1 [[_MSCMP]], label [[TMP10:%.*]], label [[TMP6:%.*]], !prof [[PROF0]] +; CHECK: 5: +; CHECK-NEXT: call void @__msan_warning_noreturn() #[[ATTR6]] +; CHECK-NEXT: unreachable +; CHECK: 6: +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.sse.pshuf.w(x86_mmx [[TMP1]], i8 3) #[[ATTR5]] +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to <4 x i16> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast <4 x i16> [[TMP3]] to <1 x i64> +; CHECK-NEXT: [[TMP5:%.*]] = extractelement <1 x i64> [[TMP4]], i32 0 +; CHECK-NEXT: store i64 0, ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP5]] +; +entry: + %0 = bitcast <1 x i64> %a to <4 x i16> + %1 = bitcast <4 x i16> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.sse.pshuf.w(x86_mmx %1, i8 3) nounwind readnone + %3 = bitcast x86_mmx %2 to <4 x i16> + %4 = bitcast <4 x i16> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +define i32 @test21_2(<1 x i64> %a) #0 { +; CHECK-LABEL: define i32 @test21_2( +; CHECK-SAME: <1 x i64> [[A:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP7:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP8:%.*]] = bitcast <1 x i64> [[TMP7]] to <4 x i16> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[A]] to <4 x i16> +; CHECK-NEXT: [[TMP9:%.*]] = bitcast <4 x i16> [[TMP8]] to i64 +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <4 x i16> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSCMP:%.*]] = icmp ne i64 [[TMP9]], 0 +; CHECK-NEXT: br i1 [[_MSCMP]], label [[TMP10:%.*]], label [[TMP6:%.*]], !prof [[PROF0]] +; CHECK: 5: +; CHECK-NEXT: call void @__msan_warning_noreturn() #[[ATTR6]] +; CHECK-NEXT: unreachable +; CHECK: 6: +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.sse.pshuf.w(x86_mmx [[TMP1]], i8 3) #[[ATTR5]] +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to <4 x i16> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast <4 x i16> [[TMP3]] to <2 x i32> +; CHECK-NEXT: [[TMP5:%.*]] = extractelement <2 x i32> [[TMP4]], i32 0 +; CHECK-NEXT: store i32 0, ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i32 [[TMP5]] +; +entry: + %0 = bitcast <1 x i64> %a to <4 x i16> + %1 = bitcast <4 x i16> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.sse.pshuf.w(x86_mmx %1, i8 3) nounwind readnone + %3 = bitcast x86_mmx %2 to <4 x i16> + %4 = bitcast <4 x i16> %3 to <2 x i32> + %5 = extractelement <2 x i32> %4, i32 0 + ret i32 %5 +} + +declare x86_mmx @llvm.x86.mmx.pmulu.dq(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test20(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test20( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP5:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP8:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP9:%.*]] = bitcast <1 x i64> [[TMP5]] to <2 x i32> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <2 x i32> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast <1 x i64> [[TMP8]] to <2 x i32> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <2 x i32> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <2 x i32> [[TMP4]] to i64 +; CHECK-NEXT: [[MMX_VAR_I:%.*]] = bitcast <2 x i32> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP7:%.*]] = bitcast <2 x i32> [[TMP9]] to i64 +; CHECK-NEXT: [[MMX_VAR1_I:%.*]] = bitcast <2 x i32> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP6]], [[TMP7]] +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.mmx.pmulu.dq(x86_mmx [[MMX_VAR_I]], x86_mmx [[MMX_VAR1_I]]) #[[ATTR2]] +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to i64 +; CHECK-NEXT: store i64 [[_MSPROP]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP3]] +; +entry: + %0 = bitcast <1 x i64> %b to <2 x i32> + %1 = bitcast <1 x i64> %a to <2 x i32> + %mmx_var.i = bitcast <2 x i32> %1 to x86_mmx + %mmx_var1.i = bitcast <2 x i32> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.pmulu.dq(x86_mmx %mmx_var.i, x86_mmx %mmx_var1.i) nounwind + %3 = bitcast x86_mmx %2 to i64 + ret i64 %3 +} + +declare <2 x double> @llvm.x86.sse.cvtpi2pd(x86_mmx) nounwind readnone + +define <2 x double> @test19(<1 x i64> %a) #0 { +; CHECK-LABEL: define <2 x double> @test19( +; CHECK-SAME: <1 x i64> [[A:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP4:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP7:%.*]] = bitcast <1 x i64> [[TMP4]] to <2 x i32> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[A]] to <2 x i32> +; CHECK-NEXT: [[TMP3:%.*]] = bitcast <2 x i32> [[TMP7]] to i64 +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <2 x i32> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSCMP:%.*]] = icmp ne i64 [[TMP3]], 0 +; CHECK-NEXT: br i1 [[_MSCMP]], label [[TMP5:%.*]], label [[TMP6:%.*]], !prof [[PROF0]] +; CHECK: 5: +; CHECK-NEXT: call void @__msan_warning_noreturn() #[[ATTR6]] +; CHECK-NEXT: unreachable +; CHECK: 6: +; CHECK-NEXT: [[TMP2:%.*]] = tail call <2 x double> @llvm.x86.sse.cvtpi2pd(x86_mmx [[TMP1]]) #[[ATTR5]] +; CHECK-NEXT: store <2 x i64> zeroinitializer, ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret <2 x double> [[TMP2]] +; +entry: + %0 = bitcast <1 x i64> %a to <2 x i32> + %1 = bitcast <2 x i32> %0 to x86_mmx + %2 = tail call <2 x double> @llvm.x86.sse.cvtpi2pd(x86_mmx %1) nounwind readnone + ret <2 x double> %2 +} + +declare x86_mmx @llvm.x86.sse.cvttpd2pi(<2 x double>) nounwind readnone + +define i64 @test18(<2 x double> %a) #0 { +; CHECK-LABEL: define i64 @test18( +; CHECK-SAME: <2 x double> [[A:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP4:%.*]] = load <2 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP5:%.*]] = bitcast <2 x i64> [[TMP4]] to i128 +; CHECK-NEXT: [[_MSCMP:%.*]] = icmp ne i128 [[TMP5]], 0 +; CHECK-NEXT: br i1 [[_MSCMP]], label [[TMP6:%.*]], label [[TMP7:%.*]], !prof [[PROF0]] +; CHECK: 2: +; CHECK-NEXT: call void @__msan_warning_noreturn() #[[ATTR6]] +; CHECK-NEXT: unreachable +; CHECK: 3: +; CHECK-NEXT: [[TMP0:%.*]] = tail call x86_mmx @llvm.x86.sse.cvttpd2pi(<2 x double> [[A]]) #[[ATTR5]] +; CHECK-NEXT: [[TMP1:%.*]] = bitcast x86_mmx [[TMP0]] to <2 x i32> +; CHECK-NEXT: [[TMP2:%.*]] = bitcast <2 x i32> [[TMP1]] to <1 x i64> +; CHECK-NEXT: [[TMP3:%.*]] = extractelement <1 x i64> [[TMP2]], i32 0 +; CHECK-NEXT: store i64 0, ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP3]] +; +entry: + %0 = tail call x86_mmx @llvm.x86.sse.cvttpd2pi(<2 x double> %a) nounwind readnone + %1 = bitcast x86_mmx %0 to <2 x i32> + %2 = bitcast <2 x i32> %1 to <1 x i64> + %3 = extractelement <1 x i64> %2, i32 0 + ret i64 %3 +} + +declare x86_mmx @llvm.x86.sse.cvtpd2pi(<2 x double>) nounwind readnone + +define i64 @test17(<2 x double> %a) #0 { +; CHECK-LABEL: define i64 @test17( +; CHECK-SAME: <2 x double> [[A:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP4:%.*]] = load <2 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP5:%.*]] = bitcast <2 x i64> [[TMP4]] to i128 +; CHECK-NEXT: [[_MSCMP:%.*]] = icmp ne i128 [[TMP5]], 0 +; CHECK-NEXT: br i1 [[_MSCMP]], label [[TMP6:%.*]], label [[TMP7:%.*]], !prof [[PROF0]] +; CHECK: 2: +; CHECK-NEXT: call void @__msan_warning_noreturn() #[[ATTR6]] +; CHECK-NEXT: unreachable +; CHECK: 3: +; CHECK-NEXT: [[TMP0:%.*]] = tail call x86_mmx @llvm.x86.sse.cvtpd2pi(<2 x double> [[A]]) #[[ATTR5]] +; CHECK-NEXT: [[TMP1:%.*]] = bitcast x86_mmx [[TMP0]] to <2 x i32> +; CHECK-NEXT: [[TMP2:%.*]] = bitcast <2 x i32> [[TMP1]] to <1 x i64> +; CHECK-NEXT: [[TMP3:%.*]] = extractelement <1 x i64> [[TMP2]], i32 0 +; CHECK-NEXT: store i64 0, ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP3]] +; +entry: + %0 = tail call x86_mmx @llvm.x86.sse.cvtpd2pi(<2 x double> %a) nounwind readnone + %1 = bitcast x86_mmx %0 to <2 x i32> + %2 = bitcast <2 x i32> %1 to <1 x i64> + %3 = extractelement <1 x i64> %2, i32 0 + ret i64 %3 +} + +declare x86_mmx @llvm.x86.mmx.palignr.b(x86_mmx, x86_mmx, i8) nounwind readnone + +define i64 @test16(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test16( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP6:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: [[TMP7:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[_MSPROP:%.*]] = extractelement <1 x i64> [[TMP6]], i32 0 +; CHECK-NEXT: [[TMP0:%.*]] = extractelement <1 x i64> [[A]], i32 0 +; CHECK-NEXT: [[MMX_VAR:%.*]] = bitcast i64 [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP1:%.*]] = extractelement <1 x i64> [[TMP7]], i32 0 +; CHECK-NEXT: [[TMP1:%.*]] = extractelement <1 x i64> [[B]], i32 0 +; CHECK-NEXT: [[MMX_VAR1:%.*]] = bitcast i64 [[TMP1]] to x86_mmx +; CHECK-NEXT: [[_MSCMP:%.*]] = icmp ne i64 [[_MSPROP]], 0 +; CHECK-NEXT: [[_MSCMP2:%.*]] = icmp ne i64 [[_MSPROP1]], 0 +; CHECK-NEXT: [[_MSOR:%.*]] = or i1 [[_MSCMP]], [[_MSCMP2]] +; CHECK-NEXT: br i1 [[_MSOR]], label [[TMP4:%.*]], label [[TMP5:%.*]], !prof [[PROF0]] +; CHECK: 4: +; CHECK-NEXT: call void @__msan_warning_noreturn() #[[ATTR6]] +; CHECK-NEXT: unreachable +; CHECK: 5: +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.mmx.palignr.b(x86_mmx [[MMX_VAR]], x86_mmx [[MMX_VAR1]], i8 16) +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to i64 +; CHECK-NEXT: store i64 0, ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP3]] +; +entry: + %0 = extractelement <1 x i64> %a, i32 0 + %mmx_var = bitcast i64 %0 to x86_mmx + %1 = extractelement <1 x i64> %b, i32 0 + %mmx_var1 = bitcast i64 %1 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.mmx.palignr.b(x86_mmx %mmx_var, x86_mmx %mmx_var1, i8 16) + %3 = bitcast x86_mmx %2 to i64 + ret i64 %3 +} + +declare x86_mmx @llvm.x86.ssse3.pabs.d(x86_mmx) nounwind readnone + +define i64 @test15(<1 x i64> %a) #0 { +; CHECK-LABEL: define i64 @test15( +; CHECK-SAME: <1 x i64> [[A:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP7:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP8:%.*]] = bitcast <1 x i64> [[TMP7]] to <2 x i32> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[A]] to <2 x i32> +; CHECK-NEXT: [[TMP11:%.*]] = bitcast <2 x i32> [[TMP8]] to i64 +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <2 x i32> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.ssse3.pabs.d(x86_mmx [[TMP1]]) #[[ATTR5]] +; CHECK-NEXT: [[TMP6:%.*]] = bitcast i64 [[TMP11]] to <2 x i32> +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to <2 x i32> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast <2 x i32> [[TMP6]] to <1 x i64> +; CHECK-NEXT: [[TMP9:%.*]] = bitcast <2 x i32> [[TMP3]] to <1 x i64> +; CHECK-NEXT: [[TMP5:%.*]] = extractelement <1 x i64> [[TMP4]], i32 0 +; CHECK-NEXT: [[TMP10:%.*]] = extractelement <1 x i64> [[TMP9]], i32 0 +; CHECK-NEXT: store i64 [[TMP5]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP10]] +; +entry: + %0 = bitcast <1 x i64> %a to <2 x i32> + %1 = bitcast <2 x i32> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.ssse3.pabs.d(x86_mmx %1) nounwind readnone + %3 = bitcast x86_mmx %2 to <2 x i32> + %4 = bitcast <2 x i32> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.ssse3.pabs.w(x86_mmx) nounwind readnone + +define i64 @test14(<1 x i64> %a) #0 { +; CHECK-LABEL: define i64 @test14( +; CHECK-SAME: <1 x i64> [[A:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP7:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP8:%.*]] = bitcast <1 x i64> [[TMP7]] to <4 x i16> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[A]] to <4 x i16> +; CHECK-NEXT: [[TMP11:%.*]] = bitcast <4 x i16> [[TMP8]] to i64 +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <4 x i16> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.ssse3.pabs.w(x86_mmx [[TMP1]]) #[[ATTR5]] +; CHECK-NEXT: [[TMP6:%.*]] = bitcast i64 [[TMP11]] to <4 x i16> +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to <4 x i16> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast <4 x i16> [[TMP6]] to <1 x i64> +; CHECK-NEXT: [[TMP9:%.*]] = bitcast <4 x i16> [[TMP3]] to <1 x i64> +; CHECK-NEXT: [[TMP5:%.*]] = extractelement <1 x i64> [[TMP4]], i32 0 +; CHECK-NEXT: [[TMP10:%.*]] = extractelement <1 x i64> [[TMP9]], i32 0 +; CHECK-NEXT: store i64 [[TMP5]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP10]] +; +entry: + %0 = bitcast <1 x i64> %a to <4 x i16> + %1 = bitcast <4 x i16> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.ssse3.pabs.w(x86_mmx %1) nounwind readnone + %3 = bitcast x86_mmx %2 to <4 x i16> + %4 = bitcast <4 x i16> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.ssse3.pabs.b(x86_mmx) nounwind readnone + +define i64 @test13(<1 x i64> %a) #0 { +; CHECK-LABEL: define i64 @test13( +; CHECK-SAME: <1 x i64> [[A:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP7:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP8:%.*]] = bitcast <1 x i64> [[TMP7]] to <8 x i8> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[A]] to <8 x i8> +; CHECK-NEXT: [[TMP11:%.*]] = bitcast <8 x i8> [[TMP8]] to i64 +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <8 x i8> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[TMP2:%.*]] = tail call x86_mmx @llvm.x86.ssse3.pabs.b(x86_mmx [[TMP1]]) #[[ATTR5]] +; CHECK-NEXT: [[TMP6:%.*]] = bitcast i64 [[TMP11]] to <8 x i8> +; CHECK-NEXT: [[TMP3:%.*]] = bitcast x86_mmx [[TMP2]] to <8 x i8> +; CHECK-NEXT: [[TMP4:%.*]] = bitcast <8 x i8> [[TMP6]] to <1 x i64> +; CHECK-NEXT: [[TMP9:%.*]] = bitcast <8 x i8> [[TMP3]] to <1 x i64> +; CHECK-NEXT: [[TMP5:%.*]] = extractelement <1 x i64> [[TMP4]], i32 0 +; CHECK-NEXT: [[TMP10:%.*]] = extractelement <1 x i64> [[TMP9]], i32 0 +; CHECK-NEXT: store i64 [[TMP5]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP10]] +; +entry: + %0 = bitcast <1 x i64> %a to <8 x i8> + %1 = bitcast <8 x i8> %0 to x86_mmx + %2 = tail call x86_mmx @llvm.x86.ssse3.pabs.b(x86_mmx %1) nounwind readnone + %3 = bitcast x86_mmx %2 to <8 x i8> + %4 = bitcast <8 x i8> %3 to <1 x i64> + %5 = extractelement <1 x i64> %4, i32 0 + ret i64 %5 +} + +declare x86_mmx @llvm.x86.ssse3.psign.d(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test12(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test12( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP9:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <1 x i64> [[TMP9]] to <2 x i32> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <2 x i32> +; CHECK-NEXT: [[TMP13:%.*]] = bitcast <1 x i64> [[TMP10]] to <2 x i32> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <2 x i32> +; CHECK-NEXT: [[TMP16:%.*]] = bitcast <2 x i32> [[TMP13]] to i64 +; CHECK-NEXT: [[TMP2:%.*]] = bitcast <2 x i32> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP8:%.*]] = bitcast <2 x i32> [[TMP12]] to i64 +; CHECK-NEXT: [[TMP3:%.*]] = bitcast <2 x i32> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP16]], [[TMP8]] +; CHECK-NEXT: [[TMP4:%.*]] = tail call x86_mmx @llvm.x86.ssse3.psign.d(x86_mmx [[TMP2]], x86_mmx [[TMP3]]) #[[ATTR5]] +; CHECK-NEXT: [[TMP11:%.*]] = bitcast i64 [[_MSPROP]] to <2 x i32> +; CHECK-NEXT: [[TMP5:%.*]] = bitcast x86_mmx [[TMP4]] to <2 x i32> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <2 x i32> [[TMP11]] to <1 x i64> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <2 x i32> [[TMP5]] to <1 x i64> +; CHECK-NEXT: [[TMP7:%.*]] = extractelement <1 x i64> [[TMP6]], i32 0 +; CHECK-NEXT: [[TMP15:%.*]] = extractelement <1 x i64> [[TMP14]], i32 0 +; CHECK-NEXT: store i64 [[TMP7]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP15]] +; +entry: + %0 = bitcast <1 x i64> %b to <2 x i32> + %1 = bitcast <1 x i64> %a to <2 x i32> + %2 = bitcast <2 x i32> %1 to x86_mmx + %3 = bitcast <2 x i32> %0 to x86_mmx + %4 = tail call x86_mmx @llvm.x86.ssse3.psign.d(x86_mmx %2, x86_mmx %3) nounwind readnone + %5 = bitcast x86_mmx %4 to <2 x i32> + %6 = bitcast <2 x i32> %5 to <1 x i64> + %7 = extractelement <1 x i64> %6, i32 0 + ret i64 %7 +} + +declare x86_mmx @llvm.x86.ssse3.psign.w(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test11(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test11( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP9:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <1 x i64> [[TMP9]] to <4 x i16> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <4 x i16> +; CHECK-NEXT: [[TMP13:%.*]] = bitcast <1 x i64> [[TMP10]] to <4 x i16> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <4 x i16> +; CHECK-NEXT: [[TMP16:%.*]] = bitcast <4 x i16> [[TMP13]] to i64 +; CHECK-NEXT: [[TMP2:%.*]] = bitcast <4 x i16> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP8:%.*]] = bitcast <4 x i16> [[TMP12]] to i64 +; CHECK-NEXT: [[TMP3:%.*]] = bitcast <4 x i16> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP16]], [[TMP8]] +; CHECK-NEXT: [[TMP4:%.*]] = tail call x86_mmx @llvm.x86.ssse3.psign.w(x86_mmx [[TMP2]], x86_mmx [[TMP3]]) #[[ATTR5]] +; CHECK-NEXT: [[TMP11:%.*]] = bitcast i64 [[_MSPROP]] to <4 x i16> +; CHECK-NEXT: [[TMP5:%.*]] = bitcast x86_mmx [[TMP4]] to <4 x i16> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <4 x i16> [[TMP11]] to <1 x i64> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <4 x i16> [[TMP5]] to <1 x i64> +; CHECK-NEXT: [[TMP7:%.*]] = extractelement <1 x i64> [[TMP6]], i32 0 +; CHECK-NEXT: [[TMP15:%.*]] = extractelement <1 x i64> [[TMP14]], i32 0 +; CHECK-NEXT: store i64 [[TMP7]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP15]] +; +entry: + %0 = bitcast <1 x i64> %b to <4 x i16> + %1 = bitcast <1 x i64> %a to <4 x i16> + %2 = bitcast <4 x i16> %1 to x86_mmx + %3 = bitcast <4 x i16> %0 to x86_mmx + %4 = tail call x86_mmx @llvm.x86.ssse3.psign.w(x86_mmx %2, x86_mmx %3) nounwind readnone + %5 = bitcast x86_mmx %4 to <4 x i16> + %6 = bitcast <4 x i16> %5 to <1 x i64> + %7 = extractelement <1 x i64> %6, i32 0 + ret i64 %7 +} + +declare x86_mmx @llvm.x86.ssse3.psign.b(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test10(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test10( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP9:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <1 x i64> [[TMP9]] to <8 x i8> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <8 x i8> +; CHECK-NEXT: [[TMP13:%.*]] = bitcast <1 x i64> [[TMP10]] to <8 x i8> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <8 x i8> +; CHECK-NEXT: [[TMP16:%.*]] = bitcast <8 x i8> [[TMP13]] to i64 +; CHECK-NEXT: [[TMP2:%.*]] = bitcast <8 x i8> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP8:%.*]] = bitcast <8 x i8> [[TMP12]] to i64 +; CHECK-NEXT: [[TMP3:%.*]] = bitcast <8 x i8> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP16]], [[TMP8]] +; CHECK-NEXT: [[TMP4:%.*]] = tail call x86_mmx @llvm.x86.ssse3.psign.b(x86_mmx [[TMP2]], x86_mmx [[TMP3]]) #[[ATTR5]] +; CHECK-NEXT: [[TMP11:%.*]] = bitcast i64 [[_MSPROP]] to <8 x i8> +; CHECK-NEXT: [[TMP5:%.*]] = bitcast x86_mmx [[TMP4]] to <8 x i8> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <8 x i8> [[TMP11]] to <1 x i64> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <8 x i8> [[TMP5]] to <1 x i64> +; CHECK-NEXT: [[TMP7:%.*]] = extractelement <1 x i64> [[TMP6]], i32 0 +; CHECK-NEXT: [[TMP15:%.*]] = extractelement <1 x i64> [[TMP14]], i32 0 +; CHECK-NEXT: store i64 [[TMP7]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP15]] +; +entry: + %0 = bitcast <1 x i64> %b to <8 x i8> + %1 = bitcast <1 x i64> %a to <8 x i8> + %2 = bitcast <8 x i8> %1 to x86_mmx + %3 = bitcast <8 x i8> %0 to x86_mmx + %4 = tail call x86_mmx @llvm.x86.ssse3.psign.b(x86_mmx %2, x86_mmx %3) nounwind readnone + %5 = bitcast x86_mmx %4 to <8 x i8> + %6 = bitcast <8 x i8> %5 to <1 x i64> + %7 = extractelement <1 x i64> %6, i32 0 + ret i64 %7 +} + +declare x86_mmx @llvm.x86.ssse3.pshuf.b(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test9(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test9( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP9:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <1 x i64> [[TMP9]] to <8 x i8> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <8 x i8> +; CHECK-NEXT: [[TMP13:%.*]] = bitcast <1 x i64> [[TMP10]] to <8 x i8> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <8 x i8> +; CHECK-NEXT: [[TMP16:%.*]] = bitcast <8 x i8> [[TMP13]] to i64 +; CHECK-NEXT: [[TMP2:%.*]] = bitcast <8 x i8> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP8:%.*]] = bitcast <8 x i8> [[TMP12]] to i64 +; CHECK-NEXT: [[TMP3:%.*]] = bitcast <8 x i8> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP16]], [[TMP8]] +; CHECK-NEXT: [[TMP4:%.*]] = tail call x86_mmx @llvm.x86.ssse3.pshuf.b(x86_mmx [[TMP2]], x86_mmx [[TMP3]]) #[[ATTR5]] +; CHECK-NEXT: [[TMP11:%.*]] = bitcast i64 [[_MSPROP]] to <8 x i8> +; CHECK-NEXT: [[TMP5:%.*]] = bitcast x86_mmx [[TMP4]] to <8 x i8> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <8 x i8> [[TMP11]] to <1 x i64> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <8 x i8> [[TMP5]] to <1 x i64> +; CHECK-NEXT: [[TMP7:%.*]] = extractelement <1 x i64> [[TMP6]], i32 0 +; CHECK-NEXT: [[TMP15:%.*]] = extractelement <1 x i64> [[TMP14]], i32 0 +; CHECK-NEXT: store i64 [[TMP7]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP15]] +; +entry: + %0 = bitcast <1 x i64> %b to <8 x i8> + %1 = bitcast <1 x i64> %a to <8 x i8> + %2 = bitcast <8 x i8> %1 to x86_mmx + %3 = bitcast <8 x i8> %0 to x86_mmx + %4 = tail call x86_mmx @llvm.x86.ssse3.pshuf.b(x86_mmx %2, x86_mmx %3) nounwind readnone + %5 = bitcast x86_mmx %4 to <8 x i8> + %6 = bitcast <8 x i8> %5 to <1 x i64> + %7 = extractelement <1 x i64> %6, i32 0 + ret i64 %7 +} + +declare x86_mmx @llvm.x86.ssse3.pmul.hr.sw(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test8(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test8( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP9:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <1 x i64> [[TMP9]] to <4 x i16> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <4 x i16> +; CHECK-NEXT: [[TMP13:%.*]] = bitcast <1 x i64> [[TMP10]] to <4 x i16> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <4 x i16> +; CHECK-NEXT: [[TMP16:%.*]] = bitcast <4 x i16> [[TMP13]] to i64 +; CHECK-NEXT: [[TMP2:%.*]] = bitcast <4 x i16> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP8:%.*]] = bitcast <4 x i16> [[TMP12]] to i64 +; CHECK-NEXT: [[TMP3:%.*]] = bitcast <4 x i16> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP16]], [[TMP8]] +; CHECK-NEXT: [[TMP4:%.*]] = tail call x86_mmx @llvm.x86.ssse3.pmul.hr.sw(x86_mmx [[TMP2]], x86_mmx [[TMP3]]) #[[ATTR5]] +; CHECK-NEXT: [[TMP11:%.*]] = bitcast i64 [[_MSPROP]] to <4 x i16> +; CHECK-NEXT: [[TMP5:%.*]] = bitcast x86_mmx [[TMP4]] to <4 x i16> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <4 x i16> [[TMP11]] to <1 x i64> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <4 x i16> [[TMP5]] to <1 x i64> +; CHECK-NEXT: [[TMP7:%.*]] = extractelement <1 x i64> [[TMP6]], i32 0 +; CHECK-NEXT: [[TMP15:%.*]] = extractelement <1 x i64> [[TMP14]], i32 0 +; CHECK-NEXT: store i64 [[TMP7]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP15]] +; +entry: + %0 = bitcast <1 x i64> %b to <4 x i16> + %1 = bitcast <1 x i64> %a to <4 x i16> + %2 = bitcast <4 x i16> %1 to x86_mmx + %3 = bitcast <4 x i16> %0 to x86_mmx + %4 = tail call x86_mmx @llvm.x86.ssse3.pmul.hr.sw(x86_mmx %2, x86_mmx %3) nounwind readnone + %5 = bitcast x86_mmx %4 to <4 x i16> + %6 = bitcast <4 x i16> %5 to <1 x i64> + %7 = extractelement <1 x i64> %6, i32 0 + ret i64 %7 +} + +declare x86_mmx @llvm.x86.ssse3.pmadd.ub.sw(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test7(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test7( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP9:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP15:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP17:%.*]] = bitcast <1 x i64> [[TMP9]] to <8 x i8> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <8 x i8> +; CHECK-NEXT: [[TMP18:%.*]] = bitcast <1 x i64> [[TMP15]] to <8 x i8> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <8 x i8> +; CHECK-NEXT: [[TMP21:%.*]] = bitcast <8 x i8> [[TMP18]] to i64 +; CHECK-NEXT: [[TMP2:%.*]] = bitcast <8 x i8> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP8:%.*]] = bitcast <8 x i8> [[TMP17]] to i64 +; CHECK-NEXT: [[TMP3:%.*]] = bitcast <8 x i8> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[TMP10:%.*]] = or i64 [[TMP21]], [[TMP8]] +; CHECK-NEXT: [[TMP11:%.*]] = bitcast i64 [[TMP10]] to <4 x i16> +; CHECK-NEXT: [[TMP12:%.*]] = icmp ne <4 x i16> [[TMP11]], zeroinitializer +; CHECK-NEXT: [[TMP13:%.*]] = sext <4 x i1> [[TMP12]] to <4 x i16> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <4 x i16> [[TMP13]] to i64 +; CHECK-NEXT: [[TMP4:%.*]] = tail call x86_mmx @llvm.x86.ssse3.pmadd.ub.sw(x86_mmx [[TMP2]], x86_mmx [[TMP3]]) #[[ATTR5]] +; CHECK-NEXT: [[TMP16:%.*]] = bitcast i64 [[TMP14]] to <8 x i8> +; CHECK-NEXT: [[TMP5:%.*]] = bitcast x86_mmx [[TMP4]] to <8 x i8> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <8 x i8> [[TMP16]] to <1 x i64> +; CHECK-NEXT: [[TMP19:%.*]] = bitcast <8 x i8> [[TMP5]] to <1 x i64> +; CHECK-NEXT: [[TMP7:%.*]] = extractelement <1 x i64> [[TMP6]], i32 0 +; CHECK-NEXT: [[TMP20:%.*]] = extractelement <1 x i64> [[TMP19]], i32 0 +; CHECK-NEXT: store i64 [[TMP7]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP20]] +; +entry: + %0 = bitcast <1 x i64> %b to <8 x i8> + %1 = bitcast <1 x i64> %a to <8 x i8> + %2 = bitcast <8 x i8> %1 to x86_mmx + %3 = bitcast <8 x i8> %0 to x86_mmx + %4 = tail call x86_mmx @llvm.x86.ssse3.pmadd.ub.sw(x86_mmx %2, x86_mmx %3) nounwind readnone + %5 = bitcast x86_mmx %4 to <8 x i8> + %6 = bitcast <8 x i8> %5 to <1 x i64> + %7 = extractelement <1 x i64> %6, i32 0 + ret i64 %7 +} + +declare x86_mmx @llvm.x86.ssse3.phsub.sw(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test6(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test6( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP9:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <1 x i64> [[TMP9]] to <4 x i16> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <4 x i16> +; CHECK-NEXT: [[TMP13:%.*]] = bitcast <1 x i64> [[TMP10]] to <4 x i16> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <4 x i16> +; CHECK-NEXT: [[TMP16:%.*]] = bitcast <4 x i16> [[TMP13]] to i64 +; CHECK-NEXT: [[TMP2:%.*]] = bitcast <4 x i16> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP8:%.*]] = bitcast <4 x i16> [[TMP12]] to i64 +; CHECK-NEXT: [[TMP3:%.*]] = bitcast <4 x i16> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP16]], [[TMP8]] +; CHECK-NEXT: [[TMP4:%.*]] = tail call x86_mmx @llvm.x86.ssse3.phsub.sw(x86_mmx [[TMP2]], x86_mmx [[TMP3]]) #[[ATTR5]] +; CHECK-NEXT: [[TMP11:%.*]] = bitcast i64 [[_MSPROP]] to <4 x i16> +; CHECK-NEXT: [[TMP5:%.*]] = bitcast x86_mmx [[TMP4]] to <4 x i16> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <4 x i16> [[TMP11]] to <1 x i64> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <4 x i16> [[TMP5]] to <1 x i64> +; CHECK-NEXT: [[TMP7:%.*]] = extractelement <1 x i64> [[TMP6]], i32 0 +; CHECK-NEXT: [[TMP15:%.*]] = extractelement <1 x i64> [[TMP14]], i32 0 +; CHECK-NEXT: store i64 [[TMP7]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP15]] +; +entry: + %0 = bitcast <1 x i64> %b to <4 x i16> + %1 = bitcast <1 x i64> %a to <4 x i16> + %2 = bitcast <4 x i16> %1 to x86_mmx + %3 = bitcast <4 x i16> %0 to x86_mmx + %4 = tail call x86_mmx @llvm.x86.ssse3.phsub.sw(x86_mmx %2, x86_mmx %3) nounwind readnone + %5 = bitcast x86_mmx %4 to <4 x i16> + %6 = bitcast <4 x i16> %5 to <1 x i64> + %7 = extractelement <1 x i64> %6, i32 0 + ret i64 %7 +} + +declare x86_mmx @llvm.x86.ssse3.phsub.d(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test5(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test5( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP9:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <1 x i64> [[TMP9]] to <2 x i32> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <2 x i32> +; CHECK-NEXT: [[TMP13:%.*]] = bitcast <1 x i64> [[TMP10]] to <2 x i32> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <2 x i32> +; CHECK-NEXT: [[TMP16:%.*]] = bitcast <2 x i32> [[TMP13]] to i64 +; CHECK-NEXT: [[TMP2:%.*]] = bitcast <2 x i32> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP8:%.*]] = bitcast <2 x i32> [[TMP12]] to i64 +; CHECK-NEXT: [[TMP3:%.*]] = bitcast <2 x i32> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP16]], [[TMP8]] +; CHECK-NEXT: [[TMP4:%.*]] = tail call x86_mmx @llvm.x86.ssse3.phsub.d(x86_mmx [[TMP2]], x86_mmx [[TMP3]]) #[[ATTR5]] +; CHECK-NEXT: [[TMP11:%.*]] = bitcast i64 [[_MSPROP]] to <2 x i32> +; CHECK-NEXT: [[TMP5:%.*]] = bitcast x86_mmx [[TMP4]] to <2 x i32> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <2 x i32> [[TMP11]] to <1 x i64> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <2 x i32> [[TMP5]] to <1 x i64> +; CHECK-NEXT: [[TMP7:%.*]] = extractelement <1 x i64> [[TMP6]], i32 0 +; CHECK-NEXT: [[TMP15:%.*]] = extractelement <1 x i64> [[TMP14]], i32 0 +; CHECK-NEXT: store i64 [[TMP7]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP15]] +; +entry: + %0 = bitcast <1 x i64> %b to <2 x i32> + %1 = bitcast <1 x i64> %a to <2 x i32> + %2 = bitcast <2 x i32> %1 to x86_mmx + %3 = bitcast <2 x i32> %0 to x86_mmx + %4 = tail call x86_mmx @llvm.x86.ssse3.phsub.d(x86_mmx %2, x86_mmx %3) nounwind readnone + %5 = bitcast x86_mmx %4 to <2 x i32> + %6 = bitcast <2 x i32> %5 to <1 x i64> + %7 = extractelement <1 x i64> %6, i32 0 + ret i64 %7 +} + +declare x86_mmx @llvm.x86.ssse3.phsub.w(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test4(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test4( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP9:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <1 x i64> [[TMP9]] to <4 x i16> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <4 x i16> +; CHECK-NEXT: [[TMP13:%.*]] = bitcast <1 x i64> [[TMP10]] to <4 x i16> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <4 x i16> +; CHECK-NEXT: [[TMP16:%.*]] = bitcast <4 x i16> [[TMP13]] to i64 +; CHECK-NEXT: [[TMP2:%.*]] = bitcast <4 x i16> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP8:%.*]] = bitcast <4 x i16> [[TMP12]] to i64 +; CHECK-NEXT: [[TMP3:%.*]] = bitcast <4 x i16> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP16]], [[TMP8]] +; CHECK-NEXT: [[TMP4:%.*]] = tail call x86_mmx @llvm.x86.ssse3.phsub.w(x86_mmx [[TMP2]], x86_mmx [[TMP3]]) #[[ATTR5]] +; CHECK-NEXT: [[TMP11:%.*]] = bitcast i64 [[_MSPROP]] to <4 x i16> +; CHECK-NEXT: [[TMP5:%.*]] = bitcast x86_mmx [[TMP4]] to <4 x i16> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <4 x i16> [[TMP11]] to <1 x i64> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <4 x i16> [[TMP5]] to <1 x i64> +; CHECK-NEXT: [[TMP7:%.*]] = extractelement <1 x i64> [[TMP6]], i32 0 +; CHECK-NEXT: [[TMP15:%.*]] = extractelement <1 x i64> [[TMP14]], i32 0 +; CHECK-NEXT: store i64 [[TMP7]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP15]] +; +entry: + %0 = bitcast <1 x i64> %b to <4 x i16> + %1 = bitcast <1 x i64> %a to <4 x i16> + %2 = bitcast <4 x i16> %1 to x86_mmx + %3 = bitcast <4 x i16> %0 to x86_mmx + %4 = tail call x86_mmx @llvm.x86.ssse3.phsub.w(x86_mmx %2, x86_mmx %3) nounwind readnone + %5 = bitcast x86_mmx %4 to <4 x i16> + %6 = bitcast <4 x i16> %5 to <1 x i64> + %7 = extractelement <1 x i64> %6, i32 0 + ret i64 %7 +} + +declare x86_mmx @llvm.x86.ssse3.phadd.sw(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test3(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test3( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP9:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <1 x i64> [[TMP9]] to <4 x i16> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <4 x i16> +; CHECK-NEXT: [[TMP13:%.*]] = bitcast <1 x i64> [[TMP10]] to <4 x i16> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <4 x i16> +; CHECK-NEXT: [[TMP16:%.*]] = bitcast <4 x i16> [[TMP13]] to i64 +; CHECK-NEXT: [[TMP2:%.*]] = bitcast <4 x i16> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP8:%.*]] = bitcast <4 x i16> [[TMP12]] to i64 +; CHECK-NEXT: [[TMP3:%.*]] = bitcast <4 x i16> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP16]], [[TMP8]] +; CHECK-NEXT: [[TMP4:%.*]] = tail call x86_mmx @llvm.x86.ssse3.phadd.sw(x86_mmx [[TMP2]], x86_mmx [[TMP3]]) #[[ATTR5]] +; CHECK-NEXT: [[TMP11:%.*]] = bitcast i64 [[_MSPROP]] to <4 x i16> +; CHECK-NEXT: [[TMP5:%.*]] = bitcast x86_mmx [[TMP4]] to <4 x i16> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <4 x i16> [[TMP11]] to <1 x i64> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <4 x i16> [[TMP5]] to <1 x i64> +; CHECK-NEXT: [[TMP7:%.*]] = extractelement <1 x i64> [[TMP6]], i32 0 +; CHECK-NEXT: [[TMP15:%.*]] = extractelement <1 x i64> [[TMP14]], i32 0 +; CHECK-NEXT: store i64 [[TMP7]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP15]] +; +entry: + %0 = bitcast <1 x i64> %b to <4 x i16> + %1 = bitcast <1 x i64> %a to <4 x i16> + %2 = bitcast <4 x i16> %1 to x86_mmx + %3 = bitcast <4 x i16> %0 to x86_mmx + %4 = tail call x86_mmx @llvm.x86.ssse3.phadd.sw(x86_mmx %2, x86_mmx %3) nounwind readnone + %5 = bitcast x86_mmx %4 to <4 x i16> + %6 = bitcast <4 x i16> %5 to <1 x i64> + %7 = extractelement <1 x i64> %6, i32 0 + ret i64 %7 +} + +declare x86_mmx @llvm.x86.ssse3.phadd.d(x86_mmx, x86_mmx) nounwind readnone + +define i64 @test2(<1 x i64> %a, <1 x i64> %b) #0 { +; CHECK-LABEL: define i64 @test2( +; CHECK-SAME: <1 x i64> [[A:%.*]], <1 x i64> [[B:%.*]]) #[[ATTR1]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP9:%.*]] = load <1 x i64>, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: [[TMP10:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP12:%.*]] = bitcast <1 x i64> [[TMP9]] to <2 x i32> +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[B]] to <2 x i32> +; CHECK-NEXT: [[TMP13:%.*]] = bitcast <1 x i64> [[TMP10]] to <2 x i32> +; CHECK-NEXT: [[TMP1:%.*]] = bitcast <1 x i64> [[A]] to <2 x i32> +; CHECK-NEXT: [[TMP16:%.*]] = bitcast <2 x i32> [[TMP13]] to i64 +; CHECK-NEXT: [[TMP2:%.*]] = bitcast <2 x i32> [[TMP1]] to x86_mmx +; CHECK-NEXT: [[TMP8:%.*]] = bitcast <2 x i32> [[TMP12]] to i64 +; CHECK-NEXT: [[TMP3:%.*]] = bitcast <2 x i32> [[TMP0]] to x86_mmx +; CHECK-NEXT: [[_MSPROP:%.*]] = or i64 [[TMP16]], [[TMP8]] +; CHECK-NEXT: [[TMP4:%.*]] = tail call x86_mmx @llvm.x86.ssse3.phadd.d(x86_mmx [[TMP2]], x86_mmx [[TMP3]]) #[[ATTR5]] +; CHECK-NEXT: [[TMP11:%.*]] = bitcast i64 [[_MSPROP]] to <2 x i32> +; CHECK-NEXT: [[TMP5:%.*]] = bitcast x86_mmx [[TMP4]] to <2 x i32> +; CHECK-NEXT: [[TMP6:%.*]] = bitcast <2 x i32> [[TMP11]] to <1 x i64> +; CHECK-NEXT: [[TMP14:%.*]] = bitcast <2 x i32> [[TMP5]] to <1 x i64> +; CHECK-NEXT: [[TMP7:%.*]] = extractelement <1 x i64> [[TMP6]], i32 0 +; CHECK-NEXT: [[TMP15:%.*]] = extractelement <1 x i64> [[TMP14]], i32 0 +; CHECK-NEXT: store i64 [[TMP7]], ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i64 [[TMP15]] +; +entry: + %0 = bitcast <1 x i64> %b to <2 x i32> + %1 = bitcast <1 x i64> %a to <2 x i32> + %2 = bitcast <2 x i32> %1 to x86_mmx + %3 = bitcast <2 x i32> %0 to x86_mmx + %4 = tail call x86_mmx @llvm.x86.ssse3.phadd.d(x86_mmx %2, x86_mmx %3) nounwind readnone + %5 = bitcast x86_mmx %4 to <2 x i32> + %6 = bitcast <2 x i32> %5 to <1 x i64> + %7 = extractelement <1 x i64> %6, i32 0 + ret i64 %7 +} + +define <4 x float> @test89(<4 x float> %a, x86_mmx %b) nounwind #0 { +; ALL-LABEL: test89: +; ALL: # %bb.0: +; ALL-NEXT: cvtpi2ps %mm0, %xmm0 +; ALL-NEXT: ret{{[l|q]}} +; CHECK-LABEL: define <4 x float> @test89( +; CHECK-SAME: <4 x float> [[A:%.*]], x86_mmx [[B:%.*]]) #[[ATTR4:[0-9]+]] { +; CHECK-NEXT: [[TMP1:%.*]] = load <4 x i32>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: [[TMP2:%.*]] = load i64, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 16) to ptr), align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP3:%.*]] = bitcast <4 x i32> [[TMP1]] to i128 +; CHECK-NEXT: [[_MSCMP:%.*]] = icmp ne i128 [[TMP3]], 0 +; CHECK-NEXT: [[_MSCMP1:%.*]] = icmp ne i64 [[TMP2]], 0 +; CHECK-NEXT: [[_MSOR:%.*]] = or i1 [[_MSCMP]], [[_MSCMP1]] +; CHECK-NEXT: br i1 [[_MSOR]], label [[TMP4:%.*]], label [[TMP5:%.*]], !prof [[PROF0]] +; CHECK: 4: +; CHECK-NEXT: call void @__msan_warning_noreturn() #[[ATTR6]] +; CHECK-NEXT: unreachable +; CHECK: 5: +; CHECK-NEXT: [[C:%.*]] = tail call <4 x float> @llvm.x86.sse.cvtpi2ps(<4 x float> [[A]], x86_mmx [[B]]) +; CHECK-NEXT: store <4 x i32> zeroinitializer, ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret <4 x float> [[C]] +; + %c = tail call <4 x float> @llvm.x86.sse.cvtpi2ps(<4 x float> %a, x86_mmx %b) + ret <4 x float> %c +} + +declare <4 x float> @llvm.x86.sse.cvtpi2ps(<4 x float>, x86_mmx) nounwind readnone + +define void @test90() #0 { +; ALL-LABEL: test90: +; ALL: # %bb.0: +; ALL-NEXT: emms +; ALL-NEXT: ret{{[l|q]}} +; CHECK-LABEL: define void @test90( +; CHECK-SAME: ) #[[ATTR1]] { +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: call void @llvm.x86.mmx.emms() +; CHECK-NEXT: ret void +; + call void @llvm.x86.mmx.emms() + ret void +} + +declare void @llvm.x86.mmx.emms() + +define <1 x i64> @test_mm_insert_pi16(<1 x i64> %a.coerce, i32 %d) nounwind #0 { +; CHECK-LABEL: define <1 x i64> @test_mm_insert_pi16( +; CHECK-SAME: <1 x i64> [[A_COERCE:%.*]], i32 [[D:%.*]]) #[[ATTR4]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP3:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: [[TMP6:%.*]] = load i32, ptr inttoptr (i64 add (i64 ptrtoint (ptr @__msan_param_tls to i64), i64 8) to ptr), align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP7:%.*]] = bitcast <1 x i64> [[TMP3]] to i64 +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[A_COERCE]] to x86_mmx +; CHECK-NEXT: [[_MSCMP:%.*]] = icmp ne i64 [[TMP7]], 0 +; CHECK-NEXT: [[_MSCMP1:%.*]] = icmp ne i32 [[TMP6]], 0 +; CHECK-NEXT: [[_MSOR:%.*]] = or i1 [[_MSCMP]], [[_MSCMP1]] +; CHECK-NEXT: br i1 [[_MSOR]], label [[TMP4:%.*]], label [[TMP5:%.*]], !prof [[PROF0]] +; CHECK: 4: +; CHECK-NEXT: call void @__msan_warning_noreturn() #[[ATTR6]] +; CHECK-NEXT: unreachable +; CHECK: 5: +; CHECK-NEXT: [[TMP1:%.*]] = tail call x86_mmx @llvm.x86.mmx.pinsr.w(x86_mmx [[TMP0]], i32 [[D]], i32 2) +; CHECK-NEXT: [[TMP2:%.*]] = bitcast x86_mmx [[TMP1]] to <1 x i64> +; CHECK-NEXT: store <1 x i64> zeroinitializer, ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret <1 x i64> [[TMP2]] +; +entry: + %0 = bitcast <1 x i64> %a.coerce to x86_mmx + %1 = tail call x86_mmx @llvm.x86.mmx.pinsr.w(x86_mmx %0, i32 %d, i32 2) + %2 = bitcast x86_mmx %1 to <1 x i64> + ret <1 x i64> %2 +} + +declare x86_mmx @llvm.x86.mmx.pinsr.w(x86_mmx, i32, i32 immarg) + +define i32 @test_mm_extract_pi16(<1 x i64> %a.coerce) nounwind #0 { +; CHECK-LABEL: define i32 @test_mm_extract_pi16( +; CHECK-SAME: <1 x i64> [[A_COERCE:%.*]]) #[[ATTR4]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP2:%.*]] = load <1 x i64>, ptr @__msan_param_tls, align 8 +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP5:%.*]] = bitcast <1 x i64> [[TMP2]] to i64 +; CHECK-NEXT: [[TMP0:%.*]] = bitcast <1 x i64> [[A_COERCE]] to x86_mmx +; CHECK-NEXT: [[_MSCMP:%.*]] = icmp ne i64 [[TMP5]], 0 +; CHECK-NEXT: br i1 [[_MSCMP]], label [[TMP3:%.*]], label [[TMP4:%.*]], !prof [[PROF0]] +; CHECK: 3: +; CHECK-NEXT: call void @__msan_warning_noreturn() #[[ATTR6]] +; CHECK-NEXT: unreachable +; CHECK: 4: +; CHECK-NEXT: [[TMP1:%.*]] = tail call i32 @llvm.x86.mmx.pextr.w(x86_mmx [[TMP0]], i32 2) +; CHECK-NEXT: store i32 0, ptr @__msan_retval_tls, align 8 +; CHECK-NEXT: ret i32 [[TMP1]] +; +entry: + %0 = bitcast <1 x i64> %a.coerce to x86_mmx + %1 = tail call i32 @llvm.x86.mmx.pextr.w(x86_mmx %0, i32 2) + ret i32 %1 +} + +declare i32 @llvm.x86.mmx.pextr.w(x86_mmx, i32 immarg) + +attributes #0 = { sanitize_memory } +;. +; CHECK: [[PROF0]] = !{!"branch_weights", i32 1, i32 1048575} +;. diff --git a/llvm/test/Instrumentation/MemorySanitizer/vscale.ll b/llvm/test/Instrumentation/MemorySanitizer/vscale.ll new file mode 100644 index 0000000000000000000000000000000000000000..b1c64188157077e65d9cecbdb43c2e0e2215ad51 --- /dev/null +++ b/llvm/test/Instrumentation/MemorySanitizer/vscale.ll @@ -0,0 +1,107 @@ +; NOTE: Assertions have been autogenerated by utils/update_test_checks.py UTC_ARGS: --version 4 +; RUN: opt < %s -S -msan-check-access-address=0 -passes="msan" 2>&1 | FileCheck %s + +target datalayout = "e-p:64:64:64-i1:8:8-i8:8:8-i16:16:16-i32:32:32-i64:64:64-f32:32:32-f64:64:64-v64:64:64-v128:128:128-a0:0:64-s0:64:64-f80:128:128-n8:16:32:64-S128" +target triple = "x86_64-unknown-linux-gnu" + +define void @test_load_store_i32(ptr %a, ptr %b) sanitize_memory { +; CHECK-LABEL: define void @test_load_store_i32( +; CHECK-SAME: ptr [[A:%.*]], ptr [[B:%.*]]) #[[ATTR0:[0-9]+]] { +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP1:%.*]] = load , ptr [[A]], align 16 +; CHECK-NEXT: [[TMP2:%.*]] = ptrtoint ptr [[A]] to i64 +; CHECK-NEXT: [[TMP3:%.*]] = xor i64 [[TMP2]], 87960930222080 +; CHECK-NEXT: [[TMP4:%.*]] = inttoptr i64 [[TMP3]] to ptr +; CHECK-NEXT: [[_MSLD:%.*]] = load , ptr [[TMP4]], align 16 +; CHECK-NEXT: [[TMP5:%.*]] = ptrtoint ptr [[B]] to i64 +; CHECK-NEXT: [[TMP6:%.*]] = xor i64 [[TMP5]], 87960930222080 +; CHECK-NEXT: [[TMP7:%.*]] = inttoptr i64 [[TMP6]] to ptr +; CHECK-NEXT: store [[_MSLD]], ptr [[TMP7]], align 16 +; CHECK-NEXT: store [[TMP1]], ptr [[B]], align 16 +; CHECK-NEXT: ret void +; + %1 = load , ptr %a + store %1, ptr %b + ret void +} + +define void @test_load_store_add_int(ptr %a, ptr %b) sanitize_memory { +; CHECK-LABEL: define void @test_load_store_add_int( +; CHECK-SAME: ptr [[A:%.*]], ptr [[B:%.*]]) #[[ATTR0]] { +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP1:%.*]] = load , ptr [[A]], align 64 +; CHECK-NEXT: [[TMP2:%.*]] = ptrtoint ptr [[A]] to i64 +; CHECK-NEXT: [[TMP3:%.*]] = xor i64 [[TMP2]], 87960930222080 +; CHECK-NEXT: [[TMP4:%.*]] = inttoptr i64 [[TMP3]] to ptr +; CHECK-NEXT: [[_MSLD:%.*]] = load , ptr [[TMP4]], align 64 +; CHECK-NEXT: [[TMP5:%.*]] = load , ptr [[B]], align 64 +; CHECK-NEXT: [[TMP6:%.*]] = ptrtoint ptr [[B]] to i64 +; CHECK-NEXT: [[TMP7:%.*]] = xor i64 [[TMP6]], 87960930222080 +; CHECK-NEXT: [[TMP8:%.*]] = inttoptr i64 [[TMP7]] to ptr +; CHECK-NEXT: [[_MSLD1:%.*]] = load , ptr [[TMP8]], align 64 +; CHECK-NEXT: [[_MSPROP:%.*]] = or [[_MSLD]], [[_MSLD1]] +; CHECK-NEXT: [[TMP9:%.*]] = add [[TMP1]], [[TMP5]] +; CHECK-NEXT: [[TMP10:%.*]] = ptrtoint ptr [[B]] to i64 +; CHECK-NEXT: [[TMP11:%.*]] = xor i64 [[TMP10]], 87960930222080 +; CHECK-NEXT: [[TMP12:%.*]] = inttoptr i64 [[TMP11]] to ptr +; CHECK-NEXT: store [[_MSLD1]], ptr [[TMP12]], align 64 +; CHECK-NEXT: store [[TMP5]], ptr [[B]], align 64 +; CHECK-NEXT: ret void +; + %1 = load , ptr %a + %2 = load , ptr %b + %3 = add %1, %2 + store %2, ptr %b + ret void +} + +define void @test_load_store_float(ptr %a, ptr %b) sanitize_memory { +; CHECK-LABEL: define void @test_load_store_float( +; CHECK-SAME: ptr [[A:%.*]], ptr [[B:%.*]]) #[[ATTR0]] { +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP1:%.*]] = load , ptr [[A]], align 16 +; CHECK-NEXT: [[TMP2:%.*]] = ptrtoint ptr [[A]] to i64 +; CHECK-NEXT: [[TMP3:%.*]] = xor i64 [[TMP2]], 87960930222080 +; CHECK-NEXT: [[TMP4:%.*]] = inttoptr i64 [[TMP3]] to ptr +; CHECK-NEXT: [[_MSLD:%.*]] = load , ptr [[TMP4]], align 16 +; CHECK-NEXT: [[TMP5:%.*]] = ptrtoint ptr [[B]] to i64 +; CHECK-NEXT: [[TMP6:%.*]] = xor i64 [[TMP5]], 87960930222080 +; CHECK-NEXT: [[TMP7:%.*]] = inttoptr i64 [[TMP6]] to ptr +; CHECK-NEXT: store [[_MSLD]], ptr [[TMP7]], align 16 +; CHECK-NEXT: store [[TMP1]], ptr [[B]], align 16 +; CHECK-NEXT: ret void +; + %1 = load , ptr %a + store %1, ptr %b + ret void +} + +define void @test_load_store_add_float(ptr %a, ptr %b) sanitize_memory { +; CHECK-LABEL: define void @test_load_store_add_float( +; CHECK-SAME: ptr [[A:%.*]], ptr [[B:%.*]]) #[[ATTR0]] { +; CHECK-NEXT: call void @llvm.donothing() +; CHECK-NEXT: [[TMP1:%.*]] = load , ptr [[A]], align 8 +; CHECK-NEXT: [[TMP2:%.*]] = ptrtoint ptr [[A]] to i64 +; CHECK-NEXT: [[TMP3:%.*]] = xor i64 [[TMP2]], 87960930222080 +; CHECK-NEXT: [[TMP4:%.*]] = inttoptr i64 [[TMP3]] to ptr +; CHECK-NEXT: [[_MSLD:%.*]] = load , ptr [[TMP4]], align 8 +; CHECK-NEXT: [[TMP5:%.*]] = load , ptr [[B]], align 8 +; CHECK-NEXT: [[TMP6:%.*]] = ptrtoint ptr [[B]] to i64 +; CHECK-NEXT: [[TMP7:%.*]] = xor i64 [[TMP6]], 87960930222080 +; CHECK-NEXT: [[TMP8:%.*]] = inttoptr i64 [[TMP7]] to ptr +; CHECK-NEXT: [[_MSLD1:%.*]] = load , ptr [[TMP8]], align 8 +; CHECK-NEXT: [[_MSPROP:%.*]] = or [[_MSLD]], [[_MSLD1]] +; CHECK-NEXT: [[TMP9:%.*]] = fadd [[TMP1]], [[TMP5]] +; CHECK-NEXT: [[TMP10:%.*]] = ptrtoint ptr [[B]] to i64 +; CHECK-NEXT: [[TMP11:%.*]] = xor i64 [[TMP10]], 87960930222080 +; CHECK-NEXT: [[TMP12:%.*]] = inttoptr i64 [[TMP11]] to ptr +; CHECK-NEXT: store [[_MSLD1]], ptr [[TMP12]], align 8 +; CHECK-NEXT: store [[TMP5]], ptr [[B]], align 8 +; CHECK-NEXT: ret void +; + %1 = load , ptr %a + %2 = load , ptr %b + %3 = fadd %1, %2 + store %2, ptr %b + ret void +} diff --git a/llvm/test/LTO/X86/codemodel-2.ll b/llvm/test/LTO/X86/codemodel-2.ll index 5cd9731606f2bd106a4e3b66c78781527ee8883e..fc1074bcf2235c5d927b590ca284e0cf057edf17 100644 --- a/llvm/test/LTO/X86/codemodel-2.ll +++ b/llvm/test/LTO/X86/codemodel-2.ll @@ -1,5 +1,5 @@ ; RUN: llvm-as %s -o %t.o -; RUN: llvm-lto2 run -r %t.o,_start,px %t.o -o %t.s +; RUN: llvm-lto2 run -r %t.o,_start,px -r %t.o,_GLOBAL_OFFSET_TABLE_, %t.o -o %t.s ; RUN: llvm-objdump --no-print-imm-hex -d %t.s.0 | FileCheck %s --check-prefix=CHECK-LARGE target triple = "x86_64-unknown-linux-gnu" diff --git a/llvm/test/LTO/X86/codemodel-3.ll b/llvm/test/LTO/X86/codemodel-3.ll index 947221e9f36dc56ec271589552343917b6f132a6..13702dfbca2da410b785c71f113b90d968b22f3f 100644 --- a/llvm/test/LTO/X86/codemodel-3.ll +++ b/llvm/test/LTO/X86/codemodel-3.ll @@ -1,6 +1,7 @@ ; RUN: llvm-as %s -o %t0.o ; RUN: llvm-as < %p/Inputs/codemodel-3.ll > %t1.o -; RUN: not llvm-lto2 run -r %t0.o,_start,px -r %t1.o,bar,px %t0.o %t1.o -o %t2.s 2>&1 | FileCheck %s +; RUN: not llvm-lto2 run -r %t0.o,_start,px -r %t1.o,bar,px -r %t0.o,_GLOBAL_OFFSET_TABLE_, \ +; RUN: -r %t1.o,_GLOBAL_OFFSET_TABLE_, %t0.o %t1.o -o %t2.s 2>&1 | FileCheck %s target triple = "x86_64-unknown-linux-gnu" target datalayout = "e-m:e-p270:32:32-p271:32:32-p272:64:64-i64:64-f80:128-n8:16:32:64-S128" diff --git a/llvm/test/LTO/X86/largedatathreshold-1.ll b/llvm/test/LTO/X86/largedatathreshold-1.ll index e3be5c11baaac252c9958805f9898e76f0705860..dfd8319511b6176a0062fd0edd988d6411fb6cad 100644 --- a/llvm/test/LTO/X86/largedatathreshold-1.ll +++ b/llvm/test/LTO/X86/largedatathreshold-1.ll @@ -1,5 +1,5 @@ ; RUN: llvm-as %s -o %t.o -; RUN: llvm-lto2 run -r %t.o,_start,px %t.o -o %t.s +; RUN: llvm-lto2 run -r %t.o,_start,px -r %t.o,_GLOBAL_OFFSET_TABLE_, %t.o -o %t.s ; RUN: llvm-objdump -d %t.s.0 | FileCheck %s target triple = "x86_64-unknown-linux-gnu" diff --git a/llvm/test/LTO/X86/largedatathreshold-2.ll b/llvm/test/LTO/X86/largedatathreshold-2.ll index 103c066b744d0fa439c74078ba2e8ae0218bf88b..59438bbdb5027f87fad3a8ced46c3e940d4be6f6 100644 --- a/llvm/test/LTO/X86/largedatathreshold-2.ll +++ b/llvm/test/LTO/X86/largedatathreshold-2.ll @@ -1,5 +1,5 @@ ; RUN: llvm-as %s -o %t.o -; RUN: llvm-lto2 run -r %t.o,_start,px %t.o -o %t.s +; RUN: llvm-lto2 run -r %t.o,_start,px -r %t.o,_GLOBAL_OFFSET_TABLE_, %t.o -o %t.s ; RUN: llvm-objdump -d %t.s.0 | FileCheck %s target triple = "x86_64-unknown-linux-gnu" diff --git a/llvm/test/LTO/X86/largedatathreshold-3.ll b/llvm/test/LTO/X86/largedatathreshold-3.ll index 3c0653db334d85f9a857da36dbb73084132a515d..fea7987ff155669e2e2ef886909c28b2ec41d672 100644 --- a/llvm/test/LTO/X86/largedatathreshold-3.ll +++ b/llvm/test/LTO/X86/largedatathreshold-3.ll @@ -1,6 +1,7 @@ ; RUN: llvm-as %s -o %t0.o ; RUN: llvm-as < %p/Inputs/largedatathreshold.ll > %t1.o -; RUN: not llvm-lto2 run -r %t0.o,_start,px -r %t1.o,bar,px %t0.o %t1.o -o %t2.s 2>&1 | FileCheck %s +; RUN: not llvm-lto2 run -r %t0.o,_start,px -r %t1.o,bar,px -r %t0.o,_GLOBAL_OFFSET_TABLE_, \ +; RUN: -r %t1.o,_GLOBAL_OFFSET_TABLE_, %t0.o %t1.o -o %t2.s 2>&1 | FileCheck %s ; CHECK: 'Large Data Threshold': IDs have conflicting values diff --git a/llvm/test/MC/AArch64/SME2p1/fadd-diagnostics.s b/llvm/test/MC/AArch64/SME2p1/fadd-diagnostics.s index c13a1be05b1cd0e842ca5523c4af55ae44915ea0..a18989880a346d45af6bc699841f24d0b310507d 100644 --- a/llvm/test/MC/AArch64/SME2p1/fadd-diagnostics.s +++ b/llvm/test/MC/AArch64/SME2p1/fadd-diagnostics.s @@ -1,4 +1,4 @@ -// RUN: not llvm-mc -triple=aarch64 -show-encoding -mattr=+sme2p1,+sme-f16f16 2>&1 < %s | FileCheck %s +// RUN: not llvm-mc -triple=aarch64 -show-encoding -mattr=+sme-f16f16 2>&1 < %s | FileCheck %s // --------------------------------------------------------------------------// // Out of range index offset diff --git a/llvm/test/MC/AArch64/SME2p1/fadd.s b/llvm/test/MC/AArch64/SME2p1/fadd.s index a8e64a63dbdb60d3e396c1bb8342e341a216ca05..bdb769093c8388cfbd5d3d18e4cc819d66f86f91 100644 --- a/llvm/test/MC/AArch64/SME2p1/fadd.s +++ b/llvm/test/MC/AArch64/SME2p1/fadd.s @@ -1,300 +1,302 @@ -// RUN: llvm-mc -triple=aarch64 -show-encoding -mattr=+sme2p1,+sme-f16f16 < %s \ +// RUN: llvm-mc -triple=aarch64 -show-encoding -mattr=+sme-f16f16 < %s \ +// RUN: | FileCheck %s --check-prefixes=CHECK-ENCODING,CHECK-INST +// RUN: llvm-mc -triple=aarch64 -show-encoding -mattr=+sme-f8f16 < %s \ // RUN: | FileCheck %s --check-prefixes=CHECK-ENCODING,CHECK-INST // RUN: not llvm-mc -triple=aarch64 -show-encoding < %s 2>&1 \ // RUN: | FileCheck %s --check-prefix=CHECK-ERROR -// RUN: llvm-mc -triple=aarch64 -filetype=obj -mattr=+sme2p1,+sme-f16f16 < %s \ -// RUN: | llvm-objdump -d --mattr=+sme2p1,+sme-f16f16 - | FileCheck %s --check-prefix=CHECK-INST -// RUN: llvm-mc -triple=aarch64 -filetype=obj -mattr=+sme2p1,+sme-f16f16 < %s \ +// RUN: llvm-mc -triple=aarch64 -filetype=obj -mattr=+sme-f16f16 < %s \ +// RUN: | llvm-objdump -d --mattr=+sme-f16f16 - | FileCheck %s --check-prefix=CHECK-INST +// RUN: llvm-mc -triple=aarch64 -filetype=obj -mattr=+sme-f16f16 < %s \ // RUN: | llvm-objdump -d --mattr=-sme2p1 - | FileCheck %s --check-prefix=CHECK-UNKNOWN -// RUN: llvm-mc -triple=aarch64 -show-encoding -mattr=+sme2p1,+sme-f16f16 < %s \ +// RUN: llvm-mc -triple=aarch64 -show-encoding -mattr=+sme-f16f16 < %s \ // RUN: | sed '/.text/d' | sed 's/.*encoding: //g' \ -// RUN: | llvm-mc -triple=aarch64 -mattr=+sme2p1,+sme-f16f16 -disassemble -show-encoding \ +// RUN: | llvm-mc -triple=aarch64 -mattr=+sme-f16f16 -disassemble -show-encoding \ // RUN: | FileCheck %s --check-prefixes=CHECK-ENCODING,CHECK-INST fadd za.h[w8, 0, vgx2], {z0.h, z1.h} // 11000001-10100100-00011100-00000000 // CHECK-INST: fadd za.h[w8, 0, vgx2], { z0.h, z1.h } // CHECK-ENCODING: [0x00,0x1c,0xa4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a41c00 fadd za.h[w8, 0], {z0.h - z1.h} // 11000001-10100100-00011100-00000000 // CHECK-INST: fadd za.h[w8, 0, vgx2], { z0.h, z1.h } // CHECK-ENCODING: [0x00,0x1c,0xa4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a41c00 fadd za.h[w10, 5, vgx2], {z10.h, z11.h} // 11000001-10100100-01011101-01000101 // CHECK-INST: fadd za.h[w10, 5, vgx2], { z10.h, z11.h } // CHECK-ENCODING: [0x45,0x5d,0xa4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a45d45 fadd za.h[w10, 5], {z10.h - z11.h} // 11000001-10100100-01011101-01000101 // CHECK-INST: fadd za.h[w10, 5, vgx2], { z10.h, z11.h } // CHECK-ENCODING: [0x45,0x5d,0xa4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a45d45 fadd za.h[w11, 7, vgx2], {z12.h, z13.h} // 11000001-10100100-01111101-10000111 // CHECK-INST: fadd za.h[w11, 7, vgx2], { z12.h, z13.h } // CHECK-ENCODING: [0x87,0x7d,0xa4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a47d87 fadd za.h[w11, 7], {z12.h - z13.h} // 11000001-10100100-01111101-10000111 // CHECK-INST: fadd za.h[w11, 7, vgx2], { z12.h, z13.h } // CHECK-ENCODING: [0x87,0x7d,0xa4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a47d87 fadd za.h[w11, 7, vgx2], {z30.h, z31.h} // 11000001-10100100-01111111-11000111 // CHECK-INST: fadd za.h[w11, 7, vgx2], { z30.h, z31.h } // CHECK-ENCODING: [0xc7,0x7f,0xa4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a47fc7 fadd za.h[w11, 7], {z30.h - z31.h} // 11000001-10100100-01111111-11000111 // CHECK-INST: fadd za.h[w11, 7, vgx2], { z30.h, z31.h } // CHECK-ENCODING: [0xc7,0x7f,0xa4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a47fc7 fadd za.h[w8, 5, vgx2], {z16.h, z17.h} // 11000001-10100100-00011110-00000101 // CHECK-INST: fadd za.h[w8, 5, vgx2], { z16.h, z17.h } // CHECK-ENCODING: [0x05,0x1e,0xa4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a41e05 fadd za.h[w8, 5], {z16.h - z17.h} // 11000001-10100100-00011110-00000101 // CHECK-INST: fadd za.h[w8, 5, vgx2], { z16.h, z17.h } // CHECK-ENCODING: [0x05,0x1e,0xa4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a41e05 fadd za.h[w8, 1, vgx2], {z0.h, z1.h} // 11000001-10100100-00011100-00000001 // CHECK-INST: fadd za.h[w8, 1, vgx2], { z0.h, z1.h } // CHECK-ENCODING: [0x01,0x1c,0xa4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a41c01 fadd za.h[w8, 1], {z0.h - z1.h} // 11000001-10100100-00011100-00000001 // CHECK-INST: fadd za.h[w8, 1, vgx2], { z0.h, z1.h } // CHECK-ENCODING: [0x01,0x1c,0xa4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a41c01 fadd za.h[w10, 0, vgx2], {z18.h, z19.h} // 11000001-10100100-01011110, 01000000 // CHECK-INST: fadd za.h[w10, 0, vgx2], { z18.h, z19.h } // CHECK-ENCODING: [0x40,0x5e,0xa4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a45e40 fadd za.h[w10, 0], {z18.h - z19.h} // 11000001-10100100-01011110-01000000 // CHECK-INST: fadd za.h[w10, 0, vgx2], { z18.h, z19.h } // CHECK-ENCODING: [0x40,0x5e,0xa4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a45e40 fadd za.h[w8, 0, vgx2], {z12.h, z13.h} // 11000001-10100100-00011101-10000000 // CHECK-INST: fadd za.h[w8, 0, vgx2], { z12.h, z13.h } // CHECK-ENCODING: [0x80,0x1d,0xa4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a41d80 fadd za.h[w8, 0], {z12.h - z13.h} // 11000001-10100100-00011101-10000000 // CHECK-INST: fadd za.h[w8, 0, vgx2], { z12.h, z13.h } // CHECK-ENCODING: [0x80,0x1d,0xa4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a41d80 fadd za.h[w10, 1, vgx2], {z0.h, z1.h} // 11000001-10100100-01011100-00000001 // CHECK-INST: fadd za.h[w10, 1, vgx2], { z0.h, z1.h } // CHECK-ENCODING: [0x01,0x5c,0xa4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a45c01 fadd za.h[w10, 1], {z0.h - z1.h} // 11000001-10100100-01011100-00000001 // CHECK-INST: fadd za.h[w10, 1, vgx2], { z0.h, z1.h } // CHECK-ENCODING: [0x01,0x5c,0xa4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a45c01 fadd za.h[w8, 5, vgx2], {z22.h, z23.h} // 11000001-10100100-00011110, 11000101 // CHECK-INST: fadd za.h[w8, 5, vgx2], { z22.h, z23.h } // CHECK-ENCODING: [0xc5,0x1e,0xa4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a41ec5 fadd za.h[w8, 5], {z22.h - z23.h} // 11000001-10100100-00011110-11000101 // CHECK-INST: fadd za.h[w8, 5, vgx2], { z22.h, z23.h } // CHECK-ENCODING: [0xc5,0x1e,0xa4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a41ec5 fadd za.h[w11, 2, vgx2], {z8.h, z9.h} // 11000001-10100100-01111101-00000010 // CHECK-INST: fadd za.h[w11, 2, vgx2], { z8.h, z9.h } // CHECK-ENCODING: [0x02,0x7d,0xa4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a47d02 fadd za.h[w11, 2], {z8.h - z9.h} // 11000001-10100100-01111101-00000010 // CHECK-INST: fadd za.h[w11, 2, vgx2], { z8.h, z9.h } // CHECK-ENCODING: [0x02,0x7d,0xa4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a47d02 fadd za.h[w9, 7, vgx2], {z12.h, z13.h} // 11000001-10100100-00111101-10000111 // CHECK-INST: fadd za.h[w9, 7, vgx2], { z12.h, z13.h } // CHECK-ENCODING: [0x87,0x3d,0xa4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a43d87 fadd za.h[w9, 7], {z12.h - z13.h} // 11000001-10100100-00111101-10000111 // CHECK-INST: fadd za.h[w9, 7, vgx2], { z12.h, z13.h } // CHECK-ENCODING: [0x87,0x3d,0xa4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a43d87 fadd za.h[w8, 0, vgx4], {z0.h - z3.h} // 11000001-10100101-00011100-00000000 // CHECK-INST: fadd za.h[w8, 0, vgx4], { z0.h - z3.h } // CHECK-ENCODING: [0x00,0x1c,0xa5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a51c00 fadd za.h[w8, 0], {z0.h - z3.h} // 11000001-10100101-00011100-00000000 // CHECK-INST: fadd za.h[w8, 0, vgx4], { z0.h - z3.h } // CHECK-ENCODING: [0x00,0x1c,0xa5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a51c00 fadd za.h[w10, 5, vgx4], {z8.h - z11.h} // 11000001-10100101-01011101-00000101 // CHECK-INST: fadd za.h[w10, 5, vgx4], { z8.h - z11.h } // CHECK-ENCODING: [0x05,0x5d,0xa5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a55d05 fadd za.h[w10, 5], {z8.h - z11.h} // 11000001-10100101-01011101-00000101 // CHECK-INST: fadd za.h[w10, 5, vgx4], { z8.h - z11.h } // CHECK-ENCODING: [0x05,0x5d,0xa5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a55d05 fadd za.h[w11, 7, vgx4], {z12.h - z15.h} // 11000001-10100101-01111101-10000111 // CHECK-INST: fadd za.h[w11, 7, vgx4], { z12.h - z15.h } // CHECK-ENCODING: [0x87,0x7d,0xa5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a57d87 fadd za.h[w11, 7], {z12.h - z15.h} // 11000001-10100101-01111101-10000111 // CHECK-INST: fadd za.h[w11, 7, vgx4], { z12.h - z15.h } // CHECK-ENCODING: [0x87,0x7d,0xa5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a57d87 fadd za.h[w11, 7, vgx4], {z28.h - z31.h} // 11000001-10100101-01111111-10000111 // CHECK-INST: fadd za.h[w11, 7, vgx4], { z28.h - z31.h } // CHECK-ENCODING: [0x87,0x7f,0xa5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a57f87 fadd za.h[w11, 7], {z28.h - z31.h} // 11000001-10100101-01111111-10000111 // CHECK-INST: fadd za.h[w11, 7, vgx4], { z28.h - z31.h } // CHECK-ENCODING: [0x87,0x7f,0xa5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a57f87 fadd za.h[w8, 5, vgx4], {z16.h - z19.h} // 11000001-10100101-00011110-00000101 // CHECK-INST: fadd za.h[w8, 5, vgx4], { z16.h - z19.h } // CHECK-ENCODING: [0x05,0x1e,0xa5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a51e05 fadd za.h[w8, 5], {z16.h - z19.h} // 11000001-10100101-00011110-00000101 // CHECK-INST: fadd za.h[w8, 5, vgx4], { z16.h - z19.h } // CHECK-ENCODING: [0x05,0x1e,0xa5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a51e05 fadd za.h[w8, 1, vgx4], {z0.h - z3.h} // 11000001-10100101-00011100-00000001 // CHECK-INST: fadd za.h[w8, 1, vgx4], { z0.h - z3.h } // CHECK-ENCODING: [0x01,0x1c,0xa5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a51c01 fadd za.h[w8, 1], {z0.h - z3.h} // 11000001-10100101-00011100-00000001 // CHECK-INST: fadd za.h[w8, 1, vgx4], { z0.h - z3.h } // CHECK-ENCODING: [0x01,0x1c,0xa5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a51c01 fadd za.h[w10, 0, vgx4], {z16.h - z19.h} // 11000001-10100101-01011110-00000000 // CHECK-INST: fadd za.h[w10, 0, vgx4], { z16.h - z19.h } // CHECK-ENCODING: [0x00,0x5e,0xa5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a55e00 fadd za.h[w10, 0], {z16.h - z19.h} // 11000001-10100101-01011110-00000000 // CHECK-INST: fadd za.h[w10, 0, vgx4], { z16.h - z19.h } // CHECK-ENCODING: [0x00,0x5e,0xa5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a55e00 fadd za.h[w8, 0, vgx4], {z12.h - z15.h} // 11000001-10100101-00011101-10000000 // CHECK-INST: fadd za.h[w8, 0, vgx4], { z12.h - z15.h } // CHECK-ENCODING: [0x80,0x1d,0xa5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a51d80 fadd za.h[w8, 0], {z12.h - z15.h} // 11000001-10100101-00011101-10000000 // CHECK-INST: fadd za.h[w8, 0, vgx4], { z12.h - z15.h } // CHECK-ENCODING: [0x80,0x1d,0xa5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a51d80 fadd za.h[w10, 1, vgx4], {z0.h - z3.h} // 11000001-10100101-01011100-00000001 // CHECK-INST: fadd za.h[w10, 1, vgx4], { z0.h - z3.h } // CHECK-ENCODING: [0x01,0x5c,0xa5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a55c01 fadd za.h[w10, 1], {z0.h - z3.h} // 11000001-10100101-01011100-00000001 // CHECK-INST: fadd za.h[w10, 1, vgx4], { z0.h - z3.h } // CHECK-ENCODING: [0x01,0x5c,0xa5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a55c01 fadd za.h[w8, 5, vgx4], {z20.h - z23.h} // 11000001-10100101-00011110-10000101 // CHECK-INST: fadd za.h[w8, 5, vgx4], { z20.h - z23.h } // CHECK-ENCODING: [0x85,0x1e,0xa5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a51e85 fadd za.h[w8, 5], {z20.h - z23.h} // 11000001-10100101-00011110-10000101 // CHECK-INST: fadd za.h[w8, 5, vgx4], { z20.h - z23.h } // CHECK-ENCODING: [0x85,0x1e,0xa5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a51e85 fadd za.h[w11, 2, vgx4], {z8.h - z11.h} // 11000001-10100101-01111101-00000010 // CHECK-INST: fadd za.h[w11, 2, vgx4], { z8.h - z11.h } // CHECK-ENCODING: [0x02,0x7d,0xa5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a57d02 fadd za.h[w11, 2], {z8.h - z11.h} // 11000001-10100101-01111101-00000010 // CHECK-INST: fadd za.h[w11, 2, vgx4], { z8.h - z11.h } // CHECK-ENCODING: [0x02,0x7d,0xa5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a57d02 fadd za.h[w9, 7, vgx4], {z12.h - z15.h} // 11000001-10100101-00111101-10000111 // CHECK-INST: fadd za.h[w9, 7, vgx4], { z12.h - z15.h } // CHECK-ENCODING: [0x87,0x3d,0xa5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a53d87 fadd za.h[w9, 7], {z12.h - z15.h} // 11000001-10100101-00111101-10000111 // CHECK-INST: fadd za.h[w9, 7, vgx4], { z12.h - z15.h } // CHECK-ENCODING: [0x87,0x3d,0xa5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a53d87 diff --git a/llvm/test/MC/AArch64/SME2p1/fcvt.s b/llvm/test/MC/AArch64/SME2p1/fcvt.s index b5707bad0a24e3346df8c48f4130a9cb0a92f21d..2731055dedec41736fae24cadc5ba2dbefc0c865 100644 --- a/llvm/test/MC/AArch64/SME2p1/fcvt.s +++ b/llvm/test/MC/AArch64/SME2p1/fcvt.s @@ -1,36 +1,36 @@ -// RUN: llvm-mc -triple=aarch64 -show-encoding -mattr=+sme2p1,+sme-f16f16 < %s \ +// RUN: llvm-mc -triple=aarch64 -show-encoding -mattr=+sme-f16f16 < %s \ // RUN: | FileCheck %s --check-prefixes=CHECK-ENCODING,CHECK-INST // RUN: not llvm-mc -triple=aarch64 -show-encoding < %s 2>&1 \ // RUN: | FileCheck %s --check-prefix=CHECK-ERROR -// RUN: llvm-mc -triple=aarch64 -filetype=obj -mattr=+sme2p1,+sme-f16f16 < %s \ -// RUN: | llvm-objdump -d --mattr=+sme2p1,+sme-f16f16 - | FileCheck %s --check-prefix=CHECK-INST -// RUN: llvm-mc -triple=aarch64 -filetype=obj -mattr=+sme2p1,+sme-f16f16 < %s \ +// RUN: llvm-mc -triple=aarch64 -filetype=obj -mattr=+sme-f16f16 < %s \ +// RUN: | llvm-objdump -d --mattr=+sme-f16f16 - | FileCheck %s --check-prefix=CHECK-INST +// RUN: llvm-mc -triple=aarch64 -filetype=obj -mattr=+sme-f16f16 < %s \ // RUN: | llvm-objdump -d --mattr=-sme2p1 - | FileCheck %s --check-prefix=CHECK-UNKNOWN -// RUN: llvm-mc -triple=aarch64 -show-encoding -mattr=+sme2p1,+sme-f16f16 < %s \ +// RUN: llvm-mc -triple=aarch64 -show-encoding -mattr=+sme-f16f16 < %s \ // RUN: | sed '/.text/d' | sed 's/.*encoding: //g' \ -// RUN: | llvm-mc -triple=aarch64 -mattr=+sme2p1,+sme-f16f16 -disassemble -show-encoding \ +// RUN: | llvm-mc -triple=aarch64 -mattr=+sme-f16f16 -disassemble -show-encoding \ // RUN: | FileCheck %s --check-prefixes=CHECK-ENCODING,CHECK-INST fcvt {z0.s, z1.s}, z0.h // 11000001-10100000-11100000-00000000 // CHECK-INST: fcvt { z0.s, z1.s }, z0.h // CHECK-ENCODING: [0x00,0xe0,0xa0,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1a0e000 fcvt {z20.s, z21.s}, z10.h // 11000001-10100000-11100001-01010100 // CHECK-INST: fcvt { z20.s, z21.s }, z10.h // CHECK-ENCODING: [0x54,0xe1,0xa0,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1a0e154 fcvt {z22.s, z23.s}, z13.h // 11000001-10100000-11100001-10110110 // CHECK-INST: fcvt { z22.s, z23.s }, z13.h // CHECK-ENCODING: [0xb6,0xe1,0xa0,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1a0e1b6 fcvt {z30.s, z31.s}, z31.h // 11000001-10100000-11100011-11111110 // CHECK-INST: fcvt { z30.s, z31.s }, z31.h // CHECK-ENCODING: [0xfe,0xe3,0xa0,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1a0e3fe diff --git a/llvm/test/MC/AArch64/SME2p1/fcvtl-diagnostics.s b/llvm/test/MC/AArch64/SME2p1/fcvtl-diagnostics.s index a723d2fc6f3ac963383e8a2ef51b4d9931e8507d..ad3eaba7bdc21102c7ca94e26b1d9adaed30b16c 100644 --- a/llvm/test/MC/AArch64/SME2p1/fcvtl-diagnostics.s +++ b/llvm/test/MC/AArch64/SME2p1/fcvtl-diagnostics.s @@ -1,4 +1,4 @@ -// RUN: not llvm-mc -triple=aarch64 -show-encoding -mattr=+sme2p1,+sme-f16f16 2>&1 < %s | FileCheck %s +// RUN: not llvm-mc -triple=aarch64 -show-encoding -mattr=+sme-f16f16 2>&1 < %s | FileCheck %s // --------------------------------------------------------------------------// // Invalid vector list diff --git a/llvm/test/MC/AArch64/SME2p1/fcvtl.s b/llvm/test/MC/AArch64/SME2p1/fcvtl.s index 31cf90d037969cfe13e7b443ca1857e23bc03c06..6284915e49831b8f2d0a56c656388eb7acbbdf5c 100644 --- a/llvm/test/MC/AArch64/SME2p1/fcvtl.s +++ b/llvm/test/MC/AArch64/SME2p1/fcvtl.s @@ -1,36 +1,36 @@ -// RUN: llvm-mc -triple=aarch64 -show-encoding -mattr=+sme2p1,+sme-f16f16 < %s \ +// RUN: llvm-mc -triple=aarch64 -show-encoding -mattr=+sme-f16f16 < %s \ // RUN: | FileCheck %s --check-prefixes=CHECK-ENCODING,CHECK-INST // RUN: not llvm-mc -triple=aarch64 -show-encoding < %s 2>&1 \ // RUN: | FileCheck %s --check-prefix=CHECK-ERROR -// RUN: llvm-mc -triple=aarch64 -filetype=obj -mattr=+sme2p1,+sme-f16f16 < %s \ -// RUN: | llvm-objdump -d --mattr=+sme2p1,+sme-f16f16 - | FileCheck %s --check-prefix=CHECK-INST -// RUN: llvm-mc -triple=aarch64 -filetype=obj -mattr=+sme2p1,+sme-f16f16 < %s \ +// RUN: llvm-mc -triple=aarch64 -filetype=obj -mattr=+sme-f16f16 < %s \ +// RUN: | llvm-objdump -d --mattr=+sme-f16f16 - | FileCheck %s --check-prefix=CHECK-INST +// RUN: llvm-mc -triple=aarch64 -filetype=obj -mattr=+sme-f16f16 < %s \ // RUN: | llvm-objdump -d --mattr=-sme2p1 - | FileCheck %s --check-prefix=CHECK-UNKNOWN -// RUN: llvm-mc -triple=aarch64 -show-encoding -mattr=+sme2p1,+sme-f16f16 < %s \ +// RUN: llvm-mc -triple=aarch64 -show-encoding -mattr=+sme-f16f16 < %s \ // RUN: | sed '/.text/d' | sed 's/.*encoding: //g' \ -// RUN: | llvm-mc -triple=aarch64 -mattr=+sme2p1,+sme-f16f16 -disassemble -show-encoding \ +// RUN: | llvm-mc -triple=aarch64 -mattr=+sme-f16f16 -disassemble -show-encoding \ // RUN: | FileCheck %s --check-prefixes=CHECK-ENCODING,CHECK-INST fcvtl {z0.s, z1.s}, z0.h // 11000001-10100000-11100000-00000001 // CHECK-INST: fcvtl { z0.s, z1.s }, z0.h // CHECK-ENCODING: [0x01,0xe0,0xa0,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1a0e001 fcvtl {z20.s, z21.s}, z10.h // 11000001-10100000-11100001-01010101 // CHECK-INST: fcvtl { z20.s, z21.s }, z10.h // CHECK-ENCODING: [0x55,0xe1,0xa0,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1a0e155 fcvtl {z22.s, z23.s}, z13.h // 11000001-10100000-11100001-10110111 // CHECK-INST: fcvtl { z22.s, z23.s }, z13.h // CHECK-ENCODING: [0xb7,0xe1,0xa0,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1a0e1b7 fcvtl {z30.s, z31.s}, z31.h // 11000001-10100000-11100011-11111111 // CHECK-INST: fcvtl { z30.s, z31.s }, z31.h // CHECK-ENCODING: [0xff,0xe3,0xa0,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1a0e3ff diff --git a/llvm/test/MC/AArch64/SME2p1/fmla-diagnostics.s b/llvm/test/MC/AArch64/SME2p1/fmla-diagnostics.s index d32f795728a25910ba95e571aa4907a70e4e43f4..2f0dccb57c9076de73a2de999122dbec27f39dc2 100644 --- a/llvm/test/MC/AArch64/SME2p1/fmla-diagnostics.s +++ b/llvm/test/MC/AArch64/SME2p1/fmla-diagnostics.s @@ -1,4 +1,4 @@ -// RUN: not llvm-mc -triple=aarch64 -show-encoding -mattr=+sme2p1,+sme-f16f16 2>&1 < %s | FileCheck %s +// RUN: not llvm-mc -triple=aarch64 -show-encoding -mattr=+sme-f16f16 2>&1 < %s | FileCheck %s // --------------------------------------------------------------------------// // Invalid vector list diff --git a/llvm/test/MC/AArch64/SME2p1/fmla.s b/llvm/test/MC/AArch64/SME2p1/fmla.s index 10529d81eed634681605e23ac425829f5dbe3abe..df9ac8076e56645930725eaaee3ec41f15dd8f70 100644 --- a/llvm/test/MC/AArch64/SME2p1/fmla.s +++ b/llvm/test/MC/AArch64/SME2p1/fmla.s @@ -1,877 +1,877 @@ -// RUN: llvm-mc -triple=aarch64 -show-encoding -mattr=+sme2p1,+sme-f16f16 < %s \ +// RUN: llvm-mc -triple=aarch64 -show-encoding -mattr=+sme-f16f16 < %s \ // RUN: | FileCheck %s --check-prefixes=CHECK-ENCODING,CHECK-INST // RUN: not llvm-mc -triple=aarch64 -show-encoding < %s 2>&1 \ // RUN: | FileCheck %s --check-prefix=CHECK-ERROR -// RUN: llvm-mc -triple=aarch64 -filetype=obj -mattr=+sme2p1,+sme-f16f16 < %s \ -// RUN: | llvm-objdump -d --mattr=+sme2p1,+sme-f16f16 - | FileCheck %s --check-prefix=CHECK-INST -// RUN: llvm-mc -triple=aarch64 -filetype=obj -mattr=+sme2p1,+sme-f16f16 < %s \ +// RUN: llvm-mc -triple=aarch64 -filetype=obj -mattr=+sme-f16f16 < %s \ +// RUN: | llvm-objdump -d --mattr=+sme-f16f16 - | FileCheck %s --check-prefix=CHECK-INST +// RUN: llvm-mc -triple=aarch64 -filetype=obj -mattr=+sme-f16f16 < %s \ // RUN: | llvm-objdump -d --mattr=-sme2p1 - | FileCheck %s --check-prefix=CHECK-UNKNOWN -// RUN: llvm-mc -triple=aarch64 -show-encoding -mattr=+sme2p1,+sme-f16f16 < %s \ +// RUN: llvm-mc -triple=aarch64 -show-encoding -mattr=+sme-f16f16 < %s \ // RUN: | sed '/.text/d' | sed 's/.*encoding: //g' \ -// RUN: | llvm-mc -triple=aarch64 -mattr=+sme2p1,+sme-f16f16 -disassemble -show-encoding \ +// RUN: | llvm-mc -triple=aarch64 -mattr=+sme-f16f16 -disassemble -show-encoding \ // RUN: | FileCheck %s --check-prefixes=CHECK-ENCODING,CHECK-INST fmla za.h[w8, 0, vgx2], {z0.h, z1.h}, z0.h // 11000001-00100000-00011100-00000000 // CHECK-INST: fmla za.h[w8, 0, vgx2], { z0.h, z1.h }, z0.h // CHECK-ENCODING: [0x00,0x1c,0x20,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1201c00 fmla za.h[w8, 0], {z0.h - z1.h}, z0.h // 11000001-00100000-00011100-00000000 // CHECK-INST: fmla za.h[w8, 0, vgx2], { z0.h, z1.h }, z0.h // CHECK-ENCODING: [0x00,0x1c,0x20,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1201c00 fmla za.h[w10, 5, vgx2], {z10.h, z11.h}, z5.h // 11000001-00100101-01011101-01000101 // CHECK-INST: fmla za.h[w10, 5, vgx2], { z10.h, z11.h }, z5.h // CHECK-ENCODING: [0x45,0x5d,0x25,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1255d45 fmla za.h[w10, 5], {z10.h - z11.h}, z5.h // 11000001-00100101-01011101-01000101 // CHECK-INST: fmla za.h[w10, 5, vgx2], { z10.h, z11.h }, z5.h // CHECK-ENCODING: [0x45,0x5d,0x25,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1255d45 fmla za.h[w11, 7, vgx2], {z13.h, z14.h}, z8.h // 11000001-00101000-01111101-10100111 // CHECK-INST: fmla za.h[w11, 7, vgx2], { z13.h, z14.h }, z8.h // CHECK-ENCODING: [0xa7,0x7d,0x28,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1287da7 fmla za.h[w11, 7], {z13.h - z14.h}, z8.h // 11000001-00101000-01111101-10100111 // CHECK-INST: fmla za.h[w11, 7, vgx2], { z13.h, z14.h }, z8.h // CHECK-ENCODING: [0xa7,0x7d,0x28,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1287da7 fmla za.h[w11, 7, vgx2], {z31.h, z0.h}, z15.h // 11000001-00101111-01111111-11100111 // CHECK-INST: fmla za.h[w11, 7, vgx2], { z31.h, z0.h }, z15.h // CHECK-ENCODING: [0xe7,0x7f,0x2f,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c12f7fe7 fmla za.h[w11, 7], {z31.h - z0.h}, z15.h // 11000001-00101111-01111111-11100111 // CHECK-INST: fmla za.h[w11, 7, vgx2], { z31.h, z0.h }, z15.h // CHECK-ENCODING: [0xe7,0x7f,0x2f,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c12f7fe7 fmla za.h[w8, 5, vgx2], {z17.h, z18.h}, z0.h // 11000001-00100000-00011110-00100101 // CHECK-INST: fmla za.h[w8, 5, vgx2], { z17.h, z18.h }, z0.h // CHECK-ENCODING: [0x25,0x1e,0x20,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1201e25 fmla za.h[w8, 5], {z17.h - z18.h}, z0.h // 11000001-00100000-00011110-00100101 // CHECK-INST: fmla za.h[w8, 5, vgx2], { z17.h, z18.h }, z0.h // CHECK-ENCODING: [0x25,0x1e,0x20,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1201e25 fmla za.h[w8, 1, vgx2], {z1.h, z2.h}, z14.h // 11000001-00101110-00011100-00100001 // CHECK-INST: fmla za.h[w8, 1, vgx2], { z1.h, z2.h }, z14.h // CHECK-ENCODING: [0x21,0x1c,0x2e,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c12e1c21 fmla za.h[w8, 1], {z1.h - z2.h}, z14.h // 11000001-00101110-00011100-00100001 // CHECK-INST: fmla za.h[w8, 1, vgx2], { z1.h, z2.h }, z14.h // CHECK-ENCODING: [0x21,0x1c,0x2e,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c12e1c21 fmla za.h[w10, 0, vgx2], {z19.h, z20.h}, z4.h // 11000001-00100100-01011110-01100000 // CHECK-INST: fmla za.h[w10, 0, vgx2], { z19.h, z20.h }, z4.h // CHECK-ENCODING: [0x60,0x5e,0x24,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1245e60 fmla za.h[w10, 0], {z19.h - z20.h}, z4.h // 11000001-00100100-01011110-01100000 // CHECK-INST: fmla za.h[w10, 0, vgx2], { z19.h, z20.h }, z4.h // CHECK-ENCODING: [0x60,0x5e,0x24,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1245e60 fmla za.h[w8, 0, vgx2], {z12.h, z13.h}, z2.h // 11000001-00100010-00011101-10000000 // CHECK-INST: fmla za.h[w8, 0, vgx2], { z12.h, z13.h }, z2.h // CHECK-ENCODING: [0x80,0x1d,0x22,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1221d80 fmla za.h[w8, 0], {z12.h - z13.h}, z2.h // 11000001-00100010-00011101-10000000 // CHECK-INST: fmla za.h[w8, 0, vgx2], { z12.h, z13.h }, z2.h // CHECK-ENCODING: [0x80,0x1d,0x22,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1221d80 fmla za.h[w10, 1, vgx2], {z1.h, z2.h}, z10.h // 11000001-00101010-01011100-00100001 // CHECK-INST: fmla za.h[w10, 1, vgx2], { z1.h, z2.h }, z10.h // CHECK-ENCODING: [0x21,0x5c,0x2a,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c12a5c21 fmla za.h[w10, 1], {z1.h - z2.h}, z10.h // 11000001-00101010-01011100-00100001 // CHECK-INST: fmla za.h[w10, 1, vgx2], { z1.h, z2.h }, z10.h // CHECK-ENCODING: [0x21,0x5c,0x2a,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c12a5c21 fmla za.h[w8, 5, vgx2], {z22.h, z23.h}, z14.h // 11000001-00101110-00011110-11000101 // CHECK-INST: fmla za.h[w8, 5, vgx2], { z22.h, z23.h }, z14.h // CHECK-ENCODING: [0xc5,0x1e,0x2e,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c12e1ec5 fmla za.h[w8, 5], {z22.h - z23.h}, z14.h // 11000001-00101110-00011110-11000101 // CHECK-INST: fmla za.h[w8, 5, vgx2], { z22.h, z23.h }, z14.h // CHECK-ENCODING: [0xc5,0x1e,0x2e,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c12e1ec5 fmla za.h[w11, 2, vgx2], {z9.h, z10.h}, z1.h // 11000001-00100001-01111101-00100010 // CHECK-INST: fmla za.h[w11, 2, vgx2], { z9.h, z10.h }, z1.h // CHECK-ENCODING: [0x22,0x7d,0x21,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1217d22 fmla za.h[w11, 2], {z9.h - z10.h}, z1.h // 11000001-00100001-01111101-00100010 // CHECK-INST: fmla za.h[w11, 2, vgx2], { z9.h, z10.h }, z1.h // CHECK-ENCODING: [0x22,0x7d,0x21,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1217d22 fmla za.h[w9, 7, vgx2], {z12.h, z13.h}, z11.h // 11000001-00101011-00111101-10000111 // CHECK-INST: fmla za.h[w9, 7, vgx2], { z12.h, z13.h }, z11.h // CHECK-ENCODING: [0x87,0x3d,0x2b,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c12b3d87 fmla za.h[w9, 7], {z12.h - z13.h}, z11.h // 11000001-00101011-00111101-10000111 // CHECK-INST: fmla za.h[w9, 7, vgx2], { z12.h, z13.h }, z11.h // CHECK-ENCODING: [0x87,0x3d,0x2b,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c12b3d87 fmla za.h[w8, 0, vgx2], {z0.h, z1.h}, z0.h[0] // 11000001-00010000-00010000-00000000 // CHECK-INST: fmla za.h[w8, 0, vgx2], { z0.h, z1.h }, z0.h[0] // CHECK-ENCODING: [0x00,0x10,0x10,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1101000 fmla za.h[w8, 0], {z0.h - z1.h}, z0.h[0] // 11000001-00010000-00010000-00000000 // CHECK-INST: fmla za.h[w8, 0, vgx2], { z0.h, z1.h }, z0.h[0] // CHECK-ENCODING: [0x00,0x10,0x10,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1101000 fmla za.h[w10, 5, vgx2], {z10.h, z11.h}, z5.h[2] // 11000001-00010101-01010101-01000101 // CHECK-INST: fmla za.h[w10, 5, vgx2], { z10.h, z11.h }, z5.h[2] // CHECK-ENCODING: [0x45,0x55,0x15,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1155545 fmla za.h[w10, 5], {z10.h - z11.h}, z5.h[2] // 11000001-00010101-01010101-01000101 // CHECK-INST: fmla za.h[w10, 5, vgx2], { z10.h, z11.h }, z5.h[2] // CHECK-ENCODING: [0x45,0x55,0x15,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1155545 fmla za.h[w11, 7, vgx2], {z12.h, z13.h}, z8.h[6] // 11000001-00011000-01111101-10000111 // CHECK-INST: fmla za.h[w11, 7, vgx2], { z12.h, z13.h }, z8.h[6] // CHECK-ENCODING: [0x87,0x7d,0x18,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1187d87 fmla za.h[w11, 7], {z12.h - z13.h}, z8.h[6] // 11000001-00011000-01111101-10000111 // CHECK-INST: fmla za.h[w11, 7, vgx2], { z12.h, z13.h }, z8.h[6] // CHECK-ENCODING: [0x87,0x7d,0x18,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1187d87 fmla za.h[w11, 7, vgx2], {z30.h, z31.h}, z15.h[7] // 11000001-00011111-01111111-11001111 // CHECK-INST: fmla za.h[w11, 7, vgx2], { z30.h, z31.h }, z15.h[7] // CHECK-ENCODING: [0xcf,0x7f,0x1f,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c11f7fcf fmla za.h[w11, 7], {z30.h - z31.h}, z15.h[7] // 11000001-00011111-01111111-11001111 // CHECK-INST: fmla za.h[w11, 7, vgx2], { z30.h, z31.h }, z15.h[7] // CHECK-ENCODING: [0xcf,0x7f,0x1f,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c11f7fcf fmla za.h[w8, 5, vgx2], {z16.h, z17.h}, z0.h[6] // 11000001-00010000-00011110-00000101 // CHECK-INST: fmla za.h[w8, 5, vgx2], { z16.h, z17.h }, z0.h[6] // CHECK-ENCODING: [0x05,0x1e,0x10,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1101e05 fmla za.h[w8, 5], {z16.h - z17.h}, z0.h[6] // 11000001-00010000-00011110-00000101 // CHECK-INST: fmla za.h[w8, 5, vgx2], { z16.h, z17.h }, z0.h[6] // CHECK-ENCODING: [0x05,0x1e,0x10,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1101e05 fmla za.h[w8, 1, vgx2], {z0.h, z1.h}, z14.h[2] // 11000001-00011110-00010100-00000001 // CHECK-INST: fmla za.h[w8, 1, vgx2], { z0.h, z1.h }, z14.h[2] // CHECK-ENCODING: [0x01,0x14,0x1e,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c11e1401 fmla za.h[w8, 1], {z0.h - z1.h}, z14.h[2] // 11000001-00011110-00010100-00000001 // CHECK-INST: fmla za.h[w8, 1, vgx2], { z0.h, z1.h }, z14.h[2] // CHECK-ENCODING: [0x01,0x14,0x1e,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c11e1401 fmla za.h[w10, 0, vgx2], {z18.h, z19.h}, z4.h[3] // 11000001-00010100-01010110-01001000 // CHECK-INST: fmla za.h[w10, 0, vgx2], { z18.h, z19.h }, z4.h[3] // CHECK-ENCODING: [0x48,0x56,0x14,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1145648 fmla za.h[w10, 0], {z18.h - z19.h}, z4.h[3] // 11000001-00010100-01010110-01001000 // CHECK-INST: fmla za.h[w10, 0, vgx2], { z18.h, z19.h }, z4.h[3] // CHECK-ENCODING: [0x48,0x56,0x14,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1145648 fmla za.h[w8, 0, vgx2], {z12.h, z13.h}, z2.h[4] // 11000001-00010010-00011001-10000000 // CHECK-INST: fmla za.h[w8, 0, vgx2], { z12.h, z13.h }, z2.h[4] // CHECK-ENCODING: [0x80,0x19,0x12,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1121980 fmla za.h[w8, 0], {z12.h - z13.h}, z2.h[4] // 11000001-00010010-00011001-10000000 // CHECK-INST: fmla za.h[w8, 0, vgx2], { z12.h, z13.h }, z2.h[4] // CHECK-ENCODING: [0x80,0x19,0x12,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1121980 fmla za.h[w10, 1, vgx2], {z0.h, z1.h}, z10.h[4] // 11000001-00011010-01011000-00000001 // CHECK-INST: fmla za.h[w10, 1, vgx2], { z0.h, z1.h }, z10.h[4] // CHECK-ENCODING: [0x01,0x58,0x1a,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c11a5801 fmla za.h[w10, 1], {z0.h - z1.h}, z10.h[4] // 11000001-00011010-01011000-00000001 // CHECK-INST: fmla za.h[w10, 1, vgx2], { z0.h, z1.h }, z10.h[4] // CHECK-ENCODING: [0x01,0x58,0x1a,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c11a5801 fmla za.h[w8, 5, vgx2], {z22.h, z23.h}, z14.h[5] // 11000001-00011110-00011010-11001101 // CHECK-INST: fmla za.h[w8, 5, vgx2], { z22.h, z23.h }, z14.h[5] // CHECK-ENCODING: [0xcd,0x1a,0x1e,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c11e1acd fmla za.h[w8, 5], {z22.h - z23.h}, z14.h[5] // 11000001-00011110-00011010-11001101 // CHECK-INST: fmla za.h[w8, 5, vgx2], { z22.h, z23.h }, z14.h[5] // CHECK-ENCODING: [0xcd,0x1a,0x1e,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c11e1acd fmla za.h[w11, 2, vgx2], {z8.h, z9.h}, z1.h[2] // 11000001-00010001-01110101-00000010 // CHECK-INST: fmla za.h[w11, 2, vgx2], { z8.h, z9.h }, z1.h[2] // CHECK-ENCODING: [0x02,0x75,0x11,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1117502 fmla za.h[w11, 2], {z8.h - z9.h}, z1.h[2] // 11000001-00010001-01110101-00000010 // CHECK-INST: fmla za.h[w11, 2, vgx2], { z8.h, z9.h }, z1.h[2] // CHECK-ENCODING: [0x02,0x75,0x11,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1117502 fmla za.h[w9, 7, vgx2], {z12.h, z13.h}, z11.h[4] // 11000001-00011011-00111001-10000111 // CHECK-INST: fmla za.h[w9, 7, vgx2], { z12.h, z13.h }, z11.h[4] // CHECK-ENCODING: [0x87,0x39,0x1b,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c11b3987 fmla za.h[w9, 7], {z12.h - z13.h}, z11.h[4] // 11000001-00011011-00111001-10000111 // CHECK-INST: fmla za.h[w9, 7, vgx2], { z12.h, z13.h }, z11.h[4] // CHECK-ENCODING: [0x87,0x39,0x1b,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c11b3987 fmla za.h[w8, 0, vgx2], {z0.h, z1.h}, {z0.h, z1.h} // 11000001-10100000-00010000-00001000 // CHECK-INST: fmla za.h[w8, 0, vgx2], { z0.h, z1.h }, { z0.h, z1.h } // CHECK-ENCODING: [0x08,0x10,0xa0,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1a01008 fmla za.h[w8, 0], {z0.h - z1.h}, {z0.h - z1.h} // 11000001-10100000-00010000-00001000 // CHECK-INST: fmla za.h[w8, 0, vgx2], { z0.h, z1.h }, { z0.h, z1.h } // CHECK-ENCODING: [0x08,0x10,0xa0,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1a01008 fmla za.h[w10, 5, vgx2], {z10.h, z11.h}, {z20.h, z21.h} // 11000001-10110100-01010001-01001101 // CHECK-INST: fmla za.h[w10, 5, vgx2], { z10.h, z11.h }, { z20.h, z21.h } // CHECK-ENCODING: [0x4d,0x51,0xb4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1b4514d fmla za.h[w10, 5], {z10.h - z11.h}, {z20.h - z21.h} // 11000001-10110100-01010001-01001101 // CHECK-INST: fmla za.h[w10, 5, vgx2], { z10.h, z11.h }, { z20.h, z21.h } // CHECK-ENCODING: [0x4d,0x51,0xb4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1b4514d fmla za.h[w11, 7, vgx2], {z12.h, z13.h}, {z8.h, z9.h} // 11000001-10101000-01110001-10001111 // CHECK-INST: fmla za.h[w11, 7, vgx2], { z12.h, z13.h }, { z8.h, z9.h } // CHECK-ENCODING: [0x8f,0x71,0xa8,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1a8718f fmla za.h[w11, 7], {z12.h - z13.h}, {z8.h - z9.h} // 11000001-10101000-01110001-10001111 // CHECK-INST: fmla za.h[w11, 7, vgx2], { z12.h, z13.h }, { z8.h, z9.h } // CHECK-ENCODING: [0x8f,0x71,0xa8,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1a8718f fmla za.h[w11, 7, vgx2], {z30.h, z31.h}, {z30.h, z31.h} // 11000001-10111110-01110011-11001111 // CHECK-INST: fmla za.h[w11, 7, vgx2], { z30.h, z31.h }, { z30.h, z31.h } // CHECK-ENCODING: [0xcf,0x73,0xbe,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1be73cf fmla za.h[w11, 7], {z30.h - z31.h}, {z30.h - z31.h} // 11000001-10111110-01110011-11001111 // CHECK-INST: fmla za.h[w11, 7, vgx2], { z30.h, z31.h }, { z30.h, z31.h } // CHECK-ENCODING: [0xcf,0x73,0xbe,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1be73cf fmla za.h[w8, 5, vgx2], {z16.h, z17.h}, {z16.h, z17.h} // 11000001-10110000-00010010-00001101 // CHECK-INST: fmla za.h[w8, 5, vgx2], { z16.h, z17.h }, { z16.h, z17.h } // CHECK-ENCODING: [0x0d,0x12,0xb0,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1b0120d fmla za.h[w8, 5], {z16.h - z17.h}, {z16.h - z17.h} // 11000001-10110000-00010010-00001101 // CHECK-INST: fmla za.h[w8, 5, vgx2], { z16.h, z17.h }, { z16.h, z17.h } // CHECK-ENCODING: [0x0d,0x12,0xb0,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1b0120d fmla za.h[w8, 1, vgx2], {z0.h, z1.h}, {z30.h, z31.h} // 11000001-10111110-00010000-00001001 // CHECK-INST: fmla za.h[w8, 1, vgx2], { z0.h, z1.h }, { z30.h, z31.h } // CHECK-ENCODING: [0x09,0x10,0xbe,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1be1009 fmla za.h[w8, 1], {z0.h - z1.h}, {z30.h - z31.h} // 11000001-10111110-00010000-00001001 // CHECK-INST: fmla za.h[w8, 1, vgx2], { z0.h, z1.h }, { z30.h, z31.h } // CHECK-ENCODING: [0x09,0x10,0xbe,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1be1009 fmla za.h[w10, 0, vgx2], {z18.h, z19.h}, {z20.h, z21.h} // 11000001-10110100-01010010-01001000 // CHECK-INST: fmla za.h[w10, 0, vgx2], { z18.h, z19.h }, { z20.h, z21.h } // CHECK-ENCODING: [0x48,0x52,0xb4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1b45248 fmla za.h[w10, 0], {z18.h - z19.h}, {z20.h - z21.h} // 11000001-10110100-01010010-01001000 // CHECK-INST: fmla za.h[w10, 0, vgx2], { z18.h, z19.h }, { z20.h, z21.h } // CHECK-ENCODING: [0x48,0x52,0xb4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1b45248 fmla za.h[w8, 0, vgx2], {z12.h, z13.h}, {z2.h, z3.h} // 11000001-10100010-00010001-10001000 // CHECK-INST: fmla za.h[w8, 0, vgx2], { z12.h, z13.h }, { z2.h, z3.h } // CHECK-ENCODING: [0x88,0x11,0xa2,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1a21188 fmla za.h[w8, 0], {z12.h - z13.h}, {z2.h - z3.h} // 11000001-10100010-00010001-10001000 // CHECK-INST: fmla za.h[w8, 0, vgx2], { z12.h, z13.h }, { z2.h, z3.h } // CHECK-ENCODING: [0x88,0x11,0xa2,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1a21188 fmla za.h[w10, 1, vgx2], {z0.h, z1.h}, {z26.h, z27.h} // 11000001-10111010-01010000-00001001 // CHECK-INST: fmla za.h[w10, 1, vgx2], { z0.h, z1.h }, { z26.h, z27.h } // CHECK-ENCODING: [0x09,0x50,0xba,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1ba5009 fmla za.h[w10, 1], {z0.h - z1.h}, {z26.h - z27.h} // 11000001-10111010-01010000-00001001 // CHECK-INST: fmla za.h[w10, 1, vgx2], { z0.h, z1.h }, { z26.h, z27.h } // CHECK-ENCODING: [0x09,0x50,0xba,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1ba5009 fmla za.h[w8, 5, vgx2], {z22.h, z23.h}, {z30.h, z31.h} // 11000001-10111110-00010010-11001101 // CHECK-INST: fmla za.h[w8, 5, vgx2], { z22.h, z23.h }, { z30.h, z31.h } // CHECK-ENCODING: [0xcd,0x12,0xbe,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1be12cd fmla za.h[w8, 5], {z22.h - z23.h}, {z30.h - z31.h} // 11000001-10111110-00010010-11001101 // CHECK-INST: fmla za.h[w8, 5, vgx2], { z22.h, z23.h }, { z30.h, z31.h } // CHECK-ENCODING: [0xcd,0x12,0xbe,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1be12cd fmla za.h[w11, 2, vgx2], {z8.h, z9.h}, {z0.h, z1.h} // 11000001-10100000-01110001-00001010 // CHECK-INST: fmla za.h[w11, 2, vgx2], { z8.h, z9.h }, { z0.h, z1.h } // CHECK-ENCODING: [0x0a,0x71,0xa0,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1a0710a fmla za.h[w11, 2], {z8.h - z9.h}, {z0.h - z1.h} // 11000001-10100000-01110001-00001010 // CHECK-INST: fmla za.h[w11, 2, vgx2], { z8.h, z9.h }, { z0.h, z1.h } // CHECK-ENCODING: [0x0a,0x71,0xa0,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1a0710a fmla za.h[w9, 7, vgx2], {z12.h, z13.h}, {z10.h, z11.h} // 11000001-10101010-00110001-10001111 // CHECK-INST: fmla za.h[w9, 7, vgx2], { z12.h, z13.h }, { z10.h, z11.h } // CHECK-ENCODING: [0x8f,0x31,0xaa,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1aa318f fmla za.h[w9, 7], {z12.h - z13.h}, {z10.h - z11.h} // 11000001-10101010-00110001-10001111 // CHECK-INST: fmla za.h[w9, 7, vgx2], { z12.h, z13.h }, { z10.h, z11.h } // CHECK-ENCODING: [0x8f,0x31,0xaa,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1aa318f fmla za.h[w8, 0, vgx4], {z0.h - z3.h}, z0.h // 11000001-00110000-00011100-00000000 // CHECK-INST: fmla za.h[w8, 0, vgx4], { z0.h - z3.h }, z0.h // CHECK-ENCODING: [0x00,0x1c,0x30,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1301c00 fmla za.h[w8, 0], {z0.h - z3.h}, z0.h // 11000001-00110000-00011100-00000000 // CHECK-INST: fmla za.h[w8, 0, vgx4], { z0.h - z3.h }, z0.h // CHECK-ENCODING: [0x00,0x1c,0x30,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1301c00 fmla za.h[w10, 5, vgx4], {z10.h - z13.h}, z5.h // 11000001-00110101-01011101-01000101 // CHECK-INST: fmla za.h[w10, 5, vgx4], { z10.h - z13.h }, z5.h // CHECK-ENCODING: [0x45,0x5d,0x35,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1355d45 fmla za.h[w10, 5], {z10.h - z13.h}, z5.h // 11000001-00110101-01011101-01000101 // CHECK-INST: fmla za.h[w10, 5, vgx4], { z10.h - z13.h }, z5.h // CHECK-ENCODING: [0x45,0x5d,0x35,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1355d45 fmla za.h[w11, 7, vgx4], {z13.h - z16.h}, z8.h // 11000001-00111000-01111101-10100111 // CHECK-INST: fmla za.h[w11, 7, vgx4], { z13.h - z16.h }, z8.h // CHECK-ENCODING: [0xa7,0x7d,0x38,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1387da7 fmla za.h[w11, 7], {z13.h - z16.h}, z8.h // 11000001-00111000-01111101-10100111 // CHECK-INST: fmla za.h[w11, 7, vgx4], { z13.h - z16.h }, z8.h // CHECK-ENCODING: [0xa7,0x7d,0x38,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1387da7 fmla za.h[w11, 7, vgx4], {z31.h, z0.h, z1.h, z2.h}, z15.h // 11000001-00111111-01111111-11100111 // CHECK-INST: fmla za.h[w11, 7, vgx4], { z31.h, z0.h, z1.h, z2.h }, z15.h // CHECK-ENCODING: [0xe7,0x7f,0x3f,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c13f7fe7 fmla za.h[w11, 7], {z31.h, z0.h, z1.h, z2.h}, z15.h // 11000001-00111111-01111111-11100111 // CHECK-INST: fmla za.h[w11, 7, vgx4], { z31.h, z0.h, z1.h, z2.h }, z15.h // CHECK-ENCODING: [0xe7,0x7f,0x3f,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c13f7fe7 fmla za.h[w8, 5, vgx4], {z17.h - z20.h}, z0.h // 11000001-00110000-00011110-00100101 // CHECK-INST: fmla za.h[w8, 5, vgx4], { z17.h - z20.h }, z0.h // CHECK-ENCODING: [0x25,0x1e,0x30,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1301e25 fmla za.h[w8, 5], {z17.h - z20.h}, z0.h // 11000001-00110000-00011110-00100101 // CHECK-INST: fmla za.h[w8, 5, vgx4], { z17.h - z20.h }, z0.h // CHECK-ENCODING: [0x25,0x1e,0x30,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1301e25 fmla za.h[w8, 1, vgx4], {z1.h - z4.h}, z14.h // 11000001-00111110-00011100-00100001 // CHECK-INST: fmla za.h[w8, 1, vgx4], { z1.h - z4.h }, z14.h // CHECK-ENCODING: [0x21,0x1c,0x3e,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c13e1c21 fmla za.h[w8, 1], {z1.h - z4.h}, z14.h // 11000001-00111110-00011100-00100001 // CHECK-INST: fmla za.h[w8, 1, vgx4], { z1.h - z4.h }, z14.h // CHECK-ENCODING: [0x21,0x1c,0x3e,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c13e1c21 fmla za.h[w10, 0, vgx4], {z19.h - z22.h}, z4.h // 11000001-00110100-01011110-01100000 // CHECK-INST: fmla za.h[w10, 0, vgx4], { z19.h - z22.h }, z4.h // CHECK-ENCODING: [0x60,0x5e,0x34,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1345e60 fmla za.h[w10, 0], {z19.h - z22.h}, z4.h // 11000001-00110100-01011110-01100000 // CHECK-INST: fmla za.h[w10, 0, vgx4], { z19.h - z22.h }, z4.h // CHECK-ENCODING: [0x60,0x5e,0x34,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1345e60 fmla za.h[w8, 0, vgx4], {z12.h - z15.h}, z2.h // 11000001-00110010-00011101-10000000 // CHECK-INST: fmla za.h[w8, 0, vgx4], { z12.h - z15.h }, z2.h // CHECK-ENCODING: [0x80,0x1d,0x32,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1321d80 fmla za.h[w8, 0], {z12.h - z15.h}, z2.h // 11000001-00110010-00011101-10000000 // CHECK-INST: fmla za.h[w8, 0, vgx4], { z12.h - z15.h }, z2.h // CHECK-ENCODING: [0x80,0x1d,0x32,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1321d80 fmla za.h[w10, 1, vgx4], {z1.h - z4.h}, z10.h // 11000001-00111010-01011100-00100001 // CHECK-INST: fmla za.h[w10, 1, vgx4], { z1.h - z4.h }, z10.h // CHECK-ENCODING: [0x21,0x5c,0x3a,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c13a5c21 fmla za.h[w10, 1], {z1.h - z4.h}, z10.h // 11000001-00111010-01011100-00100001 // CHECK-INST: fmla za.h[w10, 1, vgx4], { z1.h - z4.h }, z10.h // CHECK-ENCODING: [0x21,0x5c,0x3a,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c13a5c21 fmla za.h[w8, 5, vgx4], {z22.h - z25.h}, z14.h // 11000001-00111110-00011110-11000101 // CHECK-INST: fmla za.h[w8, 5, vgx4], { z22.h - z25.h }, z14.h // CHECK-ENCODING: [0xc5,0x1e,0x3e,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c13e1ec5 fmla za.h[w8, 5], {z22.h - z25.h}, z14.h // 11000001-00111110-00011110-11000101 // CHECK-INST: fmla za.h[w8, 5, vgx4], { z22.h - z25.h }, z14.h // CHECK-ENCODING: [0xc5,0x1e,0x3e,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c13e1ec5 fmla za.h[w11, 2, vgx4], {z9.h - z12.h}, z1.h // 11000001-00110001-01111101-00100010 // CHECK-INST: fmla za.h[w11, 2, vgx4], { z9.h - z12.h }, z1.h // CHECK-ENCODING: [0x22,0x7d,0x31,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1317d22 fmla za.h[w11, 2], {z9.h - z12.h}, z1.h // 11000001-00110001-01111101-00100010 // CHECK-INST: fmla za.h[w11, 2, vgx4], { z9.h - z12.h }, z1.h // CHECK-ENCODING: [0x22,0x7d,0x31,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1317d22 fmla za.h[w9, 7, vgx4], {z12.h - z15.h}, z11.h // 11000001-00111011-00111101-10000111 // CHECK-INST: fmla za.h[w9, 7, vgx4], { z12.h - z15.h }, z11.h // CHECK-ENCODING: [0x87,0x3d,0x3b,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c13b3d87 fmla za.h[w9, 7], {z12.h - z15.h}, z11.h // 11000001-00111011-00111101-10000111 // CHECK-INST: fmla za.h[w9, 7, vgx4], { z12.h - z15.h }, z11.h // CHECK-ENCODING: [0x87,0x3d,0x3b,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c13b3d87 fmla za.h[w8, 0, vgx4], {z0.h - z3.h}, z0.h[0] // 11000001-00010000-10010000-00000000 // CHECK-INST: fmla za.h[w8, 0, vgx4], { z0.h - z3.h }, z0.h[0] // CHECK-ENCODING: [0x00,0x90,0x10,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1109000 fmla za.h[w8, 0], {z0.h - z3.h}, z0.h[0] // 11000001-00010000-10010000-00000000 // CHECK-INST: fmla za.h[w8, 0, vgx4], { z0.h - z3.h }, z0.h[0] // CHECK-ENCODING: [0x00,0x90,0x10,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1109000 fmla za.h[w10, 5, vgx4], {z8.h - z11.h}, z5.h[2] // 11000001-00010101-11010101-00000101 // CHECK-INST: fmla za.h[w10, 5, vgx4], { z8.h - z11.h }, z5.h[2] // CHECK-ENCODING: [0x05,0xd5,0x15,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c115d505 fmla za.h[w10, 5], {z8.h - z11.h}, z5.h[2] // 11000001-00010101-11010101-00000101 // CHECK-INST: fmla za.h[w10, 5, vgx4], { z8.h - z11.h }, z5.h[2] // CHECK-ENCODING: [0x05,0xd5,0x15,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c115d505 fmla za.h[w11, 7, vgx4], {z12.h - z15.h}, z8.h[6] // 11000001-00011000-11111101-10000111 // CHECK-INST: fmla za.h[w11, 7, vgx4], { z12.h - z15.h }, z8.h[6] // CHECK-ENCODING: [0x87,0xfd,0x18,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c118fd87 fmla za.h[w11, 7], {z12.h - z15.h}, z8.h[6] // 11000001-00011000-11111101-10000111 // CHECK-INST: fmla za.h[w11, 7, vgx4], { z12.h - z15.h }, z8.h[6] // CHECK-ENCODING: [0x87,0xfd,0x18,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c118fd87 fmla za.h[w11, 7, vgx4], {z28.h - z31.h}, z15.h[7] // 11000001-00011111-11111111-10001111 // CHECK-INST: fmla za.h[w11, 7, vgx4], { z28.h - z31.h }, z15.h[7] // CHECK-ENCODING: [0x8f,0xff,0x1f,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c11fff8f fmla za.h[w11, 7], {z28.h - z31.h}, z15.h[7] // 11000001-00011111-11111111-10001111 // CHECK-INST: fmla za.h[w11, 7, vgx4], { z28.h - z31.h }, z15.h[7] // CHECK-ENCODING: [0x8f,0xff,0x1f,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c11fff8f fmla za.h[w8, 5, vgx4], {z16.h - z19.h}, z0.h[6] // 11000001-00010000-10011110-00000101 // CHECK-INST: fmla za.h[w8, 5, vgx4], { z16.h - z19.h }, z0.h[6] // CHECK-ENCODING: [0x05,0x9e,0x10,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1109e05 fmla za.h[w8, 5], {z16.h - z19.h}, z0.h[6] // 11000001-00010000-10011110-00000101 // CHECK-INST: fmla za.h[w8, 5, vgx4], { z16.h - z19.h }, z0.h[6] // CHECK-ENCODING: [0x05,0x9e,0x10,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1109e05 fmla za.h[w8, 1, vgx4], {z0.h - z3.h}, z14.h[2] // 11000001-00011110-10010100-00000001 // CHECK-INST: fmla za.h[w8, 1, vgx4], { z0.h - z3.h }, z14.h[2] // CHECK-ENCODING: [0x01,0x94,0x1e,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c11e9401 fmla za.h[w8, 1], {z0.h - z3.h}, z14.h[2] // 11000001-00011110-10010100-00000001 // CHECK-INST: fmla za.h[w8, 1, vgx4], { z0.h - z3.h }, z14.h[2] // CHECK-ENCODING: [0x01,0x94,0x1e,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c11e9401 fmla za.h[w10, 0, vgx4], {z16.h - z19.h}, z4.h[3] // 11000001-00010100-11010110-00001000 // CHECK-INST: fmla za.h[w10, 0, vgx4], { z16.h - z19.h }, z4.h[3] // CHECK-ENCODING: [0x08,0xd6,0x14,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c114d608 fmla za.h[w10, 0], {z16.h - z19.h}, z4.h[3] // 11000001-00010100-11010110-00001000 // CHECK-INST: fmla za.h[w10, 0, vgx4], { z16.h - z19.h }, z4.h[3] // CHECK-ENCODING: [0x08,0xd6,0x14,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c114d608 fmla za.h[w8, 0, vgx4], {z12.h - z15.h}, z2.h[4] // 11000001-00010010-10011001-10000000 // CHECK-INST: fmla za.h[w8, 0, vgx4], { z12.h - z15.h }, z2.h[4] // CHECK-ENCODING: [0x80,0x99,0x12,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1129980 fmla za.h[w8, 0], {z12.h - z15.h}, z2.h[4] // 11000001-00010010-10011001-10000000 // CHECK-INST: fmla za.h[w8, 0, vgx4], { z12.h - z15.h }, z2.h[4] // CHECK-ENCODING: [0x80,0x99,0x12,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1129980 fmla za.h[w10, 1, vgx4], {z0.h - z3.h}, z10.h[4] // 11000001-00011010-11011000-00000001 // CHECK-INST: fmla za.h[w10, 1, vgx4], { z0.h - z3.h }, z10.h[4] // CHECK-ENCODING: [0x01,0xd8,0x1a,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c11ad801 fmla za.h[w10, 1], {z0.h - z3.h}, z10.h[4] // 11000001-00011010-11011000-00000001 // CHECK-INST: fmla za.h[w10, 1, vgx4], { z0.h - z3.h }, z10.h[4] // CHECK-ENCODING: [0x01,0xd8,0x1a,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c11ad801 fmla za.h[w8, 5, vgx4], {z20.h - z23.h}, z14.h[5] // 11000001-00011110-10011010-10001101 // CHECK-INST: fmla za.h[w8, 5, vgx4], { z20.h - z23.h }, z14.h[5] // CHECK-ENCODING: [0x8d,0x9a,0x1e,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c11e9a8d fmla za.h[w8, 5], {z20.h - z23.h}, z14.h[5] // 11000001-00011110-10011010-10001101 // CHECK-INST: fmla za.h[w8, 5, vgx4], { z20.h - z23.h }, z14.h[5] // CHECK-ENCODING: [0x8d,0x9a,0x1e,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c11e9a8d fmla za.h[w11, 2, vgx4], {z8.h - z11.h}, z1.h[2] // 11000001-00010001-11110101-00000010 // CHECK-INST: fmla za.h[w11, 2, vgx4], { z8.h - z11.h }, z1.h[2] // CHECK-ENCODING: [0x02,0xf5,0x11,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c111f502 fmla za.h[w11, 2], {z8.h - z11.h}, z1.h[2] // 11000001-00010001-11110101-00000010 // CHECK-INST: fmla za.h[w11, 2, vgx4], { z8.h - z11.h }, z1.h[2] // CHECK-ENCODING: [0x02,0xf5,0x11,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c111f502 fmla za.h[w9, 7, vgx4], {z12.h - z15.h}, z11.h[4] // 11000001-00011011-10111001-10000111 // CHECK-INST: fmla za.h[w9, 7, vgx4], { z12.h - z15.h }, z11.h[4] // CHECK-ENCODING: [0x87,0xb9,0x1b,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c11bb987 fmla za.h[w9, 7], {z12.h - z15.h}, z11.h[4] // 11000001-00011011-10111001-10000111 // CHECK-INST: fmla za.h[w9, 7, vgx4], { z12.h - z15.h }, z11.h[4] // CHECK-ENCODING: [0x87,0xb9,0x1b,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c11bb987 fmla za.h[w8, 0, vgx4], {z0.h - z3.h}, {z0.h - z3.h} // 11000001-10100001-00010000-00001000 // CHECK-INST: fmla za.h[w8, 0, vgx4], { z0.h - z3.h }, { z0.h - z3.h } // CHECK-ENCODING: [0x08,0x10,0xa1,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1a11008 fmla za.h[w8, 0], {z0.h - z3.h}, {z0.h - z3.h} // 11000001-10100001-00010000-00001000 // CHECK-INST: fmla za.h[w8, 0, vgx4], { z0.h - z3.h }, { z0.h - z3.h } // CHECK-ENCODING: [0x08,0x10,0xa1,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1a11008 fmla za.h[w10, 5, vgx4], {z8.h - z11.h}, {z20.h - z23.h} // 11000001-10110101-01010001-00001101 // CHECK-INST: fmla za.h[w10, 5, vgx4], { z8.h - z11.h }, { z20.h - z23.h } // CHECK-ENCODING: [0x0d,0x51,0xb5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1b5510d fmla za.h[w10, 5], {z8.h - z11.h}, {z20.h - z23.h} // 11000001-10110101-01010001-00001101 // CHECK-INST: fmla za.h[w10, 5, vgx4], { z8.h - z11.h }, { z20.h - z23.h } // CHECK-ENCODING: [0x0d,0x51,0xb5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1b5510d fmla za.h[w11, 7, vgx4], {z12.h - z15.h}, {z8.h - z11.h} // 11000001-10101001-01110001-10001111 // CHECK-INST: fmla za.h[w11, 7, vgx4], { z12.h - z15.h }, { z8.h - z11.h } // CHECK-ENCODING: [0x8f,0x71,0xa9,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1a9718f fmla za.h[w11, 7], {z12.h - z15.h}, {z8.h - z11.h} // 11000001-10101001-01110001-10001111 // CHECK-INST: fmla za.h[w11, 7, vgx4], { z12.h - z15.h }, { z8.h - z11.h } // CHECK-ENCODING: [0x8f,0x71,0xa9,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1a9718f fmla za.h[w11, 7, vgx4], {z28.h - z31.h}, {z28.h - z31.h} // 11000001-10111101-01110011-10001111 // CHECK-INST: fmla za.h[w11, 7, vgx4], { z28.h - z31.h }, { z28.h - z31.h } // CHECK-ENCODING: [0x8f,0x73,0xbd,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1bd738f fmla za.h[w11, 7], {z28.h - z31.h}, {z28.h - z31.h} // 11000001-10111101-01110011-10001111 // CHECK-INST: fmla za.h[w11, 7, vgx4], { z28.h - z31.h }, { z28.h - z31.h } // CHECK-ENCODING: [0x8f,0x73,0xbd,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1bd738f fmla za.h[w8, 5, vgx4], {z16.h - z19.h}, {z16.h - z19.h} // 11000001-10110001-00010010-00001101 // CHECK-INST: fmla za.h[w8, 5, vgx4], { z16.h - z19.h }, { z16.h - z19.h } // CHECK-ENCODING: [0x0d,0x12,0xb1,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1b1120d fmla za.h[w8, 5], {z16.h - z19.h}, {z16.h - z19.h} // 11000001-10110001-00010010-00001101 // CHECK-INST: fmla za.h[w8, 5, vgx4], { z16.h - z19.h }, { z16.h - z19.h } // CHECK-ENCODING: [0x0d,0x12,0xb1,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1b1120d fmla za.h[w8, 1, vgx4], {z0.h - z3.h}, {z28.h - z31.h} // 11000001-10111101-00010000-00001001 // CHECK-INST: fmla za.h[w8, 1, vgx4], { z0.h - z3.h }, { z28.h - z31.h } // CHECK-ENCODING: [0x09,0x10,0xbd,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1bd1009 fmla za.h[w8, 1], {z0.h - z3.h}, {z28.h - z31.h} // 11000001-10111101-00010000-00001001 // CHECK-INST: fmla za.h[w8, 1, vgx4], { z0.h - z3.h }, { z28.h - z31.h } // CHECK-ENCODING: [0x09,0x10,0xbd,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1bd1009 fmla za.h[w10, 0, vgx4], {z16.h - z19.h}, {z20.h - z23.h} // 11000001-10110101-01010010-00001000 // CHECK-INST: fmla za.h[w10, 0, vgx4], { z16.h - z19.h }, { z20.h - z23.h } // CHECK-ENCODING: [0x08,0x52,0xb5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1b55208 fmla za.h[w10, 0], {z16.h - z19.h}, {z20.h - z23.h} // 11000001-10110101-01010010-00001000 // CHECK-INST: fmla za.h[w10, 0, vgx4], { z16.h - z19.h }, { z20.h - z23.h } // CHECK-ENCODING: [0x08,0x52,0xb5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1b55208 fmla za.h[w8, 0, vgx4], {z12.h - z15.h}, {z0.h - z3.h} // 11000001-10100001-00010001-10001000 // CHECK-INST: fmla za.h[w8, 0, vgx4], { z12.h - z15.h }, { z0.h - z3.h } // CHECK-ENCODING: [0x88,0x11,0xa1,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1a11188 fmla za.h[w8, 0], {z12.h - z15.h}, {z0.h - z3.h} // 11000001-10100001-00010001-10001000 // CHECK-INST: fmla za.h[w8, 0, vgx4], { z12.h - z15.h }, { z0.h - z3.h } // CHECK-ENCODING: [0x88,0x11,0xa1,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1a11188 fmla za.h[w10, 1, vgx4], {z0.h - z3.h}, {z24.h - z27.h} // 11000001-10111001-01010000-00001001 // CHECK-INST: fmla za.h[w10, 1, vgx4], { z0.h - z3.h }, { z24.h - z27.h } // CHECK-ENCODING: [0x09,0x50,0xb9,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1b95009 fmla za.h[w10, 1], {z0.h - z3.h}, {z24.h - z27.h} // 11000001-10111001-01010000-00001001 // CHECK-INST: fmla za.h[w10, 1, vgx4], { z0.h - z3.h }, { z24.h - z27.h } // CHECK-ENCODING: [0x09,0x50,0xb9,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1b95009 fmla za.h[w8, 5, vgx4], {z20.h - z23.h}, {z28.h - z31.h} // 11000001-10111101-00010010-10001101 // CHECK-INST: fmla za.h[w8, 5, vgx4], { z20.h - z23.h }, { z28.h - z31.h } // CHECK-ENCODING: [0x8d,0x12,0xbd,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1bd128d fmla za.h[w8, 5], {z20.h - z23.h}, {z28.h - z31.h} // 11000001-10111101-00010010-10001101 // CHECK-INST: fmla za.h[w8, 5, vgx4], { z20.h - z23.h }, { z28.h - z31.h } // CHECK-ENCODING: [0x8d,0x12,0xbd,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1bd128d fmla za.h[w11, 2, vgx4], {z8.h - z11.h}, {z0.h - z3.h} // 11000001-10100001-01110001-00001010 // CHECK-INST: fmla za.h[w11, 2, vgx4], { z8.h - z11.h }, { z0.h - z3.h } // CHECK-ENCODING: [0x0a,0x71,0xa1,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1a1710a fmla za.h[w11, 2], {z8.h - z11.h}, {z0.h - z3.h} // 11000001-10100001-01110001-00001010 // CHECK-INST: fmla za.h[w11, 2, vgx4], { z8.h - z11.h }, { z0.h - z3.h } // CHECK-ENCODING: [0x0a,0x71,0xa1,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1a1710a fmla za.h[w9, 7, vgx4], {z12.h - z15.h}, {z8.h - z11.h} // 11000001-10101001-00110001-10001111 // CHECK-INST: fmla za.h[w9, 7, vgx4], { z12.h - z15.h }, { z8.h - z11.h } // CHECK-ENCODING: [0x8f,0x31,0xa9,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1a9318f fmla za.h[w9, 7], {z12.h - z15.h}, {z8.h - z11.h} // 11000001-10101001-00110001-10001111 // CHECK-INST: fmla za.h[w9, 7, vgx4], { z12.h - z15.h }, { z8.h - z11.h } // CHECK-ENCODING: [0x8f,0x31,0xa9,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1a9318f diff --git a/llvm/test/MC/AArch64/SME2p1/fmls-diagnostics.s b/llvm/test/MC/AArch64/SME2p1/fmls-diagnostics.s index 2174e4202ba0d02efbe0130cf79b31996003ab7e..3ff09321e3436b278be7cccea840021852314ac3 100644 --- a/llvm/test/MC/AArch64/SME2p1/fmls-diagnostics.s +++ b/llvm/test/MC/AArch64/SME2p1/fmls-diagnostics.s @@ -1,4 +1,4 @@ -// RUN: not llvm-mc -triple=aarch64 -show-encoding -mattr=+sme2p1,+sme-f16f16 2>&1 < %s | FileCheck %s +// RUN: not llvm-mc -triple=aarch64 -show-encoding -mattr=+sme-f16f16 2>&1 < %s | FileCheck %s // --------------------------------------------------------------------------// // Invalid vector list diff --git a/llvm/test/MC/AArch64/SME2p1/fmls.s b/llvm/test/MC/AArch64/SME2p1/fmls.s index 9bbb21869e377966f732c620982c5a799c00d3c6..67b1430240e8d99786127ccde3958acd01b0569e 100644 --- a/llvm/test/MC/AArch64/SME2p1/fmls.s +++ b/llvm/test/MC/AArch64/SME2p1/fmls.s @@ -1,878 +1,878 @@ -// RUN: llvm-mc -triple=aarch64 -show-encoding -mattr=+sme2p1,+sme-f16f16 < %s \ +// RUN: llvm-mc -triple=aarch64 -show-encoding -mattr=+sme-f16f16 < %s \ // RUN: | FileCheck %s --check-prefixes=CHECK-ENCODING,CHECK-INST // RUN: not llvm-mc -triple=aarch64 -show-encoding < %s 2>&1 \ // RUN: | FileCheck %s --check-prefix=CHECK-ERROR -// RUN: llvm-mc -triple=aarch64 -filetype=obj -mattr=+sme2p1,+sme-f16f16 < %s \ -// RUN: | llvm-objdump -d --mattr=+sme2p1,+sme-f16f16 - | FileCheck %s --check-prefix=CHECK-INST -// RUN: llvm-mc -triple=aarch64 -filetype=obj -mattr=+sme2p1,+sme-f16f16 < %s \ +// RUN: llvm-mc -triple=aarch64 -filetype=obj -mattr=+sme-f16f16 < %s \ +// RUN: | llvm-objdump -d --mattr=+sme-f16f16 - | FileCheck %s --check-prefix=CHECK-INST +// RUN: llvm-mc -triple=aarch64 -filetype=obj -mattr=+sme-f16f16 < %s \ // RUN: | llvm-objdump -d --mattr=-sme2p1 - | FileCheck %s --check-prefix=CHECK-UNKNOWN -// RUN: llvm-mc -triple=aarch64 -show-encoding -mattr=+sme2p1,+sme-f16f16 < %s \ +// RUN: llvm-mc -triple=aarch64 -show-encoding -mattr=+sme-f16f16 < %s \ // RUN: | sed '/.text/d' | sed 's/.*encoding: //g' \ -// RUN: | llvm-mc -triple=aarch64 -mattr=+sme2p1,+sme-f16f16 -disassemble -show-encoding \ +// RUN: | llvm-mc -triple=aarch64 -mattr=+sme-f16f16 -disassemble -show-encoding \ // RUN: | FileCheck %s --check-prefixes=CHECK-ENCODING,CHECK-INST fmls za.h[w8, 0, vgx2], {z0.h, z1.h}, z0.h // 11000001-00100000-00011100-00001000 // CHECK-INST: fmls za.h[w8, 0, vgx2], { z0.h, z1.h }, z0.h // CHECK-ENCODING: [0x08,0x1c,0x20,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1201c08 fmls za.h[w8, 0], {z0.h - z1.h}, z0.h // 11000001-00100000-00011100-00001000 // CHECK-INST: fmls za.h[w8, 0, vgx2], { z0.h, z1.h }, z0.h // CHECK-ENCODING: [0x08,0x1c,0x20,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1201c08 fmls za.h[w10, 5, vgx2], {z10.h, z11.h}, z5.h // 11000001-00100101-01011101-01001101 // CHECK-INST: fmls za.h[w10, 5, vgx2], { z10.h, z11.h }, z5.h // CHECK-ENCODING: [0x4d,0x5d,0x25,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1255d4d fmls za.h[w10, 5], {z10.h - z11.h}, z5.h // 11000001-00100101-01011101-01001101 // CHECK-INST: fmls za.h[w10, 5, vgx2], { z10.h, z11.h }, z5.h // CHECK-ENCODING: [0x4d,0x5d,0x25,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1255d4d fmls za.h[w11, 7, vgx2], {z13.h, z14.h}, z8.h // 11000001-00101000-01111101-10101111 // CHECK-INST: fmls za.h[w11, 7, vgx2], { z13.h, z14.h }, z8.h // CHECK-ENCODING: [0xaf,0x7d,0x28,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1287daf fmls za.h[w11, 7], {z13.h - z14.h}, z8.h // 11000001-00101000-01111101-10101111 // CHECK-INST: fmls za.h[w11, 7, vgx2], { z13.h, z14.h }, z8.h // CHECK-ENCODING: [0xaf,0x7d,0x28,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1287daf fmls za.h[w11, 7, vgx2], {z31.h, z0.h}, z15.h // 11000001-00101111-01111111-11101111 // CHECK-INST: fmls za.h[w11, 7, vgx2], { z31.h, z0.h }, z15.h // CHECK-ENCODING: [0xef,0x7f,0x2f,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c12f7fef fmls za.h[w11, 7], {z31.h - z0.h}, z15.h // 11000001-00101111-01111111-11101111 // CHECK-INST: fmls za.h[w11, 7, vgx2], { z31.h, z0.h }, z15.h // CHECK-ENCODING: [0xef,0x7f,0x2f,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c12f7fef fmls za.h[w8, 5, vgx2], {z17.h, z18.h}, z0.h // 11000001-00100000-00011110-00101101 // CHECK-INST: fmls za.h[w8, 5, vgx2], { z17.h, z18.h }, z0.h // CHECK-ENCODING: [0x2d,0x1e,0x20,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1201e2d fmls za.h[w8, 5], {z17.h - z18.h}, z0.h // 11000001-00100000-00011110-00101101 // CHECK-INST: fmls za.h[w8, 5, vgx2], { z17.h, z18.h }, z0.h // CHECK-ENCODING: [0x2d,0x1e,0x20,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1201e2d fmls za.h[w8, 1, vgx2], {z1.h, z2.h}, z14.h // 11000001-00101110-00011100-00101001 // CHECK-INST: fmls za.h[w8, 1, vgx2], { z1.h, z2.h }, z14.h // CHECK-ENCODING: [0x29,0x1c,0x2e,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c12e1c29 fmls za.h[w8, 1], {z1.h - z2.h}, z14.h // 11000001-00101110-00011100-00101001 // CHECK-INST: fmls za.h[w8, 1, vgx2], { z1.h, z2.h }, z14.h // CHECK-ENCODING: [0x29,0x1c,0x2e,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c12e1c29 fmls za.h[w10, 0, vgx2], {z19.h, z20.h}, z4.h // 11000001-00100100-01011110-01101000 // CHECK-INST: fmls za.h[w10, 0, vgx2], { z19.h, z20.h }, z4.h // CHECK-ENCODING: [0x68,0x5e,0x24,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1245e68 fmls za.h[w10, 0], {z19.h - z20.h}, z4.h // 11000001-00100100-01011110-01101000 // CHECK-INST: fmls za.h[w10, 0, vgx2], { z19.h, z20.h }, z4.h // CHECK-ENCODING: [0x68,0x5e,0x24,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1245e68 fmls za.h[w8, 0, vgx2], {z12.h, z13.h}, z2.h // 11000001-00100010-00011101-10001000 // CHECK-INST: fmls za.h[w8, 0, vgx2], { z12.h, z13.h }, z2.h // CHECK-ENCODING: [0x88,0x1d,0x22,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1221d88 fmls za.h[w8, 0], {z12.h - z13.h}, z2.h // 11000001-00100010-00011101-10001000 // CHECK-INST: fmls za.h[w8, 0, vgx2], { z12.h, z13.h }, z2.h // CHECK-ENCODING: [0x88,0x1d,0x22,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1221d88 fmls za.h[w10, 1, vgx2], {z1.h, z2.h}, z10.h // 11000001-00101010-01011100-00101001 // CHECK-INST: fmls za.h[w10, 1, vgx2], { z1.h, z2.h }, z10.h // CHECK-ENCODING: [0x29,0x5c,0x2a,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c12a5c29 fmls za.h[w10, 1], {z1.h - z2.h}, z10.h // 11000001-00101010-01011100-00101001 // CHECK-INST: fmls za.h[w10, 1, vgx2], { z1.h, z2.h }, z10.h // CHECK-ENCODING: [0x29,0x5c,0x2a,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c12a5c29 fmls za.h[w8, 5, vgx2], {z22.h, z23.h}, z14.h // 11000001-00101110-00011110-11001101 // CHECK-INST: fmls za.h[w8, 5, vgx2], { z22.h, z23.h }, z14.h // CHECK-ENCODING: [0xcd,0x1e,0x2e,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c12e1ecd fmls za.h[w8, 5], {z22.h - z23.h}, z14.h // 11000001-00101110-00011110-11001101 // CHECK-INST: fmls za.h[w8, 5, vgx2], { z22.h, z23.h }, z14.h // CHECK-ENCODING: [0xcd,0x1e,0x2e,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c12e1ecd fmls za.h[w11, 2, vgx2], {z9.h, z10.h}, z1.h // 11000001-00100001-01111101-00101010 // CHECK-INST: fmls za.h[w11, 2, vgx2], { z9.h, z10.h }, z1.h // CHECK-ENCODING: [0x2a,0x7d,0x21,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1217d2a fmls za.h[w11, 2], {z9.h - z10.h}, z1.h // 11000001-00100001-01111101-00101010 // CHECK-INST: fmls za.h[w11, 2, vgx2], { z9.h, z10.h }, z1.h // CHECK-ENCODING: [0x2a,0x7d,0x21,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1217d2a fmls za.h[w9, 7, vgx2], {z12.h, z13.h}, z11.h // 11000001-00101011-00111101-10001111 // CHECK-INST: fmls za.h[w9, 7, vgx2], { z12.h, z13.h }, z11.h // CHECK-ENCODING: [0x8f,0x3d,0x2b,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c12b3d8f fmls za.h[w9, 7], {z12.h - z13.h}, z11.h // 11000001-00101011-00111101-10001111 // CHECK-INST: fmls za.h[w9, 7, vgx2], { z12.h, z13.h }, z11.h // CHECK-ENCODING: [0x8f,0x3d,0x2b,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c12b3d8f fmls za.h[w8, 0, vgx2], {z0.h, z1.h}, z0.h[0] // 11000001-00010000-00010000-00010000 // CHECK-INST: fmls za.h[w8, 0, vgx2], { z0.h, z1.h }, z0.h[0] // CHECK-ENCODING: [0x10,0x10,0x10,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1101010 fmls za.h[w8, 0], {z0.h - z1.h}, z0.h[0] // 11000001-00010000-00010000-00010000 // CHECK-INST: fmls za.h[w8, 0, vgx2], { z0.h, z1.h }, z0.h[0] // CHECK-ENCODING: [0x10,0x10,0x10,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1101010 fmls za.h[w10, 5, vgx2], {z10.h, z11.h}, z5.h[2] // 11000001-00010101-01010101-01010101 // CHECK-INST: fmls za.h[w10, 5, vgx2], { z10.h, z11.h }, z5.h[2] // CHECK-ENCODING: [0x55,0x55,0x15,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1155555 fmls za.h[w10, 5], {z10.h - z11.h}, z5.h[2] // 11000001-00010101-01010101-01010101 // CHECK-INST: fmls za.h[w10, 5, vgx2], { z10.h, z11.h }, z5.h[2] // CHECK-ENCODING: [0x55,0x55,0x15,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1155555 fmls za.h[w11, 7, vgx2], {z12.h, z13.h}, z8.h[6] // 11000001-00011000-01111101-10010111 // CHECK-INST: fmls za.h[w11, 7, vgx2], { z12.h, z13.h }, z8.h[6] // CHECK-ENCODING: [0x97,0x7d,0x18,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1187d97 fmls za.h[w11, 7], {z12.h - z13.h}, z8.h[6] // 11000001-00011000-01111101-10010111 // CHECK-INST: fmls za.h[w11, 7, vgx2], { z12.h, z13.h }, z8.h[6] // CHECK-ENCODING: [0x97,0x7d,0x18,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1187d97 fmls za.h[w11, 7, vgx2], {z30.h, z31.h}, z15.h[7] // 11000001-00011111-01111111-11011111 // CHECK-INST: fmls za.h[w11, 7, vgx2], { z30.h, z31.h }, z15.h[7] // CHECK-ENCODING: [0xdf,0x7f,0x1f,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c11f7fdf fmls za.h[w11, 7], {z30.h - z31.h}, z15.h[7] // 11000001-00011111-01111111-11011111 // CHECK-INST: fmls za.h[w11, 7, vgx2], { z30.h, z31.h }, z15.h[7] // CHECK-ENCODING: [0xdf,0x7f,0x1f,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c11f7fdf fmls za.h[w8, 5, vgx2], {z16.h, z17.h}, z0.h[6] // 11000001-00010000-00011110-00010101 // CHECK-INST: fmls za.h[w8, 5, vgx2], { z16.h, z17.h }, z0.h[6] // CHECK-ENCODING: [0x15,0x1e,0x10,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1101e15 fmls za.h[w8, 5], {z16.h - z17.h}, z0.h[6] // 11000001-00010000-00011110-00010101 // CHECK-INST: fmls za.h[w8, 5, vgx2], { z16.h, z17.h }, z0.h[6] // CHECK-ENCODING: [0x15,0x1e,0x10,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1101e15 fmls za.h[w8, 1, vgx2], {z0.h, z1.h}, z14.h[2] // 11000001-00011110-00010100-00010001 // CHECK-INST: fmls za.h[w8, 1, vgx2], { z0.h, z1.h }, z14.h[2] // CHECK-ENCODING: [0x11,0x14,0x1e,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c11e1411 fmls za.h[w8, 1], {z0.h - z1.h}, z14.h[2] // 11000001-00011110-00010100-00010001 // CHECK-INST: fmls za.h[w8, 1, vgx2], { z0.h, z1.h }, z14.h[2] // CHECK-ENCODING: [0x11,0x14,0x1e,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c11e1411 fmls za.h[w10, 0, vgx2], {z18.h, z19.h}, z4.h[3] // 11000001-00010100-01010110-01011000 // CHECK-INST: fmls za.h[w10, 0, vgx2], { z18.h, z19.h }, z4.h[3] // CHECK-ENCODING: [0x58,0x56,0x14,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1145658 fmls za.h[w10, 0], {z18.h - z19.h}, z4.h[3] // 11000001-00010100-01010110-01011000 // CHECK-INST: fmls za.h[w10, 0, vgx2], { z18.h, z19.h }, z4.h[3] // CHECK-ENCODING: [0x58,0x56,0x14,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1145658 fmls za.h[w8, 0, vgx2], {z12.h, z13.h}, z2.h[4] // 11000001-00010010-00011001-10010000 // CHECK-INST: fmls za.h[w8, 0, vgx2], { z12.h, z13.h }, z2.h[4] // CHECK-ENCODING: [0x90,0x19,0x12,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1121990 fmls za.h[w8, 0], {z12.h - z13.h}, z2.h[4] // 11000001-00010010-00011001-10010000 // CHECK-INST: fmls za.h[w8, 0, vgx2], { z12.h, z13.h }, z2.h[4] // CHECK-ENCODING: [0x90,0x19,0x12,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1121990 fmls za.h[w10, 1, vgx2], {z0.h, z1.h}, z10.h[4] // 11000001-00011010-01011000-00010001 // CHECK-INST: fmls za.h[w10, 1, vgx2], { z0.h, z1.h }, z10.h[4] // CHECK-ENCODING: [0x11,0x58,0x1a,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c11a5811 fmls za.h[w10, 1], {z0.h - z1.h}, z10.h[4] // 11000001-00011010-01011000-00010001 // CHECK-INST: fmls za.h[w10, 1, vgx2], { z0.h, z1.h }, z10.h[4] // CHECK-ENCODING: [0x11,0x58,0x1a,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c11a5811 fmls za.h[w8, 5, vgx2], {z22.h, z23.h}, z14.h[5] // 11000001-00011110-00011010-11011101 // CHECK-INST: fmls za.h[w8, 5, vgx2], { z22.h, z23.h }, z14.h[5] // CHECK-ENCODING: [0xdd,0x1a,0x1e,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c11e1add fmls za.h[w8, 5], {z22.h - z23.h}, z14.h[5] // 11000001-00011110-00011010-11011101 // CHECK-INST: fmls za.h[w8, 5, vgx2], { z22.h, z23.h }, z14.h[5] // CHECK-ENCODING: [0xdd,0x1a,0x1e,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c11e1add fmls za.h[w11, 2, vgx2], {z8.h, z9.h}, z1.h[2] // 11000001-00010001-01110101-00010010 // CHECK-INST: fmls za.h[w11, 2, vgx2], { z8.h, z9.h }, z1.h[2] // CHECK-ENCODING: [0x12,0x75,0x11,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1117512 fmls za.h[w11, 2], {z8.h - z9.h}, z1.h[2] // 11000001-00010001-01110101-00010010 // CHECK-INST: fmls za.h[w11, 2, vgx2], { z8.h, z9.h }, z1.h[2] // CHECK-ENCODING: [0x12,0x75,0x11,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1117512 fmls za.h[w9, 7, vgx2], {z12.h, z13.h}, z11.h[4] // 11000001-00011011-00111001-10010111 // CHECK-INST: fmls za.h[w9, 7, vgx2], { z12.h, z13.h }, z11.h[4] // CHECK-ENCODING: [0x97,0x39,0x1b,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c11b3997 fmls za.h[w9, 7], {z12.h - z13.h}, z11.h[4] // 11000001-00011011-00111001-10010111 // CHECK-INST: fmls za.h[w9, 7, vgx2], { z12.h, z13.h }, z11.h[4] // CHECK-ENCODING: [0x97,0x39,0x1b,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c11b3997 fmls za.h[w8, 0, vgx2], {z0.h, z1.h}, {z0.h, z1.h} // 11000001-10100000-00010000-00011000 // CHECK-INST: fmls za.h[w8, 0, vgx2], { z0.h, z1.h }, { z0.h, z1.h } // CHECK-ENCODING: [0x18,0x10,0xa0,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1a01018 fmls za.h[w8, 0], {z0.h - z1.h}, {z0.h - z1.h} // 11000001-10100000-00010000-00011000 // CHECK-INST: fmls za.h[w8, 0, vgx2], { z0.h, z1.h }, { z0.h, z1.h } // CHECK-ENCODING: [0x18,0x10,0xa0,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1a01018 fmls za.h[w10, 5, vgx2], {z10.h, z11.h}, {z20.h, z21.h} // 11000001-10110100-01010001-01011101 // CHECK-INST: fmls za.h[w10, 5, vgx2], { z10.h, z11.h }, { z20.h, z21.h } // CHECK-ENCODING: [0x5d,0x51,0xb4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1b4515d fmls za.h[w10, 5], {z10.h - z11.h}, {z20.h - z21.h} // 11000001-10110100-01010001-01011101 // CHECK-INST: fmls za.h[w10, 5, vgx2], { z10.h, z11.h }, { z20.h, z21.h } // CHECK-ENCODING: [0x5d,0x51,0xb4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1b4515d fmls za.h[w11, 7, vgx2], {z12.h, z13.h}, {z8.h, z9.h} // 11000001-10101000-01110001-10011111 // CHECK-INST: fmls za.h[w11, 7, vgx2], { z12.h, z13.h }, { z8.h, z9.h } // CHECK-ENCODING: [0x9f,0x71,0xa8,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1a8719f fmls za.h[w11, 7], {z12.h - z13.h}, {z8.h - z9.h} // 11000001-10101000-01110001-10011111 // CHECK-INST: fmls za.h[w11, 7, vgx2], { z12.h, z13.h }, { z8.h, z9.h } // CHECK-ENCODING: [0x9f,0x71,0xa8,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1a8719f fmls za.h[w11, 7, vgx2], {z30.h, z31.h}, {z30.h, z31.h} // 11000001-10111110-01110011-11011111 // CHECK-INST: fmls za.h[w11, 7, vgx2], { z30.h, z31.h }, { z30.h, z31.h } // CHECK-ENCODING: [0xdf,0x73,0xbe,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1be73df fmls za.h[w11, 7], {z30.h - z31.h}, {z30.h - z31.h} // 11000001-10111110-01110011-11011111 // CHECK-INST: fmls za.h[w11, 7, vgx2], { z30.h, z31.h }, { z30.h, z31.h } // CHECK-ENCODING: [0xdf,0x73,0xbe,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1be73df fmls za.h[w8, 5, vgx2], {z16.h, z17.h}, {z16.h, z17.h} // 11000001-10110000-00010010-00011101 // CHECK-INST: fmls za.h[w8, 5, vgx2], { z16.h, z17.h }, { z16.h, z17.h } // CHECK-ENCODING: [0x1d,0x12,0xb0,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1b0121d fmls za.h[w8, 5], {z16.h - z17.h}, {z16.h - z17.h} // 11000001-10110000-00010010-00011101 // CHECK-INST: fmls za.h[w8, 5, vgx2], { z16.h, z17.h }, { z16.h, z17.h } // CHECK-ENCODING: [0x1d,0x12,0xb0,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1b0121d fmls za.h[w8, 1, vgx2], {z0.h, z1.h}, {z30.h, z31.h} // 11000001-10111110-00010000-00011001 // CHECK-INST: fmls za.h[w8, 1, vgx2], { z0.h, z1.h }, { z30.h, z31.h } // CHECK-ENCODING: [0x19,0x10,0xbe,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1be1019 fmls za.h[w8, 1], {z0.h - z1.h}, {z30.h - z31.h} // 11000001-10111110-00010000-00011001 // CHECK-INST: fmls za.h[w8, 1, vgx2], { z0.h, z1.h }, { z30.h, z31.h } // CHECK-ENCODING: [0x19,0x10,0xbe,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1be1019 fmls za.h[w10, 0, vgx2], {z18.h, z19.h}, {z20.h, z21.h} // 11000001-10110100-01010010-01011000 // CHECK-INST: fmls za.h[w10, 0, vgx2], { z18.h, z19.h }, { z20.h, z21.h } // CHECK-ENCODING: [0x58,0x52,0xb4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1b45258 fmls za.h[w10, 0], {z18.h - z19.h}, {z20.h - z21.h} // 11000001-10110100-01010010-01011000 // CHECK-INST: fmls za.h[w10, 0, vgx2], { z18.h, z19.h }, { z20.h, z21.h } // CHECK-ENCODING: [0x58,0x52,0xb4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1b45258 fmls za.h[w8, 0, vgx2], {z12.h, z13.h}, {z2.h, z3.h} // 11000001-10100010-00010001-10011000 // CHECK-INST: fmls za.h[w8, 0, vgx2], { z12.h, z13.h }, { z2.h, z3.h } // CHECK-ENCODING: [0x98,0x11,0xa2,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1a21198 fmls za.h[w8, 0], {z12.h - z13.h}, {z2.h - z3.h} // 11000001-10100010-00010001-10011000 // CHECK-INST: fmls za.h[w8, 0, vgx2], { z12.h, z13.h }, { z2.h, z3.h } // CHECK-ENCODING: [0x98,0x11,0xa2,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1a21198 fmls za.h[w10, 1, vgx2], {z0.h, z1.h}, {z26.h, z27.h} // 11000001-10111010-01010000-00011001 // CHECK-INST: fmls za.h[w10, 1, vgx2], { z0.h, z1.h }, { z26.h, z27.h } // CHECK-ENCODING: [0x19,0x50,0xba,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1ba5019 fmls za.h[w10, 1], {z0.h - z1.h}, {z26.h - z27.h} // 11000001-10111010-01010000-00011001 // CHECK-INST: fmls za.h[w10, 1, vgx2], { z0.h, z1.h }, { z26.h, z27.h } // CHECK-ENCODING: [0x19,0x50,0xba,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1ba5019 fmls za.h[w8, 5, vgx2], {z22.h, z23.h}, {z30.h, z31.h} // 11000001-10111110-00010010-11011101 // CHECK-INST: fmls za.h[w8, 5, vgx2], { z22.h, z23.h }, { z30.h, z31.h } // CHECK-ENCODING: [0xdd,0x12,0xbe,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1be12dd fmls za.h[w8, 5], {z22.h - z23.h}, {z30.h - z31.h} // 11000001-10111110-00010010-11011101 // CHECK-INST: fmls za.h[w8, 5, vgx2], { z22.h, z23.h }, { z30.h, z31.h } // CHECK-ENCODING: [0xdd,0x12,0xbe,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1be12dd fmls za.h[w11, 2, vgx2], {z8.h, z9.h}, {z0.h, z1.h} // 11000001-10100000-01110001-00011010 // CHECK-INST: fmls za.h[w11, 2, vgx2], { z8.h, z9.h }, { z0.h, z1.h } // CHECK-ENCODING: [0x1a,0x71,0xa0,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1a0711a fmls za.h[w11, 2], {z8.h - z9.h}, {z0.h - z1.h} // 11000001-10100000-01110001-00011010 // CHECK-INST: fmls za.h[w11, 2, vgx2], { z8.h, z9.h }, { z0.h, z1.h } // CHECK-ENCODING: [0x1a,0x71,0xa0,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1a0711a fmls za.h[w9, 7, vgx2], {z12.h, z13.h}, {z10.h, z11.h} // 11000001-10101010-00110001-10011111 // CHECK-INST: fmls za.h[w9, 7, vgx2], { z12.h, z13.h }, { z10.h, z11.h } // CHECK-ENCODING: [0x9f,0x31,0xaa,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1aa319f fmls za.h[w9, 7], {z12.h - z13.h}, {z10.h - z11.h} // 11000001-10101010-00110001-10011111 // CHECK-INST: fmls za.h[w9, 7, vgx2], { z12.h, z13.h }, { z10.h, z11.h } // CHECK-ENCODING: [0x9f,0x31,0xaa,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1aa319f fmls za.h[w8, 0, vgx4], {z0.h - z3.h}, z0.h // 11000001-00110000-00011100-00001000 // CHECK-INST: fmls za.h[w8, 0, vgx4], { z0.h - z3.h }, z0.h // CHECK-ENCODING: [0x08,0x1c,0x30,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1301c08 fmls za.h[w8, 0], {z0.h - z3.h}, z0.h // 11000001-00110000-00011100-00001000 // CHECK-INST: fmls za.h[w8, 0, vgx4], { z0.h - z3.h }, z0.h // CHECK-ENCODING: [0x08,0x1c,0x30,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1301c08 fmls za.h[w10, 5, vgx4], {z10.h - z13.h}, z5.h // 11000001-00110101-01011101-01001101 // CHECK-INST: fmls za.h[w10, 5, vgx4], { z10.h - z13.h }, z5.h // CHECK-ENCODING: [0x4d,0x5d,0x35,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1355d4d fmls za.h[w10, 5], {z10.h - z13.h}, z5.h // 11000001-00110101-01011101-01001101 // CHECK-INST: fmls za.h[w10, 5, vgx4], { z10.h - z13.h }, z5.h // CHECK-ENCODING: [0x4d,0x5d,0x35,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1355d4d fmls za.h[w11, 7, vgx4], {z13.h - z16.h}, z8.h // 11000001-00111000-01111101-10101111 // CHECK-INST: fmls za.h[w11, 7, vgx4], { z13.h - z16.h }, z8.h // CHECK-ENCODING: [0xaf,0x7d,0x38,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1387daf fmls za.h[w11, 7], {z13.h - z16.h}, z8.h // 11000001-00111000-01111101-10101111 // CHECK-INST: fmls za.h[w11, 7, vgx4], { z13.h - z16.h }, z8.h // CHECK-ENCODING: [0xaf,0x7d,0x38,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1387daf fmls za.h[w11, 7, vgx4], {z31.h, z0.h, z1.h, z2.h}, z15.h // 11000001-00111111-01111111-11101111 // CHECK-INST: fmls za.h[w11, 7, vgx4], { z31.h, z0.h, z1.h, z2.h }, z15.h // CHECK-ENCODING: [0xef,0x7f,0x3f,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c13f7fef fmls za.h[w11, 7], {z31.h, z0.h, z1.h, z2.h}, z15.h // 11000001-00111111-01111111-11101111 // CHECK-INST: fmls za.h[w11, 7, vgx4], { z31.h, z0.h, z1.h, z2.h }, z15.h // CHECK-ENCODING: [0xef,0x7f,0x3f,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c13f7fef fmls za.h[w8, 5, vgx4], {z17.h - z20.h}, z0.h // 11000001-00110000-00011110-00101101 // CHECK-INST: fmls za.h[w8, 5, vgx4], { z17.h - z20.h }, z0.h // CHECK-ENCODING: [0x2d,0x1e,0x30,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1301e2d fmls za.h[w8, 5], {z17.h - z20.h}, z0.h // 11000001-00110000-00011110-00101101 // CHECK-INST: fmls za.h[w8, 5, vgx4], { z17.h - z20.h }, z0.h // CHECK-ENCODING: [0x2d,0x1e,0x30,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1301e2d fmls za.h[w8, 1, vgx4], {z1.h - z4.h}, z14.h // 11000001-00111110-00011100-00101001 // CHECK-INST: fmls za.h[w8, 1, vgx4], { z1.h - z4.h }, z14.h // CHECK-ENCODING: [0x29,0x1c,0x3e,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c13e1c29 fmls za.h[w8, 1], {z1.h - z4.h}, z14.h // 11000001-00111110-00011100-00101001 // CHECK-INST: fmls za.h[w8, 1, vgx4], { z1.h - z4.h }, z14.h // CHECK-ENCODING: [0x29,0x1c,0x3e,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c13e1c29 fmls za.h[w10, 0, vgx4], {z19.h - z22.h}, z4.h // 11000001-00110100-01011110-01101000 // CHECK-INST: fmls za.h[w10, 0, vgx4], { z19.h - z22.h }, z4.h // CHECK-ENCODING: [0x68,0x5e,0x34,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1345e68 fmls za.h[w10, 0], {z19.h - z22.h}, z4.h // 11000001-00110100-01011110-01101000 // CHECK-INST: fmls za.h[w10, 0, vgx4], { z19.h - z22.h }, z4.h // CHECK-ENCODING: [0x68,0x5e,0x34,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1345e68 fmls za.h[w8, 0, vgx4], {z12.h - z15.h}, z2.h // 11000001-00110010-00011101-10001000 // CHECK-INST: fmls za.h[w8, 0, vgx4], { z12.h - z15.h }, z2.h // CHECK-ENCODING: [0x88,0x1d,0x32,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1321d88 fmls za.h[w8, 0], {z12.h - z15.h}, z2.h // 11000001-00110010-00011101-10001000 // CHECK-INST: fmls za.h[w8, 0, vgx4], { z12.h - z15.h }, z2.h // CHECK-ENCODING: [0x88,0x1d,0x32,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1321d88 fmls za.h[w10, 1, vgx4], {z1.h - z4.h}, z10.h // 11000001-00111010-01011100-00101001 // CHECK-INST: fmls za.h[w10, 1, vgx4], { z1.h - z4.h }, z10.h // CHECK-ENCODING: [0x29,0x5c,0x3a,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c13a5c29 fmls za.h[w10, 1], {z1.h - z4.h}, z10.h // 11000001-00111010-01011100-00101001 // CHECK-INST: fmls za.h[w10, 1, vgx4], { z1.h - z4.h }, z10.h // CHECK-ENCODING: [0x29,0x5c,0x3a,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c13a5c29 fmls za.h[w8, 5, vgx4], {z22.h - z25.h}, z14.h // 11000001-00111110-00011110-11001101 // CHECK-INST: fmls za.h[w8, 5, vgx4], { z22.h - z25.h }, z14.h // CHECK-ENCODING: [0xcd,0x1e,0x3e,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c13e1ecd fmls za.h[w8, 5], {z22.h - z25.h}, z14.h // 11000001-00111110-00011110-11001101 // CHECK-INST: fmls za.h[w8, 5, vgx4], { z22.h - z25.h }, z14.h // CHECK-ENCODING: [0xcd,0x1e,0x3e,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c13e1ecd fmls za.h[w11, 2, vgx4], {z9.h - z12.h}, z1.h // 11000001-00110001-01111101-00101010 // CHECK-INST: fmls za.h[w11, 2, vgx4], { z9.h - z12.h }, z1.h // CHECK-ENCODING: [0x2a,0x7d,0x31,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1317d2a fmls za.h[w11, 2], {z9.h - z12.h}, z1.h // 11000001-00110001-01111101-00101010 // CHECK-INST: fmls za.h[w11, 2, vgx4], { z9.h - z12.h }, z1.h // CHECK-ENCODING: [0x2a,0x7d,0x31,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1317d2a fmls za.h[w9, 7, vgx4], {z12.h - z15.h}, z11.h // 11000001-00111011-00111101-10001111 // CHECK-INST: fmls za.h[w9, 7, vgx4], { z12.h - z15.h }, z11.h // CHECK-ENCODING: [0x8f,0x3d,0x3b,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c13b3d8f fmls za.h[w9, 7], {z12.h - z15.h}, z11.h // 11000001-00111011-00111101-10001111 // CHECK-INST: fmls za.h[w9, 7, vgx4], { z12.h - z15.h }, z11.h // CHECK-ENCODING: [0x8f,0x3d,0x3b,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c13b3d8f fmls za.h[w8, 0, vgx4], {z0.h - z3.h}, z0.h[0] // 11000001-00010000-10010000-00010000 // CHECK-INST: fmls za.h[w8, 0, vgx4], { z0.h - z3.h }, z0.h[0] // CHECK-ENCODING: [0x10,0x90,0x10,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1109010 fmls za.h[w8, 0], {z0.h - z3.h}, z0.h[0] // 11000001-00010000-10010000-00010000 // CHECK-INST: fmls za.h[w8, 0, vgx4], { z0.h - z3.h }, z0.h[0] // CHECK-ENCODING: [0x10,0x90,0x10,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1109010 fmls za.h[w10, 5, vgx4], {z8.h - z11.h}, z5.h[2] // 11000001-00010101-11010101-00010101 // CHECK-INST: fmls za.h[w10, 5, vgx4], { z8.h - z11.h }, z5.h[2] // CHECK-ENCODING: [0x15,0xd5,0x15,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c115d515 fmls za.h[w10, 5], {z8.h - z11.h}, z5.h[2] // 11000001-00010101-11010101-00010101 // CHECK-INST: fmls za.h[w10, 5, vgx4], { z8.h - z11.h }, z5.h[2] // CHECK-ENCODING: [0x15,0xd5,0x15,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c115d515 fmls za.h[w11, 7, vgx4], {z12.h - z15.h}, z8.h[6] // 11000001-00011000-11111101-10010111 // CHECK-INST: fmls za.h[w11, 7, vgx4], { z12.h - z15.h }, z8.h[6] // CHECK-ENCODING: [0x97,0xfd,0x18,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c118fd97 fmls za.h[w11, 7], {z12.h - z15.h}, z8.h[6] // 11000001-00011000-11111101-10010111 // CHECK-INST: fmls za.h[w11, 7, vgx4], { z12.h - z15.h }, z8.h[6] // CHECK-ENCODING: [0x97,0xfd,0x18,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c118fd97 fmls za.h[w11, 7, vgx4], {z28.h - z31.h}, z15.h[7] // 11000001-00011111-11111111-10011111 // CHECK-INST: fmls za.h[w11, 7, vgx4], { z28.h - z31.h }, z15.h[7] // CHECK-ENCODING: [0x9f,0xff,0x1f,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c11fff9f fmls za.h[w11, 7], {z28.h - z31.h}, z15.h[7] // 11000001-00011111-11111111-10011111 // CHECK-INST: fmls za.h[w11, 7, vgx4], { z28.h - z31.h }, z15.h[7] // CHECK-ENCODING: [0x9f,0xff,0x1f,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c11fff9f fmls za.h[w8, 5, vgx4], {z16.h - z19.h}, z0.h[6] // 11000001-00010000-10011110-00010101 // CHECK-INST: fmls za.h[w8, 5, vgx4], { z16.h - z19.h }, z0.h[6] // CHECK-ENCODING: [0x15,0x9e,0x10,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1109e15 fmls za.h[w8, 5], {z16.h - z19.h}, z0.h[6] // 11000001-00010000-10011110-00010101 // CHECK-INST: fmls za.h[w8, 5, vgx4], { z16.h - z19.h }, z0.h[6] // CHECK-ENCODING: [0x15,0x9e,0x10,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1109e15 fmls za.h[w8, 1, vgx4], {z0.h - z3.h}, z14.h[2] // 11000001-00011110-10010100-00010001 // CHECK-INST: fmls za.h[w8, 1, vgx4], { z0.h - z3.h }, z14.h[2] // CHECK-ENCODING: [0x11,0x94,0x1e,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c11e9411 fmls za.h[w8, 1], {z0.h - z3.h}, z14.h[2] // 11000001-00011110-10010100-00010001 // CHECK-INST: fmls za.h[w8, 1, vgx4], { z0.h - z3.h }, z14.h[2] // CHECK-ENCODING: [0x11,0x94,0x1e,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c11e9411 fmls za.h[w10, 0, vgx4], {z16.h - z19.h}, z4.h[3] // 11000001-00010100-11010110-00011000 // CHECK-INST: fmls za.h[w10, 0, vgx4], { z16.h - z19.h }, z4.h[3] // CHECK-ENCODING: [0x18,0xd6,0x14,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c114d618 fmls za.h[w10, 0], {z16.h - z19.h}, z4.h[3] // 11000001-00010100-11010110-00011000 // CHECK-INST: fmls za.h[w10, 0, vgx4], { z16.h - z19.h }, z4.h[3] // CHECK-ENCODING: [0x18,0xd6,0x14,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c114d618 fmls za.h[w8, 0, vgx4], {z12.h - z15.h}, z2.h[4] // 11000001-00010010-10011001-10010000 // CHECK-INST: fmls za.h[w8, 0, vgx4], { z12.h - z15.h }, z2.h[4] // CHECK-ENCODING: [0x90,0x99,0x12,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1129990 fmls za.h[w8, 0], {z12.h - z15.h}, z2.h[4] // 11000001-00010010-10011001-10010000 // CHECK-INST: fmls za.h[w8, 0, vgx4], { z12.h - z15.h }, z2.h[4] // CHECK-ENCODING: [0x90,0x99,0x12,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1129990 fmls za.h[w10, 1, vgx4], {z0.h - z3.h}, z10.h[4] // 11000001-00011010-11011000-00010001 // CHECK-INST: fmls za.h[w10, 1, vgx4], { z0.h - z3.h }, z10.h[4] // CHECK-ENCODING: [0x11,0xd8,0x1a,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c11ad811 fmls za.h[w10, 1], {z0.h - z3.h}, z10.h[4] // 11000001-00011010-11011000-00010001 // CHECK-INST: fmls za.h[w10, 1, vgx4], { z0.h - z3.h }, z10.h[4] // CHECK-ENCODING: [0x11,0xd8,0x1a,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c11ad811 fmls za.h[w8, 5, vgx4], {z20.h - z23.h}, z14.h[5] // 11000001-00011110-10011010-10011101 // CHECK-INST: fmls za.h[w8, 5, vgx4], { z20.h - z23.h }, z14.h[5] // CHECK-ENCODING: [0x9d,0x9a,0x1e,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c11e9a9d fmls za.h[w8, 5], {z20.h - z23.h}, z14.h[5] // 11000001-00011110-10011010-10011101 // CHECK-INST: fmls za.h[w8, 5, vgx4], { z20.h - z23.h }, z14.h[5] // CHECK-ENCODING: [0x9d,0x9a,0x1e,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c11e9a9d fmls za.h[w11, 2, vgx4], {z8.h - z11.h}, z1.h[2] // 11000001-00010001-11110101-00010010 // CHECK-INST: fmls za.h[w11, 2, vgx4], { z8.h - z11.h }, z1.h[2] // CHECK-ENCODING: [0x12,0xf5,0x11,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c111f512 fmls za.h[w11, 2], {z8.h - z11.h}, z1.h[2] // 11000001-00010001-11110101-00010010 // CHECK-INST: fmls za.h[w11, 2, vgx4], { z8.h - z11.h }, z1.h[2] // CHECK-ENCODING: [0x12,0xf5,0x11,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c111f512 fmls za.h[w9, 7, vgx4], {z12.h - z15.h}, z11.h[4] // 11000001-00011011-10111001-10010111 // CHECK-INST: fmls za.h[w9, 7, vgx4], { z12.h - z15.h }, z11.h[4] // CHECK-ENCODING: [0x97,0xb9,0x1b,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c11bb997 fmls za.h[w9, 7], {z12.h - z15.h}, z11.h[4] // 11000001-00011011-10111001-10010111 // CHECK-INST: fmls za.h[w9, 7, vgx4], { z12.h - z15.h }, z11.h[4] // CHECK-ENCODING: [0x97,0xb9,0x1b,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c11bb997 fmls za.h[w8, 0, vgx4], {z0.h - z3.h}, {z0.h - z3.h} // 11000001-10100001-00010000-00011000 // CHECK-INST: fmls za.h[w8, 0, vgx4], { z0.h - z3.h }, { z0.h - z3.h } // CHECK-ENCODING: [0x18,0x10,0xa1,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1a11018 fmls za.h[w8, 0], {z0.h - z3.h}, {z0.h - z3.h} // 11000001-10100001-00010000-00011000 // CHECK-INST: fmls za.h[w8, 0, vgx4], { z0.h - z3.h }, { z0.h - z3.h } // CHECK-ENCODING: [0x18,0x10,0xa1,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1a11018 fmls za.h[w10, 5, vgx4], {z8.h - z11.h}, {z20.h - z23.h} // 11000001-10110101-01010001-00011101 // CHECK-INST: fmls za.h[w10, 5, vgx4], { z8.h - z11.h }, { z20.h - z23.h } // CHECK-ENCODING: [0x1d,0x51,0xb5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1b5511d fmls za.h[w10, 5], {z8.h - z11.h}, {z20.h - z23.h} // 11000001-10110101-01010001-00011101 // CHECK-INST: fmls za.h[w10, 5, vgx4], { z8.h - z11.h }, { z20.h - z23.h } // CHECK-ENCODING: [0x1d,0x51,0xb5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1b5511d fmls za.h[w11, 7, vgx4], {z12.h - z15.h}, {z8.h - z11.h} // 11000001-10101001-01110001-10011111 // CHECK-INST: fmls za.h[w11, 7, vgx4], { z12.h - z15.h }, { z8.h - z11.h } // CHECK-ENCODING: [0x9f,0x71,0xa9,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1a9719f fmls za.h[w11, 7], {z12.h - z15.h}, {z8.h - z11.h} // 11000001-10101001-01110001-10011111 // CHECK-INST: fmls za.h[w11, 7, vgx4], { z12.h - z15.h }, { z8.h - z11.h } // CHECK-ENCODING: [0x9f,0x71,0xa9,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1a9719f fmls za.h[w11, 7, vgx4], {z28.h - z31.h}, {z28.h - z31.h} // 11000001-10111101-01110011-10011111 // CHECK-INST: fmls za.h[w11, 7, vgx4], { z28.h - z31.h }, { z28.h - z31.h } // CHECK-ENCODING: [0x9f,0x73,0xbd,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1bd739f fmls za.h[w11, 7], {z28.h - z31.h}, {z28.h - z31.h} // 11000001-10111101-01110011-10011111 // CHECK-INST: fmls za.h[w11, 7, vgx4], { z28.h - z31.h }, { z28.h - z31.h } // CHECK-ENCODING: [0x9f,0x73,0xbd,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1bd739f fmls za.h[w8, 5, vgx4], {z16.h - z19.h}, {z16.h - z19.h} // 11000001-10110001-00010010-00011101 // CHECK-INST: fmls za.h[w8, 5, vgx4], { z16.h - z19.h }, { z16.h - z19.h } // CHECK-ENCODING: [0x1d,0x12,0xb1,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1b1121d fmls za.h[w8, 5], {z16.h - z19.h}, {z16.h - z19.h} // 11000001-10110001-00010010-00011101 // CHECK-INST: fmls za.h[w8, 5, vgx4], { z16.h - z19.h }, { z16.h - z19.h } // CHECK-ENCODING: [0x1d,0x12,0xb1,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1b1121d fmls za.h[w8, 1, vgx4], {z0.h - z3.h}, {z28.h - z31.h} // 11000001-10111101-00010000-00011001 // CHECK-INST: fmls za.h[w8, 1, vgx4], { z0.h - z3.h }, { z28.h - z31.h } // CHECK-ENCODING: [0x19,0x10,0xbd,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1bd1019 fmls za.h[w8, 1], {z0.h - z3.h}, {z28.h - z31.h} // 11000001-10111101-00010000-00011001 // CHECK-INST: fmls za.h[w8, 1, vgx4], { z0.h - z3.h }, { z28.h - z31.h } // CHECK-ENCODING: [0x19,0x10,0xbd,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1bd1019 fmls za.h[w10, 0, vgx4], {z16.h - z19.h}, {z20.h - z23.h} // 11000001-10110101-01010010-00011000 // CHECK-INST: fmls za.h[w10, 0, vgx4], { z16.h - z19.h }, { z20.h - z23.h } // CHECK-ENCODING: [0x18,0x52,0xb5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1b55218 fmls za.h[w10, 0], {z16.h - z19.h}, {z20.h - z23.h} // 11000001-10110101-01010010-00011000 // CHECK-INST: fmls za.h[w10, 0, vgx4], { z16.h - z19.h }, { z20.h - z23.h } // CHECK-ENCODING: [0x18,0x52,0xb5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1b55218 fmls za.h[w8, 0, vgx4], {z12.h - z15.h}, {z0.h - z3.h} // 11000001-10100001-00010001-10011000 // CHECK-INST: fmls za.h[w8, 0, vgx4], { z12.h - z15.h }, { z0.h - z3.h } // CHECK-ENCODING: [0x98,0x11,0xa1,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1a11198 fmls za.h[w8, 0], {z12.h - z15.h}, {z0.h - z3.h} // 11000001-10100001-00010001-10011000 // CHECK-INST: fmls za.h[w8, 0, vgx4], { z12.h - z15.h }, { z0.h - z3.h } // CHECK-ENCODING: [0x98,0x11,0xa1,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1a11198 fmls za.h[w10, 1, vgx4], {z0.h - z3.h}, {z24.h - z27.h} // 11000001-10111001-01010000-00011001 // CHECK-INST: fmls za.h[w10, 1, vgx4], { z0.h - z3.h }, { z24.h - z27.h } // CHECK-ENCODING: [0x19,0x50,0xb9,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1b95019 fmls za.h[w10, 1], {z0.h - z3.h}, {z24.h - z27.h} // 11000001-10111001-01010000-00011001 // CHECK-INST: fmls za.h[w10, 1, vgx4], { z0.h - z3.h }, { z24.h - z27.h } // CHECK-ENCODING: [0x19,0x50,0xb9,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1b95019 fmls za.h[w8, 5, vgx4], {z20.h - z23.h}, {z28.h - z31.h} // 11000001-10111101-00010010-10011101 // CHECK-INST: fmls za.h[w8, 5, vgx4], { z20.h - z23.h }, { z28.h - z31.h } // CHECK-ENCODING: [0x9d,0x12,0xbd,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1bd129d fmls za.h[w8, 5], {z20.h - z23.h}, {z28.h - z31.h} // 11000001-10111101-00010010-10011101 // CHECK-INST: fmls za.h[w8, 5, vgx4], { z20.h - z23.h }, { z28.h - z31.h } // CHECK-ENCODING: [0x9d,0x12,0xbd,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1bd129d fmls za.h[w11, 2, vgx4], {z8.h - z11.h}, {z0.h - z3.h} // 11000001-10100001-01110001-00011010 // CHECK-INST: fmls za.h[w11, 2, vgx4], { z8.h - z11.h }, { z0.h - z3.h } // CHECK-ENCODING: [0x1a,0x71,0xa1,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1a1711a fmls za.h[w11, 2], {z8.h - z11.h}, {z0.h - z3.h} // 11000001-10100001-01110001-00011010 // CHECK-INST: fmls za.h[w11, 2, vgx4], { z8.h - z11.h }, { z0.h - z3.h } // CHECK-ENCODING: [0x1a,0x71,0xa1,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1a1711a fmls za.h[w9, 7, vgx4], {z12.h - z15.h}, {z8.h - z11.h} // 11000001-10101001-00110001-10011111 // CHECK-INST: fmls za.h[w9, 7, vgx4], { z12.h - z15.h }, { z8.h - z11.h } // CHECK-ENCODING: [0x9f,0x31,0xa9,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1a9319f fmls za.h[w9, 7], {z12.h - z15.h}, {z8.h - z11.h} // 11000001-10101001-00110001-10011111 // CHECK-INST: fmls za.h[w9, 7, vgx4], { z12.h - z15.h }, { z8.h - z11.h } // CHECK-ENCODING: [0x9f,0x31,0xa9,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: c1a9319f diff --git a/llvm/test/MC/AArch64/SME2p1/fmopa-diagnostics.s b/llvm/test/MC/AArch64/SME2p1/fmopa-diagnostics.s index def19a316c2ac80c26315d625710f57734f403a4..1c561959c25e0f20be40d2a5542e306c12c4f816 100644 --- a/llvm/test/MC/AArch64/SME2p1/fmopa-diagnostics.s +++ b/llvm/test/MC/AArch64/SME2p1/fmopa-diagnostics.s @@ -1,4 +1,4 @@ -// RUN: not llvm-mc -triple=aarch64 -show-encoding -mattr=+sme2p1,+sme-f16f16 2>&1 < %s | FileCheck %s +// RUN: not llvm-mc -triple=aarch64 -show-encoding -mattr=+sme-f16f16 2>&1 < %s | FileCheck %s // --------------------------------------------------------------------------// // Invalid predicate register diff --git a/llvm/test/MC/AArch64/SME2p1/fmopa.s b/llvm/test/MC/AArch64/SME2p1/fmopa.s index e53d21244fde39b62be1c8dea1858450b3001c66..0a586d3acc42223218d2da5f1174d816e8d9d60c 100644 --- a/llvm/test/MC/AArch64/SME2p1/fmopa.s +++ b/llvm/test/MC/AArch64/SME2p1/fmopa.s @@ -1,85 +1,85 @@ -// RUN: llvm-mc -triple=aarch64 -show-encoding -mattr=+sme2p1,+sme-f16f16 < %s \ +// RUN: llvm-mc -triple=aarch64 -show-encoding -mattr=+sme-f16f16 < %s \ // RUN: | FileCheck %s --check-prefixes=CHECK-ENCODING,CHECK-INST // RUN: not llvm-mc -triple=aarch64 -show-encoding < %s 2>&1 \ // RUN: | FileCheck %s --check-prefix=CHECK-ERROR -// RUN: llvm-mc -triple=aarch64 -filetype=obj -mattr=+sme2p1,+sme-f16f16 < %s \ -// RUN: | llvm-objdump -d --mattr=+sme2p1,+sme-f16f16 - | FileCheck %s --check-prefix=CHECK-INST -// RUN: llvm-mc -triple=aarch64 -filetype=obj -mattr=+sme2p1,+sme-f16f16 < %s \ +// RUN: llvm-mc -triple=aarch64 -filetype=obj -mattr=+sme-f16f16 < %s \ +// RUN: | llvm-objdump -d --mattr=+sme-f16f16 - | FileCheck %s --check-prefix=CHECK-INST +// RUN: llvm-mc -triple=aarch64 -filetype=obj -mattr=+sme-f16f16 < %s \ // RUN: | llvm-objdump -d --mattr=-sme2p1 - | FileCheck %s --check-prefix=CHECK-UNKNOWN -// RUN: llvm-mc -triple=aarch64 -show-encoding -mattr=+sme2p1,+sme-f16f16 < %s \ +// RUN: llvm-mc -triple=aarch64 -show-encoding -mattr=+sme-f16f16 < %s \ // RUN: | sed '/.text/d' | sed 's/.*encoding: //g' \ -// RUN: | llvm-mc -triple=aarch64 -mattr=+sme2p1,+sme-f16f16 -disassemble -show-encoding \ +// RUN: | llvm-mc -triple=aarch64 -mattr=+sme-f16f16 -disassemble -show-encoding \ // RUN: | FileCheck %s --check-prefixes=CHECK-ENCODING,CHECK-INST fmopa za0.h, p0/m, p0/m, z0.h, z0.h // 10000001-10000000-00000000-00001000 // CHECK-INST: fmopa za0.h, p0/m, p0/m, z0.h, z0.h // CHECK-ENCODING: [0x08,0x00,0x80,0x81] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: 81800008 fmopa za1.h, p5/m, p2/m, z10.h, z21.h // 10000001-10010101-01010101-01001001 // CHECK-INST: fmopa za1.h, p5/m, p2/m, z10.h, z21.h // CHECK-ENCODING: [0x49,0x55,0x95,0x81] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: 81955549 fmopa za1.h, p3/m, p7/m, z13.h, z8.h // 10000001-10001000-11101101-10101001 // CHECK-INST: fmopa za1.h, p3/m, p7/m, z13.h, z8.h // CHECK-ENCODING: [0xa9,0xed,0x88,0x81] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: 8188eda9 fmopa za1.h, p7/m, p7/m, z31.h, z31.h // 10000001-10011111-11111111-11101001 // CHECK-INST: fmopa za1.h, p7/m, p7/m, z31.h, z31.h // CHECK-ENCODING: [0xe9,0xff,0x9f,0x81] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: 819fffe9 fmopa za1.h, p3/m, p0/m, z17.h, z16.h // 10000001-10010000-00001110-00101001 // CHECK-INST: fmopa za1.h, p3/m, p0/m, z17.h, z16.h // CHECK-ENCODING: [0x29,0x0e,0x90,0x81] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: 81900e29 fmopa za1.h, p1/m, p4/m, z1.h, z30.h // 10000001-10011110-10000100-00101001 // CHECK-INST: fmopa za1.h, p1/m, p4/m, z1.h, z30.h // CHECK-ENCODING: [0x29,0x84,0x9e,0x81] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: 819e8429 fmopa za0.h, p5/m, p2/m, z19.h, z20.h // 10000001-10010100-01010110-01101000 // CHECK-INST: fmopa za0.h, p5/m, p2/m, z19.h, z20.h // CHECK-ENCODING: [0x68,0x56,0x94,0x81] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: 81945668 fmopa za0.h, p6/m, p0/m, z12.h, z2.h // 10000001-10000010-00011001-10001000 // CHECK-INST: fmopa za0.h, p6/m, p0/m, z12.h, z2.h // CHECK-ENCODING: [0x88,0x19,0x82,0x81] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: 81821988 fmopa za1.h, p2/m, p6/m, z1.h, z26.h // 10000001-10011010-11001000-00101001 // CHECK-INST: fmopa za1.h, p2/m, p6/m, z1.h, z26.h // CHECK-ENCODING: [0x29,0xc8,0x9a,0x81] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: 819ac829 fmopa za1.h, p2/m, p0/m, z22.h, z30.h // 10000001-10011110-00001010-11001001 // CHECK-INST: fmopa za1.h, p2/m, p0/m, z22.h, z30.h // CHECK-ENCODING: [0xc9,0x0a,0x9e,0x81] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: 819e0ac9 fmopa za0.h, p5/m, p7/m, z9.h, z1.h // 10000001-10000001-11110101-00101000 // CHECK-INST: fmopa za0.h, p5/m, p7/m, z9.h, z1.h // CHECK-ENCODING: [0x28,0xf5,0x81,0x81] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: 8181f528 fmopa za1.h, p2/m, p5/m, z12.h, z11.h // 10000001-10001011-10101001-10001001 // CHECK-INST: fmopa za1.h, p2/m, p5/m, z12.h, z11.h // CHECK-ENCODING: [0x89,0xa9,0x8b,0x81] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: 818ba989 diff --git a/llvm/test/MC/AArch64/SME2p1/fmops-diagnostics.s b/llvm/test/MC/AArch64/SME2p1/fmops-diagnostics.s index 75eea8113262448ef3cade9ff3f724a727b321d8..0ec227ae0e68ec2d50a6113ce26858fcf262d955 100644 --- a/llvm/test/MC/AArch64/SME2p1/fmops-diagnostics.s +++ b/llvm/test/MC/AArch64/SME2p1/fmops-diagnostics.s @@ -1,4 +1,4 @@ -// RUN: not llvm-mc -triple=aarch64 -show-encoding -mattr=+sme2p1,+sme-f16f16 2>&1 < %s | FileCheck %s +// RUN: not llvm-mc -triple=aarch64 -show-encoding -mattr=+sme-f16f16 2>&1 < %s | FileCheck %s // --------------------------------------------------------------------------// // Invalid predicate register diff --git a/llvm/test/MC/AArch64/SME2p1/fmops.s b/llvm/test/MC/AArch64/SME2p1/fmops.s index 325d4c125b6064a17efc06d28e5d7259e2eaade5..597665d591501378f849b531c559cfc19d557f51 100644 --- a/llvm/test/MC/AArch64/SME2p1/fmops.s +++ b/llvm/test/MC/AArch64/SME2p1/fmops.s @@ -1,84 +1,84 @@ -// RUN: llvm-mc -triple=aarch64 -show-encoding -mattr=+sme2p1,+sme-f16f16 < %s \ +// RUN: llvm-mc -triple=aarch64 -show-encoding -mattr=+sme-f16f16 < %s \ // RUN: | FileCheck %s --check-prefixes=CHECK-ENCODING,CHECK-INST // RUN: not llvm-mc -triple=aarch64 -show-encoding < %s 2>&1 \ // RUN: | FileCheck %s --check-prefix=CHECK-ERROR -// RUN: llvm-mc -triple=aarch64 -filetype=obj -mattr=+sme2p1,+sme-f16f16 < %s \ -// RUN: | llvm-objdump -d --mattr=+sme2p1,+sme-f16f16 - | FileCheck %s --check-prefix=CHECK-INST -// RUN: llvm-mc -triple=aarch64 -filetype=obj -mattr=+sme2p1,+sme-f16f16 < %s \ +// RUN: llvm-mc -triple=aarch64 -filetype=obj -mattr=+sme-f16f16 < %s \ +// RUN: | llvm-objdump -d --mattr=+sme-f16f16 - | FileCheck %s --check-prefix=CHECK-INST +// RUN: llvm-mc -triple=aarch64 -filetype=obj -mattr=+sme-f16f16 < %s \ // RUN: | llvm-objdump -d --mattr=-sme2p1 - | FileCheck %s --check-prefix=CHECK-UNKNOWN -// RUN: llvm-mc -triple=aarch64 -show-encoding -mattr=+sme2p1,+sme-f16f16 < %s \ +// RUN: llvm-mc -triple=aarch64 -show-encoding -mattr=+sme-f16f16 < %s \ // RUN: | sed '/.text/d' | sed 's/.*encoding: //g' \ -// RUN: | llvm-mc -triple=aarch64 -mattr=+sme2p1,+sme-f16f16 -disassemble -show-encoding \ +// RUN: | llvm-mc -triple=aarch64 -mattr=+sme-f16f16 -disassemble -show-encoding \ // RUN: | FileCheck %s --check-prefixes=CHECK-ENCODING,CHECK-INST fmops za0.h, p0/m, p0/m, z0.h, z0.h // 10000001-10000000-00000000-00011000 // CHECK-INST: fmops za0.h, p0/m, p0/m, z0.h, z0.h // CHECK-ENCODING: [0x18,0x00,0x80,0x81] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: 81800018 fmops za1.h, p5/m, p2/m, z10.h, z21.h // 10000001-10010101-01010101-01011001 // CHECK-INST: fmops za1.h, p5/m, p2/m, z10.h, z21.h // CHECK-ENCODING: [0x59,0x55,0x95,0x81] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: 81955559 fmops za1.h, p3/m, p7/m, z13.h, z8.h // 10000001-10001000-11101101-10111001 // CHECK-INST: fmops za1.h, p3/m, p7/m, z13.h, z8.h // CHECK-ENCODING: [0xb9,0xed,0x88,0x81] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: 8188edb9 fmops za1.h, p7/m, p7/m, z31.h, z31.h // 10000001-10011111-11111111-11111001 // CHECK-INST: fmops za1.h, p7/m, p7/m, z31.h, z31.h // CHECK-ENCODING: [0xf9,0xff,0x9f,0x81] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: 819ffff9 fmops za1.h, p3/m, p0/m, z17.h, z16.h // 10000001-10010000-00001110-00111001 // CHECK-INST: fmops za1.h, p3/m, p0/m, z17.h, z16.h // CHECK-ENCODING: [0x39,0x0e,0x90,0x81] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: 81900e39 fmops za1.h, p1/m, p4/m, z1.h, z30.h // 10000001-10011110-10000100-00111001 // CHECK-INST: fmops za1.h, p1/m, p4/m, z1.h, z30.h // CHECK-ENCODING: [0x39,0x84,0x9e,0x81] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: 819e8439 fmops za0.h, p5/m, p2/m, z19.h, z20.h // 10000001-10010100-01010110-01111000 // CHECK-INST: fmops za0.h, p5/m, p2/m, z19.h, z20.h // CHECK-ENCODING: [0x78,0x56,0x94,0x81] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: 81945678 fmops za0.h, p6/m, p0/m, z12.h, z2.h // 10000001-10000010-00011001-10011000 // CHECK-INST: fmops za0.h, p6/m, p0/m, z12.h, z2.h // CHECK-ENCODING: [0x98,0x19,0x82,0x81] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: 81821998 fmops za1.h, p2/m, p6/m, z1.h, z26.h // 10000001-10011010-11001000-00111001 // CHECK-INST: fmops za1.h, p2/m, p6/m, z1.h, z26.h // CHECK-ENCODING: [0x39,0xc8,0x9a,0x81] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: 819ac839 fmops za1.h, p2/m, p0/m, z22.h, z30.h // 10000001-10011110-00001010-11011001 // CHECK-INST: fmops za1.h, p2/m, p0/m, z22.h, z30.h // CHECK-ENCODING: [0xd9,0x0a,0x9e,0x81] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: 819e0ad9 fmops za0.h, p5/m, p7/m, z9.h, z1.h // 10000001-10000001-11110101-00111000 // CHECK-INST: fmops za0.h, p5/m, p7/m, z9.h, z1.h // CHECK-ENCODING: [0x38,0xf5,0x81,0x81] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: 8181f538 fmops za1.h, p2/m, p5/m, z12.h, z11.h // 10000001-10001011-10101001-10011001 // CHECK-INST: fmops za1.h, p2/m, p5/m, z12.h, z11.h // CHECK-ENCODING: [0x99,0xa9,0x8b,0x81] -// CHECK-ERROR: instruction requires: sme2p1 sme-f16f16 +// CHECK-ERROR: instruction requires: sme-f16f16 // CHECK-UNKNOWN: 818ba999 diff --git a/llvm/test/MC/AArch64/SME2p1/fsub-diagnostics.s b/llvm/test/MC/AArch64/SME2p1/fsub-diagnostics.s index 716427a2f725d1eadae8ee941e07e463faf79eef..60cef4260be94986d5b818fa42c555ead0f4b172 100644 --- a/llvm/test/MC/AArch64/SME2p1/fsub-diagnostics.s +++ b/llvm/test/MC/AArch64/SME2p1/fsub-diagnostics.s @@ -1,5 +1,4 @@ -// RUN: not llvm-mc -triple=aarch64 -show-encoding -mattr=+sme2p1,+sme-f16f16 2>&1 < %s | FileCheck %s - +// RUN: not llvm-mc -triple=aarch64 -show-encoding -mattr=+sme-f16f16 2>&1 < %s | FileCheck %s // --------------------------------------------------------------------------// // Out of range index offset diff --git a/llvm/test/MC/AArch64/SME2p1/fsub.s b/llvm/test/MC/AArch64/SME2p1/fsub.s index b3735d554765ac1670a3b5503737df12e5f6da16..66410008eb11d1e0f995cd7af3f020e963fb8d0f 100644 --- a/llvm/test/MC/AArch64/SME2p1/fsub.s +++ b/llvm/test/MC/AArch64/SME2p1/fsub.s @@ -1,296 +1,298 @@ -// RUN: llvm-mc -triple=aarch64 -show-encoding -mattr=+sme2p1,+sme-f16f16 < %s \ +// RUN: llvm-mc -triple=aarch64 -show-encoding -mattr=+sme-f16f16 < %s \ +// RUN: | FileCheck %s --check-prefixes=CHECK-ENCODING,CHECK-INST +// RUN: llvm-mc -triple=aarch64 -show-encoding -mattr=+sme-f8f16 < %s \ // RUN: | FileCheck %s --check-prefixes=CHECK-ENCODING,CHECK-INST // RUN: not llvm-mc -triple=aarch64 -show-encoding < %s 2>&1 \ // RUN: | FileCheck %s --check-prefix=CHECK-ERROR -// RUN: llvm-mc -triple=aarch64 -filetype=obj -mattr=+sme2p1,+sme-f16f16 < %s \ -// RUN: | llvm-objdump -d --mattr=+sme2p1,+sme-f16f16 - | FileCheck %s --check-prefix=CHECK-INST -// RUN: llvm-mc -triple=aarch64 -filetype=obj -mattr=+sme2p1,+sme-f16f16 < %s \ +// RUN: llvm-mc -triple=aarch64 -filetype=obj -mattr=+sme-f16f16 < %s \ +// RUN: | llvm-objdump -d --mattr=+sme-f16f16 - | FileCheck %s --check-prefix=CHECK-INST +// RUN: llvm-mc -triple=aarch64 -filetype=obj -mattr=+sme-f16f16 < %s \ // RUN: | llvm-objdump -d --mattr=-sme2p1 - | FileCheck %s --check-prefix=CHECK-UNKNOWN -// RUN: llvm-mc -triple=aarch64 -show-encoding -mattr=+sme2p1,+sme-f16f16 < %s \ +// RUN: llvm-mc -triple=aarch64 -show-encoding -mattr=+sme-f16f16 < %s \ // RUN: | sed '/.text/d' | sed 's/.*encoding: //g' \ -// RUN: | llvm-mc -triple=aarch64 -mattr=+sme2p1,+sme-f16f16 -disassemble -show-encoding \ +// RUN: | llvm-mc -triple=aarch64 -mattr=+sme-f16f16 -disassemble -show-encoding \ // RUN: | FileCheck %s --check-prefixes=CHECK-ENCODING,CHECK-INST fsub za.h[w8, 0], {z0.h - z1.h} // 11000001-10100100-00011100-00001000 // CHECK-INST: fsub za.h[w8, 0, vgx2], { z0.h, z1.h } // CHECK-ENCODING: [0x08,0x1c,0xa4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a41c08 fsub za.h[w10, 5, vgx2], {z10.h, z11.h} // 11000001-10100100-01011101-01001101 // CHECK-INST: fsub za.h[w10, 5, vgx2], { z10.h, z11.h } // CHECK-ENCODING: [0x4d,0x5d,0xa4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a45d4d fsub za.h[w10, 5], {z10.h - z11.h} // 11000001-10100100-01011101-01001101 // CHECK-INST: fsub za.h[w10, 5, vgx2], { z10.h, z11.h } // CHECK-ENCODING: [0x4d,0x5d,0xa4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a45d4d fsub za.h[w11, 7, vgx2], {z12.h, z13.h} // 11000001-10100100-01111101-10001111 // CHECK-INST: fsub za.h[w11, 7, vgx2], { z12.h, z13.h } // CHECK-ENCODING: [0x8f,0x7d,0xa4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a47d8f fsub za.h[w11, 7], {z12.h - z13.h} // 11000001-10100100-01111101-10001111 // CHECK-INST: fsub za.h[w11, 7, vgx2], { z12.h, z13.h } // CHECK-ENCODING: [0x8f,0x7d,0xa4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a47d8f fsub za.h[w11, 7, vgx2], {z30.h, z31.h} // 11000001-10100100-01111111-11001111 // CHECK-INST: fsub za.h[w11, 7, vgx2], { z30.h, z31.h } // CHECK-ENCODING: [0xcf,0x7f,0xa4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a47fcf fsub za.h[w11, 7], {z30.h - z31.h} // 11000001-10100100-01111111-11001111 // CHECK-INST: fsub za.h[w11, 7, vgx2], { z30.h, z31.h } // CHECK-ENCODING: [0xcf,0x7f,0xa4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a47fcf fsub za.h[w8, 5, vgx2], {z16.h, z17.h} // 11000001-10100100-00011110-00001101 // CHECK-INST: fsub za.h[w8, 5, vgx2], { z16.h, z17.h } // CHECK-ENCODING: [0x0d,0x1e,0xa4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a41e0d fsub za.h[w8, 5], {z16.h - z17.h} // 11000001-10100100-00011110-00001101 // CHECK-INST: fsub za.h[w8, 5, vgx2], { z16.h, z17.h } // CHECK-ENCODING: [0x0d,0x1e,0xa4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a41e0d fsub za.h[w8, 1, vgx2], {z0.h, z1.h} // 11000001-10100100-00011100-00001001 // CHECK-INST: fsub za.h[w8, 1, vgx2], { z0.h, z1.h } // CHECK-ENCODING: [0x09,0x1c,0xa4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a41c09 fsub za.h[w8, 1], {z0.h - z1.h} // 11000001-10100100-00011100-00001001 // CHECK-INST: fsub za.h[w8, 1, vgx2], { z0.h, z1.h } // CHECK-ENCODING: [0x09,0x1c,0xa4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a41c09 fsub za.h[w10, 0, vgx2], {z18.h, z19.h} // 11000001-10100100-01011110, 01001000 // CHECK-INST: fsub za.h[w10, 0, vgx2], { z18.h, z19.h } // CHECK-ENCODING: [0x48,0x5e,0xa4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a45e48 fsub za.h[w10, 0], {z18.h - z19.h} // 11000001-10100100-01011110-01001000 // CHECK-INST: fsub za.h[w10, 0, vgx2], { z18.h, z19.h } // CHECK-ENCODING: [0x48,0x5e,0xa4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a45e48 fsub za.h[w8, 0, vgx2], {z12.h, z13.h} // 11000001-10100100-00011101-10001000 // CHECK-INST: fsub za.h[w8, 0, vgx2], { z12.h, z13.h } // CHECK-ENCODING: [0x88,0x1d,0xa4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a41d88 fsub za.h[w8, 0], {z12.h - z13.h} // 11000001-10100100-00011101-10001000 // CHECK-INST: fsub za.h[w8, 0, vgx2], { z12.h, z13.h } // CHECK-ENCODING: [0x88,0x1d,0xa4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a41d88 fsub za.h[w10, 1, vgx2], {z0.h, z1.h} // 11000001-10100100-01011100-00001001 // CHECK-INST: fsub za.h[w10, 1, vgx2], { z0.h, z1.h } // CHECK-ENCODING: [0x09,0x5c,0xa4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a45c09 fsub za.h[w10, 1], {z0.h - z1.h} // 11000001-10100100-01011100-00001001 // CHECK-INST: fsub za.h[w10, 1, vgx2], { z0.h, z1.h } // CHECK-ENCODING: [0x09,0x5c,0xa4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a45c09 fsub za.h[w8, 5, vgx2], {z22.h, z23.h} // 11000001-10100100-00011110, 11001101 // CHECK-INST: fsub za.h[w8, 5, vgx2], { z22.h, z23.h } // CHECK-ENCODING: [0xcd,0x1e,0xa4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a41ecd fsub za.h[w8, 5], {z22.h - z23.h} // 11000001-10100100-00011110-11001101 // CHECK-INST: fsub za.h[w8, 5, vgx2], { z22.h, z23.h } // CHECK-ENCODING: [0xcd,0x1e,0xa4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a41ecd fsub za.h[w11, 2, vgx2], {z8.h, z9.h} // 11000001-10100100-01111101-00001010 // CHECK-INST: fsub za.h[w11, 2, vgx2], { z8.h, z9.h } // CHECK-ENCODING: [0x0a,0x7d,0xa4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a47d0a fsub za.h[w11, 2], {z8.h - z9.h} // 11000001-10100100-01111101-00001010 // CHECK-INST: fsub za.h[w11, 2, vgx2], { z8.h, z9.h } // CHECK-ENCODING: [0x0a,0x7d,0xa4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a47d0a fsub za.h[w9, 7, vgx2], {z12.h, z13.h} // 11000001-10100100-00111101-10001111 // CHECK-INST: fsub za.h[w9, 7, vgx2], { z12.h, z13.h } // CHECK-ENCODING: [0x8f,0x3d,0xa4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a43d8f fsub za.h[w9, 7], {z12.h - z13.h} // 11000001-10100100-00111101-10001111 // CHECK-INST: fsub za.h[w9, 7, vgx2], { z12.h, z13.h } // CHECK-ENCODING: [0x8f,0x3d,0xa4,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a43d8f fsub za.h[w8, 0, vgx4], {z0.h - z3.h} // 11000001-10100101-00011100-00001000 // CHECK-INST: fsub za.h[w8, 0, vgx4], { z0.h - z3.h } // CHECK-ENCODING: [0x08,0x1c,0xa5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a51c08 fsub za.h[w8, 0], {z0.h - z3.h} // 11000001-10100101-00011100-00001000 // CHECK-INST: fsub za.h[w8, 0, vgx4], { z0.h - z3.h } // CHECK-ENCODING: [0x08,0x1c,0xa5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a51c08 fsub za.h[w10, 5, vgx4], {z8.h - z11.h} // 11000001-10100101-01011101-00001101 // CHECK-INST: fsub za.h[w10, 5, vgx4], { z8.h - z11.h } // CHECK-ENCODING: [0x0d,0x5d,0xa5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a55d0d fsub za.h[w10, 5], {z8.h - z11.h} // 11000001-10100101-01011101-00001101 // CHECK-INST: fsub za.h[w10, 5, vgx4], { z8.h - z11.h } // CHECK-ENCODING: [0x0d,0x5d,0xa5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a55d0d fsub za.h[w11, 7, vgx4], {z12.h - z15.h} // 11000001-10100101-01111101-10001111 // CHECK-INST: fsub za.h[w11, 7, vgx4], { z12.h - z15.h } // CHECK-ENCODING: [0x8f,0x7d,0xa5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a57d8f fsub za.h[w11, 7], {z12.h - z15.h} // 11000001-10100101-01111101-10001111 // CHECK-INST: fsub za.h[w11, 7, vgx4], { z12.h - z15.h } // CHECK-ENCODING: [0x8f,0x7d,0xa5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a57d8f fsub za.h[w11, 7, vgx4], {z28.h - z31.h} // 11000001-10100101-01111111-10001111 // CHECK-INST: fsub za.h[w11, 7, vgx4], { z28.h - z31.h } // CHECK-ENCODING: [0x8f,0x7f,0xa5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a57f8f fsub za.h[w11, 7], {z28.h - z31.h} // 11000001-10100101-01111111-10001111 // CHECK-INST: fsub za.h[w11, 7, vgx4], { z28.h - z31.h } // CHECK-ENCODING: [0x8f,0x7f,0xa5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a57f8f fsub za.h[w8, 5, vgx4], {z16.h - z19.h} // 11000001-10100101-00011110-00001101 // CHECK-INST: fsub za.h[w8, 5, vgx4], { z16.h - z19.h } // CHECK-ENCODING: [0x0d,0x1e,0xa5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a51e0d fsub za.h[w8, 5], {z16.h - z19.h} // 11000001-10100101-00011110-00001101 // CHECK-INST: fsub za.h[w8, 5, vgx4], { z16.h - z19.h } // CHECK-ENCODING: [0x0d,0x1e,0xa5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a51e0d fsub za.h[w8, 1, vgx4], {z0.h - z3.h} // 11000001-10100101-00011100-00001001 // CHECK-INST: fsub za.h[w8, 1, vgx4], { z0.h - z3.h } // CHECK-ENCODING: [0x09,0x1c,0xa5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a51c09 fsub za.h[w8, 1], {z0.h - z3.h} // 11000001-10100101-00011100-00001001 // CHECK-INST: fsub za.h[w8, 1, vgx4], { z0.h - z3.h } // CHECK-ENCODING: [0x09,0x1c,0xa5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a51c09 fsub za.h[w10, 0, vgx4], {z16.h - z19.h} // 11000001-10100101-01011110-00001000 // CHECK-INST: fsub za.h[w10, 0, vgx4], { z16.h - z19.h } // CHECK-ENCODING: [0x08,0x5e,0xa5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a55e08 fsub za.h[w10, 0], {z16.h - z19.h} // 11000001-10100101-01011110-00001000 // CHECK-INST: fsub za.h[w10, 0, vgx4], { z16.h - z19.h } // CHECK-ENCODING: [0x08,0x5e,0xa5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a55e08 fsub za.h[w8, 0, vgx4], {z12.h - z15.h} // 11000001-10100101-00011101-10001000 // CHECK-INST: fsub za.h[w8, 0, vgx4], { z12.h - z15.h } // CHECK-ENCODING: [0x88,0x1d,0xa5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a51d88 fsub za.h[w8, 0], {z12.h - z15.h} // 11000001-10100101-00011101-10001000 // CHECK-INST: fsub za.h[w8, 0, vgx4], { z12.h - z15.h } // CHECK-ENCODING: [0x88,0x1d,0xa5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a51d88 fsub za.h[w10, 1, vgx4], {z0.h - z3.h} // 11000001-10100101-01011100-00001001 // CHECK-INST: fsub za.h[w10, 1, vgx4], { z0.h - z3.h } // CHECK-ENCODING: [0x09,0x5c,0xa5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a55c09 fsub za.h[w10, 1], {z0.h - z3.h} // 11000001-10100101-01011100-00001001 // CHECK-INST: fsub za.h[w10, 1, vgx4], { z0.h - z3.h } // CHECK-ENCODING: [0x09,0x5c,0xa5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a55c09 fsub za.h[w8, 5, vgx4], {z20.h - z23.h} // 11000001-10100101-00011110-10001101 // CHECK-INST: fsub za.h[w8, 5, vgx4], { z20.h - z23.h } // CHECK-ENCODING: [0x8d,0x1e,0xa5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a51e8d fsub za.h[w8, 5], {z20.h - z23.h} // 11000001-10100101-00011110-10001101 // CHECK-INST: fsub za.h[w8, 5, vgx4], { z20.h - z23.h } // CHECK-ENCODING: [0x8d,0x1e,0xa5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a51e8d fsub za.h[w11, 2, vgx4], {z8.h - z11.h} // 11000001-10100101-01111101-00001010 // CHECK-INST: fsub za.h[w11, 2, vgx4], { z8.h - z11.h } // CHECK-ENCODING: [0x0a,0x7d,0xa5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a57d0a fsub za.h[w11, 2], {z8.h - z11.h} // 11000001-10100101-01111101-00001010 // CHECK-INST: fsub za.h[w11, 2, vgx4], { z8.h - z11.h } // CHECK-ENCODING: [0x0a,0x7d,0xa5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a57d0a fsub za.h[w9, 7, vgx4], {z12.h - z15.h} // 11000001-10100101-00111101-10001111 // CHECK-INST: fsub za.h[w9, 7, vgx4], { z12.h - z15.h } // CHECK-ENCODING: [0x8f,0x3d,0xa5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a53d8f fsub za.h[w9, 7], {z12.h - z15.h} // 11000001-10100101-00111101-10001111 // CHECK-INST: fsub za.h[w9, 7, vgx4], { z12.h - z15.h } // CHECK-ENCODING: [0x8f,0x3d,0xa5,0xc1] -// CHECK-ERROR: instruction requires: sme2p1 +// CHECK-ERROR: instruction requires: sme-f16f16 or sme-f8f16 // CHECK-UNKNOWN: c1a53d8f diff --git a/llvm/test/MC/Disassembler/M68k/data.txt b/llvm/test/MC/Disassembler/M68k/data.txt index 8e2fb3f13560865eb483a5b62bf1bccca4657e19..3951ea677f11f77d315a71d28a4469cbb52bc0a2 100644 --- a/llvm/test/MC/Disassembler/M68k/data.txt +++ b/llvm/test/MC/Disassembler/M68k/data.txt @@ -36,6 +36,12 @@ # CHECK: move.l (64,%sp,%a0), %d0 0x20 0x37 0x88 0x40 +# CHECK: move.b #234, %d2 +0x14 0x3c 0x00 0xea + +# CHECK: moveq #100, %d2 +0x74 0x64 + # CHECK: move.l $f0000000, %a5 0x2a 0x79 0xf0 0x00 0x00 0x00 diff --git a/llvm/test/MC/M68k/Data/Classes/MxMove_RI.s b/llvm/test/MC/M68k/Data/Classes/MxMove_RI.s index 091367a68256683873d8bc367567a31cc72a25d9..2081924d7b17d2c1ce640b36070f3e695b0e2786 100644 --- a/llvm/test/MC/M68k/Data/Classes/MxMove_RI.s +++ b/llvm/test/MC/M68k/Data/Classes/MxMove_RI.s @@ -9,3 +9,6 @@ move.l #42, %a1 ; CHECK: move.l #-1, %a1 ; CHECK-SAME: encoding: [0x22,0x7c,0xff,0xff,0xff,0xff] move.l #-1, %a1 +; CHECK: moveq #-17, %d3 +; CHECK-SAME: encoding: [0x76,0xef] +moveq #-17, %d3 diff --git a/llvm/test/MC/RISCV/attribute-arch.s b/llvm/test/MC/RISCV/attribute-arch.s index 8835ff22446c8d1700cc0c7b2ffc938e3017c0d2..aea27146e37047841af93d10ede0008add1cee2f 100644 --- a/llvm/test/MC/RISCV/attribute-arch.s +++ b/llvm/test/MC/RISCV/attribute-arch.s @@ -366,7 +366,7 @@ .attribute arch, "rv32i_zvfbfwma1p0" # CHECK: .attribute 5, "rv32i2p1_f2p2_zicsr2p0_zfbfmin1p0_zve32f1p0_zve32x1p0_zvfbfmin1p0_zvfbfwma1p0_zvl32b1p0" -.attribute arch, "rv32izacas1p0" +.attribute arch, "rv32ia_zacas1p0" # CHECK: attribute 5, "rv32i2p1_a2p1_zacas1p0" .attribute arch, "rv32izalasr0p1" diff --git a/llvm/test/MC/RISCV/rv32dc-valid.s b/llvm/test/MC/RISCV/rv32dc-valid.s index 4e30fadac34bc2e7caa09ffe6e346a07fdaa4cad..201aee545d4a420a3575ca4be8f089aa24956604 100644 --- a/llvm/test/MC/RISCV/rv32dc-valid.s +++ b/llvm/test/MC/RISCV/rv32dc-valid.s @@ -12,9 +12,6 @@ # RUN: not llvm-mc -triple riscv32 -mattr=+c \ # RUN: -riscv-no-aliases -show-encoding < %s 2>&1 \ # RUN: | FileCheck -check-prefixes=CHECK-NO-EXT-D %s -# RUN: not llvm-mc -triple riscv32 -mattr=+zcd \ -# RUN: -riscv-no-aliases -show-encoding < %s 2>&1 \ -# RUN: | FileCheck -check-prefixes=CHECK-NO-EXT-D %s # RUN: not llvm-mc -triple riscv32 -riscv-no-aliases -show-encoding < %s 2>&1 \ # RUN: | FileCheck -check-prefixes=CHECK-NO-EXT-DC %s diff --git a/llvm/test/MC/RISCV/rv32fc-valid.s b/llvm/test/MC/RISCV/rv32fc-valid.s index f8be0336779472f40fdd7103ed2752a6820d4a38..936032594457f6755a033dfc347f6b56d77e0c85 100644 --- a/llvm/test/MC/RISCV/rv32fc-valid.s +++ b/llvm/test/MC/RISCV/rv32fc-valid.s @@ -12,9 +12,6 @@ # RUN: not llvm-mc -triple riscv32 -mattr=+c \ # RUN: -riscv-no-aliases -show-encoding < %s 2>&1 \ # RUN: | FileCheck -check-prefixes=CHECK-NO-EXT-F %s -# RUN: not llvm-mc -triple riscv32 -mattr=+zcf \ -# RUN: -riscv-no-aliases -show-encoding < %s 2>&1 \ -# RUN: | FileCheck -check-prefixes=CHECK-NO-EXT-F %s # RUN: not llvm-mc -triple riscv32 \ # RUN: -riscv-no-aliases -show-encoding < %s 2>&1 \ # RUN: | FileCheck -check-prefixes=CHECK-NO-EXT-FC %s diff --git a/llvm/test/MC/RISCV/rv32zacas-invalid.s b/llvm/test/MC/RISCV/rv32zacas-invalid.s index 11d20dacd8a78834de57ad3027940b46e51f08e8..66f939d139a1268e6613f18ec2d2e8e99e6b17e8 100644 --- a/llvm/test/MC/RISCV/rv32zacas-invalid.s +++ b/llvm/test/MC/RISCV/rv32zacas-invalid.s @@ -1,4 +1,4 @@ -# RUN: not llvm-mc -triple riscv32 -mattr=+zacas < %s 2>&1 | FileCheck %s +# RUN: not llvm-mc -triple riscv32 -mattr=+a,zacas < %s 2>&1 | FileCheck %s # Non-zero offsets not supported for the third operand (rs1). amocas.w a1, a3, 1(a5) # CHECK: :[[@LINE]]:18: error: optional integer offset must be 0 diff --git a/llvm/test/MC/RISCV/rv32zacas-valid.s b/llvm/test/MC/RISCV/rv32zacas-valid.s index 05a9cdd5cc2188b284a1e3a50a6452bd2af573bc..0e76f023994833b493b6c78955a67981e898230a 100644 --- a/llvm/test/MC/RISCV/rv32zacas-valid.s +++ b/llvm/test/MC/RISCV/rv32zacas-valid.s @@ -1,12 +1,12 @@ -# RUN: llvm-mc %s -triple=riscv32 -mattr=+zacas -riscv-no-aliases -show-encoding \ +# RUN: llvm-mc %s -triple=riscv32 -mattr=+a,+zacas -riscv-no-aliases -show-encoding \ # RUN: | FileCheck -check-prefixes=CHECK-ASM,CHECK-ASM-AND-OBJ %s -# RUN: llvm-mc %s -triple=riscv64 -mattr=+zacas -riscv-no-aliases -show-encoding \ +# RUN: llvm-mc %s -triple=riscv64 -mattr=+a,+zacas -riscv-no-aliases -show-encoding \ # RUN: | FileCheck -check-prefixes=CHECK-ASM,CHECK-ASM-AND-OBJ %s -# RUN: llvm-mc -filetype=obj -triple=riscv32 -mattr=+zacas < %s \ -# RUN: | llvm-objdump --mattr=+zacas -M no-aliases -d -r - \ +# RUN: llvm-mc -filetype=obj -triple=riscv32 -mattr=+a,+zacas < %s \ +# RUN: | llvm-objdump --mattr=+a,+zacas -M no-aliases -d -r - \ # RUN: | FileCheck --check-prefix=CHECK-ASM-AND-OBJ %s -# RUN: llvm-mc -filetype=obj -triple=riscv64 -mattr=+zacas < %s \ -# RUN: | llvm-objdump --mattr=+zacas -M no-aliases -d -r - \ +# RUN: llvm-mc -filetype=obj -triple=riscv64 -mattr=+a,+zacas < %s \ +# RUN: | llvm-objdump --mattr=+a,+zacas -M no-aliases -d -r - \ # RUN: | FileCheck --check-prefix=CHECK-ASM-AND-OBJ %s # RUN: not llvm-mc -triple=riscv32 -mattr=+a -show-encoding %s 2>&1 \ # RUN: | FileCheck %s --check-prefix=CHECK-ERROR diff --git a/llvm/test/MC/RISCV/rv64dc-valid.s b/llvm/test/MC/RISCV/rv64dc-valid.s index 5347714761dc8c08940e9bba5fd9cd5ac2b2691c..83225b2c68562c568939e24a9bd51e84b7a5d77a 100644 --- a/llvm/test/MC/RISCV/rv64dc-valid.s +++ b/llvm/test/MC/RISCV/rv64dc-valid.s @@ -12,9 +12,6 @@ # RUN: not llvm-mc -triple riscv64 -mattr=+c \ # RUN: -riscv-no-aliases -show-encoding < %s 2>&1 \ # RUN: | FileCheck -check-prefixes=CHECK-NO-EXT-D %s -# RUN: not llvm-mc -triple riscv64 -mattr=+zcd \ -# RUN: -riscv-no-aliases -show-encoding < %s 2>&1 \ -# RUN: | FileCheck -check-prefixes=CHECK-NO-EXT-D %s # RUN: not llvm-mc -triple riscv64 -riscv-no-aliases -show-encoding < %s 2>&1 \ # RUN: | FileCheck -check-prefixes=CHECK-NO-EXT-DC %s diff --git a/llvm/test/MC/RISCV/rv64zacas-valid.s b/llvm/test/MC/RISCV/rv64zacas-valid.s index 694f43b9b4407b3a88a1800ab186958ca2b451a4..c6bf1252fa40d631102479dece2a862d2f910dc3 100644 --- a/llvm/test/MC/RISCV/rv64zacas-valid.s +++ b/llvm/test/MC/RISCV/rv64zacas-valid.s @@ -1,7 +1,7 @@ -# RUN: llvm-mc %s -triple=riscv64 -mattr=+zacas -riscv-no-aliases -show-encoding \ +# RUN: llvm-mc %s -triple=riscv64 -mattr=+a,zacas -riscv-no-aliases -show-encoding \ # RUN: | FileCheck -check-prefixes=CHECK-ASM,CHECK-ASM-AND-OBJ %s -# RUN: llvm-mc -filetype=obj -triple=riscv64 -mattr=+zacas < %s \ -# RUN: | llvm-objdump --mattr=+zacas -M no-aliases -d -r - \ +# RUN: llvm-mc -filetype=obj -triple=riscv64 -mattr=+a,zacas < %s \ +# RUN: | llvm-objdump --mattr=+a,zacas -M no-aliases -d -r - \ # RUN: | FileCheck --check-prefix=CHECK-ASM-AND-OBJ %s # RUN: not llvm-mc -triple=riscv64 -mattr=+a -show-encoding %s 2>&1 \ # RUN: | FileCheck %s --check-prefix=CHECK-ERROR diff --git a/llvm/test/MC/RISCV/rvzabha-invalid.s b/llvm/test/MC/RISCV/rvzabha-invalid.s index 091f7e59ae184430780e66ced1459891a9beda38..62cb1d8c8913948d681c389b1f3c69831675fa79 100644 --- a/llvm/test/MC/RISCV/rvzabha-invalid.s +++ b/llvm/test/MC/RISCV/rvzabha-invalid.s @@ -1,5 +1,5 @@ -# RUN: not llvm-mc -triple riscv32 -mattr=+experimental-zabha < %s 2>&1 | FileCheck %s -# RUN: not llvm-mc -triple riscv64 -mattr=+experimental-zabha < %s 2>&1 | FileCheck %s +# RUN: not llvm-mc -triple riscv32 -mattr=+a,+experimental-zabha < %s 2>&1 | FileCheck %s +# RUN: not llvm-mc -triple riscv64 -mattr=+a,+experimental-zabha < %s 2>&1 | FileCheck %s # Final operand must have parentheses amoswap.b a1, a2, a3 # CHECK: :[[@LINE]]:19: error: expected '(' or optional integer offset diff --git a/llvm/test/MC/RISCV/rvzabha-valid.s b/llvm/test/MC/RISCV/rvzabha-valid.s index c1f7f44a04ddd081a4d2a850f7b7e35dea3b451b..333e58d1268e6ed68a1a2d049a7bca09a0f01629 100644 --- a/llvm/test/MC/RISCV/rvzabha-valid.s +++ b/llvm/test/MC/RISCV/rvzabha-valid.s @@ -1,12 +1,12 @@ -# RUN: llvm-mc %s -triple=riscv32 -mattr=+experimental-zabha -riscv-no-aliases -show-encoding \ +# RUN: llvm-mc %s -triple=riscv32 -mattr=+a,+experimental-zabha -riscv-no-aliases -show-encoding \ # RUN: | FileCheck -check-prefixes=CHECK-ASM,CHECK-ASM-AND-OBJ %s -# RUN: llvm-mc %s -triple=riscv64 -mattr=+experimental-zabha -riscv-no-aliases -show-encoding \ +# RUN: llvm-mc %s -triple=riscv64 -mattr=+a,+experimental-zabha -riscv-no-aliases -show-encoding \ # RUN: | FileCheck -check-prefixes=CHECK-ASM,CHECK-ASM-AND-OBJ %s -# RUN: llvm-mc -filetype=obj -triple=riscv32 -mattr=+experimental-zabha < %s \ -# RUN: | llvm-objdump --mattr=+experimental-zabha -M no-aliases -d -r - \ +# RUN: llvm-mc -filetype=obj -triple=riscv32 -mattr=+a,+experimental-zabha < %s \ +# RUN: | llvm-objdump --mattr=+a,+experimental-zabha -M no-aliases -d -r - \ # RUN: | FileCheck --check-prefix=CHECK-ASM-AND-OBJ %s -# RUN: llvm-mc -filetype=obj -triple=riscv64 -mattr=+experimental-zabha < %s \ -# RUN: | llvm-objdump --mattr=+experimental-zabha -M no-aliases -d -r - \ +# RUN: llvm-mc -filetype=obj -triple=riscv64 -mattr=+a,+experimental-zabha < %s \ +# RUN: | llvm-objdump --mattr=+a,+experimental-zabha -M no-aliases -d -r - \ # RUN: | FileCheck --check-prefix=CHECK-ASM-AND-OBJ %s # CHECK-ASM-AND-OBJ: amoswap.b a4, ra, (s0) diff --git a/llvm/test/MC/RISCV/rvzabha-zacas-valid.s b/llvm/test/MC/RISCV/rvzabha-zacas-valid.s index f1f705e625b87a2f717314ec82b67b0c90f79f85..994112c6b6e5b86f122fcc031517b6806a879feb 100644 --- a/llvm/test/MC/RISCV/rvzabha-zacas-valid.s +++ b/llvm/test/MC/RISCV/rvzabha-zacas-valid.s @@ -1,16 +1,16 @@ -# RUN: llvm-mc %s -triple=riscv32 -mattr=+experimental-zabha,+zacas -riscv-no-aliases -show-encoding \ +# RUN: llvm-mc %s -triple=riscv32 -mattr=+a,+experimental-zabha,+zacas -riscv-no-aliases -show-encoding \ # RUN: | FileCheck -check-prefixes=CHECK-ASM,CHECK-ASM-AND-OBJ %s -# RUN: llvm-mc %s -triple=riscv64 -mattr=+experimental-zabha,+zacas -riscv-no-aliases -show-encoding \ +# RUN: llvm-mc %s -triple=riscv64 -mattr=+a,+experimental-zabha,+zacas -riscv-no-aliases -show-encoding \ # RUN: | FileCheck -check-prefixes=CHECK-ASM,CHECK-ASM-AND-OBJ %s -# RUN: llvm-mc -filetype=obj -triple=riscv32 -mattr=+experimental-zabha,+zacas < %s \ -# RUN: | llvm-objdump --mattr=+experimental-zabha,+zacas -M no-aliases -d -r - \ +# RUN: llvm-mc -filetype=obj -triple=riscv32 -mattr=+a,+experimental-zabha,+zacas < %s \ +# RUN: | llvm-objdump --mattr=+a,+experimental-zabha,+zacas -M no-aliases -d -r - \ # RUN: | FileCheck --check-prefix=CHECK-ASM-AND-OBJ %s -# RUN: llvm-mc -filetype=obj -triple=riscv64 -mattr=+experimental-zabha,+zacas < %s \ -# RUN: | llvm-objdump --mattr=+experimental-zabha,+zacas -M no-aliases -d -r - \ +# RUN: llvm-mc -filetype=obj -triple=riscv64 -mattr=+a,+experimental-zabha,+zacas < %s \ +# RUN: | llvm-objdump --mattr=+a,+experimental-zabha,+zacas -M no-aliases -d -r - \ # RUN: | FileCheck --check-prefix=CHECK-ASM-AND-OBJ %s -# RUN: not llvm-mc -triple=riscv32 -mattr=+experimental-zabha -show-encoding %s 2>&1 \ +# RUN: not llvm-mc -triple=riscv32 -mattr=+a,+experimental-zabha -show-encoding %s 2>&1 \ # RUN: | FileCheck %s --check-prefix=CHECK-ERROR -# RUN: not llvm-mc -triple=riscv64 -mattr=+experimental-zabha -show-encoding %s 2>&1 \ +# RUN: not llvm-mc -triple=riscv64 -mattr=+a,+experimental-zabha -show-encoding %s 2>&1 \ # RUN: | FileCheck %s --check-prefix=CHECK-ERROR # CHECK-ASM-AND-OBJ: amocas.b a1, a3, (a5) diff --git a/llvm/test/MC/Xtensa/Core/invalid.s b/llvm/test/MC/Xtensa/Core/invalid.s index d3d8fba8169a6d2206621184398ea0accd97f358..c7473e90c10ba378c4dca713fae1ef1dc7fead07 100644 --- a/llvm/test/MC/Xtensa/Core/invalid.s +++ b/llvm/test/MC/Xtensa/Core/invalid.s @@ -4,10 +4,6 @@ LBL0: # Out of range immediates -# imm12m -movi a1, 3000 -# CHECK: :[[#@LINE-1]]:10: error: expected immediate in range [-2048, 2047] - # imm8 addi a1, a2, 300 # CHECK: :[[#@LINE-1]]:14: error: expected immediate in range [-128, 127] diff --git a/llvm/test/MC/Xtensa/directive-literal.s b/llvm/test/MC/Xtensa/directive-literal.s new file mode 100644 index 0000000000000000000000000000000000000000..269cf20ed45eb2a5edd6a0b2625d6d8df0119a1c --- /dev/null +++ b/llvm/test/MC/Xtensa/directive-literal.s @@ -0,0 +1,42 @@ +# RUN: llvm-mc -triple=xtensa -filetype obj -o - %s \ +# RUN: | llvm-readobj -S --sd - \ +# RUN: | FileCheck -check-prefix=CHECK-LITERAL %s + +# RUN: llvm-mc %s -triple=xtensa -show-encoding \ +# RUN: | FileCheck -check-prefix=CHECK-INST %s + + .text + .literal_position + .literal .LCPI0_0, 305419896 + .literal .LCPI1_0, ext_var + .global test_literal + .p2align 2 + .type test_literal,@function +test_literal: + l32r a2, .LCPI0_0 + l32r a3, .LCPI1_0 + movi a4, 30000 + movi a5, 1000 + ret + +# CHECK-LITERAL: Section { +# CHECK-LITERAL: Name: .literal +# CHECK-LITERAL: SectionData ( +# CHECK-LITERAL: 0000: 78563412 00000000 30750000 +# CHECK-LITERAL: ) +# CHECK-LITERAL: } + +# CHECK-INST: .literal_position +# CHECK-INST: .literal .LCPI0_0, 305419896 +# CHECK-INST: .literal .LCPI1_0, ext_var +# CHECK-INST: .global test_literal +# CHECK-INST: .p2align 2 +# CHECK-INST: .type test_literal,@function +# CHECK-INST: test_literal: +# CHECK-INST: l32r a2, .LCPI0_0 +# CHECK-INST: l32r a3, .LCPI1_0 +# CHECK-INST: .literal .Ltmp0, 30000 +# CHECK-INST: l32r a4, .Ltmp0 +# CHECK-INST: movi a5, 1000 +# CHECK-INST: ret + diff --git a/llvm/test/MC/Xtensa/invalid-literal.s b/llvm/test/MC/Xtensa/invalid-literal.s new file mode 100644 index 0000000000000000000000000000000000000000..ebb37441059cad4eed300cce15bed01ec65a4042 --- /dev/null +++ b/llvm/test/MC/Xtensa/invalid-literal.s @@ -0,0 +1,10 @@ +# RUN: not llvm-mc %s -triple=xtensa -filetype=asm 2>&1 | FileCheck %s + +.text +.literal_position +.literal .LCPI0_0 a +# CHECK: [[@LINE-1]]:20: error: expected comma +.literal 123, a +# CHECK: [[@LINE-1]]:10: error: literal label must be a symbol +.literal .LCPI1_0, +# CHECK: [[@LINE-1]]:19: error: expected value diff --git a/llvm/test/TableGen/ContextlessPredicates.td b/llvm/test/TableGen/ContextlessPredicates.td index 5e4e69069c3e3298226908411baa85de5646e559..eead9655111e6815c962dd6883830dc6655484ba 100644 --- a/llvm/test/TableGen/ContextlessPredicates.td +++ b/llvm/test/TableGen/ContextlessPredicates.td @@ -22,26 +22,26 @@ def : Pat<(test_atomic_op_frag GPR32:$ptr, GPR32:$val) , // CHECK_NOPT-LABEL: const uint8_t *MyTargetInstructionSelector::getMatchTable() const { // CHECK_NOPT-NEXT: constexpr static uint8_t MatchTable0[] = { -// CHECK_NOPT-NEXT: GIM_Try, /*On fail goto*//*Label 0*/ GIMT_Encode4(58), // Rule ID 0 // +// CHECK_NOPT-NEXT: GIM_Try, /*On fail goto*//*Label 0*/ GIMT_Encode4(52), // Rule ID 0 // // CHECK_NOPT-NEXT: GIM_CheckNumOperands, /*MI*/0, /*Expected*/3, // CHECK_NOPT-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_ATOMICRMW_XCHG), // CHECK_NOPT-NEXT: GIM_CheckMemorySizeEqualTo, /*MI*/0, /*MMO*/0, /*Size*/GIMT_Encode4(4), // CHECK_NOPT-NEXT: // MIs[0] DstI[dst] -// CHECK_NOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// CHECK_NOPT-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// CHECK_NOPT-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// CHECK_NOPT-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // CHECK_NOPT-NEXT: // MIs[0] ptr // CHECK_NOPT-NEXT: GIM_CheckPointerToAny, /*MI*/0, /*Op*/1, /*SizeInBits*/32, -// CHECK_NOPT-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// CHECK_NOPT-NEXT: GIM_RootCheckRegBankForClass, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // CHECK_NOPT-NEXT: // MIs[0] val -// CHECK_NOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/2, /*Type*/GILLT_s32, -// CHECK_NOPT-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/2, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// CHECK_NOPT-NEXT: GIM_RootCheckType, /*Op*/2, /*Type*/GILLT_s32, +// CHECK_NOPT-NEXT: GIM_RootCheckRegBankForClass, /*Op*/2, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // CHECK_NOPT-NEXT: GIM_CheckCxxInsnPredicate, /*MI*/0, /*FnId*/GIMT_Encode2(GICXXPred_MI_Predicate_test_atomic_op_frag), // CHECK_NOPT-NEXT: // (atomic_swap:{ *:[i32] } GPR32:{ *:[i32] }:$ptr, GPR32:{ *:[i32] }:$val)<> => (INSN:{ *:[i32] } GPR32:{ *:[i32] }:$ptr, GPR32:{ *:[i32] }:$val) // CHECK_NOPT-NEXT: GIR_MutateOpcode, /*InsnID*/0, /*RecycleInsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::INSN), -// CHECK_NOPT-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, +// CHECK_NOPT-NEXT: GIR_RootConstrainSelectedInstOperands, // CHECK_NOPT-NEXT: // GIR_Coverage, 0, // CHECK_NOPT-NEXT: GIR_Done, -// CHECK_NOPT-NEXT: // Label 0: @58 +// CHECK_NOPT-NEXT: // Label 0: @52 // CHECK_NOPT-NEXT: GIM_Reject, // CHECK_NOPT-NEXT: }; // CHECK_NOPT-NEXT: return MatchTable0; @@ -49,23 +49,23 @@ def : Pat<(test_atomic_op_frag GPR32:$ptr, GPR32:$val) , // CHECK_OPT-LABEL: const uint8_t *MyTargetInstructionSelector::getMatchTable() const { // CHECK_OPT-NEXT: constexpr static uint8_t MatchTable0[] = { -// CHECK_OPT-NEXT: GIM_Try, /*On fail goto*//*Label 0*/ GIMT_Encode4(55), // Rule ID 0 // +// CHECK_OPT-NEXT: GIM_Try, /*On fail goto*//*Label 0*/ GIMT_Encode4(49), // Rule ID 0 // // CHECK_OPT-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_ATOMICRMW_XCHG), -// CHECK_OPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// CHECK_OPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/2, /*Type*/GILLT_s32, +// CHECK_OPT-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// CHECK_OPT-NEXT: GIM_RootCheckType, /*Op*/2, /*Type*/GILLT_s32, // CHECK_OPT-NEXT: GIM_CheckMemorySizeEqualTo, /*MI*/0, /*MMO*/0, /*Size*/GIMT_Encode4(4), -// CHECK_OPT-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// CHECK_OPT-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // CHECK_OPT-NEXT: // MIs[0] ptr // CHECK_OPT-NEXT: GIM_CheckPointerToAny, /*MI*/0, /*Op*/1, /*SizeInBits*/32, -// CHECK_OPT-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), -// CHECK_OPT-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/2, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// CHECK_OPT-NEXT: GIM_RootCheckRegBankForClass, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// CHECK_OPT-NEXT: GIM_RootCheckRegBankForClass, /*Op*/2, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // CHECK_OPT-NEXT: GIM_CheckCxxInsnPredicate, /*MI*/0, /*FnId*/GIMT_Encode2(GICXXPred_MI_Predicate_test_atomic_op_frag), // CHECK_OPT-NEXT: // (atomic_swap:{ *:[i32] } GPR32:{ *:[i32] }:$ptr, GPR32:{ *:[i32] }:$val)<> => (INSN:{ *:[i32] } GPR32:{ *:[i32] }:$ptr, GPR32:{ *:[i32] }:$val) // CHECK_OPT-NEXT: GIR_MutateOpcode, /*InsnID*/0, /*RecycleInsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::INSN), -// CHECK_OPT-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, +// CHECK_OPT-NEXT: GIR_RootConstrainSelectedInstOperands, // CHECK_OPT-NEXT: // GIR_Coverage, 0, // CHECK_OPT-NEXT: GIR_Done, -// CHECK_OPT-NEXT: // Label 0: @55 +// CHECK_OPT-NEXT: // Label 0: @49 // CHECK_OPT-NEXT: GIM_Reject, // CHECK_OPT-NEXT: }; // CHECK_OPT-NEXT: return MatchTable0; diff --git a/llvm/test/TableGen/DefaultOpsGlobalISel.td b/llvm/test/TableGen/DefaultOpsGlobalISel.td index 0c5aa0b912f5492f20a33af0b86ffa97e7e360f2..8f4176a2aa730b8f6f1802f0e160fcefb983b422 100644 --- a/llvm/test/TableGen/DefaultOpsGlobalISel.td +++ b/llvm/test/TableGen/DefaultOpsGlobalISel.td @@ -33,101 +33,97 @@ def clamp : OperandWithDefaultOps ; // CHECK: const uint8_t *MyTargetInstructionSelector::getMatchTable() const { // CHECK-NEXT: constexpr static uint8_t MatchTable0[] = { -// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 0*/ GIMT_Encode4(79), // Rule ID 3 // +// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 0*/ GIMT_Encode4(69), // Rule ID 3 // // CHECK-NEXT: GIM_CheckNumOperands, /*MI*/0, /*Expected*/3, // CHECK-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_FMAXNUM), // CHECK-NEXT: // MIs[0] DstI[dst] -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::FPR32RegClassID), +// CHECK-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::FPR32RegClassID), // CHECK-NEXT: // MIs[0] SelectSrcMods:src0:mods0 -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, // CHECK-NEXT: GIM_CheckComplexPattern, /*MI*/0, /*Op*/1, /*Renderer*/GIMT_Encode2(0), GIMT_Encode2(GICP_gi_SelectSrcMods), // CHECK-NEXT: // MIs[0] SelectSrcMods:src1:mods1 -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/2, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckType, /*Op*/2, /*Type*/GILLT_s32, // CHECK-NEXT: GIM_CheckComplexPattern, /*MI*/0, /*Op*/2, /*Renderer*/GIMT_Encode2(1), GIMT_Encode2(GICP_gi_SelectSrcMods), // CHECK-NEXT: // (fmaxnum:{ *:[f32] } (SelectSrcMods:{ *:[f32] } f32:{ *:[f32] }:$src0, src_mods:{ *:[i32] }:$mods0), (SelectSrcMods:{ *:[f32] } f32:{ *:[f32] }:$src1, src_mods:{ *:[i32] }:$mods1)) => (FMAX:{ *:[f32] } src_mods:{ *:[i32] }:$mods0, f32:{ *:[f32] }:$src0, src_mods:{ *:[i32] }:$mods1, f32:{ *:[f32] }:$src1) -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::FMAX), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::FMAX), +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] // CHECK-NEXT: GIR_ComplexSubOperandRenderer, /*InsnID*/0, /*RendererID*/GIMT_Encode2(0), /*SubOperand*/1, // mods0 // CHECK-NEXT: GIR_ComplexSubOperandRenderer, /*InsnID*/0, /*RendererID*/GIMT_Encode2(0), /*SubOperand*/0, // src0 // CHECK-NEXT: GIR_ComplexSubOperandRenderer, /*InsnID*/0, /*RendererID*/GIMT_Encode2(1), /*SubOperand*/1, // mods1 // CHECK-NEXT: GIR_ComplexSubOperandRenderer, /*InsnID*/0, /*RendererID*/GIMT_Encode2(1), /*SubOperand*/0, // src1 // CHECK-NEXT: GIR_AddImm8, /*InsnID*/0, /*Imm*/0, -// CHECK-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// CHECK-NEXT: GIR_RootConstrainSelectedInstOperands, // CHECK-NEXT: // GIR_Coverage, 3, -// CHECK-NEXT: GIR_Done, -// CHECK-NEXT: // Label 0: @79 -// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 1*/ GIMT_Encode4(139), // Rule ID 2 // +// CHECK-NEXT: GIR_EraseRootFromParent_Done, +// CHECK-NEXT: // Label 0: @69 +// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 1*/ GIMT_Encode4(120), // Rule ID 2 // // CHECK-NEXT: GIM_CheckNumOperands, /*MI*/0, /*Expected*/2, // CHECK-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_FFLOOR), // CHECK-NEXT: // MIs[0] DstI[dst] -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::FPR32RegClassID), +// CHECK-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::FPR32RegClassID), // CHECK-NEXT: // MIs[0] SelectClampOMod:src0:omod:clamp -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, // CHECK-NEXT: GIM_CheckComplexPattern, /*MI*/0, /*Op*/1, /*Renderer*/GIMT_Encode2(0), GIMT_Encode2(GICP_gi_SelectClampOMod), // CHECK-NEXT: // (ffloor:{ *:[f32] } (SelectClampOMod:{ *:[f32] } f32:{ *:[f32] }:$src0, omod:{ *:[i32] }:$omod, i1:{ *:[i1] }:$clamp)) => (FLOMP:{ *:[f32] } f32:{ *:[f32] }:$src0, i1:{ *:[i1] }:$clamp, omod:{ *:[i32] }:$omod) -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::FLOMP), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::FLOMP), +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] // CHECK-NEXT: GIR_ComplexSubOperandRenderer, /*InsnID*/0, /*RendererID*/GIMT_Encode2(0), /*SubOperand*/0, // src0 // CHECK-NEXT: GIR_ComplexSubOperandRenderer, /*InsnID*/0, /*RendererID*/GIMT_Encode2(0), /*SubOperand*/2, // clamp // CHECK-NEXT: GIR_ComplexSubOperandRenderer, /*InsnID*/0, /*RendererID*/GIMT_Encode2(0), /*SubOperand*/1, // omod -// CHECK-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// CHECK-NEXT: GIR_RootConstrainSelectedInstOperands, // CHECK-NEXT: // GIR_Coverage, 2, -// CHECK-NEXT: GIR_Done, -// CHECK-NEXT: // Label 1: @139 -// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 2*/ GIMT_Encode4(207), // Rule ID 8 // +// CHECK-NEXT: GIR_EraseRootFromParent_Done, +// CHECK-NEXT: // Label 1: @120 +// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 2*/ GIMT_Encode4(179), // Rule ID 8 // // CHECK-NEXT: GIM_CheckNumOperands, /*MI*/0, /*Expected*/2, // CHECK-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_FCANONICALIZE), // CHECK-NEXT: // MIs[0] DstI[dst] -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::FPR32RegClassID), +// CHECK-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::FPR32RegClassID), // CHECK-NEXT: // MIs[0] SelectSrcMods:src:mods -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, // CHECK-NEXT: GIM_CheckComplexPattern, /*MI*/0, /*Op*/1, /*Renderer*/GIMT_Encode2(0), GIMT_Encode2(GICP_gi_SelectSrcMods), // CHECK-NEXT: // (fcanonicalize:{ *:[f32] } (SelectSrcMods:{ *:[f32] } f32:{ *:[f32] }:$src, i32:{ *:[i32] }:$mods)) => (FMAX:{ *:[f32] } ?:{ *:[i32] }:$mods, ?:{ *:[f32] }:$src, ?:{ *:[i32] }:$mods, ?:{ *:[f32] }:$src, 0:{ *:[i1] }) -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::FMAX), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::FMAX), +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] // CHECK-NEXT: GIR_ComplexSubOperandRenderer, /*InsnID*/0, /*RendererID*/GIMT_Encode2(0), /*SubOperand*/1, // mods // CHECK-NEXT: GIR_ComplexSubOperandRenderer, /*InsnID*/0, /*RendererID*/GIMT_Encode2(0), /*SubOperand*/0, // src // CHECK-NEXT: GIR_ComplexSubOperandRenderer, /*InsnID*/0, /*RendererID*/GIMT_Encode2(0), /*SubOperand*/1, // mods // CHECK-NEXT: GIR_ComplexSubOperandRenderer, /*InsnID*/0, /*RendererID*/GIMT_Encode2(0), /*SubOperand*/0, // src // CHECK-NEXT: GIR_AddImm8, /*InsnID*/0, /*Imm*/0, -// CHECK-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// CHECK-NEXT: GIR_RootConstrainSelectedInstOperands, // CHECK-NEXT: // GIR_Coverage, 8, -// CHECK-NEXT: GIR_Done, -// CHECK-NEXT: // Label 2: @207 -// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 3*/ GIMT_Encode4(265), // Rule ID 5 // +// CHECK-NEXT: GIR_EraseRootFromParent_Done, +// CHECK-NEXT: // Label 2: @179 +// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 3*/ GIMT_Encode4(228), // Rule ID 5 // // CHECK-NEXT: GIM_CheckNumOperands, /*MI*/0, /*Expected*/2, // CHECK-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_FCOS), // CHECK-NEXT: // MIs[0] DstI[dst] -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::FPR32RegClassID), +// CHECK-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::FPR32RegClassID), // CHECK-NEXT: // MIs[0] SelectOMod:src0:omod -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, // CHECK-NEXT: GIM_CheckComplexPattern, /*MI*/0, /*Op*/1, /*Renderer*/GIMT_Encode2(0), GIMT_Encode2(GICP_gi_SelectOMod), // CHECK-NEXT: // (fcos:{ *:[f32] } (SelectOMod:{ *:[f32] } f32:{ *:[f32] }:$src0, i32:{ *:[i32] }:$omod)) => (FLAMP:{ *:[f32] } FPR32:{ *:[f32] }:$src0, omod:{ *:[i32] }:$omod) -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::FLAMP), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::FLAMP), +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] // CHECK-NEXT: GIR_ComplexSubOperandRenderer, /*InsnID*/0, /*RendererID*/GIMT_Encode2(0), /*SubOperand*/0, // src0 // CHECK-NEXT: GIR_ComplexSubOperandRenderer, /*InsnID*/0, /*RendererID*/GIMT_Encode2(0), /*SubOperand*/1, // omod // CHECK-NEXT: GIR_AddImm8, /*InsnID*/0, /*Imm*/0, -// CHECK-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// CHECK-NEXT: GIR_RootConstrainSelectedInstOperands, // CHECK-NEXT: // GIR_Coverage, 5, -// CHECK-NEXT: GIR_Done, -// CHECK-NEXT: // Label 3: @265 -// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 4*/ GIMT_Encode4(345), // Rule ID 7 // +// CHECK-NEXT: GIR_EraseRootFromParent_Done, +// CHECK-NEXT: // Label 3: @228 +// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 4*/ GIMT_Encode4(299), // Rule ID 7 // // CHECK-NEXT: GIM_CheckNumOperands, /*MI*/0, /*Expected*/2, // CHECK-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_FEXP2), // CHECK-NEXT: // MIs[0] DstI[dst] -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::FPR32RegClassID), +// CHECK-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::FPR32RegClassID), // CHECK-NEXT: // MIs[0] SelectClamp:src0:clamp -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, // CHECK-NEXT: GIM_CheckComplexPattern, /*MI*/0, /*Op*/1, /*Renderer*/GIMT_Encode2(0), GIMT_Encode2(GICP_gi_SelectClamp), // CHECK-NEXT: // (fexp2:{ *:[f32] } (SelectClamp:{ *:[f32] } f32:{ *:[f32] }:$src0, i1:{ *:[i1] }:$clamp)) => (FEEPLE:{ *:[f32] } FPR32:{ *:[f32] }:$src0, (FFOO:{ *:[f32] } FPR32:{ *:[f32] }:$src0), clamp:{ *:[i1] }:$clamp) // CHECK-NEXT: GIR_MakeTempReg, /*TempRegID*/0, /*TypeID*/GILLT_s32, @@ -136,93 +132,88 @@ def clamp : OperandWithDefaultOps ; // CHECK-NEXT: GIR_ComplexSubOperandRenderer, /*InsnID*/1, /*RendererID*/GIMT_Encode2(0), /*SubOperand*/0, // src0 // CHECK-NEXT: GIR_AddImm8, /*InsnID*/1, /*Imm*/0, // CHECK-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/1, -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::FEEPLE), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::FEEPLE), +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] // CHECK-NEXT: GIR_ComplexSubOperandRenderer, /*InsnID*/0, /*RendererID*/GIMT_Encode2(0), /*SubOperand*/0, // src0 // CHECK-NEXT: GIR_AddSimpleTempRegister, /*InsnID*/0, /*TempRegID*/0, // CHECK-NEXT: GIR_ComplexSubOperandRenderer, /*InsnID*/0, /*RendererID*/GIMT_Encode2(0), /*SubOperand*/1, // clamp -// CHECK-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// CHECK-NEXT: GIR_RootConstrainSelectedInstOperands, // CHECK-NEXT: // GIR_Coverage, 7, -// CHECK-NEXT: GIR_Done, -// CHECK-NEXT: // Label 4: @345 -// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 5*/ GIMT_Encode4(400), // Rule ID 0 // +// CHECK-NEXT: GIR_EraseRootFromParent_Done, +// CHECK-NEXT: // Label 4: @299 +// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 5*/ GIMT_Encode4(345), // Rule ID 0 // // CHECK-NEXT: GIM_CheckNumOperands, /*MI*/0, /*Expected*/2, // CHECK-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_FSIN), // CHECK-NEXT: // MIs[0] DstI[dst] -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::FPR32RegClassID), +// CHECK-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::FPR32RegClassID), // CHECK-NEXT: // MIs[0] SelectClamp:src0:clamp -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, // CHECK-NEXT: GIM_CheckComplexPattern, /*MI*/0, /*Op*/1, /*Renderer*/GIMT_Encode2(0), GIMT_Encode2(GICP_gi_SelectClamp), // CHECK-NEXT: // (fsin:{ *:[f32] } (SelectClamp:{ *:[f32] } f32:{ *:[f32] }:$src0, i1:{ *:[i1] }:$clamp)) => (FFOO:{ *:[f32] } f32:{ *:[f32] }:$src0, i1:{ *:[i1] }:$clamp) -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::FFOO), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::FFOO), +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] // CHECK-NEXT: GIR_ComplexSubOperandRenderer, /*InsnID*/0, /*RendererID*/GIMT_Encode2(0), /*SubOperand*/0, // src0 // CHECK-NEXT: GIR_ComplexSubOperandRenderer, /*InsnID*/0, /*RendererID*/GIMT_Encode2(0), /*SubOperand*/1, // clamp -// CHECK-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// CHECK-NEXT: GIR_RootConstrainSelectedInstOperands, // CHECK-NEXT: // GIR_Coverage, 0, -// CHECK-NEXT: GIR_Done, -// CHECK-NEXT: // Label 5: @400 -// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 6*/ GIMT_Encode4(458), // Rule ID 6 // +// CHECK-NEXT: GIR_EraseRootFromParent_Done, +// CHECK-NEXT: // Label 5: @345 +// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 6*/ GIMT_Encode4(394), // Rule ID 6 // // CHECK-NEXT: GIM_CheckNumOperands, /*MI*/0, /*Expected*/2, // CHECK-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_FSQRT), // CHECK-NEXT: // MIs[0] DstI[dst] -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::FPR32RegClassID), +// CHECK-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::FPR32RegClassID), // CHECK-NEXT: // MIs[0] SelectClamp:src0:clamp -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, // CHECK-NEXT: GIM_CheckComplexPattern, /*MI*/0, /*Op*/1, /*Renderer*/GIMT_Encode2(0), GIMT_Encode2(GICP_gi_SelectClamp), // CHECK-NEXT: // (fsqrt:{ *:[f32] } (SelectClamp:{ *:[f32] } f32:{ *:[f32] }:$src0, i1:{ *:[i1] }:$clamp)) => (FLAMP:{ *:[f32] } FPR32:{ *:[f32] }:$src0, 93:{ *:[i32] }, clamp:{ *:[i1] }:$clamp) -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::FLAMP), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::FLAMP), +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] // CHECK-NEXT: GIR_ComplexSubOperandRenderer, /*InsnID*/0, /*RendererID*/GIMT_Encode2(0), /*SubOperand*/0, // src0 // CHECK-NEXT: GIR_AddImm8, /*InsnID*/0, /*Imm*/93, // CHECK-NEXT: GIR_ComplexSubOperandRenderer, /*InsnID*/0, /*RendererID*/GIMT_Encode2(0), /*SubOperand*/1, // clamp -// CHECK-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// CHECK-NEXT: GIR_RootConstrainSelectedInstOperands, // CHECK-NEXT: // GIR_Coverage, 6, -// CHECK-NEXT: GIR_Done, -// CHECK-NEXT: // Label 6: @458 -// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 7*/ GIMT_Encode4(503), // Rule ID 1 // +// CHECK-NEXT: GIR_EraseRootFromParent_Done, +// CHECK-NEXT: // Label 6: @394 +// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 7*/ GIMT_Encode4(428), // Rule ID 1 // // CHECK-NEXT: GIM_CheckNumOperands, /*MI*/0, /*Expected*/2, // CHECK-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_INTRINSIC_ROUND), // CHECK-NEXT: // MIs[0] DstI[dst] -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::FPR32RegClassID), +// CHECK-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::FPR32RegClassID), // CHECK-NEXT: // MIs[0] src0 -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, // CHECK-NEXT: // (fround:{ *:[f32] } f32:{ *:[f32] }:$src0) => (FBAR:{ *:[f32] } f32:{ *:[f32] }:$src0) -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::FBAR), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/1, // src0 +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::FBAR), +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/1, // src0 // CHECK-NEXT: GIR_AddImm8, /*InsnID*/0, /*Imm*/0, -// CHECK-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// CHECK-NEXT: GIR_RootConstrainSelectedInstOperands, // CHECK-NEXT: // GIR_Coverage, 1, -// CHECK-NEXT: GIR_Done, -// CHECK-NEXT: // Label 7: @503 -// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 8*/ GIMT_Encode4(548), // Rule ID 4 // +// CHECK-NEXT: GIR_EraseRootFromParent_Done, +// CHECK-NEXT: // Label 7: @428 +// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 8*/ GIMT_Encode4(462), // Rule ID 4 // // CHECK-NEXT: GIM_CheckNumOperands, /*MI*/0, /*Expected*/2, // CHECK-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_INTRINSIC_TRUNC), // CHECK-NEXT: // MIs[0] DstI[dst] -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::FPR32RegClassID), +// CHECK-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::FPR32RegClassID), // CHECK-NEXT: // MIs[0] src0 -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, // CHECK-NEXT: // (ftrunc:{ *:[f32] } f32:{ *:[f32] }:$src0) => (FFOO:{ *:[f32] } FPR32:{ *:[f32] }:$src0) -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::FFOO), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/1, // src0 +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::FFOO), +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/1, // src0 // CHECK-NEXT: GIR_AddImm8, /*InsnID*/0, /*Imm*/0, -// CHECK-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// CHECK-NEXT: GIR_RootConstrainSelectedInstOperands, // CHECK-NEXT: // GIR_Coverage, 4, -// CHECK-NEXT: GIR_Done, -// CHECK-NEXT: // Label 8: @548 +// CHECK-NEXT: GIR_EraseRootFromParent_Done, +// CHECK-NEXT: // Label 8: @462 // CHECK-NEXT: GIM_Reject, -// CHECK-NEXT: }; // Size: 549 bytes +// CHECK-NEXT: }; // Size: 463 bytes // CHECK-NEXT: return MatchTable0; // CHECK-NEXT: } diff --git a/llvm/test/TableGen/GlobalISelCombinerEmitter/builtins/match-table-eraseroot.td b/llvm/test/TableGen/GlobalISelCombinerEmitter/builtins/match-table-eraseroot.td index 25fdd887b20b50b4b41b30fd61ffa299cf9df3fa..c227737080e195eb3dc63e250e19bd654fa00543 100644 --- a/llvm/test/TableGen/GlobalISelCombinerEmitter/builtins/match-table-eraseroot.td +++ b/llvm/test/TableGen/GlobalISelCombinerEmitter/builtins/match-table-eraseroot.td @@ -19,7 +19,7 @@ def MyCombiner: GICombiner<"GenMyCombiner", [ // CHECK: const uint8_t *GenMyCombiner::getMatchTable() const { // CHECK-NEXT: constexpr static uint8_t MatchTable0[] = { -// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 0*/ GIMT_Encode4(15), // Rule ID 0 // +// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 0*/ GIMT_Encode4(13), // Rule ID 0 // // CHECK-NEXT: GIM_CheckSimplePredicate, GIMT_Encode2(GICXXPred_Simple_IsRule0Enabled), // CHECK-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_STORE), // CHECK-NEXT: // MIs[0] a @@ -27,9 +27,8 @@ def MyCombiner: GICombiner<"GenMyCombiner", [ // CHECK-NEXT: // MIs[0] b // CHECK-NEXT: // No operand predicates // CHECK-NEXT: // Combiner Rule #0: Test0 -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, -// CHECK-NEXT: GIR_Done, -// CHECK-NEXT: // Label 0: @15 +// CHECK-NEXT: GIR_EraseRootFromParent_Done, +// CHECK-NEXT: // Label 0: @13 // CHECK-NEXT: GIM_Reject, // CHECK-NEXT: }; // CHECK-NEXT: return MatchTable0; diff --git a/llvm/test/TableGen/GlobalISelCombinerEmitter/builtins/match-table-replacerreg.td b/llvm/test/TableGen/GlobalISelCombinerEmitter/builtins/match-table-replacerreg.td index ebb95ccb2104082d7ea851824d14599537c62d4c..9c9b39027f8f957524cd45a1b7974ba92c4a8c15 100644 --- a/llvm/test/TableGen/GlobalISelCombinerEmitter/builtins/match-table-replacerreg.td +++ b/llvm/test/TableGen/GlobalISelCombinerEmitter/builtins/match-table-replacerreg.td @@ -47,16 +47,15 @@ def MyCombiner: GICombiner<"GenMyCombiner", [ // CHECK-NEXT: // No operand predicates // CHECK-NEXT: // MIs[1] y // CHECK-NEXT: // No operand predicates -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/1, +// CHECK-NEXT: GIM_CheckIsSafeToFold, /*NumInsns*/1, // CHECK-NEXT: GIR_MakeTempReg, /*TempRegID*/0, /*TypeID*/GILLT_s32, // CHECK-NEXT: // Combiner Rule #1: ReplaceTemp -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(TargetOpcode::G_UNMERGE_VALUES), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // a +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(TargetOpcode::G_UNMERGE_VALUES), +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // a // CHECK-NEXT: GIR_AddTempRegister, /*InsnID*/0, /*TempRegID*/0, /*TempRegFlags*/GIMT_Encode2(RegState::Define), // CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/1, /*OpIdx*/2, // y // CHECK-NEXT: GIR_ReplaceRegWithTempReg, /*OldInsnID*/0, /*OldOpIdx*/1, /*TempRegID*/0, -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, -// CHECK-NEXT: GIR_Done, +// CHECK-NEXT: GIR_EraseRootFromParent_Done, // CHECK-NEXT: // Label 3: @[[L529]] // CHECK-NEXT: GIM_Reject, // CHECK-NEXT: // Label 1: @[[L530]] @@ -70,11 +69,10 @@ def MyCombiner: GICombiner<"GenMyCombiner", [ // CHECK-NEXT: // MIs[1] src // CHECK-NEXT: // No operand predicates // CHECK-NEXT: GIM_CheckCanReplaceReg, /*OldInsnID*/0, /*OldOpIdx*/0, /*NewInsnId*/1, /*NewOpIdx*/1, -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/1, +// CHECK-NEXT: GIM_CheckIsSafeToFold, /*NumInsns*/1, // CHECK-NEXT: // Combiner Rule #0: ReplaceMatched // CHECK-NEXT: GIR_ReplaceReg, /*OldInsnID*/0, /*OldOpIdx*/0, /*NewInsnId*/1, /*NewOpIdx*/1, -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, -// CHECK-NEXT: GIR_Done, +// CHECK-NEXT: GIR_EraseRootFromParent_Done, // CHECK-NEXT: // Label 4: @[[L561]] // CHECK-NEXT: GIM_Reject, // CHECK-NEXT: // Label 2: @[[L562]] diff --git a/llvm/test/TableGen/GlobalISelCombinerEmitter/match-table-imms.td b/llvm/test/TableGen/GlobalISelCombinerEmitter/match-table-imms.td index 6004a17d351be76017601522492bb4c054e274f8..d9a8854cd018f87c7ff623e9061dcfb3096e1581 100644 --- a/llvm/test/TableGen/GlobalISelCombinerEmitter/match-table-imms.td +++ b/llvm/test/TableGen/GlobalISelCombinerEmitter/match-table-imms.td @@ -41,31 +41,29 @@ def MyCombiner: GICombiner<"GenMyCombiner", [ // CHECK-NEXT: // Label 0: @[[L462]] // CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 4*/ GIMT_Encode4([[L492:[0-9]+]]), // Rule ID 0 // // CHECK-NEXT: GIM_CheckSimplePredicate, GIMT_Encode2(GICXXPred_Simple_IsRule0Enabled), -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, // CHECK-NEXT: // MIs[0] a // CHECK-NEXT: // No operand predicates // CHECK-NEXT: GIM_CheckConstantInt8, /*MI*/0, /*Op*/1, 0, // CHECK-NEXT: // Combiner Rule #0: InstTest0 -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(TargetOpcode::COPY), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // a +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(TargetOpcode::COPY), +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // a // CHECK-NEXT: GIR_AddImm8, /*InsnID*/0, /*Imm*/0, -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, -// CHECK-NEXT: GIR_Done, +// CHECK-NEXT: GIR_EraseRootFromParent_Done, // CHECK-NEXT: // Label 4: @[[L492]] // CHECK-NEXT: GIM_Reject, // CHECK-NEXT: // Label 1: @[[L493]] // CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 5*/ GIMT_Encode4([[L538:[0-9]+]]), // Rule ID 2 // // CHECK-NEXT: GIM_CheckSimplePredicate, GIMT_Encode2(GICXXPred_Simple_IsRule2Enabled), -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, // CHECK-NEXT: // MIs[0] a // CHECK-NEXT: // No operand predicates // CHECK-NEXT: GIM_CheckLiteralInt, /*MI*/0, /*Op*/1, GIMT_Encode8(0), // CHECK-NEXT: // Combiner Rule #2: CImmInstTest1 -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(TargetOpcode::G_CONSTANT), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // a +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(TargetOpcode::G_CONSTANT), +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // a // CHECK-NEXT: GIR_AddCImm, /*InsnID*/0, /*Type*/GILLT_s32, /*Imm*/GIMT_Encode8(42), -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, -// CHECK-NEXT: GIR_Done, +// CHECK-NEXT: GIR_EraseRootFromParent_Done, // CHECK-NEXT: // Label 5: @[[L538]] // CHECK-NEXT: GIM_Reject, // CHECK-NEXT: // Label 2: @{{[0-9]+}} @@ -78,11 +76,10 @@ def MyCombiner: GICombiner<"GenMyCombiner", [ // CHECK-NEXT: GIR_MakeTempReg, /*TempRegID*/0, /*TypeID*/GILLT_s32, // CHECK-NEXT: GIR_BuildConstant, /*TempRegID*/0, /*Val*/GIMT_Encode8(0), // CHECK-NEXT: // Combiner Rule #1: InstTest1 -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(TargetOpcode::COPY), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // a +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(TargetOpcode::COPY), +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // a // CHECK-NEXT: GIR_AddSimpleTempRegister, /*InsnID*/0, /*TempRegID*/0, -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, -// CHECK-NEXT: GIR_Done, +// CHECK-NEXT: GIR_EraseRootFromParent_Done, // CHECK-NEXT: // Label 6: @[[L578]] // CHECK-NEXT: GIM_Reject, // CHECK-NEXT: // Label 3: @[[L579]] diff --git a/llvm/test/TableGen/GlobalISelCombinerEmitter/match-table-intrinsics.td b/llvm/test/TableGen/GlobalISelCombinerEmitter/match-table-intrinsics.td index b2dd8b6684b1d3f49fda6d0ea2cb14198284253c..365d0c9fbff4940f8d54b4820bf3ac08ea58ceee 100644 --- a/llvm/test/TableGen/GlobalISelCombinerEmitter/match-table-intrinsics.td +++ b/llvm/test/TableGen/GlobalISelCombinerEmitter/match-table-intrinsics.td @@ -43,15 +43,14 @@ def MyCombiner: GICombiner<"GenMyCombiner", [ // CHECK-NEXT: GIM_CheckConstantInt8, /*MI*/0, /*Op*/2, 0, // CHECK-NEXT: GIR_MakeTempReg, /*TempRegID*/0, /*TypeID*/GILLT_s32, // CHECK-NEXT: // Combiner Rule #0: IntrinTest0 -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(TargetOpcode::G_INTRINSIC), +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(TargetOpcode::G_INTRINSIC), // CHECK-NEXT: GIR_AddTempRegister, /*InsnID*/0, /*TempRegID*/0, /*TempRegFlags*/GIMT_Encode2(RegState::Define), // CHECK-NEXT: GIR_AddIntrinsicID, /*MI*/0, GIMT_Encode2(Intrinsic::0in_1out), // CHECK-NEXT: GIR_BuildMI, /*InsnID*/1, /*Opcode*/GIMT_Encode2(TargetOpcode::G_INTRINSIC), // CHECK-NEXT: GIR_Copy, /*NewInsnID*/1, /*OldInsnID*/0, /*OpIdx*/0, // a // CHECK-NEXT: GIR_AddIntrinsicID, /*MI*/1, GIMT_Encode2(Intrinsic::1in_1out), // CHECK-NEXT: GIR_AddSimpleTempRegister, /*InsnID*/1, /*TempRegID*/0, -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, -// CHECK-NEXT: GIR_Done, +// CHECK-NEXT: GIR_EraseRootFromParent_Done, // CHECK-NEXT: // Label 3: @[[L72]] // CHECK-NEXT: GIM_Reject, // CHECK-NEXT: // Label 1: @[[L73]] @@ -65,21 +64,20 @@ def MyCombiner: GICombiner<"GenMyCombiner", [ // CHECK-NEXT: // No operand predicates // CHECK-NEXT: GIR_MakeTempReg, /*TempRegID*/0, /*TypeID*/GILLT_s32, // CHECK-NEXT: // Combiner Rule #1: SpecialIntrins -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(TargetOpcode::G_INTRINSIC_CONVERGENT), +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(TargetOpcode::G_INTRINSIC_CONVERGENT), // CHECK-NEXT: GIR_AddTempRegister, /*InsnID*/0, /*TempRegID*/0, /*TempRegFlags*/GIMT_Encode2(RegState::Define), // CHECK-NEXT: GIR_AddIntrinsicID, /*MI*/0, GIMT_Encode2(Intrinsic::convergent_1in_1out), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/2, // b +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/2, // b // CHECK-NEXT: GIR_BuildMI, /*InsnID*/1, /*Opcode*/GIMT_Encode2(TargetOpcode::G_INTRINSIC_CONVERGENT_W_SIDE_EFFECTS), // CHECK-NEXT: GIR_Copy, /*NewInsnID*/1, /*OldInsnID*/0, /*OpIdx*/0, // a // CHECK-NEXT: GIR_AddIntrinsicID, /*MI*/1, GIMT_Encode2(Intrinsic::convergent_sideeffects_1in_1out), // CHECK-NEXT: GIR_AddSimpleTempRegister, /*InsnID*/1, /*TempRegID*/0, // CHECK-NEXT: GIR_MergeMemOperands, /*InsnID*/1, /*NumInsns*/1, /*MergeInsnID's*/0, -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, -// CHECK-NEXT: GIR_Done, +// CHECK-NEXT: GIR_EraseRootFromParent_Done, // CHECK-NEXT: // Label 4: @[[L131]] // CHECK-NEXT: GIM_Reject, // CHECK-NEXT: // Label 2: @[[L132]] // CHECK-NEXT: GIM_Reject, -// CHECK-NEXT: }; // Size: 133 bytes +// CHECK-NEXT: }; // Size: 125 bytes // CHECK-NEXT: return MatchTable0; // CHECK-NEXT: } diff --git a/llvm/test/TableGen/GlobalISelCombinerEmitter/match-table-miflags.td b/llvm/test/TableGen/GlobalISelCombinerEmitter/match-table-miflags.td index 22e4d2d5d9d14b7058d08f233061ac9676f819f9..24864e8aef45690ffc48fc4b31721534ecd016da 100644 --- a/llvm/test/TableGen/GlobalISelCombinerEmitter/match-table-miflags.td +++ b/llvm/test/TableGen/GlobalISelCombinerEmitter/match-table-miflags.td @@ -17,7 +17,7 @@ def MyCombiner: GICombiner<"GenMyCombiner", [MIFlagsTest]>; // CHECK: const uint8_t *GenMyCombiner::getMatchTable() const { // CHECK-NEXT: constexpr static uint8_t MatchTable0[] = { -// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 0*/ GIMT_Encode4(68), // Rule ID 0 // +// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 0*/ GIMT_Encode4(63), // Rule ID 0 // // CHECK-NEXT: GIM_CheckSimplePredicate, GIMT_Encode2(GICXXPred_Simple_IsRule0Enabled), // CHECK-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_SEXT), // CHECK-NEXT: // MIs[0] dst @@ -29,18 +29,17 @@ def MyCombiner: GICombiner<"GenMyCombiner", [MIFlagsTest]>; // CHECK-NEXT: GIM_MIFlagsNot, /*MI*/1, GIMT_Encode4(MachineInstr::FmArcp | MachineInstr::FmNoNans), // CHECK-NEXT: // MIs[1] src // CHECK-NEXT: // No operand predicates -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/1, +// CHECK-NEXT: GIM_CheckIsSafeToFold, /*NumInsns*/1, // CHECK-NEXT: // Combiner Rule #0: MIFlagsTest -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(TargetOpcode::G_MUL), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // dst +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(TargetOpcode::G_MUL), +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // dst // CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/1, /*OpIdx*/1, // src // CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/1, /*OpIdx*/1, // src // CHECK-NEXT: GIR_CopyMIFlags, /*InsnID*/0, /*OldInsnID*/1, // CHECK-NEXT: GIR_SetMIFlags, /*InsnID*/0, GIMT_Encode4(MachineInstr::FmReassoc), // CHECK-NEXT: GIR_UnsetMIFlags, /*InsnID*/0, GIMT_Encode4(MachineInstr::FmNsz | MachineInstr::FmArcp), -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, -// CHECK-NEXT: GIR_Done, -// CHECK-NEXT: // Label 0: @68 +// CHECK-NEXT: GIR_EraseRootFromParent_Done, +// CHECK-NEXT: // Label 0: @63 // CHECK-NEXT: GIM_Reject, // CHECK-NEXT: }; // CHECK-NEXT: return MatchTable0; diff --git a/llvm/test/TableGen/GlobalISelCombinerEmitter/match-table-operand-types.td b/llvm/test/TableGen/GlobalISelCombinerEmitter/match-table-operand-types.td index 0fb63bce1d6a6ea759a80d420f001e2e6709553a..a23b54afb51252f1481f38990cc168307da313c0 100644 --- a/llvm/test/TableGen/GlobalISelCombinerEmitter/match-table-operand-types.td +++ b/llvm/test/TableGen/GlobalISelCombinerEmitter/match-table-operand-types.td @@ -21,32 +21,31 @@ def MyCombiner: GICombiner<"GenMyCombiner", [ // CHECK: const uint8_t *GenMyCombiner::getMatchTable() const { // CHECK-NEXT: constexpr static uint8_t MatchTable0[] = { -// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 0*/ GIMT_Encode4(81), // Rule ID 0 // +// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 0*/ GIMT_Encode4(73), // Rule ID 0 // // CHECK-NEXT: GIM_CheckSimplePredicate, GIMT_Encode2(GICXXPred_Simple_IsRule0Enabled), // CHECK-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_MUL), -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s8, -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/2, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s8, +// CHECK-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckType, /*Op*/2, /*Type*/GILLT_s32, // CHECK-NEXT: GIM_RecordInsnIgnoreCopies, /*DefineMI*/1, /*MI*/0, /*OpIdx*/2, // MIs[1] // CHECK-NEXT: GIM_CheckOpcode, /*MI*/1, GIMT_Encode2(TargetOpcode::G_MUL), // CHECK-NEXT: GIM_CheckType, /*MI*/1, /*Op*/2, /*Type*/GILLT_s32, // CHECK-NEXT: // MIs[1] b // CHECK-NEXT: GIM_CheckIsSameOperandIgnoreCopies, /*MI*/1, /*OpIdx*/1, /*OtherMI*/0, /*OtherOpIdx*/1, -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/1, +// CHECK-NEXT: GIM_CheckIsSafeToFold, /*NumInsns*/1, // CHECK-NEXT: GIR_MakeTempReg, /*TempRegID*/0, /*TypeID*/GILLT_s64, // CHECK-NEXT: // Combiner Rule #0: InstTest0 -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(TargetOpcode::G_ADD), +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(TargetOpcode::G_ADD), // CHECK-NEXT: GIR_AddTempRegister, /*InsnID*/0, /*TempRegID*/0, /*TempRegFlags*/GIMT_Encode2(RegState::Define), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/1, // b +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/1, // b // CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/1, /*OpIdx*/2, // c // CHECK-NEXT: GIR_BuildMI, /*InsnID*/1, /*Opcode*/GIMT_Encode2(TargetOpcode::G_ADD), // CHECK-NEXT: GIR_Copy, /*NewInsnID*/1, /*OldInsnID*/0, /*OpIdx*/0, // a // CHECK-NEXT: GIR_Copy, /*NewInsnID*/1, /*OldInsnID*/0, /*OpIdx*/1, // b // CHECK-NEXT: GIR_AddSimpleTempRegister, /*InsnID*/1, /*TempRegID*/0, -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, -// CHECK-NEXT: GIR_Done, -// CHECK-NEXT: // Label 0: @81 +// CHECK-NEXT: GIR_EraseRootFromParent_Done, +// CHECK-NEXT: // Label 0: @73 // CHECK-NEXT: GIM_Reject, -// CHECK-NEXT: }; // Size: 82 bytes +// CHECK-NEXT: }; // Size: 74 bytes // CHECK-NEXT: return MatchTable0; // CHECK-NEXT: } diff --git a/llvm/test/TableGen/GlobalISelCombinerEmitter/match-table-patfrag-root.td b/llvm/test/TableGen/GlobalISelCombinerEmitter/match-table-patfrag-root.td index 016ab05ca01e4ea0135baa729ea81f751f6f6f13..5a8b51dfc8324a2892751ae40b2693eb5e002a7c 100644 --- a/llvm/test/TableGen/GlobalISelCombinerEmitter/match-table-patfrag-root.td +++ b/llvm/test/TableGen/GlobalISelCombinerEmitter/match-table-patfrag-root.td @@ -42,11 +42,10 @@ def MyCombiner: GICombiner<"GenMyCombiner", [ // CHECK-NEXT: GIR_MakeTempReg, /*TempRegID*/0, /*TypeID*/GILLT_s32, // CHECK-NEXT: GIR_BuildConstant, /*TempRegID*/0, /*Val*/GIMT_Encode8(0), // CHECK-NEXT: // Combiner Rule #0: Test0 @ [__Test0_match_0[1]] -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(TargetOpcode::COPY), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // root +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(TargetOpcode::COPY), +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // root // CHECK-NEXT: GIR_AddSimpleTempRegister, /*InsnID*/0, /*TempRegID*/0, -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, -// CHECK-NEXT: GIR_Done, +// CHECK-NEXT: GIR_EraseRootFromParent_Done, // CHECK-NEXT: // Label 4: @[[L297]] // CHECK-NEXT: GIM_Reject, // CHECK-NEXT: // Label 1: @[[L298]] @@ -59,15 +58,14 @@ def MyCombiner: GICombiner<"GenMyCombiner", [ // CHECK-NEXT: GIM_CheckOpcode, /*MI*/1, GIMT_Encode2(TargetOpcode::G_TRUNC), // CHECK-NEXT: // MIs[1] __Test0_match_0.x // CHECK-NEXT: // No operand predicates -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/1, +// CHECK-NEXT: GIM_CheckIsSafeToFold, /*NumInsns*/1, // CHECK-NEXT: GIR_MakeTempReg, /*TempRegID*/0, /*TypeID*/GILLT_s32, // CHECK-NEXT: GIR_BuildConstant, /*TempRegID*/0, /*Val*/GIMT_Encode8(0), // CHECK-NEXT: // Combiner Rule #0: Test0 @ [__Test0_match_0[0]] -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(TargetOpcode::COPY), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // root +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(TargetOpcode::COPY), +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // root // CHECK-NEXT: GIR_AddSimpleTempRegister, /*InsnID*/0, /*TempRegID*/0, -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, -// CHECK-NEXT: GIR_Done, +// CHECK-NEXT: GIR_EraseRootFromParent_Done, // CHECK-NEXT: // Label 5: @[[L343]] // CHECK-NEXT: GIM_Reject, // CHECK-NEXT: // Label 2: @[[L344]] @@ -80,11 +78,10 @@ def MyCombiner: GICombiner<"GenMyCombiner", [ // CHECK-NEXT: GIR_MakeTempReg, /*TempRegID*/0, /*TypeID*/GILLT_s32, // CHECK-NEXT: GIR_BuildConstant, /*TempRegID*/0, /*Val*/GIMT_Encode8(0), // CHECK-NEXT: // Combiner Rule #0: Test0 @ [__Test0_match_0[2]] -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(TargetOpcode::COPY), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // root +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(TargetOpcode::COPY), +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // root // CHECK-NEXT: GIR_AddSimpleTempRegister, /*InsnID*/0, /*TempRegID*/0, -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, -// CHECK-NEXT: GIR_Done, +// CHECK-NEXT: GIR_EraseRootFromParent_Done, // CHECK-NEXT: // Label 6: @[[L379]] // CHECK-NEXT: GIM_Reject, // CHECK-NEXT: // Label 3: @[[L380]] diff --git a/llvm/test/TableGen/GlobalISelCombinerEmitter/match-table-permutations.td b/llvm/test/TableGen/GlobalISelCombinerEmitter/match-table-permutations.td index c38c4be9d54558533c276b19aabf7da506a14a0c..fda57d5b64e028c57673383aa699e0dd4ee04a53 100644 --- a/llvm/test/TableGen/GlobalISelCombinerEmitter/match-table-permutations.td +++ b/llvm/test/TableGen/GlobalISelCombinerEmitter/match-table-permutations.td @@ -159,9 +159,9 @@ def MyCombiner: GICombiner<"GenMyCombiner", [ // CHECK: const uint8_t *GenMyCombiner::getMatchTable() const { // CHECK-NEXT: constexpr static uint8_t MatchTable0[] = { -// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 0*/ GIMT_Encode4(850), +// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 0*/ GIMT_Encode4(738), // CHECK-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_AND), -// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 1*/ GIMT_Encode4(99), // Rule ID 7 // +// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 1*/ GIMT_Encode4(88), // Rule ID 7 // // CHECK-NEXT: GIM_CheckSimplePredicate, GIMT_Encode2(GICXXPred_Simple_IsRule0Enabled), // CHECK-NEXT: // MIs[0] dst // CHECK-NEXT: // No operand predicates @@ -186,21 +186,17 @@ def MyCombiner: GICombiner<"GenMyCombiner", [ // CHECK-NEXT: GIM_CheckCxxInsnPredicate, /*MI*/0, /*FnId*/GIMT_Encode2(GICXXPred_MI_Predicate_GICombiner21), // CHECK-NEXT: GIM_CheckCxxInsnPredicate, /*MI*/0, /*FnId*/GIMT_Encode2(GICXXPred_MI_Predicate_GICombiner22), // CHECK-NEXT: GIM_CheckCxxInsnPredicate, /*MI*/0, /*FnId*/GIMT_Encode2(GICXXPred_MI_Predicate_GICombiner23), -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/1, -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/2, -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/3, -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/4, +// CHECK-NEXT: GIM_CheckIsSafeToFold, /*NumInsns*/4, // CHECK-NEXT: GIR_MakeTempReg, /*TempRegID*/0, /*TypeID*/GILLT_s32, // CHECK-NEXT: GIR_BuildConstant, /*TempRegID*/0, /*Val*/GIMT_Encode8(0), // CHECK-NEXT: // Combiner Rule #0: Test0 @ [a[1], b[1], c[1]] -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(TargetOpcode::COPY), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // dst +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(TargetOpcode::COPY), +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // dst // CHECK-NEXT: GIR_AddSimpleTempRegister, /*InsnID*/0, /*TempRegID*/0, // CHECK-NEXT: GIR_CustomAction, GIMT_Encode2(GICXXCustomAction_CombineApplyGICombiner0), -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, -// CHECK-NEXT: GIR_Done, -// CHECK-NEXT: // Label 1: @99 -// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 2*/ GIMT_Encode4(199), // Rule ID 6 // +// CHECK-NEXT: GIR_EraseRootFromParent_Done, +// CHECK-NEXT: // Label 1: @88 +// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 2*/ GIMT_Encode4(175), // Rule ID 6 // // CHECK-NEXT: GIM_CheckSimplePredicate, GIMT_Encode2(GICXXPred_Simple_IsRule0Enabled), // CHECK-NEXT: // MIs[0] dst // CHECK-NEXT: // No operand predicates @@ -228,22 +224,17 @@ def MyCombiner: GICombiner<"GenMyCombiner", [ // CHECK-NEXT: GIM_CheckCxxInsnPredicate, /*MI*/0, /*FnId*/GIMT_Encode2(GICXXPred_MI_Predicate_GICombiner18), // CHECK-NEXT: GIM_CheckCxxInsnPredicate, /*MI*/0, /*FnId*/GIMT_Encode2(GICXXPred_MI_Predicate_GICombiner19), // CHECK-NEXT: GIM_CheckCxxInsnPredicate, /*MI*/0, /*FnId*/GIMT_Encode2(GICXXPred_MI_Predicate_GICombiner20), -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/1, -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/2, -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/3, -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/4, -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/5, +// CHECK-NEXT: GIM_CheckIsSafeToFold, /*NumInsns*/5, // CHECK-NEXT: GIR_MakeTempReg, /*TempRegID*/0, /*TypeID*/GILLT_s32, // CHECK-NEXT: GIR_BuildConstant, /*TempRegID*/0, /*Val*/GIMT_Encode8(0), // CHECK-NEXT: // Combiner Rule #0: Test0 @ [a[1], b[1], c[0]] -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(TargetOpcode::COPY), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // dst +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(TargetOpcode::COPY), +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // dst // CHECK-NEXT: GIR_AddSimpleTempRegister, /*InsnID*/0, /*TempRegID*/0, // CHECK-NEXT: GIR_CustomAction, GIMT_Encode2(GICXXCustomAction_CombineApplyGICombiner0), -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, -// CHECK-NEXT: GIR_Done, -// CHECK-NEXT: // Label 2: @199 -// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 3*/ GIMT_Encode4(299), // Rule ID 5 // +// CHECK-NEXT: GIR_EraseRootFromParent_Done, +// CHECK-NEXT: // Label 2: @175 +// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 3*/ GIMT_Encode4(262), // Rule ID 5 // // CHECK-NEXT: GIM_CheckSimplePredicate, GIMT_Encode2(GICXXPred_Simple_IsRule0Enabled), // CHECK-NEXT: // MIs[0] dst // CHECK-NEXT: // No operand predicates @@ -271,22 +262,17 @@ def MyCombiner: GICombiner<"GenMyCombiner", [ // CHECK-NEXT: GIM_CheckCxxInsnPredicate, /*MI*/0, /*FnId*/GIMT_Encode2(GICXXPred_MI_Predicate_GICombiner15), // CHECK-NEXT: GIM_CheckCxxInsnPredicate, /*MI*/0, /*FnId*/GIMT_Encode2(GICXXPred_MI_Predicate_GICombiner16), // CHECK-NEXT: GIM_CheckCxxInsnPredicate, /*MI*/0, /*FnId*/GIMT_Encode2(GICXXPred_MI_Predicate_GICombiner17), -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/1, -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/2, -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/3, -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/4, -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/5, +// CHECK-NEXT: GIM_CheckIsSafeToFold, /*NumInsns*/5, // CHECK-NEXT: GIR_MakeTempReg, /*TempRegID*/0, /*TypeID*/GILLT_s32, // CHECK-NEXT: GIR_BuildConstant, /*TempRegID*/0, /*Val*/GIMT_Encode8(0), // CHECK-NEXT: // Combiner Rule #0: Test0 @ [a[1], b[0], c[1]] -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(TargetOpcode::COPY), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // dst +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(TargetOpcode::COPY), +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // dst // CHECK-NEXT: GIR_AddSimpleTempRegister, /*InsnID*/0, /*TempRegID*/0, // CHECK-NEXT: GIR_CustomAction, GIMT_Encode2(GICXXCustomAction_CombineApplyGICombiner0), -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, -// CHECK-NEXT: GIR_Done, -// CHECK-NEXT: // Label 3: @299 -// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 4*/ GIMT_Encode4(409), // Rule ID 4 // +// CHECK-NEXT: GIR_EraseRootFromParent_Done, +// CHECK-NEXT: // Label 3: @262 +// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 4*/ GIMT_Encode4(357), // Rule ID 4 // // CHECK-NEXT: GIM_CheckSimplePredicate, GIMT_Encode2(GICXXPred_Simple_IsRule0Enabled), // CHECK-NEXT: // MIs[0] dst // CHECK-NEXT: // No operand predicates @@ -317,23 +303,17 @@ def MyCombiner: GICombiner<"GenMyCombiner", [ // CHECK-NEXT: GIM_CheckCxxInsnPredicate, /*MI*/0, /*FnId*/GIMT_Encode2(GICXXPred_MI_Predicate_GICombiner12), // CHECK-NEXT: GIM_CheckCxxInsnPredicate, /*MI*/0, /*FnId*/GIMT_Encode2(GICXXPred_MI_Predicate_GICombiner13), // CHECK-NEXT: GIM_CheckCxxInsnPredicate, /*MI*/0, /*FnId*/GIMT_Encode2(GICXXPred_MI_Predicate_GICombiner14), -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/1, -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/2, -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/3, -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/4, -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/5, -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/6, +// CHECK-NEXT: GIM_CheckIsSafeToFold, /*NumInsns*/6, // CHECK-NEXT: GIR_MakeTempReg, /*TempRegID*/0, /*TypeID*/GILLT_s32, // CHECK-NEXT: GIR_BuildConstant, /*TempRegID*/0, /*Val*/GIMT_Encode8(0), // CHECK-NEXT: // Combiner Rule #0: Test0 @ [a[1], b[0], c[0]] -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(TargetOpcode::COPY), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // dst +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(TargetOpcode::COPY), +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // dst // CHECK-NEXT: GIR_AddSimpleTempRegister, /*InsnID*/0, /*TempRegID*/0, // CHECK-NEXT: GIR_CustomAction, GIMT_Encode2(GICXXCustomAction_CombineApplyGICombiner0), -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, -// CHECK-NEXT: GIR_Done, -// CHECK-NEXT: // Label 4: @409 -// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 5*/ GIMT_Encode4(509), // Rule ID 3 // +// CHECK-NEXT: GIR_EraseRootFromParent_Done, +// CHECK-NEXT: // Label 4: @357 +// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 5*/ GIMT_Encode4(444), // Rule ID 3 // // CHECK-NEXT: GIM_CheckSimplePredicate, GIMT_Encode2(GICXXPred_Simple_IsRule0Enabled), // CHECK-NEXT: // MIs[0] dst // CHECK-NEXT: // No operand predicates @@ -361,22 +341,17 @@ def MyCombiner: GICombiner<"GenMyCombiner", [ // CHECK-NEXT: GIM_CheckCxxInsnPredicate, /*MI*/0, /*FnId*/GIMT_Encode2(GICXXPred_MI_Predicate_GICombiner9), // CHECK-NEXT: GIM_CheckCxxInsnPredicate, /*MI*/0, /*FnId*/GIMT_Encode2(GICXXPred_MI_Predicate_GICombiner10), // CHECK-NEXT: GIM_CheckCxxInsnPredicate, /*MI*/0, /*FnId*/GIMT_Encode2(GICXXPred_MI_Predicate_GICombiner11), -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/1, -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/2, -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/3, -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/4, -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/5, +// CHECK-NEXT: GIM_CheckIsSafeToFold, /*NumInsns*/5, // CHECK-NEXT: GIR_MakeTempReg, /*TempRegID*/0, /*TypeID*/GILLT_s32, // CHECK-NEXT: GIR_BuildConstant, /*TempRegID*/0, /*Val*/GIMT_Encode8(0), // CHECK-NEXT: // Combiner Rule #0: Test0 @ [a[0], b[1], c[1]] -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(TargetOpcode::COPY), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // dst +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(TargetOpcode::COPY), +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // dst // CHECK-NEXT: GIR_AddSimpleTempRegister, /*InsnID*/0, /*TempRegID*/0, // CHECK-NEXT: GIR_CustomAction, GIMT_Encode2(GICXXCustomAction_CombineApplyGICombiner0), -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, -// CHECK-NEXT: GIR_Done, -// CHECK-NEXT: // Label 5: @509 -// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 6*/ GIMT_Encode4(619), // Rule ID 2 // +// CHECK-NEXT: GIR_EraseRootFromParent_Done, +// CHECK-NEXT: // Label 5: @444 +// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 6*/ GIMT_Encode4(539), // Rule ID 2 // // CHECK-NEXT: GIM_CheckSimplePredicate, GIMT_Encode2(GICXXPred_Simple_IsRule0Enabled), // CHECK-NEXT: // MIs[0] dst // CHECK-NEXT: // No operand predicates @@ -407,23 +382,17 @@ def MyCombiner: GICombiner<"GenMyCombiner", [ // CHECK-NEXT: GIM_CheckCxxInsnPredicate, /*MI*/0, /*FnId*/GIMT_Encode2(GICXXPred_MI_Predicate_GICombiner6), // CHECK-NEXT: GIM_CheckCxxInsnPredicate, /*MI*/0, /*FnId*/GIMT_Encode2(GICXXPred_MI_Predicate_GICombiner7), // CHECK-NEXT: GIM_CheckCxxInsnPredicate, /*MI*/0, /*FnId*/GIMT_Encode2(GICXXPred_MI_Predicate_GICombiner8), -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/1, -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/2, -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/3, -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/4, -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/5, -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/6, +// CHECK-NEXT: GIM_CheckIsSafeToFold, /*NumInsns*/6, // CHECK-NEXT: GIR_MakeTempReg, /*TempRegID*/0, /*TypeID*/GILLT_s32, // CHECK-NEXT: GIR_BuildConstant, /*TempRegID*/0, /*Val*/GIMT_Encode8(0), // CHECK-NEXT: // Combiner Rule #0: Test0 @ [a[0], b[1], c[0]] -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(TargetOpcode::COPY), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // dst +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(TargetOpcode::COPY), +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // dst // CHECK-NEXT: GIR_AddSimpleTempRegister, /*InsnID*/0, /*TempRegID*/0, // CHECK-NEXT: GIR_CustomAction, GIMT_Encode2(GICXXCustomAction_CombineApplyGICombiner0), -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, -// CHECK-NEXT: GIR_Done, -// CHECK-NEXT: // Label 6: @619 -// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 7*/ GIMT_Encode4(729), // Rule ID 1 // +// CHECK-NEXT: GIR_EraseRootFromParent_Done, +// CHECK-NEXT: // Label 6: @539 +// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 7*/ GIMT_Encode4(634), // Rule ID 1 // // CHECK-NEXT: GIM_CheckSimplePredicate, GIMT_Encode2(GICXXPred_Simple_IsRule0Enabled), // CHECK-NEXT: // MIs[0] dst // CHECK-NEXT: // No operand predicates @@ -454,23 +423,17 @@ def MyCombiner: GICombiner<"GenMyCombiner", [ // CHECK-NEXT: GIM_CheckCxxInsnPredicate, /*MI*/0, /*FnId*/GIMT_Encode2(GICXXPred_MI_Predicate_GICombiner3), // CHECK-NEXT: GIM_CheckCxxInsnPredicate, /*MI*/0, /*FnId*/GIMT_Encode2(GICXXPred_MI_Predicate_GICombiner4), // CHECK-NEXT: GIM_CheckCxxInsnPredicate, /*MI*/0, /*FnId*/GIMT_Encode2(GICXXPred_MI_Predicate_GICombiner5), -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/1, -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/2, -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/3, -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/4, -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/5, -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/6, +// CHECK-NEXT: GIM_CheckIsSafeToFold, /*NumInsns*/6, // CHECK-NEXT: GIR_MakeTempReg, /*TempRegID*/0, /*TypeID*/GILLT_s32, // CHECK-NEXT: GIR_BuildConstant, /*TempRegID*/0, /*Val*/GIMT_Encode8(0), // CHECK-NEXT: // Combiner Rule #0: Test0 @ [a[0], b[0], c[1]] -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(TargetOpcode::COPY), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // dst +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(TargetOpcode::COPY), +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // dst // CHECK-NEXT: GIR_AddSimpleTempRegister, /*InsnID*/0, /*TempRegID*/0, // CHECK-NEXT: GIR_CustomAction, GIMT_Encode2(GICXXCustomAction_CombineApplyGICombiner0), -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, -// CHECK-NEXT: GIR_Done, -// CHECK-NEXT: // Label 7: @729 -// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 8*/ GIMT_Encode4(849), // Rule ID 0 // +// CHECK-NEXT: GIR_EraseRootFromParent_Done, +// CHECK-NEXT: // Label 7: @634 +// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 8*/ GIMT_Encode4(737), // Rule ID 0 // // CHECK-NEXT: GIM_CheckSimplePredicate, GIMT_Encode2(GICXXPred_Simple_IsRule0Enabled), // CHECK-NEXT: // MIs[0] dst // CHECK-NEXT: // No operand predicates @@ -504,26 +467,19 @@ def MyCombiner: GICombiner<"GenMyCombiner", [ // CHECK-NEXT: GIM_CheckCxxInsnPredicate, /*MI*/0, /*FnId*/GIMT_Encode2(GICXXPred_MI_Predicate_GICombiner0), // CHECK-NEXT: GIM_CheckCxxInsnPredicate, /*MI*/0, /*FnId*/GIMT_Encode2(GICXXPred_MI_Predicate_GICombiner1), // CHECK-NEXT: GIM_CheckCxxInsnPredicate, /*MI*/0, /*FnId*/GIMT_Encode2(GICXXPred_MI_Predicate_GICombiner2), -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/1, -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/2, -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/3, -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/4, -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/5, -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/6, -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/7, +// CHECK-NEXT: GIM_CheckIsSafeToFold, /*NumInsns*/7, // CHECK-NEXT: GIR_MakeTempReg, /*TempRegID*/0, /*TypeID*/GILLT_s32, // CHECK-NEXT: GIR_BuildConstant, /*TempRegID*/0, /*Val*/GIMT_Encode8(0), // CHECK-NEXT: // Combiner Rule #0: Test0 @ [a[0], b[0], c[0]] -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(TargetOpcode::COPY), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // dst +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(TargetOpcode::COPY), +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // dst // CHECK-NEXT: GIR_AddSimpleTempRegister, /*InsnID*/0, /*TempRegID*/0, // CHECK-NEXT: GIR_CustomAction, GIMT_Encode2(GICXXCustomAction_CombineApplyGICombiner0), -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, -// CHECK-NEXT: GIR_Done, -// CHECK-NEXT: // Label 8: @849 +// CHECK-NEXT: GIR_EraseRootFromParent_Done, +// CHECK-NEXT: // Label 8: @737 // CHECK-NEXT: GIM_Reject, -// CHECK-NEXT: // Label 0: @850 +// CHECK-NEXT: // Label 0: @738 // CHECK-NEXT: GIM_Reject, -// CHECK-NEXT: }; // Size: 851 bytes +// CHECK-NEXT: }; // Size: 739 bytes // CHECK-NEXT: return MatchTable0; // CHECK-NEXT: } diff --git a/llvm/test/TableGen/GlobalISelCombinerEmitter/match-table-temp-defs.td b/llvm/test/TableGen/GlobalISelCombinerEmitter/match-table-temp-defs.td index 4e473355e14c36c2f17f6531d4e157f40fbcc00b..9a7716e54b27ffaa60a35ca9a7a9464edd22d106 100644 --- a/llvm/test/TableGen/GlobalISelCombinerEmitter/match-table-temp-defs.td +++ b/llvm/test/TableGen/GlobalISelCombinerEmitter/match-table-temp-defs.td @@ -36,21 +36,21 @@ def MyCombiner: GICombiner<"GenMyCombiner", [ ]>; // CHECK: // Combiner Rule #0: Test0 -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(TargetOpcode::G_UDIVREM), +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(TargetOpcode::G_UDIVREM), // CHECK-NEXT: GIR_AddTempRegister, /*InsnID*/0, /*TempRegID*/0, /*TempRegFlags*/GIMT_Encode2(RegState::Define), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // dst -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/1, // lhs -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/2, // rhs +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // dst +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/1, // lhs +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/2, // rhs // CHECK: // Combiner Rule #1: Test1 -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(TargetOpcode::G_UDIVREM), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // dst +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(TargetOpcode::G_UDIVREM), +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // dst // CHECK-NEXT: GIR_AddTempRegister, /*InsnID*/0, /*TempRegID*/0, /*TempRegFlags*/GIMT_Encode2(RegState::Define), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/1, // lhs -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/2, // rhs +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/1, // lhs +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/2, // rhs // CHECK: // Combiner Rule #2: Test2 -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(TargetOpcode::G_ADD), +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(TargetOpcode::G_ADD), // CHECK-NEXT: GIR_AddTempRegister, /*InsnID*/0, /*TempRegID*/0, /*TempRegFlags*/GIMT_Encode2(RegState::Define), // CHECK-NEXT: GIR_AddSimpleTempRegister, /*InsnID*/0, /*TempRegID*/1, -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/1, // lhs +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/1, // lhs diff --git a/llvm/test/TableGen/GlobalISelCombinerEmitter/match-table-typeof.td b/llvm/test/TableGen/GlobalISelCombinerEmitter/match-table-typeof.td index ca653674d9c2569cec48c866f7850c5ec7f7cadb..7fe63b1298ae7ed4d683f00084609fda15563d81 100644 --- a/llvm/test/TableGen/GlobalISelCombinerEmitter/match-table-typeof.td +++ b/llvm/test/TableGen/GlobalISelCombinerEmitter/match-table-typeof.td @@ -16,7 +16,7 @@ def Test0 : GICombineRule< // CHECK: const uint8_t *GenMyCombiner::getMatchTable() const { // CHECK-NEXT: constexpr static uint8_t MatchTable0[] = { -// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 0*/ GIMT_Encode4(77), // Rule ID 0 // +// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 0*/ GIMT_Encode4(74), // Rule ID 0 // // CHECK-NEXT: GIM_CheckSimplePredicate, GIMT_Encode2(GICXXPred_Simple_IsRule0Enabled), // CHECK-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_MUL), // CHECK-NEXT: // MIs[0] dst @@ -29,18 +29,17 @@ def Test0 : GICombineRule< // CHECK-NEXT: GIR_BuildConstant, /*TempRegID*/1, /*Val*/GIMT_Encode8(0), // CHECK-NEXT: GIR_MakeTempReg, /*TempRegID*/0, /*TypeID*/uint8_t(-1), // CHECK-NEXT: // Combiner Rule #0: Test0 -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(TargetOpcode::G_CONSTANT), +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(TargetOpcode::G_CONSTANT), // CHECK-NEXT: GIR_AddTempRegister, /*InsnID*/0, /*TempRegID*/0, /*TempRegFlags*/GIMT_Encode2(RegState::Define), // CHECK-NEXT: GIR_AddCImm, /*InsnID*/0, /*Type*/uint8_t(-2), /*Imm*/GIMT_Encode8(42), // CHECK-NEXT: GIR_BuildMI, /*InsnID*/1, /*Opcode*/GIMT_Encode2(TargetOpcode::G_SUB), // CHECK-NEXT: GIR_Copy, /*NewInsnID*/1, /*OldInsnID*/0, /*OpIdx*/0, // dst // CHECK-NEXT: GIR_AddSimpleTempRegister, /*InsnID*/1, /*TempRegID*/1, // CHECK-NEXT: GIR_AddSimpleTempRegister, /*InsnID*/1, /*TempRegID*/0, -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, -// CHECK-NEXT: GIR_Done, -// CHECK-NEXT: // Label 0: @77 +// CHECK-NEXT: GIR_EraseRootFromParent_Done, +// CHECK-NEXT: // Label 0: @74 // CHECK-NEXT: GIM_Reject, -// CHECK-NEXT: }; // Size: 78 bytes +// CHECK-NEXT: }; // Size: 75 bytes // CHECK-NEXT: return MatchTable0; // CHECK-NEXT: } diff --git a/llvm/test/TableGen/GlobalISelCombinerEmitter/match-table.td b/llvm/test/TableGen/GlobalISelCombinerEmitter/match-table.td index 02085c1fd2666b969fb648d5d80de55e6e9700eb..1052e31b2d051e0555f3eda09516bcea980d0f03 100644 --- a/llvm/test/TableGen/GlobalISelCombinerEmitter/match-table.td +++ b/llvm/test/TableGen/GlobalISelCombinerEmitter/match-table.td @@ -154,7 +154,7 @@ def MyCombiner: GICombiner<"GenMyCombiner", [ // CHECK-NEXT: // MIs[1] c // CHECK-NEXT: // No operand predicates // CHECK-NEXT: GIM_CheckCxxInsnPredicate, /*MI*/0, /*FnId*/GIMT_Encode2(GICXXPred_MI_Predicate_GICombiner0), -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/1, +// CHECK-NEXT: GIM_CheckIsSafeToFold, /*NumInsns*/1, // CHECK-NEXT: // Combiner Rule #3: InstTest1 // CHECK-NEXT: GIR_CustomAction, GIMT_Encode2(GICXXCustomAction_CombineApplyGICombiner0), // CHECK-NEXT: GIR_Done, @@ -173,7 +173,7 @@ def MyCombiner: GICombiner<"GenMyCombiner", [ // CHECK-NEXT: // Label 1: @[[L504]] // CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 9*/ GIMT_Encode4([[L556:[0-9]+]]), // Rule ID 6 // // CHECK-NEXT: GIM_CheckSimplePredicate, GIMT_Encode2(GICXXPred_Simple_IsRule5Enabled), -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/2, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckType, /*Op*/2, /*Type*/GILLT_s32, // CHECK-NEXT: // MIs[0] dst // CHECK-NEXT: // No operand predicates // CHECK-NEXT: // MIs[0] x @@ -182,13 +182,12 @@ def MyCombiner: GICombiner<"GenMyCombiner", [ // CHECK-NEXT: // MIs[1] z // CHECK-NEXT: GIM_CheckLiteralInt, /*MI*/1, /*Op*/1, GIMT_Encode8(-42), // CHECK-NEXT: GIM_CheckConstantInt8, /*MI*/0, /*Op*/2, 43, -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/1, +// CHECK-NEXT: GIM_CheckIsSafeToFold, /*NumInsns*/1, // CHECK-NEXT: // Combiner Rule #5: InOutInstTest1 -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(TargetOpcode::G_TRUNC), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // dst +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(TargetOpcode::G_TRUNC), +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // dst // CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/1, /*OpIdx*/1, // z -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, -// CHECK-NEXT: GIR_Done, +// CHECK-NEXT: GIR_EraseRootFromParent_Done, // CHECK-NEXT: // Label 9: @[[L556]] // CHECK-NEXT: GIM_Reject, // CHECK-NEXT: // Label 2: @[[L557]] @@ -201,15 +200,14 @@ def MyCombiner: GICombiner<"GenMyCombiner", [ // CHECK-NEXT: // No operand predicates // CHECK-NEXT: // MIs[0] ptr // CHECK-NEXT: // No operand predicates -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/1, +// CHECK-NEXT: GIM_CheckIsSafeToFold, /*NumInsns*/1, // CHECK-NEXT: // Combiner Rule #4: InOutInstTest0 -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(TargetOpcode::G_STORE), +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(TargetOpcode::G_STORE), // CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/1, /*OpIdx*/1, // ext -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/1, // ptr +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/1, // ptr // CHECK-NEXT: GIR_MergeMemOperands, /*InsnID*/0, /*NumInsns*/2, /*MergeInsnID's*/0, 1, // CHECK-NEXT: GIR_CustomAction, GIMT_Encode2(GICXXCustomAction_CombineApplyGICombiner2), -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, -// CHECK-NEXT: GIR_Done, +// CHECK-NEXT: GIR_EraseRootFromParent_Done, // CHECK-NEXT: // Label 10: @[[L598]] // CHECK-NEXT: GIM_Reject, // CHECK-NEXT: // Label 3: @[[L599]] @@ -245,11 +243,10 @@ def MyCombiner: GICombiner<"GenMyCombiner", [ // CHECK-NEXT: GIR_MakeTempReg, /*TempRegID*/0, /*TypeID*/GILLT_s32, // CHECK-NEXT: GIR_BuildConstant, /*TempRegID*/0, /*Val*/GIMT_Encode8(0), // CHECK-NEXT: // Combiner Rule #6: PatFragTest0 @ [__PatFragTest0_match_1[0]] -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(TargetOpcode::COPY), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // dst +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(TargetOpcode::COPY), +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // dst // CHECK-NEXT: GIR_AddSimpleTempRegister, /*InsnID*/0, /*TempRegID*/0, -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, -// CHECK-NEXT: GIR_Done, +// CHECK-NEXT: GIR_EraseRootFromParent_Done, // CHECK-NEXT: // Label 14: @[[L676]] // CHECK-NEXT: GIM_Reject, // CHECK-NEXT: // Label 6: @[[L677]] diff --git a/llvm/test/TableGen/GlobalISelEmitter-atomic_store.td b/llvm/test/TableGen/GlobalISelEmitter-atomic_store.td index 081c9e8634592064658fb9cdbdbe1dcf996ab092..da2dfe8004289de71d2c024a28c09382bb5eb246 100644 --- a/llvm/test/TableGen/GlobalISelEmitter-atomic_store.td +++ b/llvm/test/TableGen/GlobalISelEmitter-atomic_store.td @@ -9,7 +9,7 @@ def ST_ATOM_B32 : I<(outs), (ins GPR32Op:$val, GPR32Op:$ptr), []>; // GISEL-NEXT: GIM_CheckMemorySizeEqualTo, /*MI*/0, /*MMO*/0, /*Size*/GIMT_Encode4(1), // GISEL-NEXT: GIM_CheckAtomicOrderingOrStrongerThan, /*MI*/0, /*Order*/(uint8_t)AtomicOrdering::Unordered, // GISEL-NEXT: // MIs[0] val -// GISEL-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, +// GISEL-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, // GISEL-NEXT: // MIs[0] ptr // GISEL-NEXT: GIM_CheckPointerToAny, /*MI*/0, /*Op*/1, /*SizeInBits*/0, // GISEL-NEXT: // (atomic_store i32:{ *:[i32] }:$val, iPTR:{ *:[iPTR] }:$ptr)<> => (ST_ATOM_B32 GPR32Op:{ *:[i32] }:$val, GPR32Op:{ *:[i32] }:$ptr) diff --git a/llvm/test/TableGen/GlobalISelEmitter-immAllZeroOne.td b/llvm/test/TableGen/GlobalISelEmitter-immAllZeroOne.td index eae29308aa1bdc9946ed735fbd8403509dcb56cd..0125aa5c30fa6d27f0194e58f1bad5aaf408e8ea 100644 --- a/llvm/test/TableGen/GlobalISelEmitter-immAllZeroOne.td +++ b/llvm/test/TableGen/GlobalISelEmitter-immAllZeroOne.td @@ -11,12 +11,12 @@ include "GlobalISelEmitterCommon.td" // GISEL-OPT: GIM_Try, -// GISEL-OPT: GIM_CheckType, /*MI*/0, /*Op*/2, /*Type*/GILLT_v4s16, +// GISEL-OPT: GIM_RootCheckType, /*Op*/2, /*Type*/GILLT_v4s16, // GISEL-OPT: GIM_CheckOpcodeIsEither, /*MI*/1, GIMT_Encode2(TargetOpcode::G_BUILD_VECTOR), GIMT_Encode2(TargetOpcode::G_BUILD_VECTOR_TRUNC), // GISEL-OPT: GIM_CheckIsBuildVectorAllZeros, /*MI*/1, // GISEL-OPT: GIM_Try, -// GISEL-OPT: GIM_CheckType, /*MI*/0, /*Op*/2, /*Type*/GILLT_v4s16, +// GISEL-OPT: GIM_RootCheckType, /*Op*/2, /*Type*/GILLT_v4s16, // GISEL-OPT: GIM_CheckOpcodeIsEither, /*MI*/1, GIMT_Encode2(TargetOpcode::G_BUILD_VECTOR), GIMT_Encode2(TargetOpcode::G_BUILD_VECTOR_TRUNC), // GISEL-OPT: GIM_CheckIsBuildVectorAllOnes, /*MI*/1, @@ -24,13 +24,13 @@ include "GlobalISelEmitterCommon.td" // GISEL-NOOPT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_LSHR), // GISEL-NOOPT: // MIs[0] Operand 2 -// GISEL-NOOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/2, /*Type*/GILLT_v4s16, +// GISEL-NOOPT-NEXT: GIM_RootCheckType, /*Op*/2, /*Type*/GILLT_v4s16, // GISEL-NOOPT-NEXT: GIM_RecordInsn, /*DefineMI*/1, /*MI*/0, /*OpIdx*/2, // MIs[1] // GISEL-NOOPT-NEXT: GIM_CheckOpcodeIsEither, /*MI*/1, GIMT_Encode2(TargetOpcode::G_BUILD_VECTOR), GIMT_Encode2(TargetOpcode::G_BUILD_VECTOR_TRUNC), // GISEL-NOOPT-NEXT: GIM_CheckIsBuildVectorAllOnes, /*MI*/1, // GISEL-NOOPT-NEXT: // MIs[1] Operand 0 // GISEL-NOOPT-NEXT: GIM_CheckType, /*MI*/1, /*Op*/0, /*Type*/GILLT_v4s16, -// GISEL-NOOPT-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/1, +// GISEL-NOOPT-NEXT: GIM_CheckIsSafeToFold, /*NumInsns*/1, // GISEL-NOOPT-NEXT: // (srl:{ *:[v4i32] } v4i32:{ *:[v4i32] }:$src0, immAllOnesV:{ *:[v4i16] }) => (VFOOONES:{ *:[v4i32] } v4i32:{ *:[v4i32] }:$src0) def VFOOONES : I<(outs VecReg128:$dst), (ins VecReg128:$src0), [(set v4i32:$dst, (srl v4i32:$src0, (v4i16 immAllOnesV)))] @@ -39,13 +39,13 @@ def VFOOONES : I<(outs VecReg128:$dst), (ins VecReg128:$src0), // GISEL-NOOPT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_SHL), // GISEL-NOOPT: // MIs[0] Operand 2 -// GISEL-NOOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/2, /*Type*/GILLT_v4s16, +// GISEL-NOOPT-NEXT: GIM_RootCheckType, /*Op*/2, /*Type*/GILLT_v4s16, // GISEL-NOOPT-NEXT: GIM_RecordInsn, /*DefineMI*/1, /*MI*/0, /*OpIdx*/2, // MIs[1] // GISEL-NOOPT-NEXT: GIM_CheckOpcodeIsEither, /*MI*/1, GIMT_Encode2(TargetOpcode::G_BUILD_VECTOR), GIMT_Encode2(TargetOpcode::G_BUILD_VECTOR_TRUNC), // GISEL-NOOPT-NEXT: GIM_CheckIsBuildVectorAllZeros, /*MI*/1, // GISEL-NOOPT-NEXT: // MIs[1] Operand 0 // GISEL-NOOPT-NEXT: GIM_CheckType, /*MI*/1, /*Op*/0, /*Type*/GILLT_v4s16, -// GISEL-NOOPT-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/1, +// GISEL-NOOPT-NEXT: GIM_CheckIsSafeToFold, /*NumInsns*/1, // GISEL-NOOPT-NEXT: // (shl:{ *:[v4i32] } v4i32:{ *:[v4i32] }:$src0, immAllZerosV:{ *:[v4i16] }) => (VFOOZERO:{ *:[v4i32] } v4i32:{ *:[v4i32] }:$src0) def VFOOZERO : I<(outs VecReg128:$dst), (ins VecReg128:$src0), [(set v4i32:$dst, (shl v4i32:$src0, (v4i16 immAllZerosV)))] diff --git a/llvm/test/TableGen/GlobalISelEmitter-immarg-literal-pattern.td b/llvm/test/TableGen/GlobalISelEmitter-immarg-literal-pattern.td index bfbeee466b1cc3723debec76fb39d1d8155139db..6b4012eb736cb35849db4d3d808a743b532921d2 100644 --- a/llvm/test/TableGen/GlobalISelEmitter-immarg-literal-pattern.td +++ b/llvm/test/TableGen/GlobalISelEmitter-immarg-literal-pattern.td @@ -43,7 +43,7 @@ def : Pat< // Check a non-intrinsic instruction with an immediate parameter. // GISEL: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(MyTarget::G_TGT_CAT), -// GISEL: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, +// GISEL: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, // GISEL-NEXT: // MIs[0] Operand 2 // GISEL-NEXT: GIM_CheckLiteralInt, /*MI*/0, /*Op*/2, GIMT_Encode8(0), def : Pat< @@ -52,7 +52,7 @@ def : Pat< >; // GISEL: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(MyTarget::G_TGT_CAT), -// GISEL: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, +// GISEL: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, // GISEL-NEXT: // MIs[0] Operand 2 // GISEL-NEXT: GIM_CheckLiteralInt, /*MI*/0, /*Op*/2, GIMT_Encode8(93), def : Pat< diff --git a/llvm/test/TableGen/GlobalISelEmitter-input-discard.td b/llvm/test/TableGen/GlobalISelEmitter-input-discard.td index 8d3c6cb180aea16c56e075d8167978329b6213c0..202ff4a5758d7f95669461b49c21af251a7f5fff 100644 --- a/llvm/test/TableGen/GlobalISelEmitter-input-discard.td +++ b/llvm/test/TableGen/GlobalISelEmitter-input-discard.td @@ -11,21 +11,22 @@ def FOO : I<(outs GPR32:$dst), (ins GPR32Op:$src0, GPR32Op:$src1), []>; // GISEL: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_INTRINSIC_W_SIDE_EFFECTS), // GISEL-NEXT: GIM_CheckNumOperands, /*MI*/0, /*Expected*/4, // GISEL-NEXT: GIM_CheckIntrinsicID, /*MI*/0, /*Op*/1, GIMT_Encode2(Intrinsic::tgt_foo), -// GISEL-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// GISEL-NEXT: GIM_CheckType, /*MI*/0, /*Op*/2, /*Type*/GILLT_s32, -// GISEL-NEXT: GIM_CheckType, /*MI*/0, /*Op*/3, /*Type*/GILLT_s32, -// GISEL-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// GISEL-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// GISEL-NEXT: GIM_RootCheckType, /*Op*/2, /*Type*/GILLT_s32, +// GISEL-NEXT: GIM_RootCheckType, /*Op*/3, /*Type*/GILLT_s32, +// GISEL-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // GISEL-NEXT: // (intrinsic_w_chain:{ *:[i32] } {{[0-9]+}}:{ *:[iPTR] }, srcvalue:{ *:[i32] }, i32:{ *:[i32] }:$src1) => (FOO:{ *:[i32] } (IMPLICIT_DEF:{ *:[i32] }), GPR32:{ *:[i32] }:$src1) // GISEL-NEXT: GIR_MakeTempReg, /*TempRegID*/0, /*TypeID*/GILLT_s32, // GISEL-NEXT: GIR_BuildMI, /*InsnID*/1, /*Opcode*/GIMT_Encode2(TargetOpcode::IMPLICIT_DEF), // GISEL-NEXT: GIR_AddTempRegister, /*InsnID*/1, /*TempRegID*/0, /*TempRegFlags*/GIMT_Encode2(RegState::Define), // GISEL-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/1, -// GISEL-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::FOO), -// GISEL-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] +// GISEL-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::FOO), +// GISEL-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] // GISEL-NEXT: GIR_AddSimpleTempRegister, /*InsnID*/0, /*TempRegID*/0, -// GISEL-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/3, // src1 -// GISEL-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, -// GISEL-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// GISEL-NEXT: GIR_RootToRootCopy, /*OpIdx*/3, // src1 +// GISEL-NEXT: GIR_RootConstrainSelectedInstOperands, +// GISEL-NEXT: // GIR_Coverage +// GISEL-NEXT: GIR_EraseRootFromParent_Done, def : Pat < (int_tgt_foo (i32 srcvalue), i32:$src1), (FOO (IMPLICIT_DEF), GPR32:$src1) diff --git a/llvm/test/TableGen/GlobalISelEmitter-multiple-output-discard.td b/llvm/test/TableGen/GlobalISelEmitter-multiple-output-discard.td index 70991ea3b69c07fda638fb2aa9a01ad384bcbe5e..2d968bebbc65e05476456ee33db74d6fc5149021 100644 --- a/llvm/test/TableGen/GlobalISelEmitter-multiple-output-discard.td +++ b/llvm/test/TableGen/GlobalISelEmitter-multiple-output-discard.td @@ -23,20 +23,21 @@ def : Pat<(two_out GPR32:$val), (THREE_OUTS GPR32:$val)>; // CHECK: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(MyTarget::G_TWO_OUT), // CHECK-NEXT: // MIs[0] DstI[out1] -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// CHECK-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // CHECK-NEXT: // MIs[0] DstI[out2] -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// CHECK-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // CHECK-NEXT: // MIs[0] val -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/2, /*Type*/GILLT_s32, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/2, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// CHECK-NEXT: GIM_RootCheckType, /*Op*/2, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/2, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // CHECK-NEXT: // (two_out:{ *:[i32] }:{ *:[i32] } GPR32:{ *:[i32] }:$val) => (THREE_OUTS:{ *:[i32] }:{ *:[i32] }:{ *:[i32] } GPR32:{ *:[i32] }:$val) // CHECK-NEXT: GIR_MakeTempReg, /*TempRegID*/0, /*TypeID*/GILLT_s32, -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::THREE_OUTS), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[out1] -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/1, // DstI[out2] +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::THREE_OUTS), +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[out1] +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/1, // DstI[out2] // CHECK-NEXT: GIR_AddTempRegister, /*InsnID*/0, /*TempRegID*/0, /*TempRegFlags*/GIMT_Encode2(RegState::Define|RegState::Dead), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/2, // val -// CHECK-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/2, // val +// CHECK-NEXT: GIR_RootConstrainSelectedInstOperands, +// CHECK-NEXT: // GIR_Coverage +// CHECK-NEXT: GIR_EraseRootFromParent_Done, diff --git a/llvm/test/TableGen/GlobalISelEmitter-multiple-output.td b/llvm/test/TableGen/GlobalISelEmitter-multiple-output.td index 94c9f60eabd3bce7c86ae68a65a54e9e45fa3e50..dea3b54960717050efe42a96432e7ca20f84ac30 100644 --- a/llvm/test/TableGen/GlobalISelEmitter-multiple-output.td +++ b/llvm/test/TableGen/GlobalISelEmitter-multiple-output.td @@ -32,20 +32,20 @@ def : Pat<(loadpost (p0 GPR32:$addr), (i32 GPR32:$off)), // CHECK: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(MyTarget::G_POST_LOAD), // CHECK-NEXT: // MIs[0] DstI[val] -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// CHECK-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // CHECK-NEXT: // MIs[0] DstI[ptr_out] -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_p0s32, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// CHECK-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_p0s32, +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // CHECK-NEXT: // MIs[0] addr -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/2, /*Type*/GILLT_p0s32, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/2, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// CHECK-NEXT: GIM_RootCheckType, /*Op*/2, /*Type*/GILLT_p0s32, +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/2, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // CHECK-NEXT: // MIs[0] off -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/3, /*Type*/GILLT_s32, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/3, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// CHECK-NEXT: GIM_RootCheckType, /*Op*/3, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/3, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // CHECK-NEXT: // (loadpost:{ *:[i32] }:{ *:[i32] } GPR32:{ *:[i32] }:$addr, GPR32:{ *:[i32] }:$off) => (LDPost:{ *:[i32] }:{ *:[i32] } GPR32:{ *:[i32] }:$addr, GPR32:{ *:[i32] }:$off) // CHECK-NEXT: GIR_MutateOpcode, /*InsnID*/0, /*RecycleInsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::LDPost), -// CHECK-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, +// CHECK-NEXT: GIR_RootConstrainSelectedInstOperands, //----------------------------------------------------------------------------- // Test where a whole new MIR instruction is created during ISel @@ -67,25 +67,26 @@ def : Pat<(two_in GPR32:$i1, GPR32:$i2), (TWO_INS GPR32:$i2, GPR32:$i1)>; // CHECK: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(MyTarget::G_TWO_IN), // CHECK-NEXT: // MIs[0] DstI[out1] -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// CHECK-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // CHECK-NEXT: // MIs[0] DstI[out2] -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// CHECK-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // CHECK-NEXT: // MIs[0] i1 -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/2, /*Type*/GILLT_s32, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/2, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// CHECK-NEXT: GIM_RootCheckType, /*Op*/2, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/2, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // CHECK-NEXT: // MIs[0] i2 -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/3, /*Type*/GILLT_s32, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/3, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// CHECK-NEXT: GIM_RootCheckType, /*Op*/3, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/3, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // CHECK-NEXT: // (two_in:{ *:[i32] }:{ *:[i32] } GPR32:{ *:[i32] }:$i1, GPR32:{ *:[i32] }:$i2) => (TWO_INS:{ *:[i32] }:{ *:[i32] } GPR32:{ *:[i32] }:$i2, GPR32:{ *:[i32] }:$i1) -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::TWO_INS), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[out1] -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/1, // DstI[out2] -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/3, // i2 -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/2, // i1 -// CHECK-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::TWO_INS), +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[out1] +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/1, // DstI[out2] +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/3, // i2 +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/2, // i1 +// CHECK-NEXT: GIR_RootConstrainSelectedInstOperands, +// CHECK-NEXT: // GIR_Coverage +// CHECK-NEXT: GIR_EraseRootFromParent_Done, //----------------------------------------------------------------------------- // Test where implicit defs are added using Defs. @@ -99,10 +100,10 @@ def : Pat<(i32 (add i32:$src, i32:$src)), // CHECK: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_ADD), // CHECK-NEXT: // MIs[0] DstI[dst] -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// CHECK-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // CHECK-NEXT: // MIs[0] src -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, // CHECK-NEXT: // MIs[0] src // CHECK-NEXT: GIM_CheckIsSameOperand, /*MI*/0, /*OpIdx*/2, /*OtherMI*/0, /*OtherOpIdx*/1, // CHECK-NEXT: // (add:{ *:[i32] } i32:{ *:[i32] }:$src, i32:{ *:[i32] }:$src) => (OtherInstr:{ *:[i32] } (ImplicitDefInstr:{ *:[i32] }:{ *:[i32] } GPR32:{ *:[i32] }:$src)) @@ -112,21 +113,22 @@ def : Pat<(i32 (add i32:$src, i32:$src)), // CHECK-NEXT: GIR_Copy, /*NewInsnID*/1, /*OldInsnID*/0, /*OpIdx*/1, // src // CHECK-NEXT: GIR_SetImplicitDefDead, /*InsnID*/1, /*OpIdx for MyTarget::R0*/0, // CHECK-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/1, -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::OtherInstr), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::OtherInstr), +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] // CHECK-NEXT: GIR_AddSimpleTempRegister, /*InsnID*/0, /*TempRegID*/0, -// CHECK-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// CHECK-NEXT: GIR_RootConstrainSelectedInstOperands, +// CHECK-NEXT: // GIR_Coverage +// CHECK-NEXT: GIR_EraseRootFromParent_Done, //----------------------------------------------------------------------------- // Test when the inner instruction in the output pattern has two outs // CHECK: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_ADD), // CHECK-NEXT: // MIs[0] DstI[dst] -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// CHECK-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // CHECK-NEXT: // MIs[0] src -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, // CHECK-NEXT: // MIs[0] src // CHECK-NEXT: GIM_CheckIsSameOperand, /*MI*/0, /*OpIdx*/2, /*OtherMI*/0, /*OtherOpIdx*/1, // CHECK-NEXT: // (add:{ *:[i32] } i32:{ *:[i32] }:$src, i32:{ *:[i32] }:$src) => (OtherInstr:{ *:[i32] } (TwoOutsInstr:{ *:[i32] }:{ *:[i32] } GPR32:{ *:[i32] }:$src)) @@ -137,11 +139,12 @@ def : Pat<(i32 (add i32:$src, i32:$src)), // CHECK-NEXT: GIR_AddTempRegister, /*InsnID*/1, /*TempRegID*/1, /*TempRegFlags*/GIMT_Encode2(RegState::Define|RegState::Dead), // CHECK-NEXT: GIR_Copy, /*NewInsnID*/1, /*OldInsnID*/0, /*OpIdx*/1, // src // CHECK-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/1, -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::OtherInstr), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::OtherInstr), +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] // CHECK-NEXT: GIR_AddSimpleTempRegister, /*InsnID*/0, /*TempRegID*/0, -// CHECK-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// CHECK-NEXT: GIR_RootConstrainSelectedInstOperands, +// CHECK-NEXT: // GIR_Coverage +// CHECK-NEXT: GIR_EraseRootFromParent_Done, def TwoOutsInstr : I<(outs GPR32:$out1, GPR32:$out2), (ins GPR32:$src), []>; diff --git a/llvm/test/TableGen/GlobalISelEmitter-nested-subregs.td b/llvm/test/TableGen/GlobalISelEmitter-nested-subregs.td index 234b19a146c150ff8368dc50d7506c3cc108f7d0..25a39a40da6188e06e70cf236cefa8ff1eba5bbd 100644 --- a/llvm/test/TableGen/GlobalISelEmitter-nested-subregs.td +++ b/llvm/test/TableGen/GlobalISelEmitter-nested-subregs.td @@ -33,10 +33,10 @@ def A0 : RegisterClass<"MyTarget", [i32], 32, (add a0)>; // CHECK: GIM_CheckNumOperands, /*MI*/0, /*Expected*/2, // CHECK-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_ANYEXT), // CHECK-NEXT: // MIs[0] DstI[dst] -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s16, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::A0RegClassID), +// CHECK-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s16, +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::A0RegClassID), // CHECK-NEXT: // MIs[0] src -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s8, +// CHECK-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s8, // CHECK-NEXT: // (anyext:{ *:[i16] } i8:{ *:[i8] }:$src) => (EXTRACT_SUBREG:{ *:[i16] } (INSERT_SUBREG:{ *:[i32] } (IMPLICIT_DEF:{ *:[i32] }), A0b:{ *:[i8] }:$src, lo8:{ *:[i32] }), lo16:{ *:[i32] }) // CHECK-NEXT: GIR_MakeTempReg, /*TempRegID*/0, /*TypeID*/GILLT_s32, // CHECK-NEXT: GIR_MakeTempReg, /*TempRegID*/1, /*TypeID*/GILLT_s32, @@ -51,12 +51,13 @@ def A0 : RegisterClass<"MyTarget", [i32], 32, (add a0)>; // CHECK-NEXT: GIR_ConstrainOperandRC, /*InsnID*/1, /*Op*/0, GIMT_Encode2(MyTarget::A0RegClassID), // CHECK-NEXT: GIR_ConstrainOperandRC, /*InsnID*/1, /*Op*/1, GIMT_Encode2(MyTarget::A0RegClassID), // CHECK-NEXT: GIR_ConstrainOperandRC, /*InsnID*/1, /*Op*/2, GIMT_Encode2(MyTarget::A0bRegClassID), -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(TargetOpcode::COPY), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(TargetOpcode::COPY), +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] // CHECK-NEXT: GIR_AddTempSubRegister, /*InsnID*/0, /*TempRegID*/0, /*TempRegFlags*/GIMT_Encode2(0), GIMT_Encode2(MyTarget::lo16), // CHECK-NEXT: GIR_ConstrainOperandRC, /*InsnID*/0, /*Op*/0, GIMT_Encode2(MyTarget::A0wRegClassID), // CHECK-NEXT: GIR_ConstrainOperandRC, /*InsnID*/0, /*Op*/1, GIMT_Encode2(MyTarget::A0RegClassID), -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// CHECK-NEXT: // GIR_Coverage +// CHECK-NEXT: GIR_EraseRootFromParent_Done, def : Pat<(i16 (anyext i8:$src)), (i16 (EXTRACT_SUBREG (i32 (INSERT_SUBREG diff --git a/llvm/test/TableGen/GlobalISelEmitter-notype-output-pattern.td b/llvm/test/TableGen/GlobalISelEmitter-notype-output-pattern.td index 86a6e1651fca503946dc9d20f269789037ca9821..622d7fa1f7955ccf9d29b9d48c0284e331035241 100644 --- a/llvm/test/TableGen/GlobalISelEmitter-notype-output-pattern.td +++ b/llvm/test/TableGen/GlobalISelEmitter-notype-output-pattern.td @@ -6,11 +6,11 @@ include "GlobalISelEmitterCommon.td" // CHECK: constexpr static uint8_t MatchTable0[] = { // CHECK-NEXT: GIM_Try, // CHECK-NEXT: GIM_CheckOpcode{{.*}}GIMT_Encode2(TargetOpcode::G_ANYEXT), -// CHECK-NEXT: GIM_CheckType{{.*}}/*Type*/GILLT_s32, -// CHECK-NEXT: GIM_CheckType{{.*}}/*Type*/GILLT_s8, -// CHECK-NEXT: GIM_CheckRegBankForClass{{.*}}/*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// CHECK-NEXT: GIM_RootCheckType{{.*}}/*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckType{{.*}}/*Type*/GILLT_s8, +// CHECK-NEXT: GIM_RootCheckRegBankForClass{{.*}}/*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // CHECK-NEXT: // (anyext:{{.*}}=>{{.*}}(SELECT_I4: -// CHECK: GIR_Done, +// CHECK: GIR_EraseRootFromParent_Done, // CHECK-NEXT: // Label 0: // CHECK-NEXT: GIM_Reject, // CHECK-NEXT: }; diff --git a/llvm/test/TableGen/GlobalISelEmitter-output-discard.td b/llvm/test/TableGen/GlobalISelEmitter-output-discard.td index 30f9c5f4755550dee1edd3917ecd46a86db5c158..7a0242d9a992437ef89baa4d56f5b6fff67dfec5 100644 --- a/llvm/test/TableGen/GlobalISelEmitter-output-discard.td +++ b/llvm/test/TableGen/GlobalISelEmitter-output-discard.td @@ -8,19 +8,20 @@ def ADD_CO : I<(outs GPR32:$dst, GPR8:$flag), (ins GPR32Op:$src0, GPR32Op:$src1), []>; // GISEL: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_ADD), -// GISEL-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// GISEL-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, -// GISEL-NEXT: GIM_CheckType, /*MI*/0, /*Op*/2, /*Type*/GILLT_s32, -// GISEL-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// GISEL-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// GISEL-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, +// GISEL-NEXT: GIM_RootCheckType, /*Op*/2, /*Type*/GILLT_s32, +// GISEL-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // GISEL-NEXT: // (add:{ *:[i32] } i32:{ *:[i32] }:$src0, i32:{ *:[i32] }:$src1) => (ADD_CO:{ *:[i32] }:{ *:[i8] } GPR32:{ *:[i32] }:$src0, GPR32:{ *:[i32] }:$src1) // GISEL-NEXT: GIR_MakeTempReg, /*TempRegID*/0, /*TypeID*/GILLT_s8, -// GISEL-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::ADD_CO), -// GISEL-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] +// GISEL-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::ADD_CO), +// GISEL-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] // GISEL-NEXT: GIR_AddTempRegister, /*InsnID*/0, /*TempRegID*/0, /*TempRegFlags*/GIMT_Encode2(RegState::Define|RegState::Dead), -// GISEL-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/1, // src0 -// GISEL-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/2, // src1 -// GISEL-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, -// GISEL-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// GISEL-NEXT: GIR_RootToRootCopy, /*OpIdx*/1, // src0 +// GISEL-NEXT: GIR_RootToRootCopy, /*OpIdx*/2, // src1 +// GISEL-NEXT: GIR_RootConstrainSelectedInstOperands, +// GISEL-NEXT: // GIR_Coverage +// GISEL-NEXT: GIR_EraseRootFromParent_Done, def : Pat < (add i32:$src0, i32:$src1), (ADD_CO GPR32:$src0, GPR32:$src1) diff --git a/llvm/test/TableGen/GlobalISelEmitter-zero-reg.td b/llvm/test/TableGen/GlobalISelEmitter-zero-reg.td index dd47b905e57d1707b8829f15900bd3fc96ed2fd6..ddf02240ee1f8badf680a52a2ae016c568eb4a87 100644 --- a/llvm/test/TableGen/GlobalISelEmitter-zero-reg.td +++ b/llvm/test/TableGen/GlobalISelEmitter-zero-reg.td @@ -25,18 +25,19 @@ def INST : PredI<(outs GPR32:$dst), (ins GPR32:$src), []>; // CHECK-NEXT: GIM_CheckMemorySizeEqualToLLT, /*MI*/0, /*MMO*/0, /*OpIdx*/0, // CHECK-NEXT: GIM_CheckAtomicOrdering, /*MI*/0, /*Order*/(uint8_t)AtomicOrdering::NotAtomic, // CHECK-NEXT: // MIs[0] DstI[dst] -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// CHECK-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // CHECK-NEXT: // MIs[0] src // CHECK-NEXT: GIM_CheckPointerToAny, /*MI*/0, /*Op*/1, /*SizeInBits*/32, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // CHECK-NEXT: // (ld:{ *:[i32] } GPR32:{ *:[i32] }:$src)<><> => (INST:{ *:[i32] } GPR32:{ *:[i32] }:$src) -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::INST), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/1, // src +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::INST), +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/1, // src // CHECK-NEXT: GIR_AddRegister, /*InsnID*/0, GIMT_Encode2(MyTarget::NoRegister), /*AddRegisterRegFlags*/GIMT_Encode2(0), // CHECK-NEXT: GIR_MergeMemOperands, /*InsnID*/0, /*NumInsns*/1, /*MergeInsnID's*/0, -// CHECK-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// CHECK-NEXT: GIR_RootConstrainSelectedInstOperands, +// CHECK-NEXT: // GIR_Coverage +// CHECK-NEXT: GIR_EraseRootFromParent_Done, def : Pat<(i32 (load GPR32:$src)), (INST GPR32:$src)>; diff --git a/llvm/test/TableGen/GlobalISelEmitter.td b/llvm/test/TableGen/GlobalISelEmitter.td index 961200d9b63542de33a76ac1d21f1e25215d9f83..23b3d6f59b381e0bf9d22240102f7eae228a892c 100644 --- a/llvm/test/TableGen/GlobalISelEmitter.td +++ b/llvm/test/TableGen/GlobalISelEmitter.td @@ -237,29 +237,29 @@ def HasC : Predicate<"Subtarget->hasC()"> { let RecomputePerFunction = 1; } // R19O: // Label [[CASE_ADD_NUM]]: @[[CASE_ADD]] // R19O: // Label [[CASE_SELECT_NUM]]: @[[CASE_SELECT]] // R19O-NEXT: GIM_Try, /*On fail goto*//*Label [[GROUP_NUM:[0-9]+]]*/ GIMT_Encode4([[GROUP:[0-9]+]]), -// R19O-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// R19O-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, -// R19O-NEXT: GIM_CheckType, /*MI*/0, /*Op*/2, /*Type*/GILLT_s32, -// R19O-NEXT: GIM_CheckType, /*MI*/0, /*Op*/3, /*Type*/GILLT_s32, +// R19O-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// R19O-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, +// R19O-NEXT: GIM_RootCheckType, /*Op*/2, /*Type*/GILLT_s32, +// R19O-NEXT: GIM_RootCheckType, /*Op*/3, /*Type*/GILLT_s32, // // R19C-NEXT: GIM_Try, /*On fail goto*//*Label [[LABEL_NUM:[0-9]+]]*/ GIMT_Encode4([[LABEL:[0-9]+]]), // -// R19O-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), -// R19O-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// R19O-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// R19O-NEXT: GIM_RootCheckRegBankForClass, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // R19N-NEXT: GIM_CheckNumOperands, /*MI*/0, /*Expected*/4, // R19N-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_SELECT), // R19N-NEXT: // MIs[0] DstI[dst] -// R19N-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// R19N-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// R19N-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// R19N-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // R19N-NEXT: // MIs[0] src1 -// R19N-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, -// R19N-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// R19N-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, +// R19N-NEXT: GIM_RootCheckRegBankForClass, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // R19N-NEXT: // MIs[0] complex_rr:src2a:src2b -// R19N-NEXT: GIM_CheckType, /*MI*/0, /*Op*/2, /*Type*/GILLT_s32, +// R19N-NEXT: GIM_RootCheckType, /*Op*/2, /*Type*/GILLT_s32, // // R19N-NEXT: GIM_CheckComplexPattern, /*MI*/0, /*Op*/2, /*Renderer*/GIMT_Encode2(0), GIMT_Encode2(GICP_gi_complex_rr), // R19N-NEXT: // MIs[0] Operand 3 -// R19N-NEXT: GIM_CheckType, /*MI*/0, /*Op*/3, /*Type*/GILLT_s32, +// R19N-NEXT: GIM_RootCheckType, /*Op*/3, /*Type*/GILLT_s32, // R19C-NEXT: GIM_RecordInsn, /*DefineMI*/1, /*MI*/0, /*OpIdx*/3, // MIs[1] // R19N-NEXT: GIM_CheckNumOperands, /*MI*/1, /*Expected*/4, // R19C-NEXT: GIM_CheckOpcode, /*MI*/1, GIMT_Encode2(TargetOpcode::G_SELECT), @@ -277,7 +277,7 @@ def HasC : Predicate<"Subtarget->hasC()"> { let RecomputePerFunction = 1; } // R19N-NEXT: GIM_CheckType, /*MI*/1, /*Op*/3, /*Type*/GILLT_s32, // R19N-NEXT: GIM_CheckComplexPattern, /*MI*/1, /*Op*/3, /*Renderer*/GIMT_Encode2(2), GIMT_Encode2(GICP_gi_complex), // R19O-NEXT: GIM_CheckRegBankForClass, /*MI*/1, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), -// R19C-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/1, +// R19C-NEXT: GIM_CheckIsSafeToFold, /*NumInsns*/1, // R19O-NEXT: GIM_CheckComplexPattern, /*MI*/0, /*Op*/2, /*Renderer*/GIMT_Encode2(0), GIMT_Encode2(GICP_gi_complex_rr), // R19O-NEXT: GIM_CheckComplexPattern, /*MI*/1, /*Op*/2, /*Renderer*/GIMT_Encode2(1), GIMT_Encode2(GICP_gi_complex), // R19O-NEXT: GIM_CheckComplexPattern, /*MI*/1, /*Op*/3, /*Renderer*/GIMT_Encode2(2), GIMT_Encode2(GICP_gi_complex), @@ -290,16 +290,15 @@ def HasC : Predicate<"Subtarget->hasC()"> { let RecomputePerFunction = 1; } // R19C-NEXT: GIR_ComplexSubOperandRenderer, /*InsnID*/1, /*RendererID*/GIMT_Encode2(2), /*SubOperand*/0, // src5a // R19C-NEXT: GIR_ComplexSubOperandRenderer, /*InsnID*/1, /*RendererID*/GIMT_Encode2(2), /*SubOperand*/1, // src5b // R19C-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/1, -// R19C-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::INSN3), -// R19C-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] -// R19C-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/1, // src1 +// R19C-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::INSN3), +// R19C-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] +// R19C-NEXT: GIR_RootToRootCopy, /*OpIdx*/1, // src1 // R19C-NEXT: GIR_ComplexSubOperandRenderer, /*InsnID*/0, /*RendererID*/GIMT_Encode2(0), /*SubOperand*/1, // src2b // R19C-NEXT: GIR_ComplexSubOperandRenderer, /*InsnID*/0, /*RendererID*/GIMT_Encode2(0), /*SubOperand*/0, // src2a // R19C-NEXT: GIR_AddSimpleTempRegister, /*InsnID*/0, /*TempRegID*/0, -// R19C-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, -// R19C-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// R19C-NEXT: GIR_RootConstrainSelectedInstOperands, // R19C-NEXT: // GIR_Coverage, 20, -// R19C-NEXT: GIR_Done, +// R19C-NEXT: GIR_EraseRootFromParent_Done, // R19C-NEXT: // Label [[LABEL_NUM]]: @[[LABEL]] // // R19O: // Label [[GROUP_NUM]]: @[[GROUP]] @@ -326,49 +325,48 @@ def : Pat<(select GPR32:$src1, (complex_rr GPR32:$src2a, GPR32:$src2b), // R21O: // Label [[CASE_ADD_NUM]]: @[[CASE_ADD]] // R21O: // Label [[CASE_SELECT_NUM]]: @[[CASE_SELECT]] // R21O-NEXT: GIM_Try, /*On fail goto*//*Label [[GROUP_NUM:[0-9]+]]*/ GIMT_Encode4([[GROUP:[0-9]+]]), -// R21O-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// R21O-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, -// R21O-NEXT: GIM_CheckType, /*MI*/0, /*Op*/2, /*Type*/GILLT_s32, -// R21O-NEXT: GIM_CheckType, /*MI*/0, /*Op*/3, /*Type*/GILLT_s32, +// R21O-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// R21O-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, +// R21O-NEXT: GIM_RootCheckType, /*Op*/2, /*Type*/GILLT_s32, +// R21O-NEXT: GIM_RootCheckType, /*Op*/3, /*Type*/GILLT_s32, // // R21C-NEXT: GIM_Try, /*On fail goto*//*Label [[PREV_NUM:[0-9]+]]*/ GIMT_Encode4([[PREV:[0-9]+]]), // Rule ID 20 // -// R21C-NOT: GIR_Done, +// R21C-NOT: GIR_EraseRootFromParent_Done, // R21C: // GIR_Coverage, 20, -// R21C-NEXT: GIR_Done, +// R21C-NEXT: GIR_EraseRootFromParent_Done, // R21C-NEXT: // Label [[PREV_NUM]]: @[[PREV]] // R21C-NEXT: GIM_Try, /*On fail goto*//*Label [[LABEL_NUM:[0-9]+]]*/ GIMT_Encode4([[LABEL:[0-9]+]]), // Rule ID 22 // // -// R21O-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), -// R21O-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// R21O-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// R21O-NEXT: GIM_RootCheckRegBankForClass, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // R21N-NEXT: GIM_CheckNumOperands, /*MI*/0, /*Expected*/4, // R21N-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_SELECT), // R21N-NEXT: // MIs[0] DstI[dst] -// R21N-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// R21N-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// R21N-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// R21N-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // R21N-NEXT: // MIs[0] src1 -// R21N-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, -// R21N-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// R21N-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, +// R21N-NEXT: GIM_RootCheckRegBankForClass, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // R21N-NEXT: // MIs[0] src2 -// R21N-NEXT: GIM_CheckType, /*MI*/0, /*Op*/2, /*Type*/GILLT_s32, +// R21N-NEXT: GIM_RootCheckType, /*Op*/2, /*Type*/GILLT_s32, // // R21O-NEXT: GIM_CheckCxxInsnPredicate, /*MI*/0, /*FnId*/GIMT_Encode2(GICXXPred_MI_Predicate_frag), // R21C-NEXT: GIM_CheckComplexPattern, /*MI*/0, /*Op*/2, /*Renderer*/GIMT_Encode2(0), GIMT_Encode2(GICP_gi_complex), // R21N-NEXT: // MIs[0] src3 -// R21N-NEXT: GIM_CheckType, /*MI*/0, /*Op*/3, /*Type*/GILLT_s32, +// R21N-NEXT: GIM_RootCheckType, /*Op*/3, /*Type*/GILLT_s32, // R21C-NEXT: GIM_CheckComplexPattern, /*MI*/0, /*Op*/3, /*Renderer*/GIMT_Encode2(1), GIMT_Encode2(GICP_gi_complex), // R21N-NEXT: GIM_CheckCxxInsnPredicate, /*MI*/0, /*FnId*/GIMT_Encode2(GICXXPred_MI_Predicate_frag), // R21C-NEXT: // (select:{ *:[i32] } GPR32:{ *:[i32] }:$src1, complex:{ *:[i32] }:$src2, complex:{ *:[i32] }:$src3)<> => (INSN2:{ *:[i32] } GPR32:{ *:[i32] }:$src1, complex:{ *:[i32] }:$src3, complex:{ *:[i32] }:$src2) -// R21C-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::INSN2), -// R21C-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] -// R21C-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/1, // src1 +// R21C-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::INSN2), +// R21C-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] +// R21C-NEXT: GIR_RootToRootCopy, /*OpIdx*/1, // src1 // R21C-NEXT: GIR_ComplexRenderer, /*InsnID*/0, /*RendererID*/GIMT_Encode2(1), // R21C-NEXT: GIR_ComplexRenderer, /*InsnID*/0, /*RendererID*/GIMT_Encode2(0), // R21C-NEXT: GIR_MergeMemOperands, /*InsnID*/0, /*NumInsns*/1, /*MergeInsnID's*/0 -// R21C-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, -// R21C-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// R21C-NEXT: GIR_RootConstrainSelectedInstOperands, // R21C-NEXT: // GIR_Coverage, 22, -// R21C-NEXT: GIR_Done, +// R21C-NEXT: GIR_EraseRootFromParent_Done, // R21C-NEXT: // Label [[LABEL_NUM]]: @[[LABEL]] // // R21O-NEXT: GIM_Reject, @@ -386,10 +384,10 @@ def : Pat<(select GPR32:$src1, (complex_rr GPR32:$src2a, GPR32:$src2b), // R20O: // Label [[CASE_ADD_NUM]]: @[[CASE_ADD]] // R20O: // Label [[CASE_SUB_NUM]]: @[[CASE_SUB]] // R20O-NEXT: GIM_Try, /*On fail goto*//*Label [[GROUP_NUM:[0-9]+]]*/ GIMT_Encode4([[GROUP:[0-9]+]]), -// R20O-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// R20O-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, -// R20O-NEXT: GIM_CheckType, /*MI*/0, /*Op*/2, /*Type*/GILLT_s32, -// R20O-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// R20O-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// R20O-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, +// R20O-NEXT: GIM_RootCheckType, /*Op*/2, /*Type*/GILLT_s32, +// R20O-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // // R20N: GIM_Try, /*On fail goto*//*Label [[PREV_NUM:[0-9]+]]*/ GIMT_Encode4([[PREV:[0-9]+]]), // Rule ID 22 // // R20N: // Label [[PREV_NUM]]: @[[PREV]] @@ -399,25 +397,24 @@ def : Pat<(select GPR32:$src1, (complex_rr GPR32:$src2a, GPR32:$src2b), // R20N-NEXT: GIM_CheckNumOperands, /*MI*/0, /*Expected*/3, // R20N-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_SUB), // R20N-NEXT: // MIs[0] DstI[dst] -// R20N-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// R20N-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// R20N-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// R20N-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // R20N-NEXT: // MIs[0] src1 -// R20N-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, +// R20N-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, // -// R20N-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// R20N-NEXT: GIM_RootCheckRegBankForClass, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // R20N-NEXT: // MIs[0] src2 -// R20N-NEXT: GIM_CheckType, /*MI*/0, /*Op*/2, /*Type*/GILLT_s32, -// R20O-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// R20N-NEXT: GIM_RootCheckType, /*Op*/2, /*Type*/GILLT_s32, +// R20O-NEXT: GIM_RootCheckRegBankForClass, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // R20C-NEXT: GIM_CheckComplexPattern, /*MI*/0, /*Op*/2, /*Renderer*/GIMT_Encode2(0), GIMT_Encode2(GICP_gi_complex), // R20C-NEXT: // (sub:{ *:[i32] } GPR32:{ *:[i32] }:$src1, complex:{ *:[i32] }:$src2) => (INSN1:{ *:[i32] } GPR32:{ *:[i32] }:$src1, complex:{ *:[i32] }:$src2) -// R20C-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::INSN1), -// R20C-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] -// R20C-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/1, // src1 +// R20C-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::INSN1), +// R20C-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] +// R20C-NEXT: GIR_RootToRootCopy, /*OpIdx*/1, // src1 // R20C-NEXT: GIR_ComplexRenderer, /*InsnID*/0, /*RendererID*/GIMT_Encode2(0), -// R20C-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, -// R20C-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// R20C-NEXT: GIR_RootConstrainSelectedInstOperands, // R20C-NEXT: // GIR_Coverage, 21, -// R20C-NEXT: GIR_Done, +// R20C-NEXT: GIR_EraseRootFromParent_Done, // R20C-NEXT: // Label [[LABEL_NUM]]: @[[LABEL]] // // R20O: // Label [[GROUP_NUM]]: @[[GROUP]] @@ -451,10 +448,10 @@ def : Pat<(frag GPR32:$src1, complex:$src2, complex:$src3), // R00O: // Label [[CASE_ADD_NUM]]: @[[CASE_ADD]] // R00O: // Label [[CASE_SUB_NUM]]: @[[CASE_SUB]] // R00O-NEXT: GIM_Try, /*On fail goto*//*Label [[GROUP_NUM:[0-9]+]]*/ GIMT_Encode4([[GROUP:[0-9]+]]), -// R00O-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// R00O-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, -// R00O-NEXT: GIM_CheckType, /*MI*/0, /*Op*/2, /*Type*/GILLT_s32, -// R00O-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// R00O-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// R00O-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, +// R00O-NEXT: GIM_RootCheckType, /*Op*/2, /*Type*/GILLT_s32, +// R00O-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // // R00C: GIM_Try, /*On fail goto*//*Label [[PREV_NUM:[0-9]+]]*/ GIMT_Encode4([[PREV:[0-9]+]]), // Rule ID 21 // // R00C: // Label [[PREV_NUM]]: @[[PREV]] @@ -464,10 +461,10 @@ def : Pat<(frag GPR32:$src1, complex:$src2, complex:$src3), // R00N-NEXT: GIM_CheckNumOperands, /*MI*/0, /*Expected*/3, // R00N-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_SUB), // R00N-NEXT: // MIs[0] DstI[dst] -// R00N-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// R00N-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// R00N-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// R00N-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // R00N-NEXT: // MIs[0] Operand 1 -// R00N-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, +// R00N-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, // R00C-NEXT: GIM_RecordInsn, /*DefineMI*/1, /*MI*/0, /*OpIdx*/1, // MIs[1] // R00N-NEXT: GIM_CheckNumOperands, /*MI*/1, /*Expected*/3, // R00C-NEXT: GIM_CheckOpcode, /*MI*/1, GIMT_Encode2(TargetOpcode::G_SUB), @@ -481,7 +478,7 @@ def : Pat<(frag GPR32:$src1, complex:$src2, complex:$src3), // R00N-NEXT: GIM_CheckType, /*MI*/1, /*Op*/2, /*Type*/GILLT_s32, // R00N-NEXT: GIM_CheckRegBankForClass, /*MI*/1, /*Op*/2, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // R00N-NEXT: // MIs[0] Operand 2 -// R00N-NEXT: GIM_CheckType, /*MI*/0, /*Op*/2, /*Type*/GILLT_s32, +// R00N-NEXT: GIM_RootCheckType, /*Op*/2, /*Type*/GILLT_s32, // R00O-NEXT: GIM_CheckRegBankForClass, /*MI*/1, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // R00O-NEXT: GIM_CheckRegBankForClass, /*MI*/1, /*Op*/2, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // R00C-NEXT: GIM_RecordInsn, /*DefineMI*/2, /*MI*/0, /*OpIdx*/2, // MIs[2] @@ -498,19 +495,17 @@ def : Pat<(frag GPR32:$src1, complex:$src2, complex:$src3), // R00N-NEXT: GIM_CheckRegBankForClass, /*MI*/2, /*Op*/2, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // R00O-NEXT: GIM_CheckRegBankForClass, /*MI*/2, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // R00O-NEXT: GIM_CheckRegBankForClass, /*MI*/2, /*Op*/2, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), -// R00C-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/1, -// R00C-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/2, +// R00C-NEXT: GIM_CheckIsSafeToFold, /*NumInsns*/2, // R00C-NEXT: // (sub:{ *:[i32] } (sub:{ *:[i32] } GPR32:{ *:[i32] }:$src1, GPR32:{ *:[i32] }:$src2), (sub:{ *:[i32] } GPR32:{ *:[i32] }:$src3, GPR32:{ *:[i32] }:$src4)) => (INSNBOB:{ *:[i32] } GPR32:{ *:[i32] }:$src1, GPR32:{ *:[i32] }:$src2, GPR32:{ *:[i32] }:$src3, GPR32:{ *:[i32] }:$src4) -// R00C-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::INSNBOB), -// R00C-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] +// R00C-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::INSNBOB), +// R00C-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] // R00C-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/1, /*OpIdx*/1, // src1 // R00C-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/1, /*OpIdx*/2, // src2 // R00C-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/2, /*OpIdx*/1, // src3 // R00C-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/2, /*OpIdx*/2, // src4 -// R00C-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, -// R00C-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// R00C-NEXT: GIR_RootConstrainSelectedInstOperands, // R00C-NEXT: // GIR_Coverage, 0, -// R00C-NEXT: GIR_Done, +// R00C-NEXT: GIR_EraseRootFromParent_Done, // R00C-NEXT: // Label [[LABEL_NUM]]: @[[LABEL]] // // R00O-NEXT: GIM_Reject, @@ -518,7 +513,7 @@ def : Pat<(frag GPR32:$src1, complex:$src2, complex:$src3), // R00O-NEXT: GIM_Reject, // R00O: // Label [[DEFAULT_NUM]]: @[[DEFAULT]] // R00O-NEXT: GIM_Reject, -// R00O-NEXT: }; // Size: 2027 bytes +// R00O-NEXT: }; // Size: 1804 bytes def INSNBOB : I<(outs GPR32:$dst), (ins GPR32:$src1, GPR32:$src2, GPR32:$src3, GPR32:$src4), [(set GPR32:$dst, @@ -540,28 +535,27 @@ def INSNBOB : I<(outs GPR32:$dst), (ins GPR32:$src1, GPR32:$src2, GPR32:$src3, G // R01C-NEXT: GIM_CheckNumOperands, /*MI*/0, /*Expected*/3, // // R01O-NEXT: GIM_CheckIntrinsicID, /*MI*/0, /*Op*/1, GIMT_Encode2(Intrinsic::mytarget_nop), -// R01O-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// R01O-NEXT: GIM_CheckType, /*MI*/0, /*Op*/2, /*Type*/GILLT_s32, -// R01O-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// R01O-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// R01O-NEXT: GIM_RootCheckType, /*Op*/2, /*Type*/GILLT_s32, +// R01O-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // // R01N-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_INTRINSIC), // R01N-NEXT: // MIs[0] DstI[dst] -// R01N-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// R01N-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// R01N-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// R01N-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // R01N-NEXT: // MIs[0] Operand 1 // R01N-NEXT: GIM_CheckIntrinsicID, /*MI*/0, /*Op*/1, GIMT_Encode2(Intrinsic::mytarget_nop), // R01N-NEXT: // MIs[0] src1 -// R01N-NEXT: GIM_CheckType, /*MI*/0, /*Op*/2, /*Type*/GILLT_s32, +// R01N-NEXT: GIM_RootCheckType, /*Op*/2, /*Type*/GILLT_s32, // -// R01C-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/2, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// R01C-NEXT: GIM_RootCheckRegBankForClass, /*Op*/2, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // R01C-NEXT: // (intrinsic_wo_chain:{ *:[i32] } [[ID:[0-9]+]]:{ *:[iPTR] }, GPR32:{ *:[i32] }:$src1) => (MOV:{ *:[i32] } GPR32:{ *:[i32] }:$src1) -// R01C-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::MOV), -// R01C-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] -// R01C-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/2, // src1 -// R01C-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, -// R01C-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// R01C-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::MOV), +// R01C-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] +// R01C-NEXT: GIR_RootToRootCopy, /*OpIdx*/2, // src1 +// R01C-NEXT: GIR_RootConstrainSelectedInstOperands, // R01C-NEXT: // GIR_Coverage, 1, -// R01C-NEXT: GIR_Done, +// R01C-NEXT: GIR_EraseRootFromParent_Done, // R01C-NEXT: // Label [[LABEL_NUM]]: @[[LABEL]] // // R01O-NEXT: GIM_Reject, @@ -579,11 +573,11 @@ def MOV : I<(outs GPR32:$dst), (ins GPR32:$src1), // R02O: // Label [[CASE_ADD_NUM]]: @[[CASE_ADD]] // R02O: // Label [[CASE_XOR_NUM]]: @[[CASE_XOR]] // R02O-NEXT: GIM_Try, /*On fail goto*//*Label [[GROUP_NUM:[0-9]+]]*/ GIMT_Encode4([[GROUP:[0-9]+]]), -// R02O-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// R02O-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, -// R02O-NEXT: GIM_CheckType, /*MI*/0, /*Op*/2, /*Type*/GILLT_s32, -// R02O-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), -// R02O-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// R02O-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// R02O-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, +// R02O-NEXT: GIM_RootCheckType, /*Op*/2, /*Type*/GILLT_s32, +// R02O-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// R02O-NEXT: GIM_RootCheckRegBankForClass, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // // R02N: GIM_Try, /*On fail goto*//*Label [[PREV_NUM:[0-9]+]]*/ GIMT_Encode4([[PREV:[0-9]+]]), // Rule ID 1 // // R02N: // Label [[PREV_NUM]]: @[[PREV]] @@ -593,24 +587,23 @@ def MOV : I<(outs GPR32:$dst), (ins GPR32:$src1), // R02N-NEXT: GIM_CheckNumOperands, /*MI*/0, /*Expected*/3, // R02N-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_XOR), // R02N-NEXT: // MIs[0] DstI[dst] -// R02N-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// R02N-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// R02N-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// R02N-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // R02N-NEXT: // MIs[0] src1 -// R02N-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, -// R02N-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// R02N-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, +// R02N-NEXT: GIM_RootCheckRegBankForClass, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // R02N-NEXT: // MIs[0] Operand 2 -// R02N-NEXT: GIM_CheckType, /*MI*/0, /*Op*/2, /*Type*/GILLT_s32, +// R02N-NEXT: GIM_RootCheckType, /*Op*/2, /*Type*/GILLT_s32, // // R02C-NEXT: GIM_CheckConstantInt8, /*MI*/0, /*Op*/2, uint8_t(-2) // R02C-NEXT: // (xor:{ *:[i32] } GPR32:{ *:[i32] }:$src1, -2:{ *:[i32] }) => (XORI:{ *:[i32] } GPR32:{ *:[i32] }:$src1) -// R02C-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::XORI), -// R02C-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] +// R02C-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::XORI), +// R02C-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] // R02C-NEXT: GIR_AddImm8, /*InsnID*/0, /*Imm*/uint8_t(-1), -// R02C-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/1, // src1 -// R02C-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, -// R02C-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// R02C-NEXT: GIR_RootToRootCopy, /*OpIdx*/1, // src1 +// R02C-NEXT: GIR_RootConstrainSelectedInstOperands, // R02C-NEXT: // GIR_Coverage, 2, -// R02C-NEXT: GIR_Done, +// R02C-NEXT: GIR_EraseRootFromParent_Done, // R02C-NEXT: // Label [[LABEL_NUM]]: @[[LABEL]] // // R02O: // Label [[DEFAULT_NUM]]: @[[DEFAULT]] @@ -626,23 +619,22 @@ def XORI : I<(outs GPR32:$dst), (ins m1:$src2, GPR32:$src1), // NOOPT-NEXT: GIM_CheckNumOperands, /*MI*/0, /*Expected*/3, // NOOPT-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_XOR), // NOOPT-NEXT: // MIs[0] DstI[dst] -// NOOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// NOOPT-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// NOOPT-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// NOOPT-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // NOOPT-NEXT: // MIs[0] src1 -// NOOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, -// NOOPT-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// NOOPT-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, +// NOOPT-NEXT: GIM_RootCheckRegBankForClass, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // NOOPT-NEXT: // MIs[0] Operand 2 -// NOOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/2, /*Type*/GILLT_s32, +// NOOPT-NEXT: GIM_RootCheckType, /*Op*/2, /*Type*/GILLT_s32, // NOOPT-NEXT: GIM_CheckConstantInt8, /*MI*/0, /*Op*/2, uint8_t(-3) // NOOPT-NEXT: // (xor:{ *:[i32] } GPR32:{ *:[i32] }:$src1, -3:{ *:[i32] }) => (XOR:{ *:[i32] } GPR32:{ *:[i32] }:$src1) -// NOOPT-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::XOR), -// NOOPT-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] +// NOOPT-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::XOR), +// NOOPT-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] // NOOPT-NEXT: GIR_AddRegister, /*InsnID*/0, GIMT_Encode2(MyTarget::R0), -// NOOPT-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/1, // src1 -// NOOPT-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, -// NOOPT-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// NOOPT-NEXT: GIR_RootToRootCopy, /*OpIdx*/1, // src1 +// NOOPT-NEXT: GIR_RootConstrainSelectedInstOperands, // NOOPT-NEXT: // GIR_Coverage, 3, -// NOOPT-NEXT: GIR_Done, +// NOOPT-NEXT: GIR_EraseRootFromParent_Done, // NOOPT-NEXT: // Label [[LABEL_NUM]]: @[[LABEL]] // The -3 is just to distinguish it from the 'not' case below and the other default op case above. @@ -655,24 +647,23 @@ def XOR : I<(outs GPR32:$dst), (ins Z:$src2, GPR32:$src1), // NOOPT-NEXT: GIM_CheckNumOperands, /*MI*/0, /*Expected*/3, // NOOPT-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_XOR), // NOOPT-NEXT: // MIs[0] DstI[dst] -// NOOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// NOOPT-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// NOOPT-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// NOOPT-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // NOOPT-NEXT: // MIs[0] src1 -// NOOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, -// NOOPT-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// NOOPT-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, +// NOOPT-NEXT: GIM_RootCheckRegBankForClass, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // NOOPT-NEXT: // MIs[0] Operand 2 -// NOOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/2, /*Type*/GILLT_s32, +// NOOPT-NEXT: GIM_RootCheckType, /*Op*/2, /*Type*/GILLT_s32, // NOOPT-NEXT: GIM_CheckConstantInt8, /*MI*/0, /*Op*/2, uint8_t(-4) // NOOPT-NEXT: // (xor:{ *:[i32] } GPR32:{ *:[i32] }:$src1, -4:{ *:[i32] }) => (XORlike:{ *:[i32] } GPR32:{ *:[i32] }:$src1) -// NOOPT-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::XORlike), -// NOOPT-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] +// NOOPT-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::XORlike), +// NOOPT-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] // NOOPT-NEXT: GIR_AddImm8, /*InsnID*/0, /*Imm*/uint8_t(-1), // NOOPT-NEXT: GIR_AddRegister, /*InsnID*/0, GIMT_Encode2(MyTarget::R0), -// NOOPT-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/1, // src1 -// NOOPT-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, -// NOOPT-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// NOOPT-NEXT: GIR_RootToRootCopy, /*OpIdx*/1, // src1 +// NOOPT-NEXT: GIR_RootConstrainSelectedInstOperands, // NOOPT-NEXT: // GIR_Coverage, 4, -// NOOPT-NEXT: GIR_Done, +// NOOPT-NEXT: GIR_EraseRootFromParent_Done, // NOOPT-NEXT: // Label [[LABEL_NUM]]: @[[LABEL]] // The -4 is just to distinguish it from the other 'not' cases. @@ -685,25 +676,24 @@ def XORlike : I<(outs GPR32:$dst), (ins m1Z:$src2, GPR32:$src1), // NOOPT-NEXT: GIM_CheckNumOperands, /*MI*/0, /*Expected*/3, // NOOPT-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_XOR), // NOOPT-NEXT: // MIs[0] DstI[dst] -// NOOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// NOOPT-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// NOOPT-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// NOOPT-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // NOOPT-NEXT: // MIs[0] src1 -// NOOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, -// NOOPT-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// NOOPT-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, +// NOOPT-NEXT: GIM_RootCheckRegBankForClass, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // NOOPT-NEXT: // MIs[0] Operand 2 -// NOOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/2, /*Type*/GILLT_s32, +// NOOPT-NEXT: GIM_RootCheckType, /*Op*/2, /*Type*/GILLT_s32, // NOOPT-NEXT: GIM_CheckConstantInt8, /*MI*/0, /*Op*/2, uint8_t(-5), // NOOPT-NEXT: // (xor:{ *:[i32] } GPR32:{ *:[i32] }:$src1, -5:{ *:[i32] }) => (XORManyDefaults:{ *:[i32] } GPR32:{ *:[i32] }:$src1) -// NOOPT-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::XORManyDefaults), -// NOOPT-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] +// NOOPT-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::XORManyDefaults), +// NOOPT-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] // NOOPT-NEXT: GIR_AddImm8, /*InsnID*/0, /*Imm*/uint8_t(-1), // NOOPT-NEXT: GIR_AddRegister, /*InsnID*/0, GIMT_Encode2(MyTarget::R0), // NOOPT-NEXT: GIR_AddRegister, /*InsnID*/0, GIMT_Encode2(MyTarget::R0), -// NOOPT-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/1, // src1 -// NOOPT-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, -// NOOPT-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// NOOPT-NEXT: GIR_RootToRootCopy, /*OpIdx*/1, // src1 +// NOOPT-NEXT: GIR_RootConstrainSelectedInstOperands, // NOOPT-NEXT: // GIR_Coverage, 5, -// NOOPT-NEXT: GIR_Done, +// NOOPT-NEXT: GIR_EraseRootFromParent_Done, // NOOPT-NEXT: // Label [[LABEL_NUM]]: @[[LABEL]] // The -5 is just to distinguish it from the other cases. @@ -716,23 +706,22 @@ def XORManyDefaults : I<(outs GPR32:$dst), (ins m1Z:$src3, Z:$src2, GPR32:$src1) // NOOPT-NEXT: GIM_CheckNumOperands, /*MI*/0, /*Expected*/3, // NOOPT-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_XOR), // NOOPT-NEXT: // MIs[0] DstI[dst] -// NOOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// NOOPT-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// NOOPT-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// NOOPT-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // NOOPT-NEXT: // MIs[0] src1 -// NOOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, -// NOOPT-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// NOOPT-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, +// NOOPT-NEXT: GIM_RootCheckRegBankForClass, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // NOOPT-NEXT: // MIs[0] Operand 2 -// NOOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/2, /*Type*/GILLT_s32, +// NOOPT-NEXT: GIM_RootCheckType, /*Op*/2, /*Type*/GILLT_s32, // NOOPT-NEXT: GIM_CheckConstantInt8, /*MI*/0, /*Op*/2, uint8_t(-6) // NOOPT-NEXT: // (xor:{ *:[i32] } GPR32:{ *:[i32] }:$src1, -6:{ *:[i32] }) => (XORIb:{ *:[i32] } GPR32:{ *:[i32] }:$src1) -// NOOPT-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::XORIb), -// NOOPT-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] +// NOOPT-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::XORIb), +// NOOPT-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] // NOOPT-NEXT: GIR_AddImm8, /*InsnID*/0, /*Imm*/13, -// NOOPT-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/1, // src1 -// NOOPT-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, -// NOOPT-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// NOOPT-NEXT: GIR_RootToRootCopy, /*OpIdx*/1, // src1 +// NOOPT-NEXT: GIR_RootConstrainSelectedInstOperands, // NOOPT-NEXT: // GIR_Coverage, 6, -// NOOPT-NEXT: GIR_Done, +// NOOPT-NEXT: GIR_EraseRootFromParent_Done, // NOOPT-NEXT: // Label [[LABEL_NUM]]: @[[LABEL]] // The -6 is just to distinguish it from the other cases. @@ -748,23 +737,22 @@ def XORIb : I<(outs GPR32:$dst), (ins mb:$src2, GPR32:$src1), // NOOPT-NEXT: GIM_CheckNumOperands, /*MI*/0, /*Expected*/3, // NOOPT-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_XOR), // NOOPT-NEXT: // MIs[0] DstI[dst] -// NOOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// NOOPT-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// NOOPT-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// NOOPT-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // NOOPT-NEXT: // MIs[0] Wm -// NOOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, -// NOOPT-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// NOOPT-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, +// NOOPT-NEXT: GIM_RootCheckRegBankForClass, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // NOOPT-NEXT: // MIs[0] Operand 2 -// NOOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/2, /*Type*/GILLT_s32, +// NOOPT-NEXT: GIM_RootCheckType, /*Op*/2, /*Type*/GILLT_s32, // NOOPT-NEXT: GIM_CheckConstantInt8, /*MI*/0, /*Op*/2, uint8_t(-1), // NOOPT-NEXT: // (xor:{ *:[i32] } GPR32:{ *:[i32] }:$Wm, -1:{ *:[i32] }) => (ORN:{ *:[i32] } R0:{ *:[i32] }, GPR32:{ *:[i32] }:$Wm) -// NOOPT-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::ORN), -// NOOPT-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] +// NOOPT-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::ORN), +// NOOPT-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] // NOOPT-NEXT: GIR_AddRegister, /*InsnID*/0, GIMT_Encode2(MyTarget::R0), -// NOOPT-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/1, // Wm -// NOOPT-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, -// NOOPT-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// NOOPT-NEXT: GIR_RootToRootCopy, /*OpIdx*/1, // Wm +// NOOPT-NEXT: GIR_RootConstrainSelectedInstOperands, // NOOPT-NEXT: // GIR_Coverage, 23, -// NOOPT-NEXT: GIR_Done, +// NOOPT-NEXT: GIR_EraseRootFromParent_Done, // NOOPT-NEXT: // Label [[LABEL_NUM]]: @[[LABEL]] def ORN : I<(outs GPR32:$dst), (ins GPR32:$src1, GPR32:$src2), []>; @@ -777,10 +765,10 @@ def : Pat<(not GPR32:$Wm), (ORN R0, GPR32:$Wm)>; // NOOPT-NEXT: GIM_CheckNumOperands, /*MI*/0, /*Expected*/3, // NOOPT-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_MUL), // NOOPT-NEXT: // MIs[0] DstI[dst] -// NOOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// NOOPT-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// NOOPT-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// NOOPT-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // NOOPT-NEXT: // MIs[0] Operand 1 -// NOOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, +// NOOPT-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, // NOOPT-NEXT: GIM_RecordInsn, /*DefineMI*/1, /*MI*/0, /*OpIdx*/1, // MIs[1] // NOOPT-NEXT: GIM_CheckNumOperands, /*MI*/1, /*Expected*/3, // NOOPT-NEXT: GIM_CheckOpcode, /*MI*/1, GIMT_Encode2(TargetOpcode::G_ADD), @@ -793,19 +781,18 @@ def : Pat<(not GPR32:$Wm), (ORN R0, GPR32:$Wm)>; // NOOPT-NEXT: GIM_CheckType, /*MI*/1, /*Op*/2, /*Type*/GILLT_s32, // NOOPT-NEXT: GIM_CheckRegBankForClass, /*MI*/1, /*Op*/2, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // NOOPT-NEXT: // MIs[0] src3 -// NOOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/2, /*Type*/GILLT_s32, -// NOOPT-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/2, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), -// NOOPT-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/1, +// NOOPT-NEXT: GIM_RootCheckType, /*Op*/2, /*Type*/GILLT_s32, +// NOOPT-NEXT: GIM_RootCheckRegBankForClass, /*Op*/2, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// NOOPT-NEXT: GIM_CheckIsSafeToFold, /*NumInsns*/1, // NOOPT-NEXT: // (mul:{ *:[i32] } (add:{ *:[i32] } GPR32:{ *:[i32] }:$src1, GPR32:{ *:[i32] }:$src2), GPR32:{ *:[i32] }:$src3) => (MULADD:{ *:[i32] } GPR32:{ *:[i32] }:$src1, GPR32:{ *:[i32] }:$src2, GPR32:{ *:[i32] }:$src3) -// NOOPT-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::MULADD), -// NOOPT-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] +// NOOPT-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::MULADD), +// NOOPT-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] // NOOPT-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/1, /*OpIdx*/1, // src1 // NOOPT-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/1, /*OpIdx*/2, // src2 -// NOOPT-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/2, // src3 -// NOOPT-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, -// NOOPT-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// NOOPT-NEXT: GIR_RootToRootCopy, /*OpIdx*/2, // src3 +// NOOPT-NEXT: GIR_RootConstrainSelectedInstOperands, // NOOPT-NEXT: // GIR_Coverage, 7, -// NOOPT-NEXT: GIR_Done, +// NOOPT-NEXT: GIR_EraseRootFromParent_Done, // NOOPT-NEXT: // Label [[LABEL_NUM]]: @[[LABEL]] // We also get a second rule by commutativity. @@ -815,13 +802,13 @@ def : Pat<(not GPR32:$Wm), (ORN R0, GPR32:$Wm)>; // NOOPT-NEXT: GIM_CheckNumOperands, /*MI*/0, /*Expected*/3, // NOOPT-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_MUL), // NOOPT-NEXT: // MIs[0] DstI[dst] -// NOOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// NOOPT-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// NOOPT-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// NOOPT-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // NOOPT-NEXT: // MIs[0] src3 -// NOOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, -// NOOPT-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// NOOPT-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, +// NOOPT-NEXT: GIM_RootCheckRegBankForClass, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // NOOPT-NEXT: // MIs[0] Operand 2 -// NOOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/2, /*Type*/GILLT_s32, +// NOOPT-NEXT: GIM_RootCheckType, /*Op*/2, /*Type*/GILLT_s32, // NOOPT-NEXT: GIM_RecordInsn, /*DefineMI*/1, /*MI*/0, /*OpIdx*/2, // NOOPT-NEXT: GIM_CheckNumOperands, /*MI*/1, /*Expected*/3, // NOOPT-NEXT: GIM_CheckOpcode, /*MI*/1, GIMT_Encode2(TargetOpcode::G_ADD), @@ -833,17 +820,16 @@ def : Pat<(not GPR32:$Wm), (ORN R0, GPR32:$Wm)>; // NOOPT-NEXT: // MIs[1] src2 // NOOPT-NEXT: GIM_CheckType, /*MI*/1, /*Op*/2, /*Type*/GILLT_s32, // NOOPT-NEXT: GIM_CheckRegBankForClass, /*MI*/1, /*Op*/2, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), -// NOOPT-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/1, +// NOOPT-NEXT: GIM_CheckIsSafeToFold, /*NumInsns*/1, // NOOPT-NEXT: // (mul:{ *:[i32] } GPR32:{ *:[i32] }:$src3, (add:{ *:[i32] } GPR32:{ *:[i32] }:$src1, GPR32:{ *:[i32] }:$src2)) => (MULADD:{ *:[i32] } GPR32:{ *:[i32] }:$src1, GPR32:{ *:[i32] }:$src2, GPR32:{ *:[i32] }:$src3) -// NOOPT-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::MULADD), -// NOOPT-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] +// NOOPT-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::MULADD), +// NOOPT-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] // NOOPT-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/1, /*OpIdx*/1, // src1 // NOOPT-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/1, /*OpIdx*/2, // src2 -// NOOPT-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/1, // src3 -// NOOPT-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, -// NOOPT-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// NOOPT-NEXT: GIR_RootToRootCopy, /*OpIdx*/1, // src3 +// NOOPT-NEXT: GIR_RootConstrainSelectedInstOperands, // NOOPT-NEXT: // GIR_Coverage, 28, -// NOOPT-NEXT: GIR_Done, +// NOOPT-NEXT: GIR_EraseRootFromParent_Done, // NOOPT-NEXT: // Label [[LABEL_NUM]]: @[[LABEL]] def MULADD : I<(outs GPR32:$dst), (ins GPR32:$src1, GPR32:$src2, GPR32:$src3), @@ -857,17 +843,16 @@ def MULADD : I<(outs GPR32:$dst), (ins GPR32:$src1, GPR32:$src2, GPR32:$src3), // NOOPT-NEXT: GIM_CheckNumOperands, /*MI*/0, /*Expected*/2, // NOOPT-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_CONSTANT), // NOOPT-NEXT: // MIs[0] DstI[dst] -// NOOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// NOOPT-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// NOOPT-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// NOOPT-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // NOOPT-NEXT: // MIs[0] Operand 1 // NOOPT-NEXT: GIM_CheckLiteralInt, /*MI*/0, /*Op*/1, GIMT_Encode8(1), // NOOPT-NEXT: // 1:{ *:[i32] } => (MOV1:{ *:[i32] }) -// NOOPT-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::MOV1), -// NOOPT-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] -// NOOPT-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, -// NOOPT-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// NOOPT-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::MOV1), +// NOOPT-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] +// NOOPT-NEXT: GIR_RootConstrainSelectedInstOperands, // NOOPT-NEXT: // GIR_Coverage, 8, -// NOOPT-NEXT: GIR_Done, +// NOOPT-NEXT: GIR_EraseRootFromParent_Done, // NOOPT-NEXT: // Label [[LABEL_NUM]]: @[[LABEL]] def MOV1 : I<(outs GPR32:$dst), (ins), [(set GPR32:$dst, 1)]>; @@ -879,18 +864,17 @@ def MOV1 : I<(outs GPR32:$dst), (ins), [(set GPR32:$dst, 1)]>; // NOOPT-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_CONSTANT), // NOOPT-NEXT: GIM_CheckI64ImmPredicate, /*MI*/0, /*Predicate*/GIMT_Encode2(GICXXPred_I64_Predicate_simm8), // NOOPT-NEXT: // MIs[0] DstI[dst] -// NOOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// NOOPT-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// NOOPT-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// NOOPT-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // NOOPT-NEXT: // MIs[0] Operand 1 // NOOPT-NEXT: // No operand predicates // NOOPT-NEXT: // (imm:{ *:[i32] })<>:$imm => (MOVimm8:{ *:[i32] } (imm:{ *:[i32] }):$imm) -// NOOPT-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::MOVimm8), -// NOOPT-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] +// NOOPT-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::MOVimm8), +// NOOPT-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] // NOOPT-NEXT: GIR_CopyConstantAsSImm, /*NewInsnID*/0, /*OldInsnID*/0, // imm -// NOOPT-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, -// NOOPT-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// NOOPT-NEXT: GIR_RootConstrainSelectedInstOperands, // NOOPT-NEXT: // GIR_Coverage, 9, -// NOOPT-NEXT: GIR_Done, +// NOOPT-NEXT: GIR_EraseRootFromParent_Done, // NOOPT-NEXT: // Label [[LABEL_NUM]]: @[[LABEL]] def simm8 : ImmLeaf(Imm); }]>; @@ -903,18 +887,17 @@ def MOVimm8 : I<(outs GPR32:$dst), (ins i32imm:$imm), [(set GPR32:$dst, simm8:$i // NOOPT-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_CONSTANT), // NOOPT-NEXT: GIM_CheckAPIntImmPredicate, /*MI*/0, /*Predicate*/GIMT_Encode2(GICXXPred_APInt_Predicate_simm9), // NOOPT-NEXT: // MIs[0] DstI[dst] -// NOOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// NOOPT-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// NOOPT-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// NOOPT-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // NOOPT-NEXT: // MIs[0] Operand 1 // NOOPT-NEXT: // No operand predicates // NOOPT-NEXT: // (imm:{ *:[i32] })<>:$imm => (MOVimm9:{ *:[i32] } (imm:{ *:[i32] }):$imm) -// NOOPT-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::MOVimm9), -// NOOPT-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] +// NOOPT-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::MOVimm9), +// NOOPT-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] // NOOPT-NEXT: GIR_CopyConstantAsSImm, /*NewInsnID*/0, /*OldInsnID*/0, // imm -// NOOPT-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, -// NOOPT-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// NOOPT-NEXT: GIR_RootConstrainSelectedInstOperands, // NOOPT-NEXT: // GIR_Coverage, 10, -// NOOPT-NEXT: GIR_Done, +// NOOPT-NEXT: GIR_EraseRootFromParent_Done, // NOOPT-NEXT: // Label [[LABEL_NUM]]: @[[LABEL]] def simm9 : IntImmLeaf(Imm->getSExtValue()); }]>; @@ -927,18 +910,17 @@ def MOVimm9 : I<(outs GPR32:$dst), (ins i32imm:$imm), [(set GPR32:$dst, simm9:$i // NOOPT-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_CONSTANT), // NOOPT-NEXT: GIM_CheckI64ImmPredicate, /*MI*/0, /*Predicate*/GIMT_Encode2(GICXXPred_I64_Predicate_cimm8), // NOOPT-NEXT: // MIs[0] DstI[dst] -// NOOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// NOOPT-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// NOOPT-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// NOOPT-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // NOOPT-NEXT: // MIs[0] Operand 1 // NOOPT-NEXT: // No operand predicates // NOOPT-NEXT: // (imm:{ *:[i32] })<><>:$imm => (MOVcimm8:{ *:[i32] } (cimm8_xform:{ *:[i32] } (imm:{ *:[i32] }):$imm)) -// NOOPT-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::MOVcimm8), -// NOOPT-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] +// NOOPT-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::MOVcimm8), +// NOOPT-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] // NOOPT-NEXT: GIR_CustomRenderer, /*InsnID*/0, /*OldInsnID*/0, /*Renderer*/GIMT_Encode2(GICR_renderImm), // imm -// NOOPT-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, -// NOOPT-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// NOOPT-NEXT: GIR_RootConstrainSelectedInstOperands, // NOOPT-NEXT: // GIR_Coverage, 11, -// NOOPT-NEXT: GIR_Done, +// NOOPT-NEXT: GIR_EraseRootFromParent_Done, // NOOPT-NEXT: // Label [[LABEL_NUM]]: @[[LABEL]] def MOVcimm8 : I<(outs GPR32:$dst), (ins i32imm:$imm), [(set GPR32:$dst, cimm8:$imm)]>; @@ -950,18 +932,17 @@ def MOVcimm8 : I<(outs GPR32:$dst), (ins i32imm:$imm), [(set GPR32:$dst, cimm8:$ // NOOPT-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_FCONSTANT), // NOOPT-NEXT: GIM_CheckAPFloatImmPredicate, /*MI*/0, /*Predicate*/GIMT_Encode2(GICXXPred_APFloat_Predicate_fpimmz), // NOOPT-NEXT: // MIs[0] DstI[dst] -// NOOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// NOOPT-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::FPR32RegClassID), +// NOOPT-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// NOOPT-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::FPR32RegClassID), // NOOPT-NEXT: // MIs[0] Operand 1 // NOOPT-NEXT: // No operand predicates // NOOPT-NEXT: // (fpimm:{ *:[f32] })<>:$imm => (MOVfpimmz:{ *:[f32] } (fpimm:{ *:[f32] }):$imm) -// NOOPT-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::MOVfpimmz), -// NOOPT-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] +// NOOPT-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::MOVfpimmz), +// NOOPT-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] // NOOPT-NEXT: GIR_CopyFConstantAsFPImm, /*NewInsnID*/0, /*OldInsnID*/0, // imm -// NOOPT-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, -// NOOPT-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// NOOPT-NEXT: GIR_RootConstrainSelectedInstOperands, // NOOPT-NEXT: // GIR_Coverage, 18, -// NOOPT-NEXT: GIR_Done, +// NOOPT-NEXT: GIR_EraseRootFromParent_Done, // NOOPT-NEXT: // Label [[LABEL_NUM]]: @[[LABEL]] //===- Test a simple pattern with inferred pointer operands. ---------------===// @@ -972,14 +953,14 @@ def MOVcimm8 : I<(outs GPR32:$dst), (ins i32imm:$imm), [(set GPR32:$dst, cimm8:$ // NOOPT-NEXT: GIM_CheckMemorySizeEqualToLLT, /*MI*/0, /*MMO*/0, /*OpIdx*/0, // NOOPT-NEXT: GIM_CheckAtomicOrdering, /*MI*/0, /*Order*/(uint8_t)AtomicOrdering::NotAtomic, // NOOPT-NEXT: // MIs[0] DstI[dst] -// NOOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// NOOPT-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// NOOPT-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// NOOPT-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // NOOPT-NEXT: // MIs[0] src1 // NOOPT-NEXT: GIM_CheckPointerToAny, /*MI*/0, /*Op*/1, /*SizeInBits*/32, -// NOOPT-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// NOOPT-NEXT: GIM_RootCheckRegBankForClass, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // NOOPT-NEXT: // (ld:{ *:[i32] } GPR32:{ *:[i32] }:$src1)<><> => (LOAD:{ *:[i32] } GPR32:{ *:[i32] }:$src1) // NOOPT-NEXT: GIR_MutateOpcode, /*InsnID*/0, /*RecycleInsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::LOAD), -// NOOPT-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, +// NOOPT-NEXT: GIR_RootConstrainSelectedInstOperands, // NOOPT-NEXT: // GIR_Coverage, 12, // NOOPT-NEXT: GIR_Done, // NOOPT-NEXT: // Label [[LABEL_NUM]]: @[[LABEL]] @@ -995,14 +976,14 @@ def LOAD : I<(outs GPR32:$dst), (ins GPR32:$src1), // NOOPT-NEXT: GIM_CheckMemorySizeEqualToLLT, /*MI*/0, /*MMO*/0, /*OpIdx*/0, // NOOPT-NEXT: GIM_CheckAtomicOrdering, /*MI*/0, /*Order*/(uint8_t)AtomicOrdering::NotAtomic, // NOOPT-NEXT: // MIs[0] DstI[dst] -// NOOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_p0s32, -// NOOPT-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// NOOPT-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_p0s32, +// NOOPT-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // NOOPT-NEXT: // MIs[0] src // NOOPT-NEXT: GIM_CheckPointerToAny, /*MI*/0, /*Op*/1, /*SizeInBits*/32, -// NOOPT-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// NOOPT-NEXT: GIM_RootCheckRegBankForClass, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // NOOPT-NEXT: // (ld:{ *:[i32] } GPR32:{ *:[i32] }:$src)<><> => (LOAD:{ *:[i32] } GPR32:{ *:[i32] }:$src) // NOOPT-NEXT: GIR_MutateOpcode, /*InsnID*/0, /*RecycleInsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::LOAD), -// NOOPT-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, +// NOOPT-NEXT: GIR_RootConstrainSelectedInstOperands, // NOOPT-NEXT: // GIR_Coverage, 24, // NOOPT-NEXT: GIR_Done, // NOOPT-NEXT: // Label [[LABEL_NUM]]: @[[LABEL]] @@ -1018,14 +999,14 @@ def : Pat<(load GPR32:$src), // NOOPT-NEXT: GIM_CheckMemorySizeEqualTo, /*MI*/0, /*MMO*/0, /*Size*/GIMT_Encode4(2), // NOOPT-NEXT: GIM_CheckAtomicOrdering, /*MI*/0, /*Order*/(uint8_t)AtomicOrdering::NotAtomic, // NOOPT-NEXT: // MIs[0] DstI[dst] -// NOOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// NOOPT-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// NOOPT-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// NOOPT-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // NOOPT-NEXT: // MIs[0] src1 // NOOPT-NEXT: GIM_CheckPointerToAny, /*MI*/0, /*Op*/1, /*SizeInBits*/32, -// NOOPT-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// NOOPT-NEXT: GIM_RootCheckRegBankForClass, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // NOOPT-NEXT: // (ld:{ *:[i32] } GPR32:{ *:[i32] }:$src1)<><><> => (SEXTLOAD:{ *:[i32] } GPR32:{ *:[i32] }:$src1) // NOOPT-NEXT: GIR_MutateOpcode, /*InsnID*/0, /*RecycleInsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::SEXTLOAD), -// NOOPT-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, +// NOOPT-NEXT: GIR_RootConstrainSelectedInstOperands, // NOOPT-NEXT: // GIR_Coverage, 13, // NOOPT-NEXT: GIR_Done, // NOOPT-NEXT: // Label [[LABEL_NUM]]: @[[LABEL]] @@ -1039,17 +1020,17 @@ def SEXTLOAD : I<(outs GPR32:$dst), (ins GPR32:$src1), // NOOPT-NEXT: GIM_CheckNumOperands, /*MI*/0, /*Expected*/3, // NOOPT-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_ADD), // NOOPT-NEXT: // MIs[0] DstI[dst] -// NOOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// NOOPT-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// NOOPT-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// NOOPT-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // NOOPT-NEXT: // MIs[0] src1 -// NOOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, -// NOOPT-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID) +// NOOPT-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, +// NOOPT-NEXT: GIM_RootCheckRegBankForClass, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID) // NOOPT-NEXT: // MIs[0] src2 -// NOOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/2, /*Type*/GILLT_s32, -// NOOPT-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/2, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// NOOPT-NEXT: GIM_RootCheckType, /*Op*/2, /*Type*/GILLT_s32, +// NOOPT-NEXT: GIM_RootCheckRegBankForClass, /*Op*/2, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // NOOPT-NEXT: // (add:{ *:[i32] } GPR32:{ *:[i32] }:$src1, GPR32:{ *:[i32] }:$src2) => (ADD:{ *:[i32] } GPR32:{ *:[i32] }:$src1, GPR32:{ *:[i32] }:$src2) // NOOPT-NEXT: GIR_MutateOpcode, /*InsnID*/0, /*RecycleInsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::ADD), -// NOOPT-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, +// NOOPT-NEXT: GIR_RootConstrainSelectedInstOperands, // NOOPT-NEXT: // GIR_Coverage, 14, // NOOPT-NEXT: GIR_Done, // NOOPT-NEXT: // Label [[LABEL_NUM]]: @[[LABEL]] @@ -1063,21 +1044,20 @@ def ADD : I<(outs GPR32:$dst), (ins GPR32:$src1, GPR32:$src2), // NOOPT-NEXT: GIM_CheckNumOperands, /*MI*/0, /*Expected*/3, // NOOPT-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_ADD), // NOOPT-NEXT: // MIs[0] DstI[dst] -// NOOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// NOOPT-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// NOOPT-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// NOOPT-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // NOOPT-NEXT: // MIs[0] src{{$}} -// NOOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, -// NOOPT-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// NOOPT-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, +// NOOPT-NEXT: GIM_RootCheckRegBankForClass, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // NOOPT-NEXT: // MIs[0] src{{$}} // NOOPT-NEXT: GIM_CheckIsSameOperand, /*MI*/0, /*OpIdx*/2, /*OtherMI*/0, /*OtherOpIdx*/1, // NOOPT-NEXT: // (add:{ *:[i32] } GPR32:{ *:[i32] }:$src, GPR32:{ *:[i32] }:$src) => (DOUBLE:{ *:[i32] } GPR32:{ *:[i32] }:$src) -// NOOPT-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::DOUBLE), -// NOOPT-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] -// NOOPT-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/1, // src -// NOOPT-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, -// NOOPT-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// NOOPT-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::DOUBLE), +// NOOPT-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] +// NOOPT-NEXT: GIR_RootToRootCopy, /*OpIdx*/1, // src +// NOOPT-NEXT: GIR_RootConstrainSelectedInstOperands, // NOOPT-NEXT: // GIR_Coverage, 15, -// NOOPT-NEXT: GIR_Done, +// NOOPT-NEXT: GIR_EraseRootFromParent_Done, // NOOPT-NEXT: // Label [[LABEL_NUM]]: @[[LABEL]] def DOUBLE : I<(outs GPR32:$dst), (ins GPR32:$src), [(set GPR32:$dst, (add GPR32:$src, GPR32:$src))]>; @@ -1094,15 +1074,15 @@ def DOUBLE : I<(outs GPR32:$dst), (ins GPR32:$src), [(set GPR32:$dst, (add GPR32 // NOOPT-NEXT: GIM_CheckNumOperands, /*MI*/0, /*Expected*/3, // NOOPT-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_ADD), // NOOPT-NEXT: // MIs[0] DstI[samename] -// NOOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// NOOPT-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// NOOPT-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// NOOPT-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // NOOPT-NEXT: // MIs[0] samename -// NOOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, +// NOOPT-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, // NOOPT-NEXT: // MIs[0] othername -// NOOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/2, /*Type*/GILLT_s32, +// NOOPT-NEXT: GIM_RootCheckType, /*Op*/2, /*Type*/GILLT_s32, // NOOPT-NEXT: // (add:{ *:[i32] } i32:{ *:[i32] }:$samename, i32:{ *:[i32] }:$othername) => (InsnWithSpeciallyNamedDef:{ *:[i32] } i32:{ *:[i32] }:$samename, i32:{ *:[i32] }:$othername) // NOOPT-NEXT: GIR_MutateOpcode, /*InsnID*/0, /*RecycleInsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::InsnWithSpeciallyNamedDef), -// NOOPT-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, +// NOOPT-NEXT: GIR_RootConstrainSelectedInstOperands, // NOOPT-NEXT: // GIR_Coverage, 25, // NOOPT-NEXT: GIR_Done, // NOOPT-NEXT: // Label [[LABEL_NUM]]: @[[LABEL]] @@ -1117,15 +1097,15 @@ def : Pat<(add i32:$samename, i32:$othername), // NOOPT-NEXT: GIM_CheckNumOperands, /*MI*/0, /*Expected*/3, // NOOPT-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_ADD), // NOOPT-NEXT: // MIs[0] DstI[dst] -// NOOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// NOOPT-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// NOOPT-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// NOOPT-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // NOOPT-NEXT: // MIs[0] src1 -// NOOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, +// NOOPT-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, // NOOPT-NEXT: // MIs[0] src2 -// NOOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/2, /*Type*/GILLT_s32, +// NOOPT-NEXT: GIM_RootCheckType, /*Op*/2, /*Type*/GILLT_s32, // NOOPT-NEXT: // (add:{ *:[i32] } i32:{ *:[i32] }:$src1, i32:{ *:[i32] }:$src2) => (ADD:{ *:[i32] } i32:{ *:[i32] }:$src1, i32:{ *:[i32] }:$src2) // NOOPT-NEXT: GIR_MutateOpcode, /*InsnID*/0, /*RecycleInsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::ADD), -// NOOPT-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, +// NOOPT-NEXT: GIR_RootConstrainSelectedInstOperands, // NOOPT-NEXT: // GIR_Coverage, 26, // NOOPT-NEXT: GIR_Done, // NOOPT-NEXT: // Label [[LABEL_NUM]]: @[[LABEL]] @@ -1140,23 +1120,22 @@ def : Pat<(add i32:$src1, i32:$src2), // NOOPT-NEXT: GIM_CheckNumOperands, /*MI*/0, /*Expected*/3, // NOOPT-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_MUL), // NOOPT-NEXT: // MIs[0] DstI[dst] -// NOOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// NOOPT-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// NOOPT-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// NOOPT-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // NOOPT-NEXT: // MIs[0] src1 -// NOOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, -// NOOPT-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// NOOPT-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, +// NOOPT-NEXT: GIM_RootCheckRegBankForClass, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // NOOPT-NEXT: // MIs[0] src2 -// NOOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/2, /*Type*/GILLT_s32, -// NOOPT-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/2, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// NOOPT-NEXT: GIM_RootCheckType, /*Op*/2, /*Type*/GILLT_s32, +// NOOPT-NEXT: GIM_RootCheckRegBankForClass, /*Op*/2, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // NOOPT-NEXT: // (mul:{ *:[i32] } GPR32:{ *:[i32] }:$src1, GPR32:{ *:[i32] }:$src2) => (MUL:{ *:[i32] } GPR32:{ *:[i32] }:$src2, GPR32:{ *:[i32] }:$src1) -// NOOPT-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::MUL), -// NOOPT-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] -// NOOPT-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/2, // src2 -// NOOPT-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/1, // src1 -// NOOPT-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, -// NOOPT-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// NOOPT-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::MUL), +// NOOPT-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] +// NOOPT-NEXT: GIR_RootToRootCopy, /*OpIdx*/2, // src2 +// NOOPT-NEXT: GIR_RootToRootCopy, /*OpIdx*/1, // src1 +// NOOPT-NEXT: GIR_RootConstrainSelectedInstOperands, // NOOPT-NEXT: // GIR_Coverage, 16, -// NOOPT-NEXT: GIR_Done, +// NOOPT-NEXT: GIR_EraseRootFromParent_Done, // NOOPT-NEXT: // Label [[LABEL_NUM]]: @[[LABEL]] def MUL : I<(outs GPR32:$dst), (ins GPR32:$src2, GPR32:$src1), @@ -1170,11 +1149,11 @@ def MUL : I<(outs GPR32:$dst), (ins GPR32:$src2, GPR32:$src1), // NOOPT-NEXT: GIM_CheckNumOperands, /*MI*/0, /*Expected*/2, // NOOPT-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_BITCAST), // NOOPT-NEXT: // MIs[0] DstI[dst] -// NOOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// NOOPT-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// NOOPT-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// NOOPT-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // NOOPT-NEXT: // MIs[0] src1 -// NOOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, -// NOOPT-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::FPR32RegClassID), +// NOOPT-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, +// NOOPT-NEXT: GIM_RootCheckRegBankForClass, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::FPR32RegClassID), // NOOPT-NEXT: // (bitconvert:{ *:[i32] } FPR32:{ *:[f32] }:$src1) => (COPY_TO_REGCLASS:{ *:[i32] } FPR32:{ *:[f32] }:$src1, GPR32:{ *:[i32] }) // NOOPT-NEXT: GIR_MutateOpcode, /*InsnID*/0, /*RecycleInsnID*/0, /*Opcode*/GIMT_Encode2(TargetOpcode::COPY), // NOOPT-NEXT: GIR_ConstrainOperandRC, /*InsnID*/0, /*Op*/0, GIMT_Encode2(MyTarget::GPR32RegClassID), @@ -1191,18 +1170,17 @@ def : Pat<(i32 (bitconvert FPR32:$src1)), // NOOPT-NEXT: GIM_CheckNumOperands, /*MI*/0, /*Expected*/2, // NOOPT-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_CONSTANT), // NOOPT-NEXT: // MIs[0] DstI[dst] -// NOOPT-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// NOOPT-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// NOOPT-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// NOOPT-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // NOOPT-NEXT: // MIs[0] Operand 1 // NOOPT-NEXT: // No operand predicates // NOOPT-NEXT: // (imm:{ *:[i32] }):$imm => (MOVimm:{ *:[i32] } (imm:{ *:[i32] }):$imm) -// NOOPT-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::MOVimm), -// NOOPT-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] +// NOOPT-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::MOVimm), +// NOOPT-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] // NOOPT-NEXT: GIR_CopyConstantAsSImm, /*NewInsnID*/0, /*OldInsnID*/0, // imm -// NOOPT-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, -// NOOPT-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// NOOPT-NEXT: GIR_RootConstrainSelectedInstOperands, // NOOPT-NEXT: // GIR_Coverage, 17, -// NOOPT-NEXT: GIR_Done, +// NOOPT-NEXT: GIR_EraseRootFromParent_Done, // NOOPT-NEXT: // Label [[LABEL_NUM]]: @[[LABEL]] def MOVimm : I<(outs GPR32:$dst), (ins i32imm:$imm), [(set GPR32:$dst, imm:$imm)]>; @@ -1219,7 +1197,7 @@ def MOVfpimmz : I<(outs FPR32:$dst), (ins f32imm:$imm), [(set FPR32:$dst, fpimmz // NOOPT-NEXT: GIM_CheckIsMBB, /*MI*/0, /*Op*/0, // NOOPT-NEXT: // (br (bb:{ *:[Other] }):$target) => (BR (bb:{ *:[Other] }):$target) // NOOPT-NEXT: GIR_MutateOpcode, /*InsnID*/0, /*RecycleInsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::BR), -// NOOPT-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, +// NOOPT-NEXT: GIR_RootConstrainSelectedInstOperands, // NOOPT-NEXT: // GIR_Coverage, 19, // NOOPT-NEXT: GIR_Done, // NOOPT-NEXT: // Label [[LABEL_NUM]]: @[[LABEL]] @@ -1228,5 +1206,5 @@ def BR : I<(outs), (ins unknown:$target), [(br bb:$target)]>; // NOOPT-NEXT: GIM_Reject, -// NOOPT-NEXT: }; // Size: 1738 bytes +// NOOPT-NEXT: }; // Size: 1459 bytes // NOOPT-NEXT: return MatchTable0; diff --git a/llvm/test/TableGen/GlobalISelEmitterCustomPredicate.td b/llvm/test/TableGen/GlobalISelEmitterCustomPredicate.td index ed43ff2f14fa2afcb43fd18b5109d8bedbbd8eab..3ceadf32f06425e7818fceb86a6e9f30f3f3905d 100644 --- a/llvm/test/TableGen/GlobalISelEmitterCustomPredicate.td +++ b/llvm/test/TableGen/GlobalISelEmitterCustomPredicate.td @@ -73,18 +73,18 @@ def and_or_pat : PatFrag< let PredicateCodeUsesOperands = 1; } -// CHECK: GIM_Try, /*On fail goto*//*Label 0*/ GIMT_Encode4(110), // Rule ID 7 // +// CHECK: GIM_Try, /*On fail goto*//*Label 0*/ GIMT_Encode4(97), // Rule ID 7 // // CHECK-NEXT: GIM_CheckNumOperands, /*MI*/0, /*Expected*/3, // CHECK-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_AND), // CHECK-NEXT: // MIs[0] DstI[dst] -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(Test::DRegsRegClassID), +// CHECK-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(Test::DRegsRegClassID), // CHECK-NEXT: // MIs[0] src2 -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, // CHECK-NEXT: GIM_RecordNamedOperand, /*MI*/0, /*Op*/1, /*StoreIdx*/2, // Name : pred:3:z -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/1, /*RC*/GIMT_Encode2(Test::DRegsRegClassID), +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/1, /*RC*/GIMT_Encode2(Test::DRegsRegClassID), // CHECK-NEXT: // MIs[0] Operand 2 -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/2, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckType, /*Op*/2, /*Type*/GILLT_s32, // CHECK-NEXT: GIM_RecordInsn, /*DefineMI*/1, /*MI*/0, /*OpIdx*/2, // MIs[1] // CHECK-NEXT: GIM_CheckNumOperands, /*MI*/1, /*Expected*/3, // CHECK-NEXT: GIM_CheckOpcode, /*MI*/1, GIMT_Encode2(TargetOpcode::G_OR), @@ -99,18 +99,18 @@ def and_or_pat : PatFrag< // CHECK-NEXT: GIM_RecordNamedOperand, /*MI*/1, /*Op*/2, /*StoreIdx*/1, // Name : pred:3:y // CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/1, /*Op*/2, /*RC*/GIMT_Encode2(Test::DRegsRegClassID), // CHECK-NEXT: GIM_CheckCxxInsnPredicate, /*MI*/0, /*FnId*/GIMT_Encode2(GICXXPred_MI_Predicate_and_or_pat), -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/1, +// CHECK-NEXT: GIM_CheckIsSafeToFold, /*NumInsns*/1, // CHECK-NEXT: // (and:{ *:[i32] } DOP:{ *:[i32] }:$src2:$pred:3:z, (or:{ *:[i32] } DOP:{ *:[i32] }:$src0:$pred:3:x, DOP:{ *:[i32] }:$src1:$pred:3:y))<> => (AND_OR:{ *:[i32] } DOP:{ *:[i32] }:$src0, DOP:{ *:[i32] }:$src1, DOP:{ *:[i32] }:$src2) -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::AND_OR), +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::AND_OR), -// CHECK: GIM_Try, /*On fail goto*//*Label 1*/ GIMT_Encode4(220), // Rule ID 3 // +// CHECK: GIM_Try, /*On fail goto*//*Label 1*/ GIMT_Encode4(194), // Rule ID 3 // // CHECK-NEXT: GIM_CheckNumOperands, /*MI*/0, /*Expected*/3, // CHECK-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_AND), // CHECK-NEXT: // MIs[0] DstI[dst] -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(Test::DRegsRegClassID), +// CHECK-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(Test::DRegsRegClassID), // CHECK-NEXT: // MIs[0] Operand 1 -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, // CHECK-NEXT: GIM_RecordInsn, /*DefineMI*/1, /*MI*/0, /*OpIdx*/1, // MIs[1] // CHECK-NEXT: GIM_CheckNumOperands, /*MI*/1, /*Expected*/3, // CHECK-NEXT: GIM_CheckOpcode, /*MI*/1, GIMT_Encode2(TargetOpcode::G_OR), @@ -125,13 +125,13 @@ def and_or_pat : PatFrag< // CHECK-NEXT: GIM_RecordNamedOperand, /*MI*/1, /*Op*/2, /*StoreIdx*/1, // Name : pred:3:y // CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/1, /*Op*/2, /*RC*/GIMT_Encode2(Test::DRegsRegClassID), // CHECK-NEXT: // MIs[0] src2 -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/2, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckType, /*Op*/2, /*Type*/GILLT_s32, // CHECK-NEXT: GIM_RecordNamedOperand, /*MI*/0, /*Op*/2, /*StoreIdx*/2, // Name : pred:3:z -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/2, /*RC*/GIMT_Encode2(Test::DRegsRegClassID), +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/2, /*RC*/GIMT_Encode2(Test::DRegsRegClassID), // CHECK-NEXT: GIM_CheckCxxInsnPredicate, /*MI*/0, /*FnId*/GIMT_Encode2(GICXXPred_MI_Predicate_and_or_pat), -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/1, +// CHECK-NEXT: GIM_CheckIsSafeToFold, /*NumInsns*/1, // CHECK-NEXT: // (and:{ *:[i32] } (or:{ *:[i32] } DOP:{ *:[i32] }:$src0:$pred:3:x, DOP:{ *:[i32] }:$src1:$pred:3:y), DOP:{ *:[i32] }:$src2:$pred:3:z)<> => (AND_OR:{ *:[i32] } DOP:{ *:[i32] }:$src0, DOP:{ *:[i32] }:$src1, DOP:{ *:[i32] }:$src2) -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::AND_OR), +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::AND_OR), // Test commutative, standalone pattern. def : Pat< @@ -148,14 +148,14 @@ def mul_pat : PatFrag< let PredicateCodeUsesOperands = 1; } -// CHECK: GIM_Try, /*On fail goto*//*Label 2*/ GIMT_Encode4(326), // Rule ID 4 // +// CHECK: GIM_Try, /*On fail goto*//*Label 2*/ GIMT_Encode4(287), // Rule ID 4 // // CHECK-NEXT: GIM_CheckNumOperands, /*MI*/0, /*Expected*/3, // CHECK-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_MUL), // CHECK-NEXT: // MIs[0] DstI[dst] -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(Test::DRegsRegClassID), +// CHECK-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(Test::DRegsRegClassID), // CHECK-NEXT: // MIs[0] Operand 1 -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, // CHECK-NEXT: GIM_RecordNamedOperand, /*MI*/0, /*Op*/1, /*StoreIdx*/0, // Name : pred:4:x // CHECK-NEXT: GIM_RecordInsn, /*DefineMI*/1, /*MI*/0, /*OpIdx*/1, // MIs[1] // CHECK-NEXT: GIM_CheckNumOperands, /*MI*/1, /*Expected*/3, @@ -169,26 +169,26 @@ def mul_pat : PatFrag< // CHECK-NEXT: GIM_CheckType, /*MI*/1, /*Op*/2, /*Type*/GILLT_s32, // CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/1, /*Op*/2, /*RC*/GIMT_Encode2(Test::DRegsRegClassID), // CHECK-NEXT: // MIs[0] src2 -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/2, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckType, /*Op*/2, /*Type*/GILLT_s32, // CHECK-NEXT: GIM_RecordNamedOperand, /*MI*/0, /*Op*/2, /*StoreIdx*/1, // Name : pred:4:y -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/2, /*RC*/GIMT_Encode2(Test::DRegsRegClassID), +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/2, /*RC*/GIMT_Encode2(Test::DRegsRegClassID), // CHECK-NEXT: GIM_CheckCxxInsnPredicate, /*MI*/0, /*FnId*/GIMT_Encode2(GICXXPred_MI_Predicate_mul_pat), -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/1, +// CHECK-NEXT: GIM_CheckIsSafeToFold, /*NumInsns*/1, // CHECK-NEXT: // (mul:{ *:[i32] } (or:{ *:[i32] } DOP:{ *:[i32] }:$src0, DOP:{ *:[i32] }:$src1):$pred:4:x, DOP:{ *:[i32] }:$src2:$pred:4:y)<> => (MUL_OR:{ *:[i32] } DOP:{ *:[i32] }:$src0, DOP:{ *:[i32] }:$src1, DOP:{ *:[i32] }:$src2) -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::MUL_OR), +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::MUL_OR), -// CHECK: GIM_Try, /*On fail goto*//*Label 3*/ GIMT_Encode4(432), // Rule ID 8 // +// CHECK: GIM_Try, /*On fail goto*//*Label 3*/ GIMT_Encode4(380), // Rule ID 8 // // CHECK-NEXT: GIM_CheckNumOperands, /*MI*/0, /*Expected*/3, // CHECK-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_MUL), // CHECK-NEXT: // MIs[0] DstI[dst] -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(Test::DRegsRegClassID), +// CHECK-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(Test::DRegsRegClassID), // CHECK-NEXT: // MIs[0] src2 -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, // CHECK-NEXT: GIM_RecordNamedOperand, /*MI*/0, /*Op*/1, /*StoreIdx*/1, // Name : pred:4:y -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/1, /*RC*/GIMT_Encode2(Test::DRegsRegClassID), +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/1, /*RC*/GIMT_Encode2(Test::DRegsRegClassID), // CHECK-NEXT: // MIs[0] Operand 2 -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/2, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckType, /*Op*/2, /*Type*/GILLT_s32, // CHECK-NEXT: GIM_RecordNamedOperand, /*MI*/0, /*Op*/2, /*StoreIdx*/0, // Name : pred:4:x // CHECK-NEXT: GIM_RecordInsn, /*DefineMI*/1, /*MI*/0, /*OpIdx*/2, // MIs[1] // CHECK-NEXT: GIM_CheckNumOperands, /*MI*/1, /*Expected*/3, @@ -202,9 +202,9 @@ def mul_pat : PatFrag< // CHECK-NEXT: GIM_CheckType, /*MI*/1, /*Op*/2, /*Type*/GILLT_s32, // CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/1, /*Op*/2, /*RC*/GIMT_Encode2(Test::DRegsRegClassID), // CHECK-NEXT: GIM_CheckCxxInsnPredicate, /*MI*/0, /*FnId*/GIMT_Encode2(GICXXPred_MI_Predicate_mul_pat), -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/1, +// CHECK-NEXT: GIM_CheckIsSafeToFold, /*NumInsns*/1, // CHECK-NEXT: // (mul:{ *:[i32] } DOP:{ *:[i32] }:$src2:$pred:4:y, (or:{ *:[i32] } DOP:{ *:[i32] }:$src0, DOP:{ *:[i32] }:$src1):$pred:4:x)<> => (MUL_OR:{ *:[i32] } DOP:{ *:[i32] }:$src0, DOP:{ *:[i32] }:$src1, DOP:{ *:[i32] }:$src2) -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::MUL_OR), +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::MUL_OR), // Test commutative patterns where named operands in the source pattern are not // directly bound to PatFrag's operands. @@ -223,14 +223,14 @@ def sub3_pat : PatFrag< let PredicateCodeUsesOperands = 1; } -// CHECK: GIM_Try, /*On fail goto*//*Label 4*/ GIMT_Encode4(527), // Rule ID 0 // +// CHECK: GIM_Try, /*On fail goto*//*Label 4*/ GIMT_Encode4(463), // Rule ID 0 // // CHECK-NEXT: GIM_CheckNumOperands, /*MI*/0, /*Expected*/3, // CHECK-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_SUB), // CHECK-NEXT: // MIs[0] DstI[dst] -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(Test::DRegsRegClassID), +// CHECK-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(Test::DRegsRegClassID), // CHECK-NEXT: // MIs[0] Operand 1 -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, // CHECK-NEXT: GIM_RecordInsn, /*DefineMI*/1, /*MI*/0, /*OpIdx*/1, // MIs[1] // CHECK-NEXT: GIM_CheckNumOperands, /*MI*/1, /*Expected*/3, // CHECK-NEXT: GIM_CheckOpcode, /*MI*/1, GIMT_Encode2(TargetOpcode::G_SUB), @@ -243,12 +243,12 @@ def sub3_pat : PatFrag< // CHECK-NEXT: GIM_CheckType, /*MI*/1, /*Op*/2, /*Type*/GILLT_s32, // CHECK-NEXT: GIM_RecordNamedOperand, /*MI*/1, /*Op*/2, /*StoreIdx*/1, // Name : pred:1:y // CHECK-NEXT: // MIs[0] src2 -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/2, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckType, /*Op*/2, /*Type*/GILLT_s32, // CHECK-NEXT: GIM_RecordNamedOperand, /*MI*/0, /*Op*/2, /*StoreIdx*/2, // Name : pred:1:z // CHECK-NEXT: GIM_CheckCxxInsnPredicate, /*MI*/0, /*FnId*/GIMT_Encode2(GICXXPred_MI_Predicate_sub3_pat), -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/1, +// CHECK-NEXT: GIM_CheckIsSafeToFold, /*NumInsns*/1, // CHECK-NEXT: // (sub:{ *:[i32] } (sub:{ *:[i32] } i32:{ *:[i32] }:$src0:$pred:1:x, i32:{ *:[i32] }:$src1:$pred:1:y), i32:{ *:[i32] }:$src2:$pred:1:z)<> => (SUB3:{ *:[i32] } i32:{ *:[i32] }:$src0, i32:{ *:[i32] }:$src1, i32:{ *:[i32] }:$src2) -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::SUB3) +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::SUB3) // Test a non-commutative pattern. def SUB3 : I<(outs DRegs:$dst), @@ -269,16 +269,16 @@ def patfrags_test_pat : PatFrags< let PredicateCodeUsesOperands = 1; } -// CHECK: GIM_Try, /*On fail goto*//*Label 5*/ GIMT_Encode4(622), // Rule ID 1 // +// CHECK: GIM_Try, /*On fail goto*//*Label 5*/ GIMT_Encode4(546), // Rule ID 1 // // CHECK: // (xor:{ *:[i32] } (add:{ *:[i32] } i32:{ *:[i32] }:$src0:$pred:2:x, i32:{ *:[i32] }:$src1:$pred:2:y), i32:{ *:[i32] }:$src2:$pred:2:z)<> => (PATFRAGS:{ *:[i32] } i32:{ *:[i32] }:$src0, i32:{ *:[i32] }:$src1, i32:{ *:[i32] }:$src2) -// CHECK: GIM_Try, /*On fail goto*//*Label 6*/ GIMT_Encode4(717), // Rule ID 2 // +// CHECK: GIM_Try, /*On fail goto*//*Label 6*/ GIMT_Encode4(629), // Rule ID 2 // // CHECK: // (xor:{ *:[i32] } (sub:{ *:[i32] } i32:{ *:[i32] }:$src0:$pred:2:x, i32:{ *:[i32] }:$src1:$pred:2:y), i32:{ *:[i32] }:$src2:$pred:2:z)<> => (PATFRAGS:{ *:[i32] } i32:{ *:[i32] }:$src0, i32:{ *:[i32] }:$src1, i32:{ *:[i32] }:$src2) -// CHECK: GIM_Try, /*On fail goto*//*Label 7*/ GIMT_Encode4(812), // Rule ID 5 // +// CHECK: GIM_Try, /*On fail goto*//*Label 7*/ GIMT_Encode4(712), // Rule ID 5 // // CHECK: // (xor:{ *:[i32] } i32:{ *:[i32] }:$src2:$pred:2:z, (add:{ *:[i32] } i32:{ *:[i32] }:$src0:$pred:2:x, i32:{ *:[i32] }:$src1:$pred:2:y))<> => (PATFRAGS:{ *:[i32] } i32:{ *:[i32] }:$src0, i32:{ *:[i32] }:$src1, i32:{ *:[i32] }:$src2) -// CHECK: GIM_Try, /*On fail goto*//*Label 8*/ GIMT_Encode4(907), // Rule ID 6 // +// CHECK: GIM_Try, /*On fail goto*//*Label 8*/ GIMT_Encode4(795), // Rule ID 6 // // CHECK: // (xor:{ *:[i32] } i32:{ *:[i32] }:$src2:$pred:2:z, (sub:{ *:[i32] } i32:{ *:[i32] }:$src0:$pred:2:x, i32:{ *:[i32] }:$src1:$pred:2:y))<> => (PATFRAGS:{ *:[i32] } i32:{ *:[i32] }:$src0, i32:{ *:[i32] }:$src1, i32:{ *:[i32] }:$src2) diff --git a/llvm/test/TableGen/GlobalISelEmitterFlags.td b/llvm/test/TableGen/GlobalISelEmitterFlags.td index 2025a2c1048e0216583fca4166d1ba1e50f25046..fa8f2a79fbce89ab268af013a1e2935c278afe0a 100644 --- a/llvm/test/TableGen/GlobalISelEmitterFlags.td +++ b/llvm/test/TableGen/GlobalISelEmitterFlags.td @@ -42,7 +42,7 @@ def : Pat< // CHECK: GIM_CheckIsSameOperand, /*MI*/2, /*OpIdx*/2, /*OtherMI*/2, /*OtherOpIdx*/1 // CHECK: GIM_CheckIsSameOperandIgnoreCopies, /*MI*/0, /*OpIdx*/2, /*OtherMI*/2, /*OtherOpIdx*/1 // CHECK: // (srl:{ *:[i32] } (srl:{ *:[i32] } (add:{ *:[i32] } i32:{ *:[i32] }:$src0, i32:{ *:[i32] }:$src0), i32:{ *:[i32] }:$src1), i32:{ *:[i32] }:$src0) -// CHECK: GIR_Done +// CHECK: GIR_EraseRootFromParent_Done // CHECK: GIM_Try // CHECK: GIM_RecordInsnIgnoreCopies, /*DefineMI*/1, /*MI*/0, /*OpIdx*/1, // MIs[1] // CHECK: GIM_CheckOpcode, /*MI*/1, GIMT_Encode2(TargetOpcode::G_SHL) @@ -51,10 +51,10 @@ def : Pat< // CHECK: GIM_CheckIsSameOperandIgnoreCopies, /*MI*/2, /*OpIdx*/2, /*OtherMI*/2, /*OtherOpIdx*/1 // CHECK: GIM_CheckIsSameOperandIgnoreCopies, /*MI*/0, /*OpIdx*/2, /*OtherMI*/2, /*OtherOpIdx*/1 // CHECK: // (srl:{ *:[i32] } (shl:{ *:[i32] } (mul:{ *:[i32] } i32:{ *:[i32] }:$src0, i32:{ *:[i32] }:$src0), i32:{ *:[i32] }:$src1), i32:{ *:[i32] }:$src0) -// CHECK: GIR_Done +// CHECK: GIR_EraseRootFromParent_Done // CHECK: GIM_Try // CHECK: GIM_RecordInsnIgnoreCopies, /*DefineMI*/1, /*MI*/0, /*OpIdx*/1, // MIs[1] // CHECK: GIM_CheckOpcode, /*MI*/1, GIMT_Encode2(TargetOpcode::G_MUL) // CHECK: GIM_CheckIsSameOperandIgnoreCopies, /*MI*/1, /*OpIdx*/2, /*OtherMI*/1, /*OtherOpIdx*/1 // CHECK: // (sub:{ *:[i32] } (mul:{ *:[i32] } i32:{ *:[i32] }:$src0, i32:{ *:[i32] }:$src0), i32:{ *:[i32] }:$src1) => (InstThreeOperands:{ *:[i32] } GPR32:{ *:[i32] }:$src0, GPR32:{ *:[i32] }:$src1, GPR32:{ *:[i32] }:$src1) -// CHECK: GIR_Done +// CHECK: GIR_EraseRootFromParent_Done diff --git a/llvm/test/TableGen/GlobalISelEmitterHwModes.td b/llvm/test/TableGen/GlobalISelEmitterHwModes.td index b96e9db0134bfe36b486ee24c6b890f44af35dd2..7c8340a154e8bee6b91f65889b645180bd52b19f 100644 --- a/llvm/test/TableGen/GlobalISelEmitterHwModes.td +++ b/llvm/test/TableGen/GlobalISelEmitterHwModes.td @@ -134,14 +134,14 @@ class I Pat> // CHECK-NEXT: GIM_CheckMemorySizeEqualToLLT, /*MI*/0, /*MMO*/0, /*OpIdx*/0, // CHECK-NEXT: GIM_CheckAtomicOrdering, /*MI*/0, /*Order*/(uint8_t)AtomicOrdering::NotAtomic, // CHECK-NEXT: // MIs[0] DstI[dst] -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s64, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPRRegClassID), +// CHECK-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s64, +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPRRegClassID), // CHECK-NEXT: // MIs[0] src1 // CHECK-NEXT: GIM_CheckPointerToAny, /*MI*/0, /*Op*/1, /*SizeInBits*/64, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPRRegClassID), +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPRRegClassID), // CHECK-NEXT: // (ld:{ *:[i64] } GPR:{ *:[i64] }:$src1)<><> => (LOAD:{ *:[i64] } GPR:{ *:[i64] }:$src1) // CHECK-NEXT: GIR_MutateOpcode, /*InsnID*/0, /*RecycleInsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::LOAD), -// CHECK-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, +// CHECK-NEXT: GIR_RootConstrainSelectedInstOperands, // CHECK-NEXT: // GIR_Coverage, 0, // CHECK-NEXT: GIR_Done, // CHECK-NEXT: // Label [[LABEL_NUM]]: @[[LABEL]] @@ -152,14 +152,14 @@ class I Pat> // CHECK-NEXT: GIM_CheckMemorySizeEqualToLLT, /*MI*/0, /*MMO*/0, /*OpIdx*/0, // CHECK-NEXT: GIM_CheckAtomicOrdering, /*MI*/0, /*Order*/(uint8_t)AtomicOrdering::NotAtomic, // CHECK-NEXT: // MIs[0] DstI[dst] -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPRRegClassID), +// CHECK-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPRRegClassID), // CHECK-NEXT: // MIs[0] src1 // CHECK-NEXT: GIM_CheckPointerToAny, /*MI*/0, /*Op*/1, /*SizeInBits*/32, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPRRegClassID), +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPRRegClassID), // CHECK-NEXT: // (ld:{ *:[i32] } GPR:{ *:[i32] }:$src1)<><> => (LOAD:{ *:[i32] } GPR:{ *:[i32] }:$src1) // CHECK-NEXT: GIR_MutateOpcode, /*InsnID*/0, /*RecycleInsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::LOAD), -// CHECK-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, +// CHECK-NEXT: GIR_RootConstrainSelectedInstOperands, // CHECK-NEXT: // GIR_Coverage, 1, // CHECK-NEXT: GIR_Done, // CHECK-NEXT: // Label [[LABEL_NUM]]: @[[LABEL]] @@ -176,14 +176,14 @@ def LOAD : I<(outs GPR:$dst), (ins GPR:$src1), // CHECK-NEXT: GIM_CheckMemorySizeEqualToLLT, /*MI*/0, /*MMO*/0, /*OpIdx*/0, // CHECK-NEXT: GIM_CheckAtomicOrdering, /*MI*/0, /*Order*/(uint8_t)AtomicOrdering::NotAtomic, // CHECK-NEXT: // MIs[0] DstI[dst] -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_p0s64, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPRRegClassID), +// CHECK-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_p0s64, +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPRRegClassID), // CHECK-NEXT: // MIs[0] src // CHECK-NEXT: GIM_CheckPointerToAny, /*MI*/0, /*Op*/1, /*SizeInBits*/64, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPRRegClassID), +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPRRegClassID), // CHECK-NEXT: // (ld:{ *:[i64] } GPR:{ *:[i64] }:$src)<><> => (LOAD:{ *:[i64] } GPR:{ *:[i64] }:$src) // CHECK-NEXT: GIR_MutateOpcode, /*InsnID*/0, /*RecycleInsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::LOAD), -// CHECK-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, +// CHECK-NEXT: GIR_RootConstrainSelectedInstOperands, // CHECK-NEXT: // GIR_Coverage, 2, // CHECK-NEXT: GIR_Done, // CHECK-NEXT: // Label [[LABEL_NUM]]: @[[LABEL]] @@ -194,14 +194,14 @@ def LOAD : I<(outs GPR:$dst), (ins GPR:$src1), // CHECK-NEXT: GIM_CheckMemorySizeEqualToLLT, /*MI*/0, /*MMO*/0, /*OpIdx*/0, // CHECK-NEXT: GIM_CheckAtomicOrdering, /*MI*/0, /*Order*/(uint8_t)AtomicOrdering::NotAtomic, // CHECK-NEXT: // MIs[0] DstI[dst] -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_p0s32, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPRRegClassID), +// CHECK-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_p0s32, +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPRRegClassID), // CHECK-NEXT: // MIs[0] src // CHECK-NEXT: GIM_CheckPointerToAny, /*MI*/0, /*Op*/1, /*SizeInBits*/32, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPRRegClassID), +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPRRegClassID), // CHECK-NEXT: // (ld:{ *:[i32] } GPR:{ *:[i32] }:$src)<><> => (LOAD:{ *:[i32] } GPR:{ *:[i32] }:$src) // CHECK-NEXT: GIR_MutateOpcode, /*InsnID*/0, /*RecycleInsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::LOAD), -// CHECK-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, +// CHECK-NEXT: GIR_RootConstrainSelectedInstOperands, // CHECK-NEXT: // GIR_Coverage, 3, // CHECK-NEXT: GIR_Done, // CHECK-NEXT: // Label [[LABEL_NUM]]: @[[LABEL]] diff --git a/llvm/test/TableGen/GlobalISelEmitterMatchTableOptimizer.td b/llvm/test/TableGen/GlobalISelEmitterMatchTableOptimizer.td index 5b534970d4d4fcd4e2da5876d0f231ac75885e45..3db31bea8612eefd7a0a841972a2823071a2bccc 100644 --- a/llvm/test/TableGen/GlobalISelEmitterMatchTableOptimizer.td +++ b/llvm/test/TableGen/GlobalISelEmitterMatchTableOptimizer.td @@ -11,24 +11,24 @@ def LOAD32 : I<(outs GPR8:$dst), (ins GPR32:$src), []>; // CHECK-NEXT: GIM_Try, /*On fail goto*//*Label [[L1_ID:[0-9]+]]*/ GIMT_Encode4([[L1_AT:[0-9]+]]), // CHECK-NEXT: GIM_CheckMemorySizeEqualToLLT, /*MI*/0, /*MMO*/0, /*OpIdx*/0, // CHECK-NEXT: GIM_CheckAtomicOrdering, /*MI*/0, /*Order*/(uint8_t)AtomicOrdering::NotAtomic, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR8RegClassID), +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR8RegClassID), // CHECK-NEXT: GIM_Try, /*On fail goto*//*Label [[L2_ID:[0-9]+]]*/ GIMT_Encode4([[L2_AT:[0-9]+]]), // CHECK-NEXT: // MIs[0] src // CHECK-NEXT: GIM_CheckPointerToAny, /*MI*/0, /*Op*/1, /*SizeInBits*/8, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR8RegClassID), +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR8RegClassID), // CHECK-NEXT: // (ld:{ *:[i8] } GPR8:{ *:[i8] }:$src)<><> => (LOAD8:{ *:[i8] } GPR8:{ *:[i8] }:$src) // CHECK-NEXT: GIR_MutateOpcode, /*InsnID*/0, /*RecycleInsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::LOAD8), -// CHECK-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, +// CHECK-NEXT: GIR_RootConstrainSelectedInstOperands, // CHECK-NEXT: // GIR_Coverage, 0, // CHECK-NEXT: GIR_Done, // CHECK-NEXT: // Label [[L2_ID]]: @[[L2_AT]] // CHECK-NEXT: GIM_Try, /*On fail goto*//*Label [[L3_ID:[0-9]+]]*/ GIMT_Encode4([[L3_AT:[0-9]+]]), // CHECK-NEXT: // MIs[0] src // CHECK-NEXT: GIM_CheckPointerToAny, /*MI*/0, /*Op*/1, /*SizeInBits*/32, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // CHECK-NEXT: // (ld:{ *:[i8] } GPR32:{ *:[i32] }:$src)<><> => (LOAD32:{ *:[i8] } GPR32:{ *:[i32] }:$src) // CHECK-NEXT: GIR_MutateOpcode, /*InsnID*/0, /*RecycleInsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::LOAD32), -// CHECK-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, +// CHECK-NEXT: GIR_RootConstrainSelectedInstOperands, // CHECK-NEXT: // GIR_Coverage, 1, // CHECK-NEXT: GIR_Done, // CHECK-NEXT: // Label [[L3_ID]]: @[[L3_AT]] @@ -49,7 +49,7 @@ def LOAD16Imm : I<(outs GPR16:$dst), (ins GPR16:$src), []>; // CHECK-NEXT: GIM_Try, /*On fail goto*//*Label [[L1_ID:[0-9]+]]*/ GIMT_Encode4([[L1_AT:[0-9]+]]), // CHECK-NEXT: GIM_CheckMemorySizeEqualToLLT, /*MI*/0, /*MMO*/0, /*OpIdx*/0, // CHECK-NEXT: GIM_CheckAtomicOrdering, /*MI*/0, /*Order*/(uint8_t)AtomicOrdering::NotAtomic, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR16RegClassID), +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR16RegClassID), // CHECK-NEXT: GIM_CheckPointerToAny, /*MI*/0, /*Op*/1, /*SizeInBits*/16, // CHECK-NEXT: GIM_Try, /*On fail goto*//*Label [[L2_ID:[0-9]+]]*/ GIMT_Encode4([[L2_AT:[0-9]+]]), // CHECK-NEXT: GIM_RecordInsn, /*DefineMI*/1, /*MI*/0, /*OpIdx*/1, // MIs[1] @@ -58,22 +58,21 @@ def LOAD16Imm : I<(outs GPR16:$dst), (ins GPR16:$src), []>; // CHECK-NEXT: GIM_CheckType, /*MI*/1, /*Op*/2, /*Type*/GILLT_s16, // CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/1, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR16RegClassID), // CHECK-NEXT: GIM_CheckConstantInt8, /*MI*/1, /*Op*/2, 10, -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/1, +// CHECK-NEXT: GIM_CheckIsSafeToFold, /*NumInsns*/1, // CHECK-NEXT: // (ld:{ *:[i16] } (add:{ *:[i16] } GPR16:{ *:[i16] }:$src, 10:{ *:[i16] }))<><> => (LOAD16Imm:{ *:[i16] } GPR16:{ *:[i16] }:$src) -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::LOAD16Imm), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::LOAD16Imm), +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] // CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/1, /*OpIdx*/1, // src // CHECK-NEXT: GIR_MergeMemOperands, /*InsnID*/0, /*NumInsns*/2, /*MergeInsnID's*/0, 1, -// CHECK-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// CHECK-NEXT: GIR_RootConstrainSelectedInstOperands, // CHECK-NEXT: // GIR_Coverage, 3, -// CHECK-NEXT: GIR_Done, +// CHECK-NEXT: GIR_EraseRootFromParent_Done, // CHECK-NEXT: // Label [[L2_ID]]: @[[L2_AT]] // CHECK-NEXT: GIM_Try, /*On fail goto*//*Label [[L3_ID:[0-9]+]]*/ GIMT_Encode4([[L3_AT:[0-9]+]]), -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR16RegClassID), +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR16RegClassID), // CHECK-NEXT: // (ld:{ *:[i16] } GPR16:{ *:[i16] }:$src)<><> => (LOAD16:{ *:[i16] } GPR16:{ *:[i16] }:$src) // CHECK-NEXT: GIR_MutateOpcode, /*InsnID*/0, /*RecycleInsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::LOAD16), -// CHECK-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, +// CHECK-NEXT: GIR_RootConstrainSelectedInstOperands, // CHECK-NEXT: // GIR_Coverage, 2, // CHECK-NEXT: GIR_Done, // CHECK-NEXT: // Label [[L3_ID]]: @[[L3_AT]] diff --git a/llvm/test/TableGen/GlobalISelEmitterMatchTableOptimizerSameOperand-invalid.td b/llvm/test/TableGen/GlobalISelEmitterMatchTableOptimizerSameOperand-invalid.td index 729a30e8cbf3001cec476c6e0661c7b6345497b2..d93805b612a19e85a158919be146425c7d29678c 100644 --- a/llvm/test/TableGen/GlobalISelEmitterMatchTableOptimizerSameOperand-invalid.td +++ b/llvm/test/TableGen/GlobalISelEmitterMatchTableOptimizerSameOperand-invalid.td @@ -5,88 +5,83 @@ include "GlobalISelEmitterCommon.td" def InstTwoOperands : I<(outs GPR32:$dst), (ins GPR32:$src1, GPR32:$src2), []>; def InstThreeOperands : I<(outs GPR32:$dst), (ins GPR32:$cond, GPR32:$src,GPR32:$src2), []>; - -// CHECK: GIM_Try, /*On fail goto*//*Label 0*/ GIMT_Encode4(255), -// CHECK-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_SELECT), -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/2, /*Type*/GILLT_s32, -// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 1*/ GIMT_Encode4(217), -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), -// CHECK-NEXT: GIM_CheckIsSameOperand, /*MI*/0, /*OpIdx*/3, /*OtherMI*/2, /*OtherOpIdx*/2, -// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 2*/ GIMT_Encode4(126), // Rule ID 1 // -// CHECK-NEXT: GIM_RecordInsn, /*DefineMI*/1, /*MI*/0, /*OpIdx*/1, // MIs[1] -// CHECK-NEXT: GIM_CheckOpcode, /*MI*/1, GIMT_Encode2(TargetOpcode::G_ICMP), -// CHECK-NEXT: GIM_CheckType, /*MI*/1, /*Op*/2, /*Type*/GILLT_s32, -// CHECK-NEXT: GIM_CheckType, /*MI*/1, /*Op*/3, /*Type*/GILLT_s32, -// CHECK-NEXT: // MIs[1] Operand 1 -// CHECK-NEXT: GIM_CheckCmpPredicate, /*MI*/1, /*Op*/1, /*Predicate*/GIMT_Encode2(CmpInst::ICMP_EQ), -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/1, /*Op*/2, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), -// CHECK-NEXT: GIM_CheckConstantInt8, /*MI*/1, /*Op*/3, 0, -// CHECK-NEXT: GIM_RecordInsn, /*DefineMI*/2, /*MI*/0, /*OpIdx*/2, // MIs[2] -// CHECK-NEXT: GIM_CheckOpcode, /*MI*/2, GIMT_Encode2(TargetOpcode::G_SUB), -// CHECK-NEXT: GIM_CheckType, /*MI*/2, /*Op*/1, /*Type*/GILLT_s32, -// CHECK-NEXT: GIM_CheckType, /*MI*/2, /*Op*/2, /*Type*/GILLT_s32, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/2, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/2, /*Op*/2, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/1, -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/2, -// CHECK-NEXT: // (select:{ *:[i32] } (setcc:{ *:[i32] } GPR32:{ *:[i32] }:$cond, 0:{ *:[i32] }, SETEQ:{ *:[Other] }), (sub:{ *:[i32] } GPR32:{ *:[i32] }:$src1, GPR32:{ *:[i32] }:$src2), GPR32:{ *:[i32] }:$src2) => (InstThreeOperands:{ *:[i32] } GPR32:{ *:[i32] }:$cond, GPR32:{ *:[i32] }:$src1, GPR32:{ *:[i32] }:$src2) -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::InstThreeOperands), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/1, /*OpIdx*/2, // cond -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/2, /*OpIdx*/1, // src1 -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/2, /*OpIdx*/2, // src2 -// CHECK-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, -// CHECK-NEXT: // GIR_Coverage, 1, -// CHECK-NEXT: GIR_Done, -// CHECK-NEXT: // Label 2: @126 -// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 3*/ GIMT_Encode4(216), // Rule ID 2 // -// CHECK-NEXT: GIM_RecordInsn, /*DefineMI*/1, /*MI*/0, /*OpIdx*/1, // MIs[1] -// CHECK-NEXT: GIM_CheckOpcode, /*MI*/1, GIMT_Encode2(TargetOpcode::G_ICMP), -// CHECK-NEXT: GIM_CheckType, /*MI*/1, /*Op*/2, /*Type*/GILLT_s32, -// CHECK-NEXT: GIM_CheckType, /*MI*/1, /*Op*/3, /*Type*/GILLT_s32, -// CHECK-NEXT: // MIs[1] Operand 1 -// CHECK-NEXT: GIM_CheckCmpPredicate, /*MI*/1, /*Op*/1, /*Predicate*/GIMT_Encode2(CmpInst::ICMP_NE), -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/1, /*Op*/2, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), -// CHECK-NEXT: GIM_CheckConstantInt8, /*MI*/1, /*Op*/3, 0, -// CHECK-NEXT: GIM_RecordInsn, /*DefineMI*/2, /*MI*/0, /*OpIdx*/2, // MIs[2] -// CHECK-NEXT: GIM_CheckOpcode, /*MI*/2, GIMT_Encode2(TargetOpcode::G_SUB), -// CHECK-NEXT: GIM_CheckType, /*MI*/2, /*Op*/1, /*Type*/GILLT_s32, -// CHECK-NEXT: GIM_CheckType, /*MI*/2, /*Op*/2, /*Type*/GILLT_s32, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/2, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/2, /*Op*/2, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/1, -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/2, -// CHECK-NEXT: // (select:{ *:[i32] } (setcc:{ *:[i32] } GPR32:{ *:[i32] }:$cond, 0:{ *:[i32] }, SETNE:{ *:[Other] }), (sub:{ *:[i32] } GPR32:{ *:[i32] }:$src1, GPR32:{ *:[i32] }:$src2), GPR32:{ *:[i32] }:$src2) => (InstThreeOperands:{ *:[i32] } GPR32:{ *:[i32] }:$cond, GPR32:{ *:[i32] }:$src1, GPR32:{ *:[i32] }:$src2) -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::InstThreeOperands), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/1, /*OpIdx*/2, // cond -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/2, /*OpIdx*/1, // src1 -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/2, /*OpIdx*/2, // src2 -// CHECK-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, -// CHECK-NEXT: // GIR_Coverage, 2, -// CHECK-NEXT: GIR_Done, -// CHECK-NEXT: // Label 3: @216 -// CHECK-NEXT: GIM_Reject, -// CHECK-NEXT: // Label 1: @217 -// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 4*/ GIMT_Encode4(254), // Rule ID 0 // -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/3, /*Type*/GILLT_s32, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/2, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/3, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), -// CHECK-NEXT: // (select:{ *:[i32] } GPR32:{ *:[i32] }:$cond, GPR32:{ *:[i32] }:$src1, GPR32:{ *:[i32] }:$src2) => (InstThreeOperands:{ *:[i32] } GPR32:{ *:[i32] }:$cond, GPR32:{ *:[i32] }:$src1, GPR32:{ *:[i32] }:$src2) -// CHECK-NEXT: GIR_MutateOpcode, /*InsnID*/0, /*RecycleInsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::InstThreeOperands), -// CHECK-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, -// CHECK-NEXT: // GIR_Coverage, 0, -// CHECK-NEXT: GIR_Done, -// CHECK-NEXT: // Label 4: @254 -// CHECK-NEXT: GIM_Reject, -// CHECK-NEXT: // Label 0: @255 -// CHECK-NEXT: GIM_Reject, +// CHECK: GIM_Try, /*On fail goto*//*Label 0*/ GIMT_Encode4(229), +// CHECK-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_SELECT), +// CHECK-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckType, /*Op*/2, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 1*/ GIMT_Encode4(197), +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// CHECK-NEXT: GIM_CheckIsSameOperand, /*MI*/0, /*OpIdx*/3, /*OtherMI*/2, /*OtherOpIdx*/2, +// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 2*/ GIMT_Encode4(114), // Rule ID 1 // +// CHECK-NEXT: GIM_RecordInsn, /*DefineMI*/1, /*MI*/0, /*OpIdx*/1, // MIs[1] +// CHECK-NEXT: GIM_CheckOpcode, /*MI*/1, GIMT_Encode2(TargetOpcode::G_ICMP), +// CHECK-NEXT: GIM_CheckType, /*MI*/1, /*Op*/2, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_CheckType, /*MI*/1, /*Op*/3, /*Type*/GILLT_s32, +// CHECK-NEXT: // MIs[1] Operand 1 +// CHECK-NEXT: GIM_CheckCmpPredicate, /*MI*/1, /*Op*/1, /*Predicate*/GIMT_Encode2(CmpInst::ICMP_EQ), +// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/1, /*Op*/2, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// CHECK-NEXT: GIM_CheckConstantInt8, /*MI*/1, /*Op*/3, 0, +// CHECK-NEXT: GIM_RecordInsn, /*DefineMI*/2, /*MI*/0, /*OpIdx*/2, // MIs[2] +// CHECK-NEXT: GIM_CheckOpcode, /*MI*/2, GIMT_Encode2(TargetOpcode::G_SUB), +// CHECK-NEXT: GIM_CheckType, /*MI*/2, /*Op*/1, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_CheckType, /*MI*/2, /*Op*/2, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/2, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/2, /*Op*/2, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// CHECK-NEXT: GIM_CheckIsSafeToFold, /*NumInsns*/2, +// CHECK-NEXT: // (select:{ *:[i32] } (setcc:{ *:[i32] } GPR32:{ *:[i32] }:$cond, 0:{ *:[i32] }, SETEQ:{ *:[Other] }), (sub:{ *:[i32] } GPR32:{ *:[i32] }:$src1, GPR32:{ *:[i32] }:$src2), GPR32:{ *:[i32] }:$src2) => (InstThreeOperands:{ *:[i32] } GPR32:{ *:[i32] }:$cond, GPR32:{ *:[i32] }:$src1, GPR32:{ *:[i32] }:$src2) +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::InstThreeOperands), +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] +// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/1, /*OpIdx*/2, // cond +// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/2, /*OpIdx*/1, // src1 +// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/2, /*OpIdx*/2, // src2 +// CHECK-NEXT: GIR_RootConstrainSelectedInstOperands, +// CHECK-NEXT: // GIR_Coverage, 1, +// CHECK-NEXT: GIR_EraseRootFromParent_Done, +// CHECK-NEXT: // Label 2: @114 +// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 3*/ GIMT_Encode4(196), // Rule ID 2 // +// CHECK-NEXT: GIM_RecordInsn, /*DefineMI*/1, /*MI*/0, /*OpIdx*/1, // MIs[1] +// CHECK-NEXT: GIM_CheckOpcode, /*MI*/1, GIMT_Encode2(TargetOpcode::G_ICMP), +// CHECK-NEXT: GIM_CheckType, /*MI*/1, /*Op*/2, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_CheckType, /*MI*/1, /*Op*/3, /*Type*/GILLT_s32, +// CHECK-NEXT: // MIs[1] Operand 1 +// CHECK-NEXT: GIM_CheckCmpPredicate, /*MI*/1, /*Op*/1, /*Predicate*/GIMT_Encode2(CmpInst::ICMP_NE), +// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/1, /*Op*/2, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// CHECK-NEXT: GIM_CheckConstantInt8, /*MI*/1, /*Op*/3, 0, +// CHECK-NEXT: GIM_RecordInsn, /*DefineMI*/2, /*MI*/0, /*OpIdx*/2, // MIs[2] +// CHECK-NEXT: GIM_CheckOpcode, /*MI*/2, GIMT_Encode2(TargetOpcode::G_SUB), +// CHECK-NEXT: GIM_CheckType, /*MI*/2, /*Op*/1, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_CheckType, /*MI*/2, /*Op*/2, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/2, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/2, /*Op*/2, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// CHECK-NEXT: GIM_CheckIsSafeToFold, /*NumInsns*/2, +// CHECK-NEXT: // (select:{ *:[i32] } (setcc:{ *:[i32] } GPR32:{ *:[i32] }:$cond, 0:{ *:[i32] }, SETNE:{ *:[Other] }), (sub:{ *:[i32] } GPR32:{ *:[i32] }:$src1, GPR32:{ *:[i32] }:$src2), GPR32:{ *:[i32] }:$src2) => (InstThreeOperands:{ *:[i32] } GPR32:{ *:[i32] }:$cond, GPR32:{ *:[i32] }:$src1, GPR32:{ *:[i32] }:$src2) +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::InstThreeOperands), +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] +// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/1, /*OpIdx*/2, // cond +// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/2, /*OpIdx*/1, // src1 +// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/2, /*OpIdx*/2, // src2 +// CHECK-NEXT: GIR_RootConstrainSelectedInstOperands, +// CHECK-NEXT: // GIR_Coverage, 2, +// CHECK-NEXT: GIR_EraseRootFromParent_Done, +// CHECK-NEXT: // Label 3: @196 +// CHECK-NEXT: GIM_Reject, +// CHECK-NEXT: // Label 1: @197 +// CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 4*/ GIMT_Encode4(228), // Rule ID 0 // +// CHECK-NEXT: GIM_RootCheckType, /*Op*/3, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/2, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/3, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// CHECK-NEXT: // (select:{ *:[i32] } GPR32:{ *:[i32] }:$cond, GPR32:{ *:[i32] }:$src1, GPR32:{ *:[i32] }:$src2) => (InstThreeOperands:{ *:[i32] } GPR32:{ *:[i32] }:$cond, GPR32:{ *:[i32] }:$src1, GPR32:{ *:[i32] }:$src2) +// CHECK-NEXT: GIR_MutateOpcode, /*InsnID*/0, /*RecycleInsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::InstThreeOperands), +// CHECK-NEXT: GIR_RootConstrainSelectedInstOperands, +// CHECK-NEXT: // GIR_Coverage, 0, +// CHECK-NEXT: GIR_Done, +// CHECK-NEXT: // Label 4: @228 +// CHECK-NEXT: GIM_Reject, +// CHECK-NEXT: // Label 0: @229 +// CHECK-NEXT: GIM_Reject, def : Pat<(i32 (select GPR32:$cond, GPR32:$src1, GPR32:$src2)), (InstThreeOperands GPR32:$cond, GPR32:$src1, GPR32:$src2)>; diff --git a/llvm/test/TableGen/GlobalISelEmitterMatchTableOptimizerSameOperand.td b/llvm/test/TableGen/GlobalISelEmitterMatchTableOptimizerSameOperand.td index 00ece5f4ca7989bce7c0e4af7f3711d05a73a4af..1ac33990ab3b10ce19bb2777c82e80919dfbc39e 100644 --- a/llvm/test/TableGen/GlobalISelEmitterMatchTableOptimizerSameOperand.td +++ b/llvm/test/TableGen/GlobalISelEmitterMatchTableOptimizerSameOperand.td @@ -9,7 +9,7 @@ def InstThreeOperands : I<(outs GPR32:$dst), (ins GPR32:$cond, GPR32:$src,GPR32: // Make sure the GIM_CheckIsSameOperand check is not hoisted into the common header group // CHECK: GIM_Try, /*On fail goto*//*Label 1*/ -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // CHECK-NOT: GIM_CheckIsSameOperand // CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 2*/ // CHECK: GIM_CheckIsSameOperand, /*MI*/0, /*OpIdx*/3, /*OtherMI*/2, /*OtherOpIdx*/1, diff --git a/llvm/test/TableGen/GlobalISelEmitterOverloadedPtr.td b/llvm/test/TableGen/GlobalISelEmitterOverloadedPtr.td index 64723a0bbd4b68b64d4fa98a7757d7a225f578df..422edbba0e7a0f042d7ed0b771ff4c44566e3cb0 100644 --- a/llvm/test/TableGen/GlobalISelEmitterOverloadedPtr.td +++ b/llvm/test/TableGen/GlobalISelEmitterOverloadedPtr.td @@ -12,14 +12,14 @@ let TargetPrefix = "mytarget" in { // GIM_CheckPointerToAny rather than a GIM_CheckType. // // CHECK: GIM_CheckIntrinsicID, /*MI*/0, /*Op*/1, GIMT_Encode2(Intrinsic::mytarget_anyptr), -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// CHECK-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // CHECK-NEXT: // MIs[0] src // CHECK-NEXT: GIM_CheckPointerToAny, /*MI*/0, /*Op*/2, /*SizeInBits*/32, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/2, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/2, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // CHECK-NEXT: GIM_CheckCxxInsnPredicate, /*MI*/0, /*FnId*/GIMT_Encode2(GICXXPred_MI_Predicate_frag_anyptr), // CHECK-NEXT: // (intrinsic_w_chain:{ *:[i32] } {{[0-9]+}}:{ *:[iPTR] }, GPR32:{ *:[i32] }:$src)<> => (ANYLOAD:{ *:[i32] } GPR32:{ *:[i32] }:$src) -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::ANYLOAD), +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::ANYLOAD), let hasSideEffects = 1 in { def ANYLOAD : I<(outs GPR32:$dst), (ins GPR32:$src1), [(set GPR32:$dst, (load GPR32:$src1))]>; diff --git a/llvm/test/TableGen/GlobalISelEmitterRegSequence.td b/llvm/test/TableGen/GlobalISelEmitterRegSequence.td index 42ac68b9d91d97efe76750aedd39068e0f877d50..3829070b28efebac6cb11db4c004b1435afd179a 100644 --- a/llvm/test/TableGen/GlobalISelEmitterRegSequence.td +++ b/llvm/test/TableGen/GlobalISelEmitterRegSequence.td @@ -33,11 +33,11 @@ def SUBSOME_INSN : I<(outs SRegs:$dst), (ins SOP:$src), []>; // CHECK: GIM_CheckNumOperands, /*MI*/0, /*Expected*/2, // CHECK-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_SEXT), // CHECK-NEXT: // MIs[0] DstI[dst] -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(Test::DRegsRegClassID), +// CHECK-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(Test::DRegsRegClassID), // CHECK-NEXT: // MIs[0] src -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s16, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/1, /*RC*/GIMT_Encode2(Test::SRegsRegClassID), +// CHECK-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s16, +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/1, /*RC*/GIMT_Encode2(Test::SRegsRegClassID), // CHECK-NEXT: // (sext:{ *:[i32] } SOP:{ *:[i16] }:$src) => (REG_SEQUENCE:{ *:[i32] } DRegs:{ *:[i32] }, (SUBSOME_INSN:{ *:[i16] } SOP:{ *:[i16] }:$src), sub0:{ *:[i32] }, (SUBSOME_INSN:{ *:[i16] } SOP:{ *:[i16] }:$src), sub1:{ *:[i32] }) // CHECK-NEXT: GIR_MakeTempReg, /*TempRegID*/0, /*TypeID*/GILLT_s16, // CHECK-NEXT: GIR_MakeTempReg, /*TempRegID*/1, /*TypeID*/GILLT_s16, @@ -49,8 +49,8 @@ def SUBSOME_INSN : I<(outs SRegs:$dst), (ins SOP:$src), []>; // CHECK-NEXT: GIR_AddTempRegister, /*InsnID*/1, /*TempRegID*/0, /*TempRegFlags*/GIMT_Encode2(RegState::Define), // CHECK-NEXT: GIR_Copy, /*NewInsnID*/1, /*OldInsnID*/0, /*OpIdx*/1, // src // CHECK-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/1, -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(TargetOpcode::REG_SEQUENCE), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(TargetOpcode::REG_SEQUENCE), +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] // CHECK-NEXT: GIR_AddSimpleTempRegister, /*InsnID*/0, /*TempRegID*/0, // CHECK-NEXT: GIR_AddImm8, /*InsnID*/0, /*SubRegIndex*/1, // CHECK-NEXT: GIR_AddSimpleTempRegister, /*InsnID*/0, /*TempRegID*/1, @@ -58,7 +58,8 @@ def SUBSOME_INSN : I<(outs SRegs:$dst), (ins SOP:$src), []>; // CHECK-NEXT: GIR_ConstrainOperandRC, /*InsnID*/0, /*Op*/0, GIMT_Encode2(Test::DRegsRegClassID), // CHECK-NEXT: GIR_ConstrainOperandRC, /*InsnID*/0, /*Op*/1, GIMT_Encode2(Test::SRegsRegClassID), // CHECK-NEXT: GIR_ConstrainOperandRC, /*InsnID*/0, /*Op*/3, GIMT_Encode2(Test::SRegsRegClassID), -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// CHECK-NEXT: // GIR_Coverage, 0, +// CHECK-NEXT: GIR_EraseRootFromParent_Done, def : Pat<(i32 (sext SOP:$src)), (REG_SEQUENCE DRegs, (SUBSOME_INSN SOP:$src), sub0, (SUBSOME_INSN SOP:$src), sub1)>; @@ -74,7 +75,7 @@ def : Pat<(i32 (sext SOP:$src)), // CHECK-NEXT: GIR_ConstrainOperandRC, /*InsnID*/1, /*Op*/0, GIMT_Encode2(Test::DRegsRegClassID), // CHECK-NEXT: GIR_ConstrainOperandRC, /*InsnID*/1, /*Op*/1, GIMT_Encode2(Test::SRegsRegClassID), // CHECK-NEXT: GIR_ConstrainOperandRC, /*InsnID*/1, /*Op*/3, GIMT_Encode2(Test::SRegsRegClassID), -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::SOME_INSN), +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::SOME_INSN), // Make sure operands are constrained when REG_SEQUENCE isn't the root instruction. def : Pat<(i32 (zext SOP:$src)), (SOME_INSN (REG_SEQUENCE DRegs, (SUBSOME_INSN SOP:$src), sub0, diff --git a/llvm/test/TableGen/GlobalISelEmitterSkippedPatterns.td b/llvm/test/TableGen/GlobalISelEmitterSkippedPatterns.td index 7c9df02ebd87c63337441bce6da5e0d1cdbc4dc9..fc8abc6fbc547e4285cc3ddf6a11aa049b2e7bf2 100644 --- a/llvm/test/TableGen/GlobalISelEmitterSkippedPatterns.td +++ b/llvm/test/TableGen/GlobalISelEmitterSkippedPatterns.td @@ -1,4 +1,6 @@ // RUN: llvm-tblgen -warn-on-skipped-patterns -gen-global-isel -I %p/../../include %s -I %p/Common -o /dev/null 2>&1 | FileCheck %s +// RUN: llvm-tblgen -warn-on-skipped-patterns -gen-global-isel -I %p/../../include %s -I %p/Common -o /dev/null -DIGNORE 2>&1 | FileCheck --allow-empty --check-prefix=IGNORED %s + include "llvm/Target/Target.td" include "GlobalISelEmitterCommon.td" @@ -23,6 +25,10 @@ def INSN : I<(outs GPR32:$dst), (ins GPR32:$src1, complex:$src2), []>; //===- Bail out when we define a variable twice wrt complex suboperands. -===// +#ifdef IGNORE +let GISelShouldIgnore = 1 in +#endif +// IGNORED-NOT: warning: Skipped pattern: Error: {{.*}} // CHECK: warning: Skipped pattern: Error: Complex suboperand x referenced by different operands: complex_rr:x:y and complex_rr:x:z. def : Pat<(add (complex_rr GPR32:$x, GPR32:$y), (complex_rr GPR32:$x, GPR32:$z)), diff --git a/llvm/test/TableGen/GlobalISelEmitterSubreg.td b/llvm/test/TableGen/GlobalISelEmitterSubreg.td index 94e321e638c5f13ce9fda0ab76e645f3dfe785a2..8df3238f6cc21e42aa20e875738f8bf3c502f9b2 100644 --- a/llvm/test/TableGen/GlobalISelEmitterSubreg.td +++ b/llvm/test/TableGen/GlobalISelEmitterSubreg.td @@ -71,12 +71,13 @@ def : Pat<(sub (complex DOP:$src1, DOP:$src2), 77), // CHECK-NEXT: GIR_ComplexSubOperandSubRegRenderer, /*InsnID*/1, /*RendererID*/GIMT_Encode2(0), /*SubOperand*/0, /*SubRegIdx*/GIMT_Encode2(1), // src1 // CHECK-NEXT: GIR_ConstrainOperandRC, /*InsnID*/1, /*Op*/0, GIMT_Encode2(Test::SRegsRegClassID), // CHECK-NEXT: GIR_ConstrainOperandRC, /*InsnID*/1, /*Op*/1, GIMT_Encode2(Test::DRegsRegClassID), -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::SOME_INSN2), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::SOME_INSN2), +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] // CHECK-NEXT: GIR_AddSimpleTempRegister, /*InsnID*/0, /*TempRegID*/0, // CHECK-NEXT: GIR_AddSimpleTempRegister, /*InsnID*/0, /*TempRegID*/1, -// CHECK-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// CHECK-NEXT: GIR_RootConstrainSelectedInstOperands, +// CHECK-NEXT: // GIR_Coverage, 2, +// CHECK-NEXT: GIR_EraseRootFromParent_Done, // Test that we import INSERT_SUBREG when its subregister source has a given // class. @@ -86,15 +87,16 @@ def : Pat<(i32 (anyext i16:$src)), (INSERT_SUBREG (i32 (IMPLICIT_DEF)), SOP:$src // CHECK-NEXT: GIR_BuildMI, /*InsnID*/1, /*Opcode*/GIMT_Encode2(TargetOpcode::IMPLICIT_DEF), // CHECK-NEXT: GIR_AddTempRegister, /*InsnID*/1, /*TempRegID*/0, /*TempRegFlags*/GIMT_Encode2(RegState::Define), // CHECK-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/1, -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(TargetOpcode::INSERT_SUBREG), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(TargetOpcode::INSERT_SUBREG), +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] // CHECK-NEXT: GIR_AddSimpleTempRegister, /*InsnID*/0, /*TempRegID*/0, -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/1, // src +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/1, // src // CHECK-NEXT: GIR_AddImm8, /*InsnID*/0, /*Imm*/1, // CHECK-NEXT: GIR_ConstrainOperandRC, /*InsnID*/0, /*Op*/0, GIMT_Encode2(Test::DRegsRegClassID), // CHECK-NEXT: GIR_ConstrainOperandRC, /*InsnID*/0, /*Op*/1, GIMT_Encode2(Test::DRegsRegClassID), // CHECK-NEXT: GIR_ConstrainOperandRC, /*InsnID*/0, /*Op*/2, GIMT_Encode2(Test::SRegsRegClassID), -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// CHECK-NEXT: // GIR_Coverage, 3, +// CHECK-NEXT: GIR_EraseRootFromParent_Done, // Test that we can import INSERT_SUBREG when it is a subinstruction of another @@ -114,11 +116,12 @@ def : Pat<(i32 (anyext i16:$src)), (SOME_INSN (INSERT_SUBREG (i32 (IMPLICIT_DEF) // CHECK-NEXT: GIR_ConstrainOperandRC, /*InsnID*/1, /*Op*/0, GIMT_Encode2(Test::DRegsRegClassID), // CHECK-NEXT: GIR_ConstrainOperandRC, /*InsnID*/1, /*Op*/1, GIMT_Encode2(Test::DRegsRegClassID), // CHECK-NEXT: GIR_ConstrainOperandRC, /*InsnID*/1, /*Op*/2, GIMT_Encode2(Test::SRegsRegClassID), -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::SOME_INSN), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::SOME_INSN), +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] // CHECK-NEXT: GIR_AddSimpleTempRegister, /*InsnID*/0, /*TempRegID*/0, -// CHECK-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// CHECK-NEXT: GIR_RootConstrainSelectedInstOperands, +// CHECK-NEXT: // GIR_Coverage, 4, +// CHECK-NEXT: GIR_EraseRootFromParent_Done, // Test that we correctly infer the super register class for INSERT_SUBREG when @@ -126,7 +129,7 @@ def : Pat<(i32 (anyext i16:$src)), (SOME_INSN (INSERT_SUBREG (i32 (IMPLICIT_DEF) // not a D register. def : Pat<(i32 (anyext i16:$src)), (INSERT_SUBREG (i32 (COPY_TO_REGCLASS SOP:$src, ERegs)), SOP:$src, sub0)>; // CHECK-LABEL: (anyext:{ *:[i32] } i16:{ *:[i16] }:$src) => (INSERT_SUBREG:{ *:[i32] } (COPY_TO_REGCLASS:{ *:[i32] } SOP:{ *:[i16] }:$src, ERegs:{ *:[i32] }), SOP:{ *:[i16] }:$src, sub0:{ *:[i32] }) -// CHECK: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(TargetOpcode::INSERT_SUBREG), +// CHECK: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(TargetOpcode::INSERT_SUBREG), // CHECK-DAG: GIR_ConstrainOperandRC, /*InsnID*/0, /*Op*/0, GIMT_Encode2(Test::ERegsRegClassID), // CHECK-NEXT: GIR_ConstrainOperandRC, /*InsnID*/0, /*Op*/1, GIMT_Encode2(Test::ERegsRegClassID), // CHECK-NEXT: GIR_ConstrainOperandRC, /*InsnID*/0, /*Op*/2, GIMT_Encode2(Test::SRegsRegClassID), @@ -144,15 +147,16 @@ def : Pat<(i32 (anyext i16:$src)), (INSERT_SUBREG (i32 (IMPLICIT_DEF)), (SUBSOME // CHECK-NEXT: GIR_BuildMI, /*InsnID*/1, /*Opcode*/GIMT_Encode2(TargetOpcode::IMPLICIT_DEF), // CHECK-NEXT: GIR_AddTempRegister, /*InsnID*/1, /*TempRegID*/0, /*TempRegFlags*/GIMT_Encode2(RegState::Define), // CHECK-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/1, -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(TargetOpcode::INSERT_SUBREG), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(TargetOpcode::INSERT_SUBREG), +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] // CHECK-NEXT: GIR_AddSimpleTempRegister, /*InsnID*/0, /*TempRegID*/0, // CHECK-NEXT: GIR_AddSimpleTempRegister, /*InsnID*/0, /*TempRegID*/1, // CHECK-NEXT: GIR_AddImm8, /*InsnID*/0, /*Imm*/1, // CHECK-NEXT: GIR_ConstrainOperandRC, /*InsnID*/0, /*Op*/0, GIMT_Encode2(Test::DRegsRegClassID), // CHECK-NEXT: GIR_ConstrainOperandRC, /*InsnID*/0, /*Op*/1, GIMT_Encode2(Test::DRegsRegClassID), // CHECK-NEXT: GIR_ConstrainOperandRC, /*InsnID*/0, /*Op*/2, GIMT_Encode2(Test::SRegsRegClassID), -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// CHECK-NEXT: // GIR_Coverage, 6, +// CHECK-NEXT: GIR_EraseRootFromParent_Done, // Test an EXTRACT_SUBREG that is a sub instruction. The individual // operands should be constrained to specific register classes, and @@ -166,7 +170,7 @@ def : Pat<(i16 (trunc (not DOP:$src))), // CHECK-NEXT: GIR_CopySubReg, /*NewInsnID*/1, /*OldInsnID*/1, /*OpIdx*/1, /*SubRegIdx*/GIMT_Encode2(1), // src // CHECK-NEXT: GIR_ConstrainOperandRC, /*InsnID*/1, /*Op*/0, GIMT_Encode2(Test::SRegsRegClassID), // CHECK-NEXT: GIR_ConstrainOperandRC, /*InsnID*/1, /*Op*/1, GIMT_Encode2(Test::DRegsRegClassID), -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::SUBSOME_INSN), +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::SUBSOME_INSN), // Test an extract from an output instruction result (nonleaf) def : Pat<(i16 (trunc (bitreverse DOP:$src))), @@ -174,26 +178,27 @@ def : Pat<(i16 (trunc (bitreverse DOP:$src))), // CHECK-LABEL: GIM_CheckOpcode, /*MI*/1, GIMT_Encode2(TargetOpcode::G_BITREVERSE), // CHECK-NEXT: GIM_CheckType, /*MI*/1, /*Op*/1, /*Type*/GILLT_s32, // CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/1, /*Op*/1, /*RC*/GIMT_Encode2(Test::DRegsRegClassID), -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/1, +// CHECK-NEXT: GIM_CheckIsSafeToFold, /*NumInsns*/1, // CHECK-NEXT: // (trunc:{ *:[i16] } (bitreverse:{ *:[i32] } DOP:{ *:[i32] }:$src)) => (EXTRACT_SUBREG:{ *:[i16] } (SOME_INSN:{ *:[i32] } DOP:{ *:[i32] }:$src), sub0:{ *:[i32] }) // CHECK-NEXT: GIR_MakeTempReg, /*TempRegID*/0, /*TypeID*/GILLT_s32, // CHECK-NEXT: GIR_BuildMI, /*InsnID*/1, /*Opcode*/GIMT_Encode2(MyTarget::SOME_INSN), // CHECK-NEXT: GIR_AddTempRegister, /*InsnID*/1, /*TempRegID*/0, /*TempRegFlags*/GIMT_Encode2(RegState::Define), // CHECK-NEXT: GIR_Copy, /*NewInsnID*/1, /*OldInsnID*/1, /*OpIdx*/1, // src // CHECK-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/1, -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(TargetOpcode::COPY), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(TargetOpcode::COPY), +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] // CHECK-NEXT: GIR_AddTempSubRegister, /*InsnID*/0, /*TempRegID*/0, /*TempRegFlags*/GIMT_Encode2(0), GIMT_Encode2(sub0), // CHECK-NEXT: GIR_ConstrainOperandRC, /*InsnID*/0, /*Op*/0, GIMT_Encode2(Test::SRegsRegClassID), // CHECK-NEXT: GIR_ConstrainOperandRC, /*InsnID*/0, /*Op*/1, GIMT_Encode2(Test::DRegsRegClassID), -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// CHECK-NEXT: // GIR_Coverage, 8, +// CHECK-NEXT: GIR_EraseRootFromParent_Done, // EXTRACT_SUBREG is subinstruction, but also doesn't have a leaf input // CHECK-LABEL: GIM_CheckOpcode, /*MI*/1, GIMT_Encode2(TargetOpcode::G_CTPOP), // CHECK-NEXT: GIM_CheckType, /*MI*/1, /*Op*/1, /*Type*/GILLT_s32, // CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/1, /*Op*/1, /*RC*/GIMT_Encode2(Test::DRegsRegClassID), -// CHECK-NEXT: GIM_CheckIsSafeToFold, /*InsnID*/1, +// CHECK-NEXT: GIM_CheckIsSafeToFold, /*NumInsns*/1, // CHECK-NEXT: // (trunc:{ *:[i16] } (ctpop:{ *:[i32] } DOP:{ *:[i32] }:$src)) => (SUBSOME_INSN2:{ *:[i16] } (EXTRACT_SUBREG:{ *:[i16] } (SOME_INSN:{ *:[i32] } DOP:{ *:[i32] }:$src), sub0:{ *:[i32] })) // CHECK-NEXT: GIR_MakeTempReg, /*TempRegID*/0, /*TypeID*/GILLT_s16, // CHECK-NEXT: GIR_MakeTempReg, /*TempRegID*/1, /*TypeID*/GILLT_s32, @@ -206,11 +211,12 @@ def : Pat<(i16 (trunc (bitreverse DOP:$src))), // CHECK-NEXT: GIR_AddTempSubRegister, /*InsnID*/1, /*TempRegID*/1, /*TempRegFlags*/GIMT_Encode2(0), GIMT_Encode2(sub0), // CHECK-NEXT: GIR_ConstrainOperandRC, /*InsnID*/1, /*Op*/0, GIMT_Encode2(Test::SRegsRegClassID), // CHECK-NEXT: GIR_ConstrainOperandRC, /*InsnID*/1, /*Op*/1, GIMT_Encode2(Test::DRegsRegClassID), -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::SUBSOME_INSN2), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::SUBSOME_INSN2), +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] // CHECK-NEXT: GIR_AddSimpleTempRegister, /*InsnID*/0, /*TempRegID*/0, -// CHECK-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// CHECK-NEXT: GIR_RootConstrainSelectedInstOperands, +// CHECK-NEXT: // GIR_Coverage, 9, +// CHECK-NEXT: GIR_EraseRootFromParent_Done, def : Pat<(i16 (trunc (ctpop DOP:$src))), (SUBSOME_INSN2 (EXTRACT_SUBREG (SOME_INSN DOP:$src), sub0))>; @@ -218,13 +224,13 @@ def : Pat<(i16 (trunc (ctpop DOP:$src))), def : Pat<(i16 (trunc DOP:$src)), (EXTRACT_SUBREG DOP:$src, sub0)>; // CHECK-LABEL: // (trunc:{ *:[i16] } DOP:{ *:[i32] }:$src) => (EXTRACT_SUBREG:{ *:[i16] } DOP:{ *:[i32] }:$src, sub0:{ *:[i32] }) -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(TargetOpcode::COPY), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(TargetOpcode::COPY), +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] // CHECK-NEXT: GIR_CopySubReg, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/1, /*SubRegIdx*/GIMT_Encode2(1), // src // CHECK-NEXT: GIR_ConstrainOperandRC, /*InsnID*/0, /*Op*/0, GIMT_Encode2(Test::SRegsRegClassID), // CHECK-NEXT: GIR_ConstrainOperandRC, /*InsnID*/0, /*Op*/1, GIMT_Encode2(Test::DRegsRegClassID), -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, - +// CHECK-NEXT: // GIR_Coverage, 10, +// CHECK-NEXT: GIR_EraseRootFromParent_Done, // Test that we can import SUBREG_TO_REG def : Pat<(i32 (zext SOP:$src)), @@ -235,11 +241,12 @@ def : Pat<(i32 (zext SOP:$src)), // CHECK-NEXT: GIR_AddTempRegister, /*InsnID*/1, /*TempRegID*/0, /*TempRegFlags*/GIMT_Encode2(RegState::Define), // CHECK-NEXT: GIR_Copy, /*NewInsnID*/1, /*OldInsnID*/0, /*OpIdx*/1, // src // CHECK-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/1, -// CHECK-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(TargetOpcode::SUBREG_TO_REG), -// CHECK-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] +// CHECK-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(TargetOpcode::SUBREG_TO_REG), +// CHECK-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] // CHECK-NEXT: GIR_AddImm8, /*InsnID*/0, /*Imm*/0, // CHECK-NEXT: GIR_AddSimpleTempRegister, /*InsnID*/0, /*TempRegID*/0, // CHECK-NEXT: GIR_AddImm8, /*InsnID*/0, /*Imm*/1, // CHECK-NEXT: GIR_ConstrainOperandRC, /*InsnID*/0, /*Op*/0, GIMT_Encode2(Test::DRegsRegClassID), // CHECK-NEXT: GIR_ConstrainOperandRC, /*InsnID*/0, /*Op*/2, GIMT_Encode2(Test::SRegsRegClassID), -// CHECK-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// CHECK-NEXT: // GIR_Coverage, 11, +// CHECK-NEXT: GIR_EraseRootFromParent_Done, diff --git a/llvm/test/TableGen/GlobalISelEmitterVariadic.td b/llvm/test/TableGen/GlobalISelEmitterVariadic.td index ba6a93bd4837f23b68b1362f3105c8f6d1ef065e..992e1a4b907c309bb94ff8af0e7ee29d3b7d8360 100644 --- a/llvm/test/TableGen/GlobalISelEmitterVariadic.td +++ b/llvm/test/TableGen/GlobalISelEmitterVariadic.td @@ -26,27 +26,27 @@ def : Pat<(build_vector GPR32:$src1, GPR32:$src2), // CHECK-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_BUILD_VECTOR), // CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 1*/ GIMT_Encode4([[NEXT_NUM_OPERANDS_LABEL_1:[0-9]+]]), // Rule ID 0 // // CHECK-NEXT: GIM_CheckNumOperands, /*MI*/0, /*Expected*/2, -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// CHECK-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // CHECK-NEXT: // (build_vector:{ *:[i32] } GPR32:{ *:[i32] }:$src1) => (ONE:{ *:[i32] } GPR32:{ *:[i32] }:$src1) // CHECK-NEXT: GIR_MutateOpcode, /*InsnID*/0, /*RecycleInsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::ONE), -// CHECK-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, +// CHECK-NEXT: GIR_RootConstrainSelectedInstOperands, // CHECK-NEXT: // GIR_Coverage, 0, // CHECK-NEXT: GIR_Done, // CHECK-NEXT: // Label 1: @[[NEXT_NUM_OPERANDS_LABEL_1]] // CHECK-NEXT: GIM_Try, /*On fail goto*//*Label 2*/ GIMT_Encode4([[NEXT_NUM_OPERANDS_LABEL_2:[0-9]+]]), // Rule ID 1 // // CHECK-NEXT: GIM_CheckNumOperands, /*MI*/0, /*Expected*/3, -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, -// CHECK-NEXT: GIM_CheckType, /*MI*/0, /*Op*/2, /*Type*/GILLT_s32, -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), -// CHECK-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/2, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// CHECK-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckType, /*Op*/2, /*Type*/GILLT_s32, +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// CHECK-NEXT: GIM_RootCheckRegBankForClass, /*Op*/2, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // CHECK-NEXT: // (build_vector:{ *:[i32] } GPR32:{ *:[i32] }:$src1, GPR32:{ *:[i32] }:$src2) => (TWO:{ *:[i32] } GPR32:{ *:[i32] }:$src1, GPR32:{ *:[i32] }:$src2) // CHECK-NEXT: GIR_MutateOpcode, /*InsnID*/0, /*RecycleInsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::TWO), -// CHECK-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, +// CHECK-NEXT: GIR_RootConstrainSelectedInstOperands, // CHECK-NEXT: // GIR_Coverage, 1, // CHECK-NEXT: GIR_Done, // CHECK-NEXT: // Label 2: @[[NEXT_NUM_OPERANDS_LABEL_2]] diff --git a/llvm/test/TableGen/HasNoUse.td b/llvm/test/TableGen/HasNoUse.td index 4fe10cd44e4fbc90a562dd2dd3ff01f77e824676..030598d1cbeec0b8c9d0dcdb1117e61702c3f69b 100644 --- a/llvm/test/TableGen/HasNoUse.td +++ b/llvm/test/TableGen/HasNoUse.td @@ -17,19 +17,20 @@ def NO_RET_ATOMIC_ADD : I<(outs), (ins GPR32Op:$src0, GPR32Op:$src1), []>; // SDAG-NEXT: return true; // GISEL: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_ATOMICRMW_ADD), -// GISEL-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// GISEL-NEXT: GIM_CheckType, /*MI*/0, /*Op*/2, /*Type*/GILLT_s32, +// GISEL-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// GISEL-NEXT: GIM_RootCheckType, /*Op*/2, /*Type*/GILLT_s32, // GISEL-NEXT: GIM_CheckMemorySizeEqualTo, /*MI*/0, /*MMO*/0, /*Size*/GIMT_Encode4(4), // GISEL-NEXT: GIM_CheckHasNoUse, /*MI*/0, // GISEL-NEXT: // MIs[0] src0 // GISEL-NEXT: GIM_CheckPointerToAny, /*MI*/0, /*Op*/1, /*SizeInBits*/0, // GISEL-NEXT: // (atomic_load_add:{ *:[i32] } iPTR:{ *:[iPTR] }:$src0, i32:{ *:[i32] }:$src1)<> => (NO_RET_ATOMIC_ADD GPR32:{ *:[i32] }:$src0, GPR32:{ *:[i32] }:$src1) -// GISEL-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::NO_RET_ATOMIC_ADD), -// GISEL-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/1, // src0 -// GISEL-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/2, // src1 +// GISEL-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::NO_RET_ATOMIC_ADD), +// GISEL-NEXT: GIR_RootToRootCopy, /*OpIdx*/1, // src0 +// GISEL-NEXT: GIR_RootToRootCopy, /*OpIdx*/2, // src1 // GISEL-NEXT: GIR_MergeMemOperands, /*InsnID*/0, /*NumInsns*/1, /*MergeInsnID's*/0, -// GISEL-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, -// GISEL-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// GISEL-NEXT: GIR_RootConstrainSelectedInstOperands, +// GISEL-NEXT: // GIR_Coverage, 0, +// GISEL-NEXT: GIR_EraseRootFromParent_Done, let HasNoUse = true in defm atomic_load_add_no_ret : binary_atomic_op; diff --git a/llvm/test/TableGen/address-space-patfrags.td b/llvm/test/TableGen/address-space-patfrags.td index 46050a70720fbe1713cd6f49ca719a882293533d..582b97d55a518579782a955967b7def9da1200f3 100644 --- a/llvm/test/TableGen/address-space-patfrags.td +++ b/llvm/test/TableGen/address-space-patfrags.td @@ -102,7 +102,7 @@ def truncstorei16_addrspace : PatFrag<(ops node:$val, node:$ptr), // GISEL-NEXT: GIM_CheckMemorySizeLessThanLLT, /*MI*/0, /*MMO*/0, /*OpIdx*/0, // GISEL-NEXT: GIM_CheckAtomicOrdering, /*MI*/0, /*Order*/(uint8_t)AtomicOrdering::NotAtomic, // GISEL-NEXT: // MIs[0] src0 -// GISEL-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, +// GISEL-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, def : Pat < (truncstore GPR32:$src0, GPR32:$src1), (inst_c GPR32:$src0, GPR32:$src1) diff --git a/llvm/test/TableGen/gisel-physreg-input.td b/llvm/test/TableGen/gisel-physreg-input.td index b0af5b7dd3c117d0389d34c8e9a7712ddff6087c..f19872a331fc89c064994520d939eca87b7274f1 100644 --- a/llvm/test/TableGen/gisel-physreg-input.td +++ b/llvm/test/TableGen/gisel-physreg-input.td @@ -28,23 +28,24 @@ class I Pat> // GISEL-NEXT: GIM_CheckNumOperands, /*MI*/0, /*Expected*/3, // GISEL-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_ADD), // GISEL-NEXT: // MIs[0] DstI[dst] -// GISEL-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// GISEL-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// GISEL-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// GISEL-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // GISEL-NEXT: // MIs[0] src0 -// GISEL-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, -// GISEL-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// GISEL-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, +// GISEL-NEXT: GIM_RootCheckRegBankForClass, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // GISEL-NEXT: // MIs[0] Operand 2 -// GISEL-NEXT: GIM_CheckType, /*MI*/0, /*Op*/2, /*Type*/GILLT_s32, -// GISEL-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/2, /*RC*/GIMT_Encode2(MyTarget::Special32RegClassID), +// GISEL-NEXT: GIM_RootCheckType, /*Op*/2, /*Type*/GILLT_s32, +// GISEL-NEXT: GIM_RootCheckRegBankForClass, /*Op*/2, /*RC*/GIMT_Encode2(MyTarget::Special32RegClassID), // GISEL-NEXT: // (add:{ *:[i32] } GPR32:{ *:[i32] }:$src0, SPECIAL:{ *:[i32] }) => (ADD_PHYS:{ *:[i32] } GPR32:{ *:[i32] }:$src0) // GISEL-NEXT: GIR_BuildMI, /*InsnID*/1, /*Opcode*/GIMT_Encode2(TargetOpcode::COPY), // GISEL-NEXT: GIR_AddRegister, /*InsnID*/1, GIMT_Encode2(MyTarget::SPECIAL), /*AddRegisterRegFlags*/GIMT_Encode2(RegState::Define), // GISEL-NEXT: GIR_Copy, /*NewInsnID*/1, /*OldInsnID*/0, /*OpIdx*/2, // SPECIAL -// GISEL-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::ADD_PHYS), -// GISEL-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] -// GISEL-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/1, // src0 -// GISEL-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, -// GISEL-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// GISEL-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::ADD_PHYS), +// GISEL-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] +// GISEL-NEXT: GIR_RootToRootCopy, /*OpIdx*/1, // src0 +// GISEL-NEXT: GIR_RootConstrainSelectedInstOperands, +// GISEL-NEXT: // GIR_Coverage, 0, +// GISEL-NEXT: GIR_EraseRootFromParent_Done, def ADD_PHYS : I<(outs GPR32:$dst), (ins GPR32:$src0), [(set GPR32:$dst, (add GPR32:$src0, SPECIAL))]> { let Uses = [SPECIAL]; @@ -56,23 +57,24 @@ def ADD_PHYS : I<(outs GPR32:$dst), (ins GPR32:$src0), // GISEL-NEXT: GIM_CheckNumOperands, /*MI*/0, /*Expected*/3, // GISEL-NEXT: GIM_CheckOpcode, /*MI*/0, GIMT_Encode2(TargetOpcode::G_MUL), // GISEL-NEXT: // MIs[0] DstI[dst] -// GISEL-NEXT: GIM_CheckType, /*MI*/0, /*Op*/0, /*Type*/GILLT_s32, -// GISEL-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// GISEL-NEXT: GIM_RootCheckType, /*Op*/0, /*Type*/GILLT_s32, +// GISEL-NEXT: GIM_RootCheckRegBankForClass, /*Op*/0, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // GISEL-NEXT: // MIs[0] SPECIAL -// GISEL-NEXT: GIM_CheckType, /*MI*/0, /*Op*/1, /*Type*/GILLT_s32, -// GISEL-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), +// GISEL-NEXT: GIM_RootCheckType, /*Op*/1, /*Type*/GILLT_s32, +// GISEL-NEXT: GIM_RootCheckRegBankForClass, /*Op*/1, /*RC*/GIMT_Encode2(MyTarget::GPR32RegClassID), // GISEL-NEXT: // MIs[0] Operand 2 -// GISEL-NEXT: GIM_CheckType, /*MI*/0, /*Op*/2, /*Type*/GILLT_s32, -// GISEL-NEXT: GIM_CheckRegBankForClass, /*MI*/0, /*Op*/2, /*RC*/GIMT_Encode2(MyTarget::Special32RegClassID), +// GISEL-NEXT: GIM_RootCheckType, /*Op*/2, /*Type*/GILLT_s32, +// GISEL-NEXT: GIM_RootCheckRegBankForClass, /*Op*/2, /*RC*/GIMT_Encode2(MyTarget::Special32RegClassID), // GISEL-NEXT: // (mul:{ *:[i32] } GPR32:{ *:[i32] }:$SPECIAL, SPECIAL:{ *:[i32] }) => (MUL_PHYS:{ *:[i32] } GPR32:{ *:[i32] }:$SPECIAL) // GISEL-NEXT: GIR_BuildMI, /*InsnID*/1, /*Opcode*/GIMT_Encode2(TargetOpcode::COPY), // GISEL-NEXT: GIR_AddRegister, /*InsnID*/1, GIMT_Encode2(MyTarget::SPECIAL), /*AddRegisterRegFlags*/GIMT_Encode2(RegState::Define), // GISEL-NEXT: GIR_Copy, /*NewInsnID*/1, /*OldInsnID*/0, /*OpIdx*/2, // SPECIAL -// GISEL-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::MUL_PHYS), -// GISEL-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/0, // DstI[dst] -// GISEL-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/1, // SPECIAL -// GISEL-NEXT: GIR_ConstrainSelectedInstOperands, /*InsnID*/0, -// GISEL-NEXT: GIR_EraseFromParent, /*InsnID*/0, +// GISEL-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::MUL_PHYS), +// GISEL-NEXT: GIR_RootToRootCopy, /*OpIdx*/0, // DstI[dst] +// GISEL-NEXT: GIR_RootToRootCopy, /*OpIdx*/1, // SPECIAL +// GISEL-NEXT: GIR_RootConstrainSelectedInstOperands, +// GISEL-NEXT: // GIR_Coverage, 1, +// GISEL-NEXT: GIR_EraseRootFromParent_Done, def MUL_PHYS : I<(outs GPR32:$dst), (ins GPR32:$SPECIAL), [(set GPR32:$dst, (mul GPR32:$SPECIAL, SPECIAL))]> { let Uses = [SPECIAL]; diff --git a/llvm/test/TableGen/immarg-predicated.td b/llvm/test/TableGen/immarg-predicated.td index 320018010cc7fec571b1a4b035a0fe700cb8e6c6..dcacb2f8f1de35ac4c0599ee925c576f1d8cd7c2 100644 --- a/llvm/test/TableGen/immarg-predicated.td +++ b/llvm/test/TableGen/immarg-predicated.td @@ -14,8 +14,8 @@ def int_mytarget_sleep0 : Intrinsic<[], [llvm_i32_ty], [ImmArg>]>; // GISEL-NEXT: GIM_CheckIsImm, /*MI*/0, /*Op*/1, // GISEL-NEXT: GIM_CheckImmOperandPredicate, /*MI*/0, /*MO*/1, /*Predicate*/GIMT_Encode2(GICXXPred_I64_Predicate_tuimm9), // GISEL-NEXT: // (intrinsic_void {{[0-9]+}}:{ *:[iPTR] }, (timm:{ *:[i32] })<>:$src) => (SLEEP0 (timm:{ *:[i32] }):$src) -// GISEL-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::SLEEP0), -// GISEL-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/1, // src +// GISEL-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::SLEEP0), +// GISEL-NEXT: GIR_RootToRootCopy, /*OpIdx*/1, // src def tuimm9 : TImmLeaf(Imm); }]>; def SLEEP0 : I<(outs), (ins i32imm:$src), [(int_mytarget_sleep0 tuimm9:$src)] diff --git a/llvm/test/TableGen/immarg.td b/llvm/test/TableGen/immarg.td index 80849d512bee3013ee6b0096af9f76c777adb57a..e5fd06ce6c083f833f325e2e406afac5fffd190d 100644 --- a/llvm/test/TableGen/immarg.td +++ b/llvm/test/TableGen/immarg.td @@ -14,8 +14,8 @@ def int_mytarget_sleep1 : Intrinsic<[], [llvm_i32_ty], [ImmArg>]>; // GISEL-NEXT: // MIs[0] src // GISEL-NEXT: GIM_CheckIsImm, /*MI*/0, /*Op*/1, // GISEL-NEXT: // (intrinsic_void {{[0-9]+}}:{ *:[iPTR] }, (timm:{ *:[i32] }):$src) => (SLEEP0 (timm:{ *:[i32] }):$src) -// GISEL-NEXT: GIR_BuildMI, /*InsnID*/0, /*Opcode*/GIMT_Encode2(MyTarget::SLEEP0), -// GISEL-NEXT: GIR_Copy, /*NewInsnID*/0, /*OldInsnID*/0, /*OpIdx*/1, // src +// GISEL-NEXT: GIR_BuildRootMI, /*Opcode*/GIMT_Encode2(MyTarget::SLEEP0), +// GISEL-NEXT: GIR_RootToRootCopy, /*OpIdx*/1, // src def SLEEP0 : I<(outs), (ins i32imm:$src), [(int_mytarget_sleep0 timm:$src)] >; diff --git a/llvm/test/TableGen/riscv-target-def.td b/llvm/test/TableGen/riscv-target-def.td index ab589b31192f3987a609f6c6d2ae6d9a6353b12a..b23c7e4d40198b62e3ac36600edacdb5a4bbc3ce 100644 --- a/llvm/test/TableGen/riscv-target-def.td +++ b/llvm/test/TableGen/riscv-target-def.td @@ -2,8 +2,9 @@ include "llvm/Target/Target.td" -class RISCVExtension implies = [], +class RISCVExtension implies = [], + string fieldname = !subst("Feature", "Has", NAME), string value = "true"> : SubtargetFeature { int MajorVersion = major; @@ -11,18 +12,36 @@ class RISCVExtension implies = [], + string fieldname = !subst("Feature", "Has", NAME), + string value = "true"> + : RISCVExtension<"experimental-"#name, major, minor, desc, implies, + fieldname, value> { + let Experimental = true; +} + def FeatureStdExtI - : RISCVExtension<"i", 2, 1, "HasStdExtI", + : RISCVExtension<"i", 2, 1, "'I' (Base Integer Instruction Set)">; def FeatureStdExtZicsr - : RISCVExtension<"zicsr", 2, 0, "HasStdExtZicsr", + : RISCVExtension<"zicsr", 2, 0, "'zicsr' (CSRs)">; def FeatureStdExtZifencei - : RISCVExtension<"zifencei", 2, 0, "HasStdExtZifencei", + : RISCVExtension<"zifencei", 2, 0, "'Zifencei' (fence.i)">; +def FeatureStdExtF + : RISCVExtension<"f", 2, 2, + "'F' (Single-Precision Floating-Point)", + [FeatureStdExtZicsr]>; + +def FeatureStdExtZidummy + : RISCVExperimentalExtension<"zidummy", 0, 1, + "Dummy">; + def Feature32Bit : SubtargetFeature<"32bit", "IsRV32", "true", "Implements RV32">; def Feature64Bit @@ -75,22 +94,49 @@ def ROCKET_RV64 : RISCVProcessorModel<"rocket-rv64", def ROCKET : RISCVTuneProcessorModel<"rocket", NoSchedModel>; -// CHECK: #ifndef PROC -// CHECK: #define PROC(ENUM, NAME, DEFAULT_MARCH, FAST_UNALIGNED_ACCESS) -// CHECK: #endif +// CHECK: #ifdef GET_SUPPORTED_EXTENSIONS +// CHECK-NEXT: #undef GET_SUPPORTED_EXTENSIONS + +// CHECK: static const RISCVSupportedExtension SupportedExtensions[] = { +// CHECK-NEXT: {"f", {2, 2}}, +// CHECK-NEXT: {"i", {2, 1}}, +// CHECK-NEXT: {"zicsr", {2, 0}}, +// CHECK-NEXT: {"zifencei", {2, 0}}, +// CHECK-NEXT: }; + +// CHECK: static const RISCVSupportedExtension SupportedExperimentalExtensions[] = { +// CHECK-NEXT: {"zidummy", {0, 1}}, +// CHECK-NEXT: }; + +// CHECK: #endif // GET_SUPPORTED_EXTENSIONS + +// CHECK: #ifdef GET_IMPLIED_EXTENSIONS +// CHECK-NEXT: #undef GET_IMPLIED_EXTENSIONS + +// CHECK: static const char *ImpliedExtsF[] = {"zicsr"}; + +// CHECK: static constexpr ImpliedExtsEntry ImpliedExts[] = { +// CHECK-NEXT: { {"f"}, {ImpliedExtsF} }, +// CHECK-NEXT: }; + +// CHECK: #endif // GET_IMPLIED_EXTENSIONS + +// CHECK: #ifndef PROC +// CHECK-NEXT: #define PROC(ENUM, NAME, DEFAULT_MARCH, FAST_UNALIGNED_ACCESS) +// CHECK-NEXT: #endif -// CHECK: PROC(GENERIC_RV32, {"generic-rv32"}, {"rv32i2p1"}, 0) -// CHECK: PROC(GENERIC_RV64, {"generic-rv64"}, {"rv64i2p1"}, 0) -// CHECK: PROC(ROCKET_RV32, {"rocket-rv32"}, {"rv32i2p1_zicsr2p0_zifencei2p0"}, 0) -// CHECK: PROC(ROCKET_RV64, {"rocket-rv64"}, {"rv64i2p1_zicsr2p0_zifencei2p0"}, 0) +// CHECK: PROC(GENERIC_RV32, {"generic-rv32"}, {"rv32i2p1"}, 0) +// CHECK-NEXT: PROC(GENERIC_RV64, {"generic-rv64"}, {"rv64i2p1"}, 0) +// CHECK-NEXT: PROC(ROCKET_RV32, {"rocket-rv32"}, {"rv32i2p1_zicsr2p0_zifencei2p0"}, 0) +// CHECK-NEXT: PROC(ROCKET_RV64, {"rocket-rv64"}, {"rv64i2p1_zicsr2p0_zifencei2p0"}, 0) // CHECK: #undef PROC -// CHECK: #ifndef TUNE_PROC -// CHECK: #define TUNE_PROC(ENUM, NAME) -// CHECK: #endif +// CHECK: #ifndef TUNE_PROC +// CHECK-NEXT: #define TUNE_PROC(ENUM, NAME) +// CHECK-NEXT: #endif // CHECK: TUNE_PROC(GENERIC, "generic") -// CHECK: TUNE_PROC(ROCKET, "rocket") +// CHECK-NEXT: TUNE_PROC(ROCKET, "rocket") // CHECK: #undef TUNE_PROC diff --git a/llvm/test/TableGen/simplify-patfrag.td b/llvm/test/TableGen/simplify-patfrag.td index 904c29696a6e2cd6dfc6f314821f02309cd26a01..fbb6f97f286311e66c9cde2e077600322c31f24d 100644 --- a/llvm/test/TableGen/simplify-patfrag.td +++ b/llvm/test/TableGen/simplify-patfrag.td @@ -1,4 +1,5 @@ // RUN: llvm-tblgen -gen-dag-isel -I %p/../../include %s 2>&1 | FileCheck %s +// RUN: llvm-tblgen -gen-dag-isel -I %p/../../include -DIGNORE %s 2>&1 | FileCheck %s include "llvm/Target/Target.td" @@ -29,6 +30,10 @@ def anyconvert : PatFrags<(ops node:$src), [(bitconvert node:$src), (specialconvert node:$src)]>; +#ifdef IGNORE +// Ensure ShouldIgnore does not disable records in dag isel emitter +let GISelShouldIgnore = 1 in +#endif // And a rule that matches that PatFrag and turns it into i2f def : Pat<(f32 (anyconvert (i32 GPR:$val))), (i2f GPR:$val)>; diff --git a/llvm/test/Transforms/AtomicExpand/AMDGPU/expand-atomic-i16.ll b/llvm/test/Transforms/AtomicExpand/AMDGPU/expand-atomic-i16.ll index 3806159ab7303c199ad9ec67b424c0471dc0409a..324b6d2f65964abdeb02ba56153a2530f35c5ffb 100644 --- a/llvm/test/Transforms/AtomicExpand/AMDGPU/expand-atomic-i16.ll +++ b/llvm/test/Transforms/AtomicExpand/AMDGPU/expand-atomic-i16.ll @@ -918,7 +918,7 @@ define half @test_atomicrmw_xchg_f16_global_agent(ptr addrspace(1) %ptr, half %v ; CHECK-NEXT: [[LOADED:%.*]] = phi i32 [ [[TMP5]], [[TMP0:%.*]] ], [ [[NEWLOADED:%.*]], [[ATOMICRMW_START]] ] ; CHECK-NEXT: [[TMP6:%.*]] = and i32 [[LOADED]], [[INV_MASK]] ; CHECK-NEXT: [[TMP7:%.*]] = or i32 [[TMP6]], [[VALOPERAND_SHIFTED]] -; CHECK-NEXT: [[TMP8:%.*]] = cmpxchg ptr addrspace(1) [[ALIGNEDADDR]], i32 [[LOADED]], i32 [[TMP7]] seq_cst seq_cst, align 4 +; CHECK-NEXT: [[TMP8:%.*]] = cmpxchg ptr addrspace(1) [[ALIGNEDADDR]], i32 [[LOADED]], i32 [[TMP7]] syncscope("agent") seq_cst seq_cst, align 4 ; CHECK-NEXT: [[SUCCESS:%.*]] = extractvalue { i32, i1 } [[TMP8]], 1 ; CHECK-NEXT: [[NEWLOADED]] = extractvalue { i32, i1 } [[TMP8]], 0 ; CHECK-NEXT: br i1 [[SUCCESS]], label [[ATOMICRMW_END:%.*]], label [[ATOMICRMW_START]] @@ -942,7 +942,7 @@ define half @test_atomicrmw_xchg_f16_global_agent_align4(ptr addrspace(1) %ptr, ; CHECK-NEXT: [[LOADED:%.*]] = phi i32 [ [[TMP3]], [[TMP0:%.*]] ], [ [[NEWLOADED:%.*]], [[ATOMICRMW_START]] ] ; CHECK-NEXT: [[TMP4:%.*]] = and i32 [[LOADED]], -65536 ; CHECK-NEXT: [[TMP5:%.*]] = or i32 [[TMP4]], [[TMP2]] -; CHECK-NEXT: [[TMP6:%.*]] = cmpxchg ptr addrspace(1) [[PTR]], i32 [[LOADED]], i32 [[TMP5]] seq_cst seq_cst, align 4 +; CHECK-NEXT: [[TMP6:%.*]] = cmpxchg ptr addrspace(1) [[PTR]], i32 [[LOADED]], i32 [[TMP5]] syncscope("agent") seq_cst seq_cst, align 4 ; CHECK-NEXT: [[SUCCESS:%.*]] = extractvalue { i32, i1 } [[TMP6]], 1 ; CHECK-NEXT: [[NEWLOADED]] = extractvalue { i32, i1 } [[TMP6]], 0 ; CHECK-NEXT: br i1 [[SUCCESS]], label [[ATOMICRMW_END:%.*]], label [[ATOMICRMW_START]] @@ -973,7 +973,7 @@ define half @test_atomicrmw_xchg_f16_flat_agent(ptr %ptr, half %value) { ; CHECK-NEXT: [[LOADED:%.*]] = phi i32 [ [[TMP5]], [[TMP0:%.*]] ], [ [[NEWLOADED:%.*]], [[ATOMICRMW_START]] ] ; CHECK-NEXT: [[TMP6:%.*]] = and i32 [[LOADED]], [[INV_MASK]] ; CHECK-NEXT: [[TMP7:%.*]] = or i32 [[TMP6]], [[VALOPERAND_SHIFTED]] -; CHECK-NEXT: [[TMP8:%.*]] = cmpxchg ptr [[ALIGNEDADDR]], i32 [[LOADED]], i32 [[TMP7]] seq_cst seq_cst, align 4 +; CHECK-NEXT: [[TMP8:%.*]] = cmpxchg ptr [[ALIGNEDADDR]], i32 [[LOADED]], i32 [[TMP7]] syncscope("agent") seq_cst seq_cst, align 4 ; CHECK-NEXT: [[SUCCESS:%.*]] = extractvalue { i32, i1 } [[TMP8]], 1 ; CHECK-NEXT: [[NEWLOADED]] = extractvalue { i32, i1 } [[TMP8]], 0 ; CHECK-NEXT: br i1 [[SUCCESS]], label [[ATOMICRMW_END:%.*]], label [[ATOMICRMW_START]] @@ -997,7 +997,7 @@ define half @test_atomicrmw_xchg_f16_flat_agent_align4(ptr %ptr, half %value) { ; CHECK-NEXT: [[LOADED:%.*]] = phi i32 [ [[TMP3]], [[TMP0:%.*]] ], [ [[NEWLOADED:%.*]], [[ATOMICRMW_START]] ] ; CHECK-NEXT: [[TMP4:%.*]] = and i32 [[LOADED]], -65536 ; CHECK-NEXT: [[TMP5:%.*]] = or i32 [[TMP4]], [[TMP2]] -; CHECK-NEXT: [[TMP6:%.*]] = cmpxchg ptr [[PTR]], i32 [[LOADED]], i32 [[TMP5]] seq_cst seq_cst, align 4 +; CHECK-NEXT: [[TMP6:%.*]] = cmpxchg ptr [[PTR]], i32 [[LOADED]], i32 [[TMP5]] syncscope("agent") seq_cst seq_cst, align 4 ; CHECK-NEXT: [[SUCCESS:%.*]] = extractvalue { i32, i1 } [[TMP6]], 1 ; CHECK-NEXT: [[NEWLOADED]] = extractvalue { i32, i1 } [[TMP6]], 0 ; CHECK-NEXT: br i1 [[SUCCESS]], label [[ATOMICRMW_END:%.*]], label [[ATOMICRMW_START]] @@ -1028,7 +1028,7 @@ define bfloat @test_atomicrmw_xchg_bf16_global_agent(ptr addrspace(1) %ptr, bflo ; CHECK-NEXT: [[LOADED:%.*]] = phi i32 [ [[TMP5]], [[TMP0:%.*]] ], [ [[NEWLOADED:%.*]], [[ATOMICRMW_START]] ] ; CHECK-NEXT: [[TMP6:%.*]] = and i32 [[LOADED]], [[INV_MASK]] ; CHECK-NEXT: [[TMP7:%.*]] = or i32 [[TMP6]], [[VALOPERAND_SHIFTED]] -; CHECK-NEXT: [[TMP8:%.*]] = cmpxchg ptr addrspace(1) [[ALIGNEDADDR]], i32 [[LOADED]], i32 [[TMP7]] seq_cst seq_cst, align 4 +; CHECK-NEXT: [[TMP8:%.*]] = cmpxchg ptr addrspace(1) [[ALIGNEDADDR]], i32 [[LOADED]], i32 [[TMP7]] syncscope("agent") seq_cst seq_cst, align 4 ; CHECK-NEXT: [[SUCCESS:%.*]] = extractvalue { i32, i1 } [[TMP8]], 1 ; CHECK-NEXT: [[NEWLOADED]] = extractvalue { i32, i1 } [[TMP8]], 0 ; CHECK-NEXT: br i1 [[SUCCESS]], label [[ATOMICRMW_END:%.*]], label [[ATOMICRMW_START]] @@ -1052,7 +1052,7 @@ define bfloat @test_atomicrmw_xchg_bf16_global_agent_align4(ptr addrspace(1) %pt ; CHECK-NEXT: [[LOADED:%.*]] = phi i32 [ [[TMP3]], [[TMP0:%.*]] ], [ [[NEWLOADED:%.*]], [[ATOMICRMW_START]] ] ; CHECK-NEXT: [[TMP4:%.*]] = and i32 [[LOADED]], -65536 ; CHECK-NEXT: [[TMP5:%.*]] = or i32 [[TMP4]], [[TMP2]] -; CHECK-NEXT: [[TMP6:%.*]] = cmpxchg ptr addrspace(1) [[PTR]], i32 [[LOADED]], i32 [[TMP5]] seq_cst seq_cst, align 4 +; CHECK-NEXT: [[TMP6:%.*]] = cmpxchg ptr addrspace(1) [[PTR]], i32 [[LOADED]], i32 [[TMP5]] syncscope("agent") seq_cst seq_cst, align 4 ; CHECK-NEXT: [[SUCCESS:%.*]] = extractvalue { i32, i1 } [[TMP6]], 1 ; CHECK-NEXT: [[NEWLOADED]] = extractvalue { i32, i1 } [[TMP6]], 0 ; CHECK-NEXT: br i1 [[SUCCESS]], label [[ATOMICRMW_END:%.*]], label [[ATOMICRMW_START]] diff --git a/llvm/test/Transforms/AtomicExpand/AMDGPU/expand-atomic-mmra.ll b/llvm/test/Transforms/AtomicExpand/AMDGPU/expand-atomic-mmra.ll new file mode 100644 index 0000000000000000000000000000000000000000..d51e9291a6119ca3b9561e14bfa6c4039ff8b3e2 --- /dev/null +++ b/llvm/test/Transforms/AtomicExpand/AMDGPU/expand-atomic-mmra.ll @@ -0,0 +1,204 @@ +; NOTE: Assertions have been autogenerated by utils/update_test_checks.py UTC_ARGS: --version 4 + +; RUN: opt -S -mtriple=amdgcn-amd-amdhsa -mcpu=gfx90a -verify-each -atomic-expand %s | FileCheck -check-prefix=GFX90A %s +; RUN: opt -S -mtriple=amdgcn-amd-amdhsa -mcpu=gfx1100 -verify-each -atomic-expand %s | FileCheck -check-prefix=GFX1100 %s + +; Contains a variety of tests with different types of atomic expansions to check that MMRAs are +; preserved. + +define i16 @test_atomicrmw_xchg_i16_global_agent(ptr addrspace(1) %ptr, i16 %value) { +; GFX90A-LABEL: define i16 @test_atomicrmw_xchg_i16_global_agent( +; GFX90A-SAME: ptr addrspace(1) [[PTR:%.*]], i16 [[VALUE:%.*]]) #[[ATTR0:[0-9]+]] { +; GFX90A-NEXT: [[ALIGNEDADDR:%.*]] = call ptr addrspace(1) @llvm.ptrmask.p1.i64(ptr addrspace(1) [[PTR]], i64 -4) +; GFX90A-NEXT: [[TMP1:%.*]] = ptrtoint ptr addrspace(1) [[PTR]] to i64 +; GFX90A-NEXT: [[PTRLSB:%.*]] = and i64 [[TMP1]], 3 +; GFX90A-NEXT: [[TMP2:%.*]] = shl i64 [[PTRLSB]], 3 +; GFX90A-NEXT: [[SHIFTAMT:%.*]] = trunc i64 [[TMP2]] to i32 +; GFX90A-NEXT: [[MASK:%.*]] = shl i32 65535, [[SHIFTAMT]] +; GFX90A-NEXT: [[INV_MASK:%.*]] = xor i32 [[MASK]], -1 +; GFX90A-NEXT: [[TMP3:%.*]] = zext i16 [[VALUE]] to i32 +; GFX90A-NEXT: [[VALOPERAND_SHIFTED:%.*]] = shl i32 [[TMP3]], [[SHIFTAMT]] +; GFX90A-NEXT: [[TMP4:%.*]] = load i32, ptr addrspace(1) [[ALIGNEDADDR]], align 4, !mmra [[META0:![0-9]+]] +; GFX90A-NEXT: br label [[ATOMICRMW_START:%.*]] +; GFX90A: atomicrmw.start: +; GFX90A-NEXT: [[LOADED:%.*]] = phi i32 [ [[TMP4]], [[TMP0:%.*]] ], [ [[NEWLOADED:%.*]], [[ATOMICRMW_START]] ] +; GFX90A-NEXT: [[TMP5:%.*]] = and i32 [[LOADED]], [[INV_MASK]] +; GFX90A-NEXT: [[TMP6:%.*]] = or i32 [[TMP5]], [[VALOPERAND_SHIFTED]] +; GFX90A-NEXT: [[TMP7:%.*]] = cmpxchg ptr addrspace(1) [[ALIGNEDADDR]], i32 [[LOADED]], i32 [[TMP6]] syncscope("agent") seq_cst seq_cst, align 4, !mmra [[META0]] +; GFX90A-NEXT: [[SUCCESS:%.*]] = extractvalue { i32, i1 } [[TMP7]], 1 +; GFX90A-NEXT: [[NEWLOADED]] = extractvalue { i32, i1 } [[TMP7]], 0 +; GFX90A-NEXT: br i1 [[SUCCESS]], label [[ATOMICRMW_END:%.*]], label [[ATOMICRMW_START]] +; GFX90A: atomicrmw.end: +; GFX90A-NEXT: [[SHIFTED:%.*]] = lshr i32 [[NEWLOADED]], [[SHIFTAMT]] +; GFX90A-NEXT: [[EXTRACTED:%.*]] = trunc i32 [[SHIFTED]] to i16 +; GFX90A-NEXT: ret i16 [[EXTRACTED]] +; +; GFX1100-LABEL: define i16 @test_atomicrmw_xchg_i16_global_agent( +; GFX1100-SAME: ptr addrspace(1) [[PTR:%.*]], i16 [[VALUE:%.*]]) #[[ATTR0:[0-9]+]] { +; GFX1100-NEXT: [[ALIGNEDADDR:%.*]] = call ptr addrspace(1) @llvm.ptrmask.p1.i64(ptr addrspace(1) [[PTR]], i64 -4) +; GFX1100-NEXT: [[TMP1:%.*]] = ptrtoint ptr addrspace(1) [[PTR]] to i64 +; GFX1100-NEXT: [[PTRLSB:%.*]] = and i64 [[TMP1]], 3 +; GFX1100-NEXT: [[TMP2:%.*]] = shl i64 [[PTRLSB]], 3 +; GFX1100-NEXT: [[SHIFTAMT:%.*]] = trunc i64 [[TMP2]] to i32 +; GFX1100-NEXT: [[MASK:%.*]] = shl i32 65535, [[SHIFTAMT]] +; GFX1100-NEXT: [[INV_MASK:%.*]] = xor i32 [[MASK]], -1 +; GFX1100-NEXT: [[TMP3:%.*]] = zext i16 [[VALUE]] to i32 +; GFX1100-NEXT: [[VALOPERAND_SHIFTED:%.*]] = shl i32 [[TMP3]], [[SHIFTAMT]] +; GFX1100-NEXT: [[TMP4:%.*]] = load i32, ptr addrspace(1) [[ALIGNEDADDR]], align 4, !mmra [[META0:![0-9]+]] +; GFX1100-NEXT: br label [[ATOMICRMW_START:%.*]] +; GFX1100: atomicrmw.start: +; GFX1100-NEXT: [[LOADED:%.*]] = phi i32 [ [[TMP4]], [[TMP0:%.*]] ], [ [[NEWLOADED:%.*]], [[ATOMICRMW_START]] ] +; GFX1100-NEXT: [[TMP5:%.*]] = and i32 [[LOADED]], [[INV_MASK]] +; GFX1100-NEXT: [[TMP6:%.*]] = or i32 [[TMP5]], [[VALOPERAND_SHIFTED]] +; GFX1100-NEXT: [[TMP7:%.*]] = cmpxchg ptr addrspace(1) [[ALIGNEDADDR]], i32 [[LOADED]], i32 [[TMP6]] syncscope("agent") seq_cst seq_cst, align 4, !mmra [[META0]] +; GFX1100-NEXT: [[SUCCESS:%.*]] = extractvalue { i32, i1 } [[TMP7]], 1 +; GFX1100-NEXT: [[NEWLOADED]] = extractvalue { i32, i1 } [[TMP7]], 0 +; GFX1100-NEXT: br i1 [[SUCCESS]], label [[ATOMICRMW_END:%.*]], label [[ATOMICRMW_START]] +; GFX1100: atomicrmw.end: +; GFX1100-NEXT: [[SHIFTED:%.*]] = lshr i32 [[NEWLOADED]], [[SHIFTAMT]] +; GFX1100-NEXT: [[EXTRACTED:%.*]] = trunc i32 [[SHIFTED]] to i16 +; GFX1100-NEXT: ret i16 [[EXTRACTED]] +; + %res = atomicrmw xchg ptr addrspace(1) %ptr, i16 %value syncscope("agent") seq_cst, !mmra !2 + ret i16 %res +} + +define i16 @test_cmpxchg_i16_global_agent_align4(ptr addrspace(1) %out, i16 %in, i16 %old) { +; GFX90A-LABEL: define i16 @test_cmpxchg_i16_global_agent_align4( +; GFX90A-SAME: ptr addrspace(1) [[OUT:%.*]], i16 [[IN:%.*]], i16 [[OLD:%.*]]) #[[ATTR0]] { +; GFX90A-NEXT: [[GEP:%.*]] = getelementptr i16, ptr addrspace(1) [[OUT]], i64 4 +; GFX90A-NEXT: [[TMP1:%.*]] = zext i16 [[IN]] to i32 +; GFX90A-NEXT: [[TMP2:%.*]] = zext i16 [[OLD]] to i32 +; GFX90A-NEXT: [[TMP3:%.*]] = load i32, ptr addrspace(1) [[GEP]], align 4, !mmra [[META0]] +; GFX90A-NEXT: [[TMP4:%.*]] = and i32 [[TMP3]], -65536 +; GFX90A-NEXT: br label [[PARTWORD_CMPXCHG_LOOP:%.*]] +; GFX90A: partword.cmpxchg.loop: +; GFX90A-NEXT: [[TMP5:%.*]] = phi i32 [ [[TMP4]], [[TMP0:%.*]] ], [ [[TMP11:%.*]], [[PARTWORD_CMPXCHG_FAILURE:%.*]] ] +; GFX90A-NEXT: [[TMP6:%.*]] = or i32 [[TMP5]], [[TMP1]] +; GFX90A-NEXT: [[TMP7:%.*]] = or i32 [[TMP5]], [[TMP2]] +; GFX90A-NEXT: [[TMP8:%.*]] = cmpxchg ptr addrspace(1) [[GEP]], i32 [[TMP7]], i32 [[TMP6]] seq_cst seq_cst, align 4, !mmra [[META0]] +; GFX90A-NEXT: [[TMP9:%.*]] = extractvalue { i32, i1 } [[TMP8]], 0 +; GFX90A-NEXT: [[TMP10:%.*]] = extractvalue { i32, i1 } [[TMP8]], 1 +; GFX90A-NEXT: br i1 [[TMP10]], label [[PARTWORD_CMPXCHG_END:%.*]], label [[PARTWORD_CMPXCHG_FAILURE]] +; GFX90A: partword.cmpxchg.failure: +; GFX90A-NEXT: [[TMP11]] = and i32 [[TMP9]], -65536 +; GFX90A-NEXT: [[TMP12:%.*]] = icmp ne i32 [[TMP5]], [[TMP11]] +; GFX90A-NEXT: br i1 [[TMP12]], label [[PARTWORD_CMPXCHG_LOOP]], label [[PARTWORD_CMPXCHG_END]] +; GFX90A: partword.cmpxchg.end: +; GFX90A-NEXT: [[EXTRACTED:%.*]] = trunc i32 [[TMP9]] to i16 +; GFX90A-NEXT: [[TMP13:%.*]] = insertvalue { i16, i1 } poison, i16 [[EXTRACTED]], 0 +; GFX90A-NEXT: [[TMP14:%.*]] = insertvalue { i16, i1 } [[TMP13]], i1 [[TMP10]], 1 +; GFX90A-NEXT: [[EXTRACT:%.*]] = extractvalue { i16, i1 } [[TMP14]], 0 +; GFX90A-NEXT: ret i16 [[EXTRACT]] +; +; GFX1100-LABEL: define i16 @test_cmpxchg_i16_global_agent_align4( +; GFX1100-SAME: ptr addrspace(1) [[OUT:%.*]], i16 [[IN:%.*]], i16 [[OLD:%.*]]) #[[ATTR0]] { +; GFX1100-NEXT: [[GEP:%.*]] = getelementptr i16, ptr addrspace(1) [[OUT]], i64 4 +; GFX1100-NEXT: [[TMP1:%.*]] = zext i16 [[IN]] to i32 +; GFX1100-NEXT: [[TMP2:%.*]] = zext i16 [[OLD]] to i32 +; GFX1100-NEXT: [[TMP3:%.*]] = load i32, ptr addrspace(1) [[GEP]], align 4, !mmra [[META0]] +; GFX1100-NEXT: [[TMP4:%.*]] = and i32 [[TMP3]], -65536 +; GFX1100-NEXT: br label [[PARTWORD_CMPXCHG_LOOP:%.*]] +; GFX1100: partword.cmpxchg.loop: +; GFX1100-NEXT: [[TMP5:%.*]] = phi i32 [ [[TMP4]], [[TMP0:%.*]] ], [ [[TMP11:%.*]], [[PARTWORD_CMPXCHG_FAILURE:%.*]] ] +; GFX1100-NEXT: [[TMP6:%.*]] = or i32 [[TMP5]], [[TMP1]] +; GFX1100-NEXT: [[TMP7:%.*]] = or i32 [[TMP5]], [[TMP2]] +; GFX1100-NEXT: [[TMP8:%.*]] = cmpxchg ptr addrspace(1) [[GEP]], i32 [[TMP7]], i32 [[TMP6]] seq_cst seq_cst, align 4, !mmra [[META0]] +; GFX1100-NEXT: [[TMP9:%.*]] = extractvalue { i32, i1 } [[TMP8]], 0 +; GFX1100-NEXT: [[TMP10:%.*]] = extractvalue { i32, i1 } [[TMP8]], 1 +; GFX1100-NEXT: br i1 [[TMP10]], label [[PARTWORD_CMPXCHG_END:%.*]], label [[PARTWORD_CMPXCHG_FAILURE]] +; GFX1100: partword.cmpxchg.failure: +; GFX1100-NEXT: [[TMP11]] = and i32 [[TMP9]], -65536 +; GFX1100-NEXT: [[TMP12:%.*]] = icmp ne i32 [[TMP5]], [[TMP11]] +; GFX1100-NEXT: br i1 [[TMP12]], label [[PARTWORD_CMPXCHG_LOOP]], label [[PARTWORD_CMPXCHG_END]] +; GFX1100: partword.cmpxchg.end: +; GFX1100-NEXT: [[EXTRACTED:%.*]] = trunc i32 [[TMP9]] to i16 +; GFX1100-NEXT: [[TMP13:%.*]] = insertvalue { i16, i1 } poison, i16 [[EXTRACTED]], 0 +; GFX1100-NEXT: [[TMP14:%.*]] = insertvalue { i16, i1 } [[TMP13]], i1 [[TMP10]], 1 +; GFX1100-NEXT: [[EXTRACT:%.*]] = extractvalue { i16, i1 } [[TMP14]], 0 +; GFX1100-NEXT: ret i16 [[EXTRACT]] +; + %gep = getelementptr i16, ptr addrspace(1) %out, i64 4 + %res = cmpxchg ptr addrspace(1) %gep, i16 %old, i16 %in seq_cst seq_cst, align 4, !mmra !2 + %extract = extractvalue {i16, i1} %res, 0 + ret i16 %extract +} + +define void @syncscope_workgroup_nortn(ptr %addr, float %val) #0 { +; GFX90A-LABEL: define void @syncscope_workgroup_nortn( +; GFX90A-SAME: ptr [[ADDR:%.*]], float [[VAL:%.*]]) #[[ATTR1:[0-9]+]] { +; GFX90A-NEXT: br label [[ATOMICRMW_CHECK_SHARED:%.*]] +; GFX90A: atomicrmw.check.shared: +; GFX90A-NEXT: [[IS_SHARED:%.*]] = call i1 @llvm.amdgcn.is.shared(ptr [[ADDR]]) +; GFX90A-NEXT: br i1 [[IS_SHARED]], label [[ATOMICRMW_SHARED:%.*]], label [[ATOMICRMW_CHECK_PRIVATE:%.*]] +; GFX90A: atomicrmw.shared: +; GFX90A-NEXT: [[TMP1:%.*]] = addrspacecast ptr [[ADDR]] to ptr addrspace(3) +; GFX90A-NEXT: [[TMP2:%.*]] = atomicrmw fadd ptr addrspace(3) [[TMP1]], float [[VAL]] syncscope("workgroup") seq_cst, align 4, !mmra [[META0]] +; GFX90A-NEXT: br label [[ATOMICRMW_PHI:%.*]] +; GFX90A: atomicrmw.check.private: +; GFX90A-NEXT: [[IS_PRIVATE:%.*]] = call i1 @llvm.amdgcn.is.private(ptr [[ADDR]]) +; GFX90A-NEXT: br i1 [[IS_PRIVATE]], label [[ATOMICRMW_PRIVATE:%.*]], label [[ATOMICRMW_GLOBAL:%.*]] +; GFX90A: atomicrmw.private: +; GFX90A-NEXT: [[TMP3:%.*]] = addrspacecast ptr [[ADDR]] to ptr addrspace(5) +; GFX90A-NEXT: [[LOADED_PRIVATE:%.*]] = load float, ptr addrspace(5) [[TMP3]], align 4 +; GFX90A-NEXT: [[VAL_NEW:%.*]] = fadd float [[LOADED_PRIVATE]], [[VAL]] +; GFX90A-NEXT: store float [[VAL_NEW]], ptr addrspace(5) [[TMP3]], align 4 +; GFX90A-NEXT: br label [[ATOMICRMW_PHI]] +; GFX90A: atomicrmw.global: +; GFX90A-NEXT: [[TMP4:%.*]] = addrspacecast ptr [[ADDR]] to ptr addrspace(1) +; GFX90A-NEXT: [[TMP5:%.*]] = atomicrmw fadd ptr addrspace(1) [[TMP4]], float [[VAL]] syncscope("workgroup") seq_cst, align 4, !mmra [[META0]] +; GFX90A-NEXT: br label [[ATOMICRMW_PHI]] +; GFX90A: atomicrmw.phi: +; GFX90A-NEXT: [[LOADED_PHI:%.*]] = phi float [ [[TMP2]], [[ATOMICRMW_SHARED]] ], [ [[LOADED_PRIVATE]], [[ATOMICRMW_PRIVATE]] ], [ [[TMP5]], [[ATOMICRMW_GLOBAL]] ] +; GFX90A-NEXT: br label [[ATOMICRMW_END:%.*]] +; GFX90A: atomicrmw.end: +; GFX90A-NEXT: ret void +; +; GFX1100-LABEL: define void @syncscope_workgroup_nortn( +; GFX1100-SAME: ptr [[ADDR:%.*]], float [[VAL:%.*]]) #[[ATTR1:[0-9]+]] { +; GFX1100-NEXT: [[RES:%.*]] = atomicrmw fadd ptr [[ADDR]], float [[VAL]] syncscope("workgroup") seq_cst, align 4, !mmra [[META0]] +; GFX1100-NEXT: ret void +; + %res = atomicrmw fadd ptr %addr, float %val syncscope("workgroup") seq_cst, !mmra !2 + ret void +} + +define i32 @atomic_load_global_align1(ptr addrspace(1) %ptr) { +; GFX90A-LABEL: define i32 @atomic_load_global_align1( +; GFX90A-SAME: ptr addrspace(1) [[PTR:%.*]]) #[[ATTR0]] { +; GFX90A-NEXT: [[TMP1:%.*]] = addrspacecast ptr addrspace(1) [[PTR]] to ptr +; GFX90A-NEXT: [[TMP2:%.*]] = alloca i32, align 4, addrspace(5) +; GFX90A-NEXT: call void @llvm.lifetime.start.p5(i64 4, ptr addrspace(5) [[TMP2]]) +; GFX90A-NEXT: call void @__atomic_load(i64 4, ptr [[TMP1]], ptr addrspace(5) [[TMP2]], i32 5) +; GFX90A-NEXT: [[TMP3:%.*]] = load i32, ptr addrspace(5) [[TMP2]], align 4 +; GFX90A-NEXT: call void @llvm.lifetime.end.p5(i64 4, ptr addrspace(5) [[TMP2]]) +; GFX90A-NEXT: ret i32 [[TMP3]] +; +; GFX1100-LABEL: define i32 @atomic_load_global_align1( +; GFX1100-SAME: ptr addrspace(1) [[PTR:%.*]]) #[[ATTR0]] { +; GFX1100-NEXT: [[TMP1:%.*]] = addrspacecast ptr addrspace(1) [[PTR]] to ptr +; GFX1100-NEXT: [[TMP2:%.*]] = alloca i32, align 4, addrspace(5) +; GFX1100-NEXT: call void @llvm.lifetime.start.p5(i64 4, ptr addrspace(5) [[TMP2]]) +; GFX1100-NEXT: call void @__atomic_load(i64 4, ptr [[TMP1]], ptr addrspace(5) [[TMP2]], i32 5) +; GFX1100-NEXT: [[TMP3:%.*]] = load i32, ptr addrspace(5) [[TMP2]], align 4 +; GFX1100-NEXT: call void @llvm.lifetime.end.p5(i64 4, ptr addrspace(5) [[TMP2]]) +; GFX1100-NEXT: ret i32 [[TMP3]] +; + %val = load atomic i32, ptr addrspace(1) %ptr seq_cst, align 1, !mmra !2 + ret i32 %val +} + +attributes #0 = { "amdgpu-unsafe-fp-atomics"="true" } + +!0 = !{!"foo", !"bar"} +!1 = !{!"bux", !"baz"} +!2 = !{!0, !1} +;. +; GFX90A: [[META0]] = !{[[META1:![0-9]+]], [[META2:![0-9]+]]} +; GFX90A: [[META1]] = !{!"foo", !"bar"} +; GFX90A: [[META2]] = !{!"bux", !"baz"} +;. +; GFX1100: [[META0]] = !{[[META1:![0-9]+]], [[META2:![0-9]+]]} +; GFX1100: [[META1]] = !{!"foo", !"bar"} +; GFX1100: [[META2]] = !{!"bux", !"baz"} +;. diff --git a/llvm/test/Transforms/AtomicExpand/AMDGPU/no-expand-atomic-load.ll b/llvm/test/Transforms/AtomicExpand/AMDGPU/no-expand-atomic-load.ll new file mode 100644 index 0000000000000000000000000000000000000000..b1497aefe9b93ea5d21392249d84703ba6308dde --- /dev/null +++ b/llvm/test/Transforms/AtomicExpand/AMDGPU/no-expand-atomic-load.ll @@ -0,0 +1,181 @@ +; NOTE: Assertions have been autogenerated by utils/update_test_checks.py UTC_ARGS: --version 4 +; RUN: opt -S -mtriple=amdgcn-amd-amdhsa -passes=atomic-expand %s | FileCheck %s + +; Make sure atomic loads are not bitcasted and lose metadata + +define float @load_atomic_f32_global_system(ptr addrspace(1) %ptr) { +; CHECK-LABEL: define float @load_atomic_f32_global_system( +; CHECK-SAME: ptr addrspace(1) [[PTR:%.*]]) { +; CHECK-NEXT: [[TMP2:%.*]] = load atomic float, ptr addrspace(1) [[PTR]] seq_cst, align 4, !some.unknown.md [[META0:![0-9]+]] +; CHECK-NEXT: ret float [[TMP2]] +; + %ld = load atomic float, ptr addrspace(1) %ptr seq_cst, align 4, !some.unknown.md !0 + ret float %ld +} + +define float @load_atomic_f32_global_agent(ptr addrspace(1) %ptr) { +; CHECK-LABEL: define float @load_atomic_f32_global_agent( +; CHECK-SAME: ptr addrspace(1) [[PTR:%.*]]) { +; CHECK-NEXT: [[TMP2:%.*]] = load atomic float, ptr addrspace(1) [[PTR]] syncscope("agent") seq_cst, align 4, !some.unknown.md [[META0]] +; CHECK-NEXT: ret float [[TMP2]] +; + %ld = load atomic float, ptr addrspace(1) %ptr syncscope("agent") seq_cst, align 4, !some.unknown.md !0 + ret float %ld +} + +define float @load_atomic_f32_local(ptr addrspace(3) %ptr) { +; CHECK-LABEL: define float @load_atomic_f32_local( +; CHECK-SAME: ptr addrspace(3) [[PTR:%.*]]) { +; CHECK-NEXT: [[TMP2:%.*]] = load atomic float, ptr addrspace(3) [[PTR]] seq_cst, align 4, !some.unknown.md [[META0]] +; CHECK-NEXT: ret float [[TMP2]] +; + %ld = load atomic float, ptr addrspace(3) %ptr seq_cst, align 4, !some.unknown.md !0 + ret float %ld +} + +define float @load_atomic_f32_flat_system(ptr %ptr) { +; CHECK-LABEL: define float @load_atomic_f32_flat_system( +; CHECK-SAME: ptr [[PTR:%.*]]) { +; CHECK-NEXT: [[TMP2:%.*]] = load atomic float, ptr [[PTR]] seq_cst, align 4, !some.unknown.md [[META0]] +; CHECK-NEXT: ret float [[TMP2]] +; + %ld = load atomic float, ptr %ptr seq_cst, align 4, !some.unknown.md !0 + ret float %ld +} + +define float @load_atomic_f32_flat_agent(ptr %ptr) { +; CHECK-LABEL: define float @load_atomic_f32_flat_agent( +; CHECK-SAME: ptr [[PTR:%.*]]) { +; CHECK-NEXT: [[TMP2:%.*]] = load atomic float, ptr [[PTR]] syncscope("agent") seq_cst, align 4, !some.unknown.md [[META0]] +; CHECK-NEXT: ret float [[TMP2]] +; + %ld = load atomic float, ptr %ptr syncscope("agent") seq_cst, align 4, !some.unknown.md !0 + ret float %ld +} + +define half @load_atomic_f16_global_system(ptr addrspace(1) %ptr) { +; CHECK-LABEL: define half @load_atomic_f16_global_system( +; CHECK-SAME: ptr addrspace(1) [[PTR:%.*]]) { +; CHECK-NEXT: [[TMP2:%.*]] = load atomic half, ptr addrspace(1) [[PTR]] seq_cst, align 4, !some.unknown.md [[META0]] +; CHECK-NEXT: ret half [[TMP2]] +; + %ld = load atomic half, ptr addrspace(1) %ptr seq_cst, align 4, !some.unknown.md !0 + ret half %ld +} + +define half @load_atomic_f16_global_agent(ptr addrspace(1) %ptr) { +; CHECK-LABEL: define half @load_atomic_f16_global_agent( +; CHECK-SAME: ptr addrspace(1) [[PTR:%.*]]) { +; CHECK-NEXT: [[TMP2:%.*]] = load atomic half, ptr addrspace(1) [[PTR]] syncscope("agent") seq_cst, align 4, !some.unknown.md [[META0]] +; CHECK-NEXT: ret half [[TMP2]] +; + %ld = load atomic half, ptr addrspace(1) %ptr syncscope("agent") seq_cst, align 4, !some.unknown.md !0 + ret half %ld +} + +define half @load_atomic_f16_local(ptr addrspace(3) %ptr) { +; CHECK-LABEL: define half @load_atomic_f16_local( +; CHECK-SAME: ptr addrspace(3) [[PTR:%.*]]) { +; CHECK-NEXT: [[TMP2:%.*]] = load atomic half, ptr addrspace(3) [[PTR]] seq_cst, align 2, !some.unknown.md [[META0]] +; CHECK-NEXT: ret half [[TMP2]] +; + %ld = load atomic half, ptr addrspace(3) %ptr seq_cst, align 2, !some.unknown.md !0 + ret half %ld +} + +define bfloat @load_atomic_bf16_global_system(ptr addrspace(1) %ptr) { +; CHECK-LABEL: define bfloat @load_atomic_bf16_global_system( +; CHECK-SAME: ptr addrspace(1) [[PTR:%.*]]) { +; CHECK-NEXT: [[TMP2:%.*]] = load atomic bfloat, ptr addrspace(1) [[PTR]] seq_cst, align 2, !some.unknown.md [[META0]] +; CHECK-NEXT: ret bfloat [[TMP2]] +; + %ld = load atomic bfloat, ptr addrspace(1) %ptr seq_cst, align 2, !some.unknown.md !0 + ret bfloat %ld +} + +define bfloat @load_atomic_bf16_global_agent(ptr addrspace(1) %ptr) { +; CHECK-LABEL: define bfloat @load_atomic_bf16_global_agent( +; CHECK-SAME: ptr addrspace(1) [[PTR:%.*]]) { +; CHECK-NEXT: [[TMP2:%.*]] = load atomic bfloat, ptr addrspace(1) [[PTR]] syncscope("agent") seq_cst, align 2, !some.unknown.md [[META0]] +; CHECK-NEXT: ret bfloat [[TMP2]] +; + %ld = load atomic bfloat, ptr addrspace(1) %ptr syncscope("agent") seq_cst, align 2, !some.unknown.md !0 + ret bfloat %ld +} + +define bfloat @load_atomic_bf16_local(ptr addrspace(3) %ptr) { +; CHECK-LABEL: define bfloat @load_atomic_bf16_local( +; CHECK-SAME: ptr addrspace(3) [[PTR:%.*]]) { +; CHECK-NEXT: [[TMP2:%.*]] = load atomic bfloat, ptr addrspace(3) [[PTR]] seq_cst, align 2, !some.unknown.md [[META0]] +; CHECK-NEXT: ret bfloat [[TMP2]] +; + %ld = load atomic bfloat, ptr addrspace(3) %ptr seq_cst, align 2, !some.unknown.md !0 + ret bfloat %ld +} + +define bfloat @load_atomic_bf16_flat(ptr %ptr) { +; CHECK-LABEL: define bfloat @load_atomic_bf16_flat( +; CHECK-SAME: ptr [[PTR:%.*]]) { +; CHECK-NEXT: [[TMP2:%.*]] = load atomic bfloat, ptr [[PTR]] seq_cst, align 2, !some.unknown.md [[META0]] +; CHECK-NEXT: ret bfloat [[TMP2]] +; + %ld = load atomic bfloat, ptr %ptr seq_cst, align 2, !some.unknown.md !0 + ret bfloat %ld +} + +define double @load_atomic_f64_global_system(ptr addrspace(1) %ptr) { +; CHECK-LABEL: define double @load_atomic_f64_global_system( +; CHECK-SAME: ptr addrspace(1) [[PTR:%.*]]) { +; CHECK-NEXT: [[TMP2:%.*]] = load atomic double, ptr addrspace(1) [[PTR]] seq_cst, align 8, !some.unknown.md [[META0]] +; CHECK-NEXT: ret double [[TMP2]] +; + %ld = load atomic double, ptr addrspace(1) %ptr seq_cst, align 8, !some.unknown.md !0 + ret double %ld +} + +define double @load_atomic_f64_global_agent(ptr addrspace(1) %ptr) { +; CHECK-LABEL: define double @load_atomic_f64_global_agent( +; CHECK-SAME: ptr addrspace(1) [[PTR:%.*]]) { +; CHECK-NEXT: [[TMP2:%.*]] = load atomic double, ptr addrspace(1) [[PTR]] syncscope("agent") seq_cst, align 8, !some.unknown.md [[META0]] +; CHECK-NEXT: ret double [[TMP2]] +; + %ld = load atomic double, ptr addrspace(1) %ptr syncscope("agent") seq_cst, align 8, !some.unknown.md !0 + ret double %ld +} + +define double @load_atomic_f64_local(ptr addrspace(3) %ptr) { +; CHECK-LABEL: define double @load_atomic_f64_local( +; CHECK-SAME: ptr addrspace(3) [[PTR:%.*]]) { +; CHECK-NEXT: [[TMP2:%.*]] = load atomic double, ptr addrspace(3) [[PTR]] seq_cst, align 8, !some.unknown.md [[META0]] +; CHECK-NEXT: ret double [[TMP2]] +; + %ld = load atomic double, ptr addrspace(3) %ptr seq_cst, align 8, !some.unknown.md !0 + ret double %ld +} + +define double @load_atomic_f64_flat_system(ptr %ptr) { +; CHECK-LABEL: define double @load_atomic_f64_flat_system( +; CHECK-SAME: ptr [[PTR:%.*]]) { +; CHECK-NEXT: [[TMP2:%.*]] = load atomic double, ptr [[PTR]] seq_cst, align 8, !some.unknown.md [[META0]] +; CHECK-NEXT: ret double [[TMP2]] +; + %ld = load atomic double, ptr %ptr seq_cst, align 8, !some.unknown.md !0 + ret double %ld +} + +define double @load_atomic_f64_flat_agent(ptr %ptr) { +; CHECK-LABEL: define double @load_atomic_f64_flat_agent( +; CHECK-SAME: ptr [[PTR:%.*]]) { +; CHECK-NEXT: [[TMP2:%.*]] = load atomic double, ptr [[PTR]] syncscope("agent") seq_cst, align 8, !some.unknown.md [[META0]] +; CHECK-NEXT: ret double [[TMP2]] +; + %ld = load atomic double, ptr %ptr syncscope("agent") seq_cst, align 8, !some.unknown.md !0 + ret double %ld +} + +!0 = !{} + + +;. +; CHECK: [[META0]] = !{} +;. diff --git a/llvm/test/Transforms/AtomicExpand/AMDGPU/no-expand-atomic-store.ll b/llvm/test/Transforms/AtomicExpand/AMDGPU/no-expand-atomic-store.ll new file mode 100644 index 0000000000000000000000000000000000000000..db0c3a20e62f4851e755a4975f7cdf97d73ce0b9 --- /dev/null +++ b/llvm/test/Transforms/AtomicExpand/AMDGPU/no-expand-atomic-store.ll @@ -0,0 +1,179 @@ +; NOTE: Assertions have been autogenerated by utils/update_test_checks.py UTC_ARGS: --version 4 +; RUN: opt -S -mtriple=amdgcn-amd-amdhsa -passes=atomic-expand %s | FileCheck %s + +define void @store_atomic_f32_global_system(float %val, ptr addrspace(1) %ptr) { +; CHECK-LABEL: define void @store_atomic_f32_global_system( +; CHECK-SAME: float [[VAL:%.*]], ptr addrspace(1) [[PTR:%.*]]) { +; CHECK-NEXT: [[TMP1:%.*]] = bitcast float [[VAL]] to i32 +; CHECK-NEXT: store atomic i32 [[TMP1]], ptr addrspace(1) [[PTR]] seq_cst, align 4 +; CHECK-NEXT: ret void +; + store atomic float %val, ptr addrspace(1) %ptr seq_cst, align 4, !some.unknown.md !0 + ret void +} + +define void @store_atomic_f32_global_agent(float %val, ptr addrspace(1) %ptr) { +; CHECK-LABEL: define void @store_atomic_f32_global_agent( +; CHECK-SAME: float [[VAL:%.*]], ptr addrspace(1) [[PTR:%.*]]) { +; CHECK-NEXT: [[TMP1:%.*]] = bitcast float [[VAL]] to i32 +; CHECK-NEXT: store atomic i32 [[TMP1]], ptr addrspace(1) [[PTR]] syncscope("agent") seq_cst, align 4 +; CHECK-NEXT: ret void +; + store atomic float %val, ptr addrspace(1) %ptr syncscope("agent") seq_cst, align 4, !some.unknown.md !0 + ret void +} + +define void @store_atomic_f32_local(float %val, ptr addrspace(3) %ptr) { +; CHECK-LABEL: define void @store_atomic_f32_local( +; CHECK-SAME: float [[VAL:%.*]], ptr addrspace(3) [[PTR:%.*]]) { +; CHECK-NEXT: [[TMP1:%.*]] = bitcast float [[VAL]] to i32 +; CHECK-NEXT: store atomic i32 [[TMP1]], ptr addrspace(3) [[PTR]] seq_cst, align 4 +; CHECK-NEXT: ret void +; + store atomic float %val, ptr addrspace(3) %ptr seq_cst, align 4, !some.unknown.md !0 + ret void +} + +define void @store_atomic_f32_flat(float %val, ptr %ptr) { +; CHECK-LABEL: define void @store_atomic_f32_flat( +; CHECK-SAME: float [[VAL:%.*]], ptr [[PTR:%.*]]) { +; CHECK-NEXT: [[TMP1:%.*]] = bitcast float [[VAL]] to i32 +; CHECK-NEXT: store atomic i32 [[TMP1]], ptr [[PTR]] seq_cst, align 4 +; CHECK-NEXT: ret void +; + store atomic float %val, ptr %ptr seq_cst, align 4, !some.unknown.md !0 + ret void +} + +define void @store_atomic_f16_global_system(half %val, ptr addrspace(1) %ptr) { +; CHECK-LABEL: define void @store_atomic_f16_global_system( +; CHECK-SAME: half [[VAL:%.*]], ptr addrspace(1) [[PTR:%.*]]) { +; CHECK-NEXT: [[TMP1:%.*]] = bitcast half [[VAL]] to i16 +; CHECK-NEXT: store atomic i16 [[TMP1]], ptr addrspace(1) [[PTR]] seq_cst, align 4 +; CHECK-NEXT: ret void +; + store atomic half %val, ptr addrspace(1) %ptr seq_cst, align 4, !some.unknown.md !0 + ret void +} + +define void @store_atomic_f16_global_agent(half %val, ptr addrspace(1) %ptr) { +; CHECK-LABEL: define void @store_atomic_f16_global_agent( +; CHECK-SAME: half [[VAL:%.*]], ptr addrspace(1) [[PTR:%.*]]) { +; CHECK-NEXT: [[TMP1:%.*]] = bitcast half [[VAL]] to i16 +; CHECK-NEXT: store atomic i16 [[TMP1]], ptr addrspace(1) [[PTR]] syncscope("agent") seq_cst, align 4 +; CHECK-NEXT: ret void +; + store atomic half %val, ptr addrspace(1) %ptr syncscope("agent") seq_cst, align 4, !some.unknown.md !0 + ret void +} + +define void @store_atomic_f16_local(half %val, ptr addrspace(3) %ptr) { +; CHECK-LABEL: define void @store_atomic_f16_local( +; CHECK-SAME: half [[VAL:%.*]], ptr addrspace(3) [[PTR:%.*]]) { +; CHECK-NEXT: [[TMP1:%.*]] = bitcast half [[VAL]] to i16 +; CHECK-NEXT: store atomic i16 [[TMP1]], ptr addrspace(3) [[PTR]] seq_cst, align 4 +; CHECK-NEXT: ret void +; + store atomic half %val, ptr addrspace(3) %ptr seq_cst, align 4, !some.unknown.md !0 + ret void +} + +define void @store_atomic_f16_flat(half %val, ptr %ptr) { +; CHECK-LABEL: define void @store_atomic_f16_flat( +; CHECK-SAME: half [[VAL:%.*]], ptr [[PTR:%.*]]) { +; CHECK-NEXT: [[TMP1:%.*]] = bitcast half [[VAL]] to i16 +; CHECK-NEXT: store atomic i16 [[TMP1]], ptr [[PTR]] seq_cst, align 4 +; CHECK-NEXT: ret void +; + store atomic half %val, ptr %ptr seq_cst, align 4, !some.unknown.md !0 + ret void +} + +define void @store_atomic_bf16_global_system(bfloat %val, ptr addrspace(1) %ptr) { +; CHECK-LABEL: define void @store_atomic_bf16_global_system( +; CHECK-SAME: bfloat [[VAL:%.*]], ptr addrspace(1) [[PTR:%.*]]) { +; CHECK-NEXT: [[TMP1:%.*]] = bitcast bfloat [[VAL]] to i16 +; CHECK-NEXT: store atomic i16 [[TMP1]], ptr addrspace(1) [[PTR]] seq_cst, align 4 +; CHECK-NEXT: ret void +; + store atomic bfloat %val, ptr addrspace(1) %ptr seq_cst, align 4, !some.unknown.md !0 + ret void +} + +define void @store_atomic_bf16_global_agent(bfloat %val, ptr addrspace(1) %ptr) { +; CHECK-LABEL: define void @store_atomic_bf16_global_agent( +; CHECK-SAME: bfloat [[VAL:%.*]], ptr addrspace(1) [[PTR:%.*]]) { +; CHECK-NEXT: [[TMP1:%.*]] = bitcast bfloat [[VAL]] to i16 +; CHECK-NEXT: store atomic i16 [[TMP1]], ptr addrspace(1) [[PTR]] syncscope("agent") seq_cst, align 4 +; CHECK-NEXT: ret void +; + store atomic bfloat %val, ptr addrspace(1) %ptr syncscope("agent") seq_cst, align 4, !some.unknown.md !0 + ret void +} + +define void @store_atomic_bf16_local(bfloat %val, ptr addrspace(3) %ptr) { +; CHECK-LABEL: define void @store_atomic_bf16_local( +; CHECK-SAME: bfloat [[VAL:%.*]], ptr addrspace(3) [[PTR:%.*]]) { +; CHECK-NEXT: [[TMP1:%.*]] = bitcast bfloat [[VAL]] to i16 +; CHECK-NEXT: store atomic i16 [[TMP1]], ptr addrspace(3) [[PTR]] seq_cst, align 4 +; CHECK-NEXT: ret void +; + store atomic bfloat %val, ptr addrspace(3) %ptr seq_cst, align 4, !some.unknown.md !0 + ret void +} + +define void @store_atomic_bf16_flat(bfloat %val, ptr %ptr) { +; CHECK-LABEL: define void @store_atomic_bf16_flat( +; CHECK-SAME: bfloat [[VAL:%.*]], ptr [[PTR:%.*]]) { +; CHECK-NEXT: [[TMP1:%.*]] = bitcast bfloat [[VAL]] to i16 +; CHECK-NEXT: store atomic i16 [[TMP1]], ptr [[PTR]] seq_cst, align 4 +; CHECK-NEXT: ret void +; + store atomic bfloat %val, ptr %ptr seq_cst, align 4, !some.unknown.md !0 + ret void +} +define void @store_atomic_f64_global_system(double %val, ptr addrspace(1) %ptr) { +; CHECK-LABEL: define void @store_atomic_f64_global_system( +; CHECK-SAME: double [[VAL:%.*]], ptr addrspace(1) [[PTR:%.*]]) { +; CHECK-NEXT: [[TMP1:%.*]] = bitcast double [[VAL]] to i64 +; CHECK-NEXT: store atomic i64 [[TMP1]], ptr addrspace(1) [[PTR]] seq_cst, align 8 +; CHECK-NEXT: ret void +; + store atomic double %val, ptr addrspace(1) %ptr seq_cst, align 8, !some.unknown.md !0 + ret void +} + +define void @store_atomic_f64_global_agent(double %val, ptr addrspace(1) %ptr) { +; CHECK-LABEL: define void @store_atomic_f64_global_agent( +; CHECK-SAME: double [[VAL:%.*]], ptr addrspace(1) [[PTR:%.*]]) { +; CHECK-NEXT: [[TMP1:%.*]] = bitcast double [[VAL]] to i64 +; CHECK-NEXT: store atomic i64 [[TMP1]], ptr addrspace(1) [[PTR]] syncscope("agent") seq_cst, align 8 +; CHECK-NEXT: ret void +; + store atomic double %val, ptr addrspace(1) %ptr syncscope("agent") seq_cst, align 8, !some.unknown.md !0 + ret void +} + +define void @store_atomic_f64_local(double %val, ptr addrspace(3) %ptr) { +; CHECK-LABEL: define void @store_atomic_f64_local( +; CHECK-SAME: double [[VAL:%.*]], ptr addrspace(3) [[PTR:%.*]]) { +; CHECK-NEXT: [[TMP1:%.*]] = bitcast double [[VAL]] to i64 +; CHECK-NEXT: store atomic i64 [[TMP1]], ptr addrspace(3) [[PTR]] seq_cst, align 8 +; CHECK-NEXT: ret void +; + store atomic double %val, ptr addrspace(3) %ptr seq_cst, align 8, !some.unknown.md !0 + ret void +} + +define void @store_atomic_f64_flat(double %val, ptr %ptr) { +; CHECK-LABEL: define void @store_atomic_f64_flat( +; CHECK-SAME: double [[VAL:%.*]], ptr [[PTR:%.*]]) { +; CHECK-NEXT: [[TMP1:%.*]] = bitcast double [[VAL]] to i64 +; CHECK-NEXT: store atomic i64 [[TMP1]], ptr [[PTR]] seq_cst, align 8 +; CHECK-NEXT: ret void +; + store atomic double %val, ptr %ptr seq_cst, align 8, !some.unknown.md !0 + ret void +} + +!0 = !{} diff --git a/llvm/test/Transforms/CallSiteSplitting/callsite-split-debug.ll b/llvm/test/Transforms/CallSiteSplitting/callsite-split-debug.ll index 8f10dcb30d7bfdf320e7ec7234b7c0e01406206c..68c906d616c92d031f76cb34927b3626f72d2d29 100644 --- a/llvm/test/Transforms/CallSiteSplitting/callsite-split-debug.ll +++ b/llvm/test/Transforms/CallSiteSplitting/callsite-split-debug.ll @@ -1,4 +1,4 @@ -; RUN: opt -S -passes=callsite-splitting -o - < %s | FileCheck %s +; RUN: opt -S -passes=callsite-splitting -o - < %s | FileCheck %s --check-prefixes=CHECK,CHECK-DEBUG ; RUN: opt -S -strip-debug -passes=callsite-splitting -o - < %s | FileCheck %s define internal i16 @bar(i16 %p1, i16 %p2) { @@ -8,6 +8,9 @@ define internal i16 @bar(i16 %p1, i16 %p2) { define i16 @foo(i16 %in) { bb0: + %a = alloca i16, align 4, !DIAssignID !12 + call void @llvm.dbg.assign(metadata i1 undef, metadata !11, metadata !DIExpression(), metadata !12, metadata ptr %a, metadata !DIExpression()), !dbg !8 + store i16 7, ptr %a, align 4, !DIAssignID !13 br label %bb1 bb1: @@ -20,13 +23,21 @@ bb2: CallsiteBB: %1 = phi i16 [ 0, %bb1 ], [ 1, %bb2 ] %c = phi i16 [ 2, %bb1 ], [ 3, %bb2 ] + %p = phi ptr [ %a, %bb1 ], [ %a, %bb2 ] + call void @llvm.dbg.value(metadata i16 %1, metadata !7, metadata !DIExpression()), !dbg !8 call void @llvm.dbg.value(metadata i16 %c, metadata !7, metadata !DIExpression()), !dbg !8 + call void @llvm.dbg.value(metadata !DIArgList(i16 %1, i16 %c), metadata !7, metadata !DIExpression()), !dbg !8 + call void @llvm.dbg.value(metadata !DIArgList(i16 %c, i16 %c), metadata !7, metadata !DIExpression()), !dbg !8 + call void @llvm.dbg.assign(metadata i16 %1, metadata !11, metadata !DIExpression(), metadata !13, metadata ptr %a, metadata !DIExpression()), !dbg !8 + call void @llvm.dbg.assign(metadata i16 %c, metadata !11, metadata !DIExpression(), metadata !13, metadata ptr %a, metadata !DIExpression()), !dbg !8 + call void @llvm.dbg.assign(metadata i16 %1, metadata !11, metadata !DIExpression(), metadata !13, metadata ptr %p, metadata !DIExpression()), !dbg !8 %2 = call i16 @bar(i16 %1, i16 5) ret i16 %2 } ; Function Attrs: nounwind readnone speculatable declare void @llvm.dbg.value(metadata, metadata, metadata) #0 +declare void @llvm.dbg.assign(metadata, metadata, metadata, metadata, metadata, metadata) attributes #0 = { nounwind readnone speculatable } @@ -43,14 +54,37 @@ attributes #0 = { nounwind readnone speculatable } !6 = distinct !DISubprogram(name: "foo", scope: !1, file: !1, line: 4, unit: !0) !7 = !DILocalVariable(name: "c", scope: !6, line: 5, type: !5) !8 = !DILocation(line: 5, column: 7, scope: !6) +!11 = !DILocalVariable(name: "a", scope: !6, line: 6, type: !5) +!12 = distinct !DIAssignID() +!13 = distinct !DIAssignID() ; The optimization should trigger even in the presence of the dbg.value in ; CallSiteBB. ; CHECK-LABEL: @foo ; CHECK-LABEL: bb1.split: +; CHECK-DEBUG: call void @llvm.dbg.value(metadata i16 0, metadata ![[DBG_1:[0-9]+]], {{.*}} +; CHECK-DEBUG: call void @llvm.dbg.value(metadata i16 2, metadata ![[DBG_1]], {{.*}} +; CHECK-DEBUG: call void @llvm.dbg.value(metadata !DIArgList(i16 0, i16 2), {{.*}} +; CHECK-DEBUG: call void @llvm.dbg.value(metadata !DIArgList(i16 2, i16 2), {{.*}} +; CHECK-DEBUG: call void @llvm.dbg.assign(metadata i16 0, metadata ![[DBG_2:[0-9]+]], {{.*}} +; CHECK-DEBUG: call void @llvm.dbg.assign(metadata i16 2, metadata ![[DBG_2]], {{.*}} +; CHECK-DEBUG: call void @llvm.dbg.assign(metadata i16 0, metadata ![[DBG_2]], metadata !DIExpression(), metadata ![[ID_1:[0-9]+]], metadata ptr %a, {{.*}} ; CHECK: [[TMP1:%[0-9]+]] = call i16 @bar(i16 0, i16 5) + ; CHECK-LABEL: bb2.split: +; CHECK-DEBUG: call void @llvm.dbg.value(metadata i16 1, metadata ![[DBG_1]], {{.*}} +; CHECK-DEBUG: call void @llvm.dbg.value(metadata i16 3, metadata ![[DBG_1]], {{.*}} +; CHECK-DEBUG: call void @llvm.dbg.value(metadata !DIArgList(i16 1, i16 3), {{.*}} +; CHECK-DEBUG: call void @llvm.dbg.value(metadata !DIArgList(i16 3, i16 3), {{.*}} +; CHECK-DEBUG: call void @llvm.dbg.assign(metadata i16 1, metadata ![[DBG_2]], {{.*}} +; CHECK-DEBUG: call void @llvm.dbg.assign(metadata i16 3, metadata ![[DBG_2]], {{.*}} +; CHECK-DEBUG: call void @llvm.dbg.assign(metadata i16 1, metadata ![[DBG_2]], metadata !DIExpression(), metadata ![[ID_1:[0-9]+]], metadata ptr %a, {{.*}} ; CHECK: [[TMP2:%[0-9]+]] = call i16 @bar(i16 1, i16 5) + ; CHECK-LABEL: CallsiteBB ; CHECK: %phi.call = phi i16 [ [[TMP2]], %bb2.split ], [ [[TMP1]], %bb1.split + +; CHECK-DEBUG-DAG: ![[DBG_1]] = !DILocalVariable(name: "c"{{.*}}) +; CHECK-DEBUG-DAG: ![[DBG_2]] = !DILocalVariable(name: "a"{{.*}}) +; CHECK-DEBUG-DAG: ![[ID_1]] = distinct !DIAssignID() diff --git a/llvm/test/Transforms/CodeGenPrepare/RISCV/noop-copy-sink.ll b/llvm/test/Transforms/CodeGenPrepare/RISCV/noop-copy-sink.ll new file mode 100644 index 0000000000000000000000000000000000000000..55cde6c1431fe30577758d8e643257ddba285424 --- /dev/null +++ b/llvm/test/Transforms/CodeGenPrepare/RISCV/noop-copy-sink.ll @@ -0,0 +1,30 @@ +; NOTE: Assertions have been autogenerated by utils/update_test_checks.py +; RUN: opt -S -passes='require,function(codegenprepare)' -mtriple=riscv64 %s \ +; RUN: | FileCheck --check-prefixes=CHECK %s + +define i16 @sink_trunc1(i64 %a) { +; CHECK-LABEL: @sink_trunc1( +; CHECK-NEXT: fnend: +; CHECK-NEXT: [[TMP0:%.*]] = trunc i64 [[A:%.*]] to i16 +; CHECK-NEXT: ret i16 [[TMP0]] +; + %trunc = trunc i64 %a to i16 + br label %fnend + +fnend: + ret i16 %trunc +} + +; The flags on the original trunc should be preserved. +define i16 @sink_trunc2(i64 %a) { +; CHECK-LABEL: @sink_trunc2( +; CHECK-NEXT: fnend: +; CHECK-NEXT: [[TMP0:%.*]] = trunc nuw nsw i64 [[A:%.*]] to i16 +; CHECK-NEXT: ret i16 [[TMP0]] +; + %trunc = trunc nuw nsw i64 %a to i16 + br label %fnend + +fnend: + ret i16 %trunc +} diff --git a/llvm/test/Transforms/Coroutines/coro-split-musttail10.ll b/llvm/test/Transforms/Coroutines/coro-split-musttail10.ll index cdd58b2a084fcd8d12c32386de102ae94c985668..3e91b79c10f736bec16d33e63a847a68ac48fca0 100644 --- a/llvm/test/Transforms/Coroutines/coro-split-musttail10.ll +++ b/llvm/test/Transforms/Coroutines/coro-split-musttail10.ll @@ -1,9 +1,12 @@ ; Tests that we would convert coro.resume to a musttail call if the target is -; Wasm64 with tail-call support. -; RUN: opt < %s -passes='cgscc(coro-split),simplifycfg,early-cse' -S | FileCheck %s -; RUN: opt < %s -passes='pgo-instr-gen,cgscc(coro-split),simplifycfg,early-cse' -S | FileCheck %s +; Wasm64 or Wasm32 with tail-call support. +; REQUIRES: webassembly-registered-target -target triple = "wasm64-unknown-unknown" +; RUN: opt -mtriple=wasm64-unknown-unknown < %s -passes='cgscc(coro-split),simplifycfg,early-cse' -S | FileCheck %s +; RUN: opt -mtriple=wasm64-unknown-unknown < %s -passes='pgo-instr-gen,cgscc(coro-split),simplifycfg,early-cse' -S | FileCheck %s + +; RUN: opt -mtriple=wasm32-unknown-unknown < %s -passes='cgscc(coro-split),simplifycfg,early-cse' -S | FileCheck %s +; RUN: opt -mtriple=wasm32-unknown-unknown < %s -passes='pgo-instr-gen,cgscc(coro-split),simplifycfg,early-cse' -S | FileCheck %s define void @f() #0 { entry: diff --git a/llvm/test/Transforms/Coroutines/coro-split-musttail11.ll b/llvm/test/Transforms/Coroutines/coro-split-musttail11.ll deleted file mode 100644 index da5d868280e967139b13858a7d4308f07362bd9b..0000000000000000000000000000000000000000 --- a/llvm/test/Transforms/Coroutines/coro-split-musttail11.ll +++ /dev/null @@ -1,55 +0,0 @@ -; Tests that we would convert coro.resume to a musttail call if the target is -; Wasm32 with tail-call support. -; RUN: opt < %s -passes='cgscc(coro-split),simplifycfg,early-cse' -S | FileCheck %s -; RUN: opt < %s -passes='pgo-instr-gen,cgscc(coro-split),simplifycfg,early-cse' -S | FileCheck %s - -target triple = "wasm32-unknown-unknown" - -define void @f() #0 { -entry: - %id = call token @llvm.coro.id(i32 0, ptr null, ptr null, ptr null) - %alloc = call ptr @malloc(i64 16) #3 - %vFrame = call noalias nonnull ptr @llvm.coro.begin(token %id, ptr %alloc) - - %save = call token @llvm.coro.save(ptr null) - %addr1 = call ptr @llvm.coro.subfn.addr(ptr null, i8 0) - call fastcc void %addr1(ptr null) - - %suspend = call i8 @llvm.coro.suspend(token %save, i1 false) - switch i8 %suspend, label %exit [ - i8 0, label %await.ready - i8 1, label %exit - ] -await.ready: - %save2 = call token @llvm.coro.save(ptr null) - %addr2 = call ptr @llvm.coro.subfn.addr(ptr null, i8 0) - call fastcc void %addr2(ptr null) - - %suspend2 = call i8 @llvm.coro.suspend(token %save2, i1 false) - switch i8 %suspend2, label %exit [ - i8 0, label %exit - i8 1, label %exit - ] -exit: - call i1 @llvm.coro.end(ptr null, i1 false, token none) - ret void -} - -; CHECK: musttail call - -declare token @llvm.coro.id(i32, ptr readnone, ptr nocapture readonly, ptr) #1 -declare i1 @llvm.coro.alloc(token) #2 -declare i64 @llvm.coro.size.i64() #3 -declare ptr @llvm.coro.begin(token, ptr writeonly) #2 -declare token @llvm.coro.save(ptr) #2 -declare ptr @llvm.coro.frame() #3 -declare i8 @llvm.coro.suspend(token, i1) #2 -declare ptr @llvm.coro.free(token, ptr nocapture readonly) #1 -declare i1 @llvm.coro.end(ptr, i1, token) #2 -declare ptr @llvm.coro.subfn.addr(ptr nocapture readonly, i8) #1 -declare ptr @malloc(i64) - -attributes #0 = { presplitcoroutine "target-features"="+tail-call" } -attributes #1 = { argmemonly nounwind readonly } -attributes #2 = { nounwind } -attributes #3 = { nounwind readnone } diff --git a/llvm/test/Transforms/FunctionSpecialization/discover-transitive-phis.ll b/llvm/test/Transforms/FunctionSpecialization/discover-transitive-phis.ll index b4c24715037bcafc2e42926339c58eaa3d4860d6..d0095231a30f934ec130f309eb0bc68f2f86b21e 100644 --- a/llvm/test/Transforms/FunctionSpecialization/discover-transitive-phis.ll +++ b/llvm/test/Transforms/FunctionSpecialization/discover-transitive-phis.ll @@ -1,22 +1,22 @@ -; NOTE: Assertions have been autogenerated by utils/update_test_checks.py +; NOTE: Assertions have been autogenerated by utils/update_test_checks.py UTC_ARGS: --version 4 ; ; RUN: opt -passes="ipsccp" -funcspec-min-function-size=20 -funcspec-for-literal-constant -S < %s | FileCheck %s --check-prefix=FUNCSPEC ; RUN: opt -passes="ipsccp" -funcspec-min-function-size=20 -funcspec-for-literal-constant -funcspec-max-discovery-iterations=16 -S < %s | FileCheck %s --check-prefix=NOFUNCSPEC define i64 @bar(i1 %c1, i1 %c2, i1 %c3, i1 %c4, i1 %c5, i1 %c6, i1 %c7, i1 %c8, i1 %c9, i1 %c10) { -; FUNCSPEC-LABEL: define i64 @bar( +; FUNCSPEC-LABEL: define range(i64 4, 13) i64 @bar( ; FUNCSPEC-SAME: i1 [[C1:%.*]], i1 [[C2:%.*]], i1 [[C3:%.*]], i1 [[C4:%.*]], i1 [[C5:%.*]], i1 [[C6:%.*]], i1 [[C7:%.*]], i1 [[C8:%.*]], i1 [[C9:%.*]], i1 [[C10:%.*]]) { ; FUNCSPEC-NEXT: entry: -; FUNCSPEC-NEXT: [[F1:%.*]] = call i64 @foo.specialized.1(i64 3, i1 [[C1]], i1 [[C2]], i1 [[C3]], i1 [[C4]], i1 [[C5]], i1 [[C6]], i1 [[C7]], i1 [[C8]], i1 [[C9]], i1 [[C10]]), !range [[RNG0:![0-9]+]] -; FUNCSPEC-NEXT: [[F2:%.*]] = call i64 @foo.specialized.2(i64 4, i1 [[C1]], i1 [[C2]], i1 [[C3]], i1 [[C4]], i1 [[C5]], i1 [[C6]], i1 [[C7]], i1 [[C8]], i1 [[C9]], i1 [[C10]]), !range [[RNG1:![0-9]+]] +; FUNCSPEC-NEXT: [[F1:%.*]] = call i64 @foo.specialized.1(i64 3, i1 [[C1]], i1 [[C2]], i1 [[C3]], i1 [[C4]], i1 [[C5]], i1 [[C6]], i1 [[C7]], i1 [[C8]], i1 [[C9]], i1 [[C10]]) +; FUNCSPEC-NEXT: [[F2:%.*]] = call i64 @foo.specialized.2(i64 4, i1 [[C1]], i1 [[C2]], i1 [[C3]], i1 [[C4]], i1 [[C5]], i1 [[C6]], i1 [[C7]], i1 [[C8]], i1 [[C9]], i1 [[C10]]) ; FUNCSPEC-NEXT: [[ADD:%.*]] = add nuw nsw i64 [[F1]], [[F2]] ; FUNCSPEC-NEXT: ret i64 [[ADD]] ; -; NOFUNCSPEC-LABEL: define i64 @bar( +; NOFUNCSPEC-LABEL: define range(i64 4, 13) i64 @bar( ; NOFUNCSPEC-SAME: i1 [[C1:%.*]], i1 [[C2:%.*]], i1 [[C3:%.*]], i1 [[C4:%.*]], i1 [[C5:%.*]], i1 [[C6:%.*]], i1 [[C7:%.*]], i1 [[C8:%.*]], i1 [[C9:%.*]], i1 [[C10:%.*]]) { ; NOFUNCSPEC-NEXT: entry: -; NOFUNCSPEC-NEXT: [[F1:%.*]] = call i64 @foo(i64 3, i1 [[C1]], i1 [[C2]], i1 [[C3]], i1 [[C4]], i1 [[C5]], i1 [[C6]], i1 [[C7]], i1 [[C8]], i1 [[C9]], i1 [[C10]]), !range [[RNG0:![0-9]+]] -; NOFUNCSPEC-NEXT: [[F2:%.*]] = call i64 @foo(i64 4, i1 [[C1]], i1 [[C2]], i1 [[C3]], i1 [[C4]], i1 [[C5]], i1 [[C6]], i1 [[C7]], i1 [[C8]], i1 [[C9]], i1 [[C10]]), !range [[RNG0]] +; NOFUNCSPEC-NEXT: [[F1:%.*]] = call i64 @foo(i64 3, i1 [[C1]], i1 [[C2]], i1 [[C3]], i1 [[C4]], i1 [[C5]], i1 [[C6]], i1 [[C7]], i1 [[C8]], i1 [[C9]], i1 [[C10]]) +; NOFUNCSPEC-NEXT: [[F2:%.*]] = call i64 @foo(i64 4, i1 [[C1]], i1 [[C2]], i1 [[C3]], i1 [[C4]], i1 [[C5]], i1 [[C6]], i1 [[C7]], i1 [[C8]], i1 [[C9]], i1 [[C10]]) ; NOFUNCSPEC-NEXT: [[ADD:%.*]] = add nuw nsw i64 [[F1]], [[F2]] ; NOFUNCSPEC-NEXT: ret i64 [[ADD]] ; @@ -28,6 +28,50 @@ entry: } define internal i64 @foo(i64 %n, i1 %c1, i1 %c2, i1 %c3, i1 %c4, i1 %c5, i1 %c6, i1 %c7, i1 %c8, i1 %c9, i1 %c10) { +; NOFUNCSPEC-LABEL: define internal range(i64 2, 7) i64 @foo( +; NOFUNCSPEC-SAME: i64 [[N:%.*]], i1 [[C1:%.*]], i1 [[C2:%.*]], i1 [[C3:%.*]], i1 [[C4:%.*]], i1 [[C5:%.*]], i1 [[C6:%.*]], i1 [[C7:%.*]], i1 [[C8:%.*]], i1 [[C9:%.*]], i1 [[C10:%.*]]) { +; NOFUNCSPEC-NEXT: entry: +; NOFUNCSPEC-NEXT: br i1 [[C1]], label [[L1:%.*]], label [[L9:%.*]] +; NOFUNCSPEC: l1: +; NOFUNCSPEC-NEXT: [[PHI1:%.*]] = phi i64 [ [[N]], [[ENTRY:%.*]] ], [ [[PHI2:%.*]], [[L2:%.*]] ] +; NOFUNCSPEC-NEXT: [[ADD:%.*]] = add nuw nsw i64 [[PHI1]], 1 +; NOFUNCSPEC-NEXT: br i1 [[C2]], label [[L1_5:%.*]], label [[EXIT:%.*]] +; NOFUNCSPEC: l1_5: +; NOFUNCSPEC-NEXT: br i1 [[C3]], label [[L1_75:%.*]], label [[L6:%.*]] +; NOFUNCSPEC: l1_75: +; NOFUNCSPEC-NEXT: br i1 [[C4]], label [[L2]], label [[L3:%.*]] +; NOFUNCSPEC: l2: +; NOFUNCSPEC-NEXT: [[PHI2]] = phi i64 [ [[PHI1]], [[L1_75]] ], [ [[PHI3:%.*]], [[L3]] ] +; NOFUNCSPEC-NEXT: br label [[L1]] +; NOFUNCSPEC: l3: +; NOFUNCSPEC-NEXT: [[PHI3]] = phi i64 [ [[PHI1]], [[L1_75]] ], [ [[PHI4:%.*]], [[L4:%.*]] ] +; NOFUNCSPEC-NEXT: br label [[L2]] +; NOFUNCSPEC: l4: +; NOFUNCSPEC-NEXT: [[PHI4]] = phi i64 [ [[PHI5:%.*]], [[L5:%.*]] ], [ [[PHI6:%.*]], [[L6]] ] +; NOFUNCSPEC-NEXT: br i1 [[C5]], label [[L3]], label [[L6]] +; NOFUNCSPEC: l5: +; NOFUNCSPEC-NEXT: [[PHI5]] = phi i64 [ [[PHI6]], [[L6_5:%.*]] ], [ [[PHI7:%.*]], [[L7:%.*]] ] +; NOFUNCSPEC-NEXT: br label [[L4]] +; NOFUNCSPEC: l6: +; NOFUNCSPEC-NEXT: [[PHI6]] = phi i64 [ [[PHI4]], [[L4]] ], [ [[PHI1]], [[L1_5]] ] +; NOFUNCSPEC-NEXT: br i1 [[C6]], label [[L4]], label [[L6_5]] +; NOFUNCSPEC: l6_5: +; NOFUNCSPEC-NEXT: br i1 [[C7]], label [[L5]], label [[L8:%.*]] +; NOFUNCSPEC: l7: +; NOFUNCSPEC-NEXT: [[PHI7]] = phi i64 [ [[PHI9:%.*]], [[L9]] ], [ [[PHI8:%.*]], [[L8]] ] +; NOFUNCSPEC-NEXT: br i1 [[C8]], label [[L5]], label [[L8]] +; NOFUNCSPEC: l8: +; NOFUNCSPEC-NEXT: [[PHI8]] = phi i64 [ [[PHI6]], [[L6_5]] ], [ [[PHI7]], [[L7]] ] +; NOFUNCSPEC-NEXT: br i1 [[C9]], label [[L7]], label [[L9]] +; NOFUNCSPEC: l9: +; NOFUNCSPEC-NEXT: [[PHI9]] = phi i64 [ [[N]], [[ENTRY]] ], [ [[PHI8]], [[L8]] ] +; NOFUNCSPEC-NEXT: [[SUB:%.*]] = sub nuw nsw i64 [[PHI9]], 1 +; NOFUNCSPEC-NEXT: [[MUL:%.*]] = mul nuw nsw i64 [[SUB]], 2 +; NOFUNCSPEC-NEXT: br i1 [[C10]], label [[L7]], label [[EXIT]] +; NOFUNCSPEC: exit: +; NOFUNCSPEC-NEXT: [[RES:%.*]] = phi i64 [ 2, [[L1]] ], [ [[MUL]], [[L9]] ] +; NOFUNCSPEC-NEXT: ret i64 [[RES]] +; entry: br i1 %c1, label %l1, label %l9 diff --git a/llvm/test/Transforms/FunctionSpecialization/global-var-constants.ll b/llvm/test/Transforms/FunctionSpecialization/global-var-constants.ll index b9481baae60b9ebdd76d1ad8ca4d4cfa91c30b26..a576d9aa32e1408621dd821928116c20dacc4a22 100644 --- a/llvm/test/Transforms/FunctionSpecialization/global-var-constants.ll +++ b/llvm/test/Transforms/FunctionSpecialization/global-var-constants.ll @@ -49,10 +49,10 @@ entry: ; Check if specialisation on the address of a non-const global variable ; is not allowed, then it is not performed. -; NO-GLOBALS-LABEL: define internal i32 @g() +; NO-GLOBALS-LABEL: define internal range(i32 -2147483646, -2147483648) i32 @g() ; NO-GLOBALS: call i32 @f(ptr @G) -; NO-GLOBALS-LABEL: define i32 @h0(ptr %p) +; NO-GLOBALS-LABEL: define range(i32 -2147483646, -2147483648) i32 @h0(ptr %p) ; NO-GLOBALS:call i32 @g() ; NO-GLOBALS-LABEL: define i32 @h1() @@ -64,10 +64,10 @@ entry: ; Check if specialisation on the address of a non-const global variable ; is allowed, then it is performed where possible. -; GLOBALS-LABEL: define internal i32 @g() +; GLOBALS-LABEL: define internal range(i32 -2147483646, -2147483648) i32 @g() ; GLOBALS: call i32 @f.specialized.2() -; GLOBALS-LABEL: define i32 @h0(ptr %p) +; GLOBALS-LABEL: define range(i32 -2147483646, -2147483648) i32 @h0(ptr %p) ; GLOBALS: call i32 @g() ; GLOBALS-LABEL: define i32 @h1() diff --git a/llvm/test/Transforms/FunctionSpecialization/literal-const.ll b/llvm/test/Transforms/FunctionSpecialization/literal-const.ll index f107ffe0ec7ebfd6e8b86dc38cf9cba93edef094..3eae3dc261fb2ac689a9ed970b8fbe24a7a349ee 100644 --- a/llvm/test/Transforms/FunctionSpecialization/literal-const.ll +++ b/llvm/test/Transforms/FunctionSpecialization/literal-const.ll @@ -71,10 +71,10 @@ entry: ; CHECK-LIT-LABEL: define i32 @f1 ; CHECK-LIT: call i32 @neg.specialized.[[#B:]] -; CHECK-LIT-LABEL: define i32 @g0 +; CHECK-LIT-LABEL: define range(i32 -2147483647, -2147483648) i32 @g0 ; CHECK-LIT: call i32 @add.specialized.[[#C:]] -; CHECK-LIT-LABEL: define i32 @g1 +; CHECK-LIT-LABEL: define range(i32 -2147483647, -2147483648) i32 @g1 ; CHECK-LIT: call i32 @add.specialized.[[#D:]] ; CHECK-LIT-LABEL: define float @h0 diff --git a/llvm/test/Transforms/GVN/condprop.ll b/llvm/test/Transforms/GVN/condprop.ll index 6b1e4d10601099b8b9dbbce969eb9499d0e3664b..6402a23157729cecae151b9b9994b942cbf37e28 100644 --- a/llvm/test/Transforms/GVN/condprop.ll +++ b/llvm/test/Transforms/GVN/condprop.ll @@ -214,11 +214,11 @@ define void @test4(i1 %b, i32 %x) { ; CHECK-NEXT: br i1 [[B:%.*]], label [[SW:%.*]], label [[CASE3:%.*]] ; CHECK: sw: ; CHECK-NEXT: switch i32 [[X:%.*]], label [[DEFAULT:%.*]] [ -; CHECK-NEXT: i32 0, label [[CASE0:%.*]] -; CHECK-NEXT: i32 1, label [[CASE1:%.*]] -; CHECK-NEXT: i32 2, label [[CASE0]] -; CHECK-NEXT: i32 3, label [[CASE3]] -; CHECK-NEXT: i32 4, label [[DEFAULT]] +; CHECK-NEXT: i32 0, label [[CASE0:%.*]] +; CHECK-NEXT: i32 1, label [[CASE1:%.*]] +; CHECK-NEXT: i32 2, label [[CASE0]] +; CHECK-NEXT: i32 3, label [[CASE3]] +; CHECK-NEXT: i32 4, label [[DEFAULT]] ; CHECK-NEXT: ] ; CHECK: default: ; CHECK-NEXT: call void @bar(i32 [[X]]) @@ -521,15 +521,16 @@ define i32 @test13(ptr %ptr1, ptr %ptr2) { ; CHECK-NEXT: [[GEP1:%.*]] = getelementptr i32, ptr [[PTR2:%.*]], i32 1 ; CHECK-NEXT: [[GEP2:%.*]] = getelementptr i32, ptr [[PTR2]], i32 2 ; CHECK-NEXT: [[CMP:%.*]] = icmp eq ptr [[PTR1:%.*]], [[PTR2]] -; CHECK-NEXT: [[VAL2_PRE:%.*]] = load i32, ptr [[GEP2]], align 4 ; CHECK-NEXT: br i1 [[CMP]], label [[IF:%.*]], label [[END:%.*]] ; CHECK: if: +; CHECK-NEXT: [[VAL1:%.*]] = load i32, ptr [[GEP2]], align 4 ; CHECK-NEXT: br label [[END]] ; CHECK: end: -; CHECK-NEXT: [[PHI1:%.*]] = phi ptr [ [[PTR2]], [[IF]] ], [ [[GEP1]], [[ENTRY:%.*]] ] -; CHECK-NEXT: [[PHI2:%.*]] = phi i32 [ [[VAL2_PRE]], [[IF]] ], [ 0, [[ENTRY]] ] +; CHECK-NEXT: [[PHI1:%.*]] = phi ptr [ [[PTR1]], [[IF]] ], [ [[GEP1]], [[ENTRY:%.*]] ] +; CHECK-NEXT: [[PHI2:%.*]] = phi i32 [ [[VAL1]], [[IF]] ], [ 0, [[ENTRY]] ] ; CHECK-NEXT: store i32 0, ptr [[PHI1]], align 4 -; CHECK-NEXT: [[RET:%.*]] = add i32 [[PHI2]], [[VAL2_PRE]] +; CHECK-NEXT: [[VAL2:%.*]] = load i32, ptr [[GEP2]], align 4 +; CHECK-NEXT: [[RET:%.*]] = add i32 [[PHI2]], [[VAL2]] ; CHECK-NEXT: ret i32 [[RET]] ; entry: @@ -552,14 +553,14 @@ end: ret i32 %ret } -define void @test14(ptr %ptr1, ptr noalias %ptr2) { +define void @test14(ptr %ptr1, ptr noalias %ptr2, i1 %b1, i1 %b2) { ; CHECK-LABEL: @test14( ; CHECK-NEXT: entry: ; CHECK-NEXT: [[GEP1:%.*]] = getelementptr inbounds i32, ptr [[PTR1:%.*]], i32 1 ; CHECK-NEXT: [[GEP2:%.*]] = getelementptr inbounds i32, ptr [[PTR1]], i32 2 ; CHECK-NEXT: br label [[LOOP:%.*]] ; CHECK: loop: -; CHECK-NEXT: br i1 undef, label [[LOOP_IF1_CRIT_EDGE:%.*]], label [[THEN:%.*]] +; CHECK-NEXT: br i1 [[B1:%.*]], label [[LOOP_IF1_CRIT_EDGE:%.*]], label [[THEN:%.*]] ; CHECK: loop.if1_crit_edge: ; CHECK-NEXT: [[VAL2_PRE:%.*]] = load i32, ptr [[GEP2]], align 4 ; CHECK-NEXT: br label [[IF1:%.*]] @@ -574,10 +575,10 @@ define void @test14(ptr %ptr1, ptr noalias %ptr2) { ; CHECK: if2: ; CHECK-NEXT: br label [[LOOP_END]] ; CHECK: loop.end: -; CHECK-NEXT: [[PHI3:%.*]] = phi ptr [ [[PTR2]], [[THEN]] ], [ [[PTR1]], [[IF2]] ] +; CHECK-NEXT: [[PHI3:%.*]] = phi ptr [ [[GEP2]], [[THEN]] ], [ [[PTR1]], [[IF2]] ] ; CHECK-NEXT: [[VAL3]] = load i32, ptr [[GEP2]], align 4 ; CHECK-NEXT: store i32 [[VAL3]], ptr [[PHI3]], align 4 -; CHECK-NEXT: br i1 undef, label [[LOOP]], label [[IF1]] +; CHECK-NEXT: br i1 [[B2:%.*]], label [[LOOP]], label [[IF1]] ; entry: %gep1 = getelementptr inbounds i32, ptr %ptr1, i32 1 @@ -586,7 +587,7 @@ entry: loop: %phi1 = phi ptr [ %gep3, %loop.end ], [ %gep1, %entry ] - br i1 undef, label %if1, label %then + br i1 %b1, label %if1, label %then if1: @@ -607,5 +608,201 @@ loop.end: %val3 = load i32, ptr %gep2, align 4 store i32 %val3, ptr %phi3, align 4 %gep3 = getelementptr inbounds i32, ptr %ptr1, i32 1 - br i1 undef, label %loop, label %if1 + br i1 %b2, label %loop, label %if1 +} + +; Make sure that the call to use_ptr does not have %p1 +define void @single_phi1(ptr %p0, ptr %p1, i8 %s) { +; CHECK-LABEL: @single_phi1( +; CHECK-NEXT: entry: +; CHECK-NEXT: [[P2:%.*]] = load ptr, ptr [[P0:%.*]], align 8 +; CHECK-NEXT: [[CMP1:%.*]] = icmp eq ptr [[P2]], [[P1:%.*]] +; CHECK-NEXT: br i1 [[CMP1]], label [[BB4:%.*]], label [[BB1:%.*]] +; CHECK: bb1: +; CHECK-NEXT: switch i8 [[S:%.*]], label [[BB2:%.*]] [ +; CHECK-NEXT: i8 0, label [[BB1]] +; CHECK-NEXT: i8 1, label [[BB3:%.*]] +; CHECK-NEXT: ] +; CHECK: bb2: +; CHECK-NEXT: unreachable +; CHECK: bb3: +; CHECK-NEXT: br label [[BB4]] +; CHECK: bb4: +; CHECK-NEXT: call void @use_bool(i1 [[CMP1]]) +; CHECK-NEXT: call void @use_ptr(ptr [[P2]]) +; CHECK-NEXT: ret void +; +entry: + %p2 = load ptr, ptr %p0, align 8 + %cmp1 = icmp eq ptr %p2, %p1 + br i1 %cmp1, label %bb4, label %bb1 + +bb1: + switch i8 %s, label %bb2 [ + i8 0, label %bb1 + i8 1, label %bb3 + ] + +bb2: + unreachable + +bb3: + br label %bb4 + +bb4: + %phi1 = phi ptr [ %p2, %entry ], [ %p2, %bb3 ] + %cmp2 = icmp eq ptr %phi1, %p1 + call void @use_bool(i1 %cmp2) + call void @use_ptr(ptr %phi1) + ret void +} + +define void @single_phi2(ptr %p0, ptr %p1, i8 %s) { +; CHECK-LABEL: @single_phi2( +; CHECK-NEXT: entry: +; CHECK-NEXT: [[P2:%.*]] = load ptr, ptr [[P0:%.*]], align 8 +; CHECK-NEXT: [[CMP1:%.*]] = icmp eq ptr [[P2]], [[P1:%.*]] +; CHECK-NEXT: br i1 [[CMP1]], label [[BB4:%.*]], label [[BB1:%.*]] +; CHECK: bb1: +; CHECK-NEXT: switch i8 [[S:%.*]], label [[BB2:%.*]] [ +; CHECK-NEXT: i8 0, label [[BB1]] +; CHECK-NEXT: i8 1, label [[BB3:%.*]] +; CHECK-NEXT: ] +; CHECK: bb2: +; CHECK-NEXT: br label [[BB4]] +; CHECK: bb3: +; CHECK-NEXT: br label [[BB4]] +; CHECK: bb4: +; CHECK-NEXT: call void @use_bool(i1 [[CMP1]]) +; CHECK-NEXT: call void @use_ptr(ptr [[P2]]) +; CHECK-NEXT: ret void +; +entry: + %p2 = load ptr, ptr %p0, align 8 + %cmp1 = icmp eq ptr %p2, %p1 + br i1 %cmp1, label %bb4, label %bb1 + +bb1: + switch i8 %s, label %bb2 [ + i8 0, label %bb1 + i8 1, label %bb3 + ] + +bb2: + br label %bb4 + +bb3: + br label %bb4 + +bb4: + %phi1 = phi ptr [ %p2, %entry ], [ %p2, %bb2 ], [ %p2, %bb3 ] + %cmp2 = icmp eq ptr %phi1, %p1 + call void @use_bool(i1 %cmp2) + call void @use_ptr(ptr %phi1) + ret void } + +define void @multiple_phi1(ptr %p0, ptr %p1, i8 %s) { +; CHECK-LABEL: @multiple_phi1( +; CHECK-NEXT: entry: +; CHECK-NEXT: [[P2:%.*]] = load ptr, ptr [[P0:%.*]], align 8 +; CHECK-NEXT: [[CMP1:%.*]] = icmp eq ptr [[P2]], [[P1:%.*]] +; CHECK-NEXT: br i1 [[CMP1]], label [[BB4:%.*]], label [[BB1:%.*]] +; CHECK: bb1: +; CHECK-NEXT: switch i8 [[S:%.*]], label [[BB2:%.*]] [ +; CHECK-NEXT: i8 0, label [[BB1]] +; CHECK-NEXT: i8 1, label [[BB3:%.*]] +; CHECK-NEXT: ] +; CHECK: bb2: +; CHECK-NEXT: unreachable +; CHECK: bb3: +; CHECK-NEXT: br label [[BB4]] +; CHECK: bb4: +; CHECK-NEXT: call void @use_bool(i1 [[CMP1]]) +; CHECK-NEXT: br label [[BB5:%.*]] +; CHECK: bb5: +; CHECK-NEXT: call void @use_ptr(ptr [[P2]]) +; CHECK-NEXT: br label [[BB5]] +; +entry: + %p2 = load ptr, ptr %p0, align 8 + %cmp1 = icmp eq ptr %p2, %p1 + br i1 %cmp1, label %bb4, label %bb1 + +bb1: + switch i8 %s, label %bb2 [ + i8 0, label %bb1 + i8 1, label %bb3 + ] + +bb2: + unreachable + +bb3: + br label %bb4 + +bb4: + %phi1 = phi ptr [ %p2, %entry ], [ poison, %bb3 ] + %cmp2 = icmp eq ptr %phi1, %p1 + call void @use_bool(i1 %cmp2) + br label %bb5 + +bb5: + %phi2 = phi ptr [ poison, %bb5 ], [ %phi1, %bb4 ] + call void @use_ptr(ptr %phi2) + br label %bb5 +} + +define void @multiple_phi2(ptr %p0, ptr %p1, i8 %s) { +; CHECK-LABEL: @multiple_phi2( +; CHECK-NEXT: entry: +; CHECK-NEXT: [[P2:%.*]] = load ptr, ptr [[P0:%.*]], align 8 +; CHECK-NEXT: [[CMP1:%.*]] = icmp eq ptr [[P2]], [[P1:%.*]] +; CHECK-NEXT: br i1 [[CMP1]], label [[BB4:%.*]], label [[BB1:%.*]] +; CHECK: bb1: +; CHECK-NEXT: switch i8 [[S:%.*]], label [[BB2:%.*]] [ +; CHECK-NEXT: i8 0, label [[BB1]] +; CHECK-NEXT: i8 1, label [[BB3:%.*]] +; CHECK-NEXT: ] +; CHECK: bb2: +; CHECK-NEXT: br label [[BB4]] +; CHECK: bb3: +; CHECK-NEXT: br label [[BB4]] +; CHECK: bb4: +; CHECK-NEXT: call void @use_bool(i1 [[CMP1]]) +; CHECK-NEXT: br label [[BB5:%.*]] +; CHECK: bb5: +; CHECK-NEXT: call void @use_ptr(ptr [[P2]]) +; CHECK-NEXT: br label [[BB5]] +; +entry: + %p2 = load ptr, ptr %p0, align 8 + %cmp1 = icmp eq ptr %p2, %p1 + br i1 %cmp1, label %bb4, label %bb1 + +bb1: + switch i8 %s, label %bb2 [ + i8 0, label %bb1 + i8 1, label %bb3 + ] + +bb2: + br label %bb4 + +bb3: + br label %bb4 + +bb4: + %phi1 = phi ptr [ %p2, %entry ], [ %p2, %bb2 ], [ poison, %bb3 ] + %cmp2 = icmp eq ptr %phi1, %p1 + call void @use_bool(i1 %cmp2) + br label %bb5 + +bb5: + %phi2 = phi ptr [ poison, %bb5 ], [ %phi1, %bb4 ] + call void @use_ptr(ptr %phi2) + br label %bb5 +} + +declare void @use_bool(i1) +declare void @use_ptr(ptr) diff --git a/llvm/test/Transforms/IRCE/pr89959.ll b/llvm/test/Transforms/IRCE/pr89959.ll new file mode 100644 index 0000000000000000000000000000000000000000..dc7c0dfbc57a97ade935a9d790020c4322e8ec3c --- /dev/null +++ b/llvm/test/Transforms/IRCE/pr89959.ll @@ -0,0 +1,33 @@ +; NOTE: Assertions have been autogenerated by utils/update_test_checks.py UTC_ARGS: --version 4 +; RUN: opt -passes=irce -S < %s 2>&1 | FileCheck %s + +; Make sure we don't crash. +define void @pr89959() { +; CHECK-LABEL: define void @pr89959() { +; CHECK-NEXT: top: +; CHECK-NEXT: br label [[L3:%.*]] +; CHECK: L3: +; CHECK-NEXT: [[VALUE_PHI:%.*]] = phi ptr [ null, [[TOP:%.*]] ], [ [[TMP0:%.*]], [[L13:%.*]] ] +; CHECK-NEXT: [[TMP0]] = getelementptr i8, ptr [[VALUE_PHI]], i64 8 +; CHECK-NEXT: [[DOTNOT:%.*]] = icmp ule ptr [[VALUE_PHI]], null +; CHECK-NEXT: br i1 [[DOTNOT]], label [[L13]], label [[L15:%.*]] +; CHECK: L13: +; CHECK-NEXT: br label [[L3]] +; CHECK: L15: +; CHECK-NEXT: ret void +; +top: + br label %L3 + +L3: + %value_phi = phi ptr [ null, %top ], [ %0, %L13 ] + %0 = getelementptr i8, ptr %value_phi, i64 8 + %.not = icmp ule ptr %value_phi, null + br i1 %.not, label %L13, label %L15 + +L13: + br label %L3 + +L15: + ret void +} diff --git a/llvm/test/Transforms/Inline/inline-deferred-instsimplify.ll b/llvm/test/Transforms/Inline/inline-deferred-instsimplify.ll new file mode 100644 index 0000000000000000000000000000000000000000..4a9c576f02719e789360361dcfeef201d815f516 --- /dev/null +++ b/llvm/test/Transforms/Inline/inline-deferred-instsimplify.ll @@ -0,0 +1,76 @@ +; NOTE: Assertions have been autogenerated by utils/update_test_checks.py UTC_ARGS: --version 4 +; RUN: opt < %s -passes=inline -S | FileCheck %s +; RUN: opt < %s -passes='cgscc(inline)' -S | FileCheck %s + +%struct.a = type { i32, i32, i32, i32, i32 } + +@g_var = global %struct.a { i32 1, i32 0, i32 0, i32 0, i32 0 }, align 8 +@other_g_var = global %struct.a zeroinitializer, align 4 + +define void @callee(ptr noundef byval(%struct.a) align 8 %ptr) { +; CHECK-LABEL: define void @callee( +; CHECK-SAME: ptr noundef byval([[STRUCT_A:%.*]]) align 8 [[PTR:%.*]]) { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[VAL:%.*]] = load i32, ptr [[PTR]], align 8 +; CHECK-NEXT: [[DOTNOT:%.*]] = icmp eq i32 [[VAL]], 0 +; CHECK-NEXT: br i1 [[DOTNOT]], label [[CHECK_POINTERS_ARE_EQUAL:%.*]], label [[STORE_PTR_IN_GVAR:%.*]] +; CHECK: store_ptr_in_gvar: +; CHECK-NEXT: store ptr [[PTR]], ptr @other_g_var, align 8 +; CHECK-NEXT: br label [[CHECK_POINTERS_ARE_EQUAL]] +; CHECK: check_pointers_are_equal: +; CHECK-NEXT: [[PHI:%.*]] = phi ptr [ [[PTR]], [[STORE_PTR_IN_GVAR]] ], [ @other_g_var, [[ENTRY:%.*]] ] +; CHECK-NEXT: [[DOTNOT1:%.*]] = icmp eq ptr [[PHI]], [[PTR]] +; CHECK-NEXT: br i1 [[DOTNOT1]], label [[RETURN:%.*]], label [[ABORT:%.*]] +; CHECK: abort: +; CHECK-NEXT: call void @abort() +; CHECK-NEXT: unreachable +; CHECK: return: +; CHECK-NEXT: ret void +; +entry: + %val = load i32, ptr %ptr, align 8 + %.not = icmp eq i32 %val, 0 + br i1 %.not, label %check_pointers_are_equal, label %store_ptr_in_gvar + +store_ptr_in_gvar: ; preds = %entry + store ptr %ptr, ptr @other_g_var, align 8 + br label %check_pointers_are_equal + +check_pointers_are_equal: ; preds = %store_ptr_in_gvar, %entry + %phi = phi ptr [ %ptr, %store_ptr_in_gvar ], [ @other_g_var, %entry ] +; FIXME: While inlining, the following is miscompiled to i1 false, +; as %ptr in the phi-node is not taken into account. + %.not1 = icmp eq ptr %phi, %ptr + br i1 %.not1, label %return, label %abort + +abort: ; preds = %check_pointers_are_equal + call void @abort() + unreachable + +return: ; preds = %check_pointers_are_equal + ret void +} + +define i32 @main() { +; CHECK-LABEL: define i32 @main() { +; CHECK-NEXT: [[G_VAR:%.*]] = alloca [[STRUCT_A:%.*]], align 8 +; CHECK-NEXT: call void @llvm.lifetime.start.p0(i64 20, ptr [[G_VAR]]) +; CHECK-NEXT: call void @llvm.memcpy.p0.p0.i64(ptr align 1 [[G_VAR]], ptr align 1 @g_var, i64 20, i1 false) +; CHECK-NEXT: [[VAL_I:%.*]] = load i32, ptr [[G_VAR]], align 8 +; CHECK-NEXT: [[DOTNOT_I:%.*]] = icmp eq i32 [[VAL_I]], 0 +; CHECK-NEXT: br i1 [[DOTNOT_I]], label [[CHECK_POINTERS_ARE_EQUAL_I:%.*]], label [[STORE_PTR_IN_GVAR_I:%.*]] +; CHECK: store_ptr_in_gvar.i: +; CHECK-NEXT: store ptr [[G_VAR]], ptr @other_g_var, align 8 +; CHECK-NEXT: br label [[CHECK_POINTERS_ARE_EQUAL_I]] +; CHECK: check_pointers_are_equal.i: +; CHECK-NEXT: [[PHI_I:%.*]] = phi ptr [ [[G_VAR]], [[STORE_PTR_IN_GVAR_I]] ], [ @other_g_var, [[TMP0:%.*]] ] +; CHECK-NEXT: call void @abort() +; CHECK-NEXT: unreachable +; CHECK: callee.exit: +; CHECK-NEXT: ret i32 0 +; + call void @callee(ptr noundef byval(%struct.a) align 8 @g_var) + ret i32 0 +} + +declare void @abort() diff --git a/llvm/test/Transforms/InstCombine/add4.ll b/llvm/test/Transforms/InstCombine/add4.ll index 7fc164c8b9a7c99b2ae5a2e68024cf1812f39db0..77f7fc7b35cd44a4e6d751b7a31d0e4138d4ec33 100644 --- a/llvm/test/Transforms/InstCombine/add4.ll +++ b/llvm/test/Transforms/InstCombine/add4.ll @@ -1,6 +1,8 @@ ; NOTE: Assertions have been autogenerated by utils/update_test_checks.py ; RUN: opt < %s -passes=instcombine -S | FileCheck %s +declare void @use(i32) + define i64 @match_unsigned(i64 %x) { ; CHECK-LABEL: @match_unsigned( ; CHECK-NEXT: [[UREM:%.*]] = urem i64 [[X:%.*]], 19136 @@ -127,3 +129,163 @@ define i32 @not_match_overflow(i32 %x) { %t4 = add i32 %t, %t3 ret i32 %t4 } + +; Tests from PR76128. +define i32 @fold_add_udiv_urem(i32 noundef %val) { +; CHECK-LABEL: @fold_add_udiv_urem( +; CHECK-NEXT: entry: +; CHECK-NEXT: [[DIV:%.*]] = udiv i32 [[VAL:%.*]], 10 +; CHECK-NEXT: [[TMP0:%.*]] = mul nuw i32 [[DIV]], 6 +; CHECK-NEXT: [[ADD:%.*]] = add i32 [[TMP0]], [[VAL]] +; CHECK-NEXT: ret i32 [[ADD]] +; +entry: + %div = udiv i32 %val, 10 + %shl = shl i32 %div, 4 + %rem = urem i32 %val, 10 + %add = add i32 %shl, %rem + ret i32 %add +} +define i32 @fold_add_sdiv_srem(i32 noundef %val) { +; CHECK-LABEL: @fold_add_sdiv_srem( +; CHECK-NEXT: entry: +; CHECK-NEXT: [[DIV:%.*]] = sdiv i32 [[VAL:%.*]], 10 +; CHECK-NEXT: [[TMP0:%.*]] = mul nsw i32 [[DIV]], 6 +; CHECK-NEXT: [[ADD:%.*]] = add i32 [[TMP0]], [[VAL]] +; CHECK-NEXT: ret i32 [[ADD]] +; +entry: + %div = sdiv i32 %val, 10 + %shl = shl i32 %div, 4 + %rem = srem i32 %val, 10 + %add = add i32 %shl, %rem + ret i32 %add +} +define i32 @fold_add_udiv_urem_to_mul(i32 noundef %val) { +; CHECK-LABEL: @fold_add_udiv_urem_to_mul( +; CHECK-NEXT: entry: +; CHECK-NEXT: [[ADD:%.*]] = mul i32 [[VAL:%.*]], 3 +; CHECK-NEXT: ret i32 [[ADD]] +; +entry: + %div = udiv i32 %val, 7 + %mul1 = mul i32 %div, 21 + %rem = urem i32 %val, 7 + %mul2 = mul i32 %rem, 3 + %add = add i32 %mul1, %mul2 + ret i32 %add +} +define i32 @fold_add_udiv_urem_to_mul_multiuse(i32 noundef %val) { +; CHECK-LABEL: @fold_add_udiv_urem_to_mul_multiuse( +; CHECK-NEXT: entry: +; CHECK-NEXT: [[REM:%.*]] = urem i32 [[VAL:%.*]], 7 +; CHECK-NEXT: call void @use(i32 [[REM]]) +; CHECK-NEXT: [[ADD:%.*]] = mul i32 [[VAL]], 3 +; CHECK-NEXT: ret i32 [[ADD]] +; +entry: + %div = udiv i32 %val, 7 + %mul1 = mul i32 %div, 21 + %rem = urem i32 %val, 7 + call void @use(i32 %rem) + %mul2 = mul i32 %rem, 3 + %add = add i32 %mul1, %mul2 + ret i32 %add +} +define i32 @fold_add_udiv_urem_commuted(i32 noundef %val) { +; CHECK-LABEL: @fold_add_udiv_urem_commuted( +; CHECK-NEXT: entry: +; CHECK-NEXT: [[DIV:%.*]] = udiv i32 [[VAL:%.*]], 10 +; CHECK-NEXT: [[TMP0:%.*]] = mul nuw i32 [[DIV]], 6 +; CHECK-NEXT: [[ADD:%.*]] = add i32 [[TMP0]], [[VAL]] +; CHECK-NEXT: ret i32 [[ADD]] +; +entry: + %div = udiv i32 %val, 10 + %shl = shl i32 %div, 4 + %rem = urem i32 %val, 10 + %add = add i32 %rem, %shl + ret i32 %add +} +define i32 @fold_add_udiv_urem_or_disjoint(i32 noundef %val) { +; CHECK-LABEL: @fold_add_udiv_urem_or_disjoint( +; CHECK-NEXT: entry: +; CHECK-NEXT: [[DIV:%.*]] = udiv i32 [[VAL:%.*]], 10 +; CHECK-NEXT: [[TMP0:%.*]] = mul nuw i32 [[DIV]], 6 +; CHECK-NEXT: [[ADD:%.*]] = add i32 [[TMP0]], [[VAL]] +; CHECK-NEXT: ret i32 [[ADD]] +; +entry: + %div = udiv i32 %val, 10 + %shl = shl i32 %div, 4 + %rem = urem i32 %val, 10 + %add = or disjoint i32 %shl, %rem + ret i32 %add +} +; Negative tests +define i32 @fold_add_udiv_urem_without_noundef(i32 %val) { +; CHECK-LABEL: @fold_add_udiv_urem_without_noundef( +; CHECK-NEXT: entry: +; CHECK-NEXT: [[DIV:%.*]] = udiv i32 [[VAL:%.*]], 10 +; CHECK-NEXT: [[SHL:%.*]] = shl i32 [[DIV]], 4 +; CHECK-NEXT: [[REM:%.*]] = urem i32 [[VAL]], 10 +; CHECK-NEXT: [[ADD:%.*]] = or disjoint i32 [[SHL]], [[REM]] +; CHECK-NEXT: ret i32 [[ADD]] +; +entry: + %div = udiv i32 %val, 10 + %shl = shl i32 %div, 4 + %rem = urem i32 %val, 10 + %add = add i32 %shl, %rem + ret i32 %add +} +define i32 @fold_add_udiv_urem_multiuse_mul(i32 noundef %val) { +; CHECK-LABEL: @fold_add_udiv_urem_multiuse_mul( +; CHECK-NEXT: entry: +; CHECK-NEXT: [[DIV:%.*]] = udiv i32 [[VAL:%.*]], 10 +; CHECK-NEXT: [[SHL:%.*]] = shl i32 [[DIV]], 4 +; CHECK-NEXT: call void @use(i32 [[SHL]]) +; CHECK-NEXT: [[REM:%.*]] = urem i32 [[VAL]], 10 +; CHECK-NEXT: [[ADD:%.*]] = or disjoint i32 [[SHL]], [[REM]] +; CHECK-NEXT: ret i32 [[ADD]] +; +entry: + %div = udiv i32 %val, 10 + %shl = shl i32 %div, 4 + call void @use(i32 %shl) + %rem = urem i32 %val, 10 + %add = add i32 %shl, %rem + ret i32 %add +} +define i32 @fold_add_udiv_srem(i32 noundef %val) { +; CHECK-LABEL: @fold_add_udiv_srem( +; CHECK-NEXT: entry: +; CHECK-NEXT: [[DIV:%.*]] = udiv i32 [[VAL:%.*]], 10 +; CHECK-NEXT: [[SHL:%.*]] = shl i32 [[DIV]], 4 +; CHECK-NEXT: [[REM:%.*]] = srem i32 [[VAL]], 10 +; CHECK-NEXT: [[ADD:%.*]] = add i32 [[SHL]], [[REM]] +; CHECK-NEXT: ret i32 [[ADD]] +; +entry: + %div = udiv i32 %val, 10 + %shl = shl i32 %div, 4 + %rem = srem i32 %val, 10 + %add = add i32 %shl, %rem + ret i32 %add +} +define i32 @fold_add_udiv_urem_non_constant(i32 noundef %val, i32 noundef %c) { +; CHECK-LABEL: @fold_add_udiv_urem_non_constant( +; CHECK-NEXT: entry: +; CHECK-NEXT: [[DIV:%.*]] = udiv i32 [[VAL:%.*]], [[C:%.*]] +; CHECK-NEXT: [[SHL:%.*]] = shl i32 [[DIV]], 4 +; CHECK-NEXT: [[REM:%.*]] = urem i32 [[VAL]], [[C]] +; CHECK-NEXT: [[ADD:%.*]] = add i32 [[SHL]], [[REM]] +; CHECK-NEXT: ret i32 [[ADD]] +; +entry: + %div = udiv i32 %val, %c + %shl = shl i32 %div, 4 + %rem = urem i32 %val, %c + %add = add i32 %shl, %rem + ret i32 %add +} diff --git a/llvm/test/Transforms/InstCombine/array.ll b/llvm/test/Transforms/InstCombine/array.ll index 236821d8ba4c0202e5254d4b273da86f6dc3c2e1..f439d4da6080c449cef0ce8b3fd428b0bdcd4f6a 100644 --- a/llvm/test/Transforms/InstCombine/array.ll +++ b/llvm/test/Transforms/InstCombine/array.ll @@ -108,3 +108,163 @@ entry: store i32 %b, ptr %gep ret void } + +define ptr @gep_inbounds_add_nsw_nonneg(ptr %ptr, i64 %a, i64 %b) { +; CHECK-LABEL: define ptr @gep_inbounds_add_nsw_nonneg( +; CHECK-SAME: ptr [[PTR:%.*]], i64 [[A:%.*]], i64 [[B:%.*]]) { +; CHECK-NEXT: [[A_NNEG:%.*]] = icmp sgt i64 [[A]], -1 +; CHECK-NEXT: call void @llvm.assume(i1 [[A_NNEG]]) +; CHECK-NEXT: [[B_NNEG:%.*]] = icmp sgt i64 [[B]], -1 +; CHECK-NEXT: call void @llvm.assume(i1 [[B_NNEG]]) +; CHECK-NEXT: [[TMP1:%.*]] = getelementptr i32, ptr [[PTR]], i64 [[A]] +; CHECK-NEXT: [[GEP:%.*]] = getelementptr i32, ptr [[TMP1]], i64 [[B]] +; CHECK-NEXT: ret ptr [[GEP]] +; + %a.nneg = icmp sgt i64 %a, -1 + call void @llvm.assume(i1 %a.nneg) + %b.nneg = icmp sgt i64 %b, -1 + call void @llvm.assume(i1 %b.nneg) + %add = add nsw i64 %a, %b + %gep = getelementptr inbounds i32, ptr %ptr, i64 %add + ret ptr %gep +} + +define ptr @gep_inbounds_add_nsw_not_nonneg1(ptr %ptr, i64 %a, i64 %b) { +; CHECK-LABEL: define ptr @gep_inbounds_add_nsw_not_nonneg1( +; CHECK-SAME: ptr [[PTR:%.*]], i64 [[A:%.*]], i64 [[B:%.*]]) { +; CHECK-NEXT: [[A_NNEG:%.*]] = icmp sgt i64 [[A]], -1 +; CHECK-NEXT: call void @llvm.assume(i1 [[A_NNEG]]) +; CHECK-NEXT: [[TMP1:%.*]] = getelementptr i32, ptr [[PTR]], i64 [[A]] +; CHECK-NEXT: [[GEP:%.*]] = getelementptr i32, ptr [[TMP1]], i64 [[B]] +; CHECK-NEXT: ret ptr [[GEP]] +; + %a.nneg = icmp sgt i64 %a, -1 + call void @llvm.assume(i1 %a.nneg) + %add = add nsw i64 %a, %b + %gep = getelementptr inbounds i32, ptr %ptr, i64 %add + ret ptr %gep +} + +define ptr @gep_inbounds_add_nsw_not_nonneg2(ptr %ptr, i64 %a, i64 %b) { +; CHECK-LABEL: define ptr @gep_inbounds_add_nsw_not_nonneg2( +; CHECK-SAME: ptr [[PTR:%.*]], i64 [[A:%.*]], i64 [[B:%.*]]) { +; CHECK-NEXT: [[B_NNEG:%.*]] = icmp sgt i64 [[B]], -1 +; CHECK-NEXT: call void @llvm.assume(i1 [[B_NNEG]]) +; CHECK-NEXT: [[TMP1:%.*]] = getelementptr i32, ptr [[PTR]], i64 [[A]] +; CHECK-NEXT: [[GEP:%.*]] = getelementptr i32, ptr [[TMP1]], i64 [[B]] +; CHECK-NEXT: ret ptr [[GEP]] +; + %b.nneg = icmp sgt i64 %b, -1 + call void @llvm.assume(i1 %b.nneg) + %add = add nsw i64 %a, %b + %gep = getelementptr inbounds i32, ptr %ptr, i64 %add + ret ptr %gep +} + +define ptr @gep_not_inbounds_add_nsw_nonneg(ptr %ptr, i64 %a, i64 %b) { +; CHECK-LABEL: define ptr @gep_not_inbounds_add_nsw_nonneg( +; CHECK-SAME: ptr [[PTR:%.*]], i64 [[A:%.*]], i64 [[B:%.*]]) { +; CHECK-NEXT: [[A_NNEG:%.*]] = icmp sgt i64 [[A]], -1 +; CHECK-NEXT: call void @llvm.assume(i1 [[A_NNEG]]) +; CHECK-NEXT: [[B_NNEG:%.*]] = icmp sgt i64 [[B]], -1 +; CHECK-NEXT: call void @llvm.assume(i1 [[B_NNEG]]) +; CHECK-NEXT: [[TMP1:%.*]] = getelementptr i32, ptr [[PTR]], i64 [[A]] +; CHECK-NEXT: [[GEP:%.*]] = getelementptr i32, ptr [[TMP1]], i64 [[B]] +; CHECK-NEXT: ret ptr [[GEP]] +; + %a.nneg = icmp sgt i64 %a, -1 + call void @llvm.assume(i1 %a.nneg) + %b.nneg = icmp sgt i64 %b, -1 + call void @llvm.assume(i1 %b.nneg) + %add = add nsw i64 %a, %b + %gep = getelementptr i32, ptr %ptr, i64 %add + ret ptr %gep +} + +define ptr @gep_inbounds_add_not_nsw_nonneg(ptr %ptr, i64 %a, i64 %b) { +; CHECK-LABEL: define ptr @gep_inbounds_add_not_nsw_nonneg( +; CHECK-SAME: ptr [[PTR:%.*]], i64 [[A:%.*]], i64 [[B:%.*]]) { +; CHECK-NEXT: [[A_NNEG:%.*]] = icmp sgt i64 [[A]], -1 +; CHECK-NEXT: call void @llvm.assume(i1 [[A_NNEG]]) +; CHECK-NEXT: [[B_NNEG:%.*]] = icmp sgt i64 [[B]], -1 +; CHECK-NEXT: call void @llvm.assume(i1 [[B_NNEG]]) +; CHECK-NEXT: [[TMP1:%.*]] = getelementptr i32, ptr [[PTR]], i64 [[A]] +; CHECK-NEXT: [[GEP:%.*]] = getelementptr i32, ptr [[TMP1]], i64 [[B]] +; CHECK-NEXT: ret ptr [[GEP]] +; + %a.nneg = icmp sgt i64 %a, -1 + call void @llvm.assume(i1 %a.nneg) + %b.nneg = icmp sgt i64 %b, -1 + call void @llvm.assume(i1 %b.nneg) + %add = add i64 %a, %b + %gep = getelementptr inbounds i32, ptr %ptr, i64 %add + ret ptr %gep +} + +define ptr @gep_inbounds_sext_add_nonneg(ptr %ptr, i32 %a) { +; CHECK-LABEL: define ptr @gep_inbounds_sext_add_nonneg( +; CHECK-SAME: ptr [[PTR:%.*]], i32 [[A:%.*]]) { +; CHECK-NEXT: [[A_NNEG:%.*]] = icmp sgt i32 [[A]], -1 +; CHECK-NEXT: call void @llvm.assume(i1 [[A_NNEG]]) +; CHECK-NEXT: [[TMP1:%.*]] = zext nneg i32 [[A]] to i64 +; CHECK-NEXT: [[TMP2:%.*]] = getelementptr i32, ptr [[PTR]], i64 [[TMP1]] +; CHECK-NEXT: [[GEP:%.*]] = getelementptr i8, ptr [[TMP2]], i64 40 +; CHECK-NEXT: ret ptr [[GEP]] +; + %a.nneg = icmp sgt i32 %a, -1 + call void @llvm.assume(i1 %a.nneg) + %add = add nsw i32 %a, 10 + %idx = sext i32 %add to i64 + %gep = getelementptr inbounds i32, ptr %ptr, i64 %idx + ret ptr %gep +} + +define ptr @gep_inbounds_sext_add_not_nonneg_1(ptr %ptr, i32 %a) { +; CHECK-LABEL: define ptr @gep_inbounds_sext_add_not_nonneg_1( +; CHECK-SAME: ptr [[PTR:%.*]], i32 [[A:%.*]]) { +; CHECK-NEXT: [[A_NNEG:%.*]] = icmp sgt i32 [[A]], -1 +; CHECK-NEXT: call void @llvm.assume(i1 [[A_NNEG]]) +; CHECK-NEXT: [[TMP1:%.*]] = zext nneg i32 [[A]] to i64 +; CHECK-NEXT: [[TMP2:%.*]] = getelementptr i32, ptr [[PTR]], i64 [[TMP1]] +; CHECK-NEXT: [[GEP:%.*]] = getelementptr i8, ptr [[TMP2]], i64 -40 +; CHECK-NEXT: ret ptr [[GEP]] +; + %a.nneg = icmp sgt i32 %a, -1 + call void @llvm.assume(i1 %a.nneg) + %add = add nsw i32 %a, -10 + %idx = sext i32 %add to i64 + %gep = getelementptr inbounds i32, ptr %ptr, i64 %idx + ret ptr %gep +} + +define ptr @gep_inbounds_sext_add_not_nonneg_2(ptr %ptr, i32 %a) { +; CHECK-LABEL: define ptr @gep_inbounds_sext_add_not_nonneg_2( +; CHECK-SAME: ptr [[PTR:%.*]], i32 [[A:%.*]]) { +; CHECK-NEXT: [[TMP1:%.*]] = sext i32 [[A]] to i64 +; CHECK-NEXT: [[TMP2:%.*]] = getelementptr i32, ptr [[PTR]], i64 [[TMP1]] +; CHECK-NEXT: [[GEP:%.*]] = getelementptr i8, ptr [[TMP2]], i64 40 +; CHECK-NEXT: ret ptr [[GEP]] +; + %add = add nsw i32 %a, 10 + %idx = sext i32 %add to i64 + %gep = getelementptr inbounds i32, ptr %ptr, i64 %idx + ret ptr %gep +} + +define ptr @gep_not_inbounds_sext_add_nonneg(ptr %ptr, i32 %a) { +; CHECK-LABEL: define ptr @gep_not_inbounds_sext_add_nonneg( +; CHECK-SAME: ptr [[PTR:%.*]], i32 [[A:%.*]]) { +; CHECK-NEXT: [[A_NNEG:%.*]] = icmp sgt i32 [[A]], -1 +; CHECK-NEXT: call void @llvm.assume(i1 [[A_NNEG]]) +; CHECK-NEXT: [[TMP1:%.*]] = zext nneg i32 [[A]] to i64 +; CHECK-NEXT: [[TMP2:%.*]] = getelementptr i32, ptr [[PTR]], i64 [[TMP1]] +; CHECK-NEXT: [[GEP:%.*]] = getelementptr i8, ptr [[TMP2]], i64 40 +; CHECK-NEXT: ret ptr [[GEP]] +; + %a.nneg = icmp sgt i32 %a, -1 + call void @llvm.assume(i1 %a.nneg) + %add = add nsw i32 %a, 10 + %idx = sext i32 %add to i64 + %gep = getelementptr i32, ptr %ptr, i64 %idx + ret ptr %gep +} diff --git a/llvm/test/Transforms/InstCombine/bit_ceil.ll b/llvm/test/Transforms/InstCombine/bit_ceil.ll index 52e70c78ba54289f212a04509449c6f3400958f0..16631afa4878da6b5a47e93c7255998825be38da 100644 --- a/llvm/test/Transforms/InstCombine/bit_ceil.ll +++ b/llvm/test/Transforms/InstCombine/bit_ceil.ll @@ -5,7 +5,7 @@ define i32 @bit_ceil_32(i32 %x) { ; CHECK-LABEL: @bit_ceil_32( ; CHECK-NEXT: [[DEC:%.*]] = add i32 [[X:%.*]], -1 -; CHECK-NEXT: [[CTLZ:%.*]] = tail call i32 @llvm.ctlz.i32(i32 [[DEC]], i1 false), !range [[RNG0:![0-9]+]] +; CHECK-NEXT: [[CTLZ:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[DEC]], i1 false) ; CHECK-NEXT: [[TMP1:%.*]] = sub nsw i32 0, [[CTLZ]] ; CHECK-NEXT: [[TMP2:%.*]] = and i32 [[TMP1]], 31 ; CHECK-NEXT: [[SEL:%.*]] = shl nuw i32 1, [[TMP2]] @@ -24,7 +24,7 @@ define i32 @bit_ceil_32(i32 %x) { define i64 @bit_ceil_64(i64 %x) { ; CHECK-LABEL: @bit_ceil_64( ; CHECK-NEXT: [[DEC:%.*]] = add i64 [[X:%.*]], -1 -; CHECK-NEXT: [[CTLZ:%.*]] = tail call i64 @llvm.ctlz.i64(i64 [[DEC]], i1 false), !range [[RNG1:![0-9]+]] +; CHECK-NEXT: [[CTLZ:%.*]] = tail call range(i64 0, 65) i64 @llvm.ctlz.i64(i64 [[DEC]], i1 false) ; CHECK-NEXT: [[TMP1:%.*]] = sub nsw i64 0, [[CTLZ]] ; CHECK-NEXT: [[TMP2:%.*]] = and i64 [[TMP1]], 63 ; CHECK-NEXT: [[SEL:%.*]] = shl nuw i64 1, [[TMP2]] @@ -44,7 +44,7 @@ define i32 @bit_ceil_32_minus_1(i32 %x) { ; CHECK-LABEL: @bit_ceil_32_minus_1( ; CHECK-NEXT: entry: ; CHECK-NEXT: [[SUB:%.*]] = add i32 [[X:%.*]], -2 -; CHECK-NEXT: [[CTLZ:%.*]] = tail call i32 @llvm.ctlz.i32(i32 [[SUB]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[CTLZ:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[SUB]], i1 false) ; CHECK-NEXT: [[TMP0:%.*]] = sub nsw i32 0, [[CTLZ]] ; CHECK-NEXT: [[TMP1:%.*]] = and i32 [[TMP0]], 31 ; CHECK-NEXT: [[SEL:%.*]] = shl nuw i32 1, [[TMP1]] @@ -64,7 +64,7 @@ entry: ; std::bit_ceil(x + 1) define i32 @bit_ceil_32_plus_1(i32 %x) { ; CHECK-LABEL: @bit_ceil_32_plus_1( -; CHECK-NEXT: [[CTLZ:%.*]] = tail call i32 @llvm.ctlz.i32(i32 [[X:%.*]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[CTLZ:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[X:%.*]], i1 false) ; CHECK-NEXT: [[TMP1:%.*]] = sub nsw i32 0, [[CTLZ]] ; CHECK-NEXT: [[TMP2:%.*]] = and i32 [[TMP1]], 31 ; CHECK-NEXT: [[SEL:%.*]] = shl nuw i32 1, [[TMP2]] @@ -84,7 +84,7 @@ define i32 @bit_ceil_plus_2(i32 %x) { ; CHECK-LABEL: @bit_ceil_plus_2( ; CHECK-NEXT: entry: ; CHECK-NEXT: [[SUB:%.*]] = add i32 [[X:%.*]], 1 -; CHECK-NEXT: [[CTLZ:%.*]] = tail call i32 @llvm.ctlz.i32(i32 [[SUB]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[CTLZ:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[SUB]], i1 false) ; CHECK-NEXT: [[TMP0:%.*]] = sub nsw i32 0, [[CTLZ]] ; CHECK-NEXT: [[TMP1:%.*]] = and i32 [[TMP0]], 31 ; CHECK-NEXT: [[SEL:%.*]] = shl nuw i32 1, [[TMP1]] @@ -105,7 +105,7 @@ define i32 @bit_ceil_32_neg(i32 %x) { ; CHECK-LABEL: @bit_ceil_32_neg( ; CHECK-NEXT: entry: ; CHECK-NEXT: [[SUB:%.*]] = xor i32 [[X:%.*]], -1 -; CHECK-NEXT: [[CTLZ:%.*]] = tail call i32 @llvm.ctlz.i32(i32 [[SUB]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[CTLZ:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[SUB]], i1 false) ; CHECK-NEXT: [[TMP0:%.*]] = sub nsw i32 0, [[CTLZ]] ; CHECK-NEXT: [[TMP1:%.*]] = and i32 [[TMP0]], 31 ; CHECK-NEXT: [[SEL:%.*]] = shl nuw i32 1, [[TMP1]] @@ -127,7 +127,7 @@ define i32 @bit_ceil_not(i32 %x) { ; CHECK-LABEL: @bit_ceil_not( ; CHECK-NEXT: entry: ; CHECK-NEXT: [[SUB:%.*]] = sub i32 -2, [[X:%.*]] -; CHECK-NEXT: [[CTLZ:%.*]] = tail call i32 @llvm.ctlz.i32(i32 [[SUB]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[CTLZ:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[SUB]], i1 false) ; CHECK-NEXT: [[TMP0:%.*]] = sub nsw i32 0, [[CTLZ]] ; CHECK-NEXT: [[TMP1:%.*]] = and i32 [[TMP0]], 31 ; CHECK-NEXT: [[SEL:%.*]] = shl nuw i32 1, [[TMP1]] @@ -147,7 +147,7 @@ entry: define i32 @bit_ceil_commuted_operands(i32 %x) { ; CHECK-LABEL: @bit_ceil_commuted_operands( ; CHECK-NEXT: [[DEC:%.*]] = add i32 [[X:%.*]], -1 -; CHECK-NEXT: [[CTLZ:%.*]] = tail call i32 @llvm.ctlz.i32(i32 [[DEC]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[CTLZ:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[DEC]], i1 false) ; CHECK-NEXT: [[SUB:%.*]] = sub nuw nsw i32 32, [[CTLZ]] ; CHECK-NEXT: [[SHL:%.*]] = shl nuw i32 1, [[SUB]] ; CHECK-NEXT: ret i32 [[SHL]] @@ -165,7 +165,7 @@ define i32 @bit_ceil_commuted_operands(i32 %x) { define i32 @bit_ceil_wrong_select_constant(i32 %x) { ; CHECK-LABEL: @bit_ceil_wrong_select_constant( ; CHECK-NEXT: [[DEC:%.*]] = add i32 [[X:%.*]], -1 -; CHECK-NEXT: [[CTLZ:%.*]] = tail call i32 @llvm.ctlz.i32(i32 [[DEC]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[CTLZ:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[DEC]], i1 false) ; CHECK-NEXT: [[SUB:%.*]] = sub nuw nsw i32 32, [[CTLZ]] ; CHECK-NEXT: [[SHL:%.*]] = shl nuw i32 1, [[SUB]] ; CHECK-NEXT: [[UGT_INV:%.*]] = icmp ult i32 [[X]], 2 @@ -185,7 +185,7 @@ define i32 @bit_ceil_wrong_select_constant(i32 %x) { define i32 @bit_ceil_32_wrong_cond(i32 %x) { ; CHECK-LABEL: @bit_ceil_32_wrong_cond( ; CHECK-NEXT: [[DEC:%.*]] = add i32 [[X:%.*]], -1 -; CHECK-NEXT: [[CTLZ:%.*]] = tail call i32 @llvm.ctlz.i32(i32 [[DEC]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[CTLZ:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[DEC]], i1 false) ; CHECK-NEXT: [[SUB:%.*]] = sub nuw nsw i32 32, [[CTLZ]] ; CHECK-NEXT: [[SHL:%.*]] = shl nuw i32 1, [[SUB]] ; CHECK-NEXT: [[UGT:%.*]] = icmp ugt i32 [[X]], 2 @@ -205,7 +205,7 @@ define i32 @bit_ceil_32_wrong_cond(i32 %x) { define i32 @bit_ceil_wrong_sub_constant(i32 %x) { ; CHECK-LABEL: @bit_ceil_wrong_sub_constant( ; CHECK-NEXT: [[DEC:%.*]] = add i32 [[X:%.*]], -1 -; CHECK-NEXT: [[CTLZ:%.*]] = tail call i32 @llvm.ctlz.i32(i32 [[DEC]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[CTLZ:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[DEC]], i1 false) ; CHECK-NEXT: [[SUB:%.*]] = sub nuw nsw i32 33, [[CTLZ]] ; CHECK-NEXT: [[SHL:%.*]] = shl nuw i32 1, [[SUB]] ; CHECK-NEXT: [[UGT:%.*]] = icmp ugt i32 [[X]], 1 @@ -225,7 +225,7 @@ define i32 @bit_ceil_wrong_sub_constant(i32 %x) { define i32 @bit_ceil_32_shl_used_twice(i32 %x, ptr %p) { ; CHECK-LABEL: @bit_ceil_32_shl_used_twice( ; CHECK-NEXT: [[DEC:%.*]] = add i32 [[X:%.*]], -1 -; CHECK-NEXT: [[CTLZ:%.*]] = tail call i32 @llvm.ctlz.i32(i32 [[DEC]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[CTLZ:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[DEC]], i1 false) ; CHECK-NEXT: [[SUB:%.*]] = sub nuw nsw i32 32, [[CTLZ]] ; CHECK-NEXT: [[SHL:%.*]] = shl nuw i32 1, [[SUB]] ; CHECK-NEXT: [[UGT:%.*]] = icmp ugt i32 [[X]], 1 @@ -247,7 +247,7 @@ define i32 @bit_ceil_32_shl_used_twice(i32 %x, ptr %p) { define i32 @bit_ceil_32_sub_used_twice(i32 %x, ptr %p) { ; CHECK-LABEL: @bit_ceil_32_sub_used_twice( ; CHECK-NEXT: [[DEC:%.*]] = add i32 [[X:%.*]], -1 -; CHECK-NEXT: [[CTLZ:%.*]] = tail call i32 @llvm.ctlz.i32(i32 [[DEC]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[CTLZ:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[DEC]], i1 false) ; CHECK-NEXT: [[SUB:%.*]] = sub nuw nsw i32 32, [[CTLZ]] ; CHECK-NEXT: [[SHL:%.*]] = shl nuw i32 1, [[SUB]] ; CHECK-NEXT: [[UGT:%.*]] = icmp ugt i32 [[X]], 1 @@ -269,7 +269,7 @@ define i32 @bit_ceil_32_sub_used_twice(i32 %x, ptr %p) { define <4 x i32> @bit_ceil_v4i32(<4 x i32> %x) { ; CHECK-LABEL: @bit_ceil_v4i32( ; CHECK-NEXT: [[DEC:%.*]] = add <4 x i32> [[X:%.*]], -; CHECK-NEXT: [[CTLZ:%.*]] = tail call <4 x i32> @llvm.ctlz.v4i32(<4 x i32> [[DEC]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[CTLZ:%.*]] = tail call range(i32 0, 33) <4 x i32> @llvm.ctlz.v4i32(<4 x i32> [[DEC]], i1 false) ; CHECK-NEXT: [[TMP1:%.*]] = sub nsw <4 x i32> zeroinitializer, [[CTLZ]] ; CHECK-NEXT: [[TMP2:%.*]] = and <4 x i32> [[TMP1]], ; CHECK-NEXT: [[SEL:%.*]] = shl nuw <4 x i32> , [[TMP2]] diff --git a/llvm/test/Transforms/InstCombine/bit_floor.ll b/llvm/test/Transforms/InstCombine/bit_floor.ll index 9daa8eee8969c0edca518db1fda4b68f069abd2a..bd8aabf4431c0a367cbf3e5c8ecb2c5f620f5105 100644 --- a/llvm/test/Transforms/InstCombine/bit_floor.ll +++ b/llvm/test/Transforms/InstCombine/bit_floor.ll @@ -5,7 +5,7 @@ define i32 @bit_floor_32(i32 %x) { ; CHECK-LABEL: @bit_floor_32( ; CHECK-NEXT: [[EQ0:%.*]] = icmp eq i32 [[X:%.*]], 0 ; CHECK-NEXT: [[LSHR:%.*]] = lshr i32 [[X]], 1 -; CHECK-NEXT: [[CTLZ:%.*]] = tail call i32 @llvm.ctlz.i32(i32 [[LSHR]], i1 false), !range [[RNG0:![0-9]+]] +; CHECK-NEXT: [[CTLZ:%.*]] = tail call range(i32 1, 33) i32 @llvm.ctlz.i32(i32 [[LSHR]], i1 false) ; CHECK-NEXT: [[SUB:%.*]] = sub nuw nsw i32 32, [[CTLZ]] ; CHECK-NEXT: [[SHL:%.*]] = shl nuw i32 1, [[SUB]] ; CHECK-NEXT: [[SEL:%.*]] = select i1 [[EQ0]], i32 0, i32 [[SHL]] @@ -24,7 +24,7 @@ define i64 @bit_floor_64(i64 %x) { ; CHECK-LABEL: @bit_floor_64( ; CHECK-NEXT: [[EQ0:%.*]] = icmp eq i64 [[X:%.*]], 0 ; CHECK-NEXT: [[LSHR:%.*]] = lshr i64 [[X]], 1 -; CHECK-NEXT: [[CTLZ:%.*]] = tail call i64 @llvm.ctlz.i64(i64 [[LSHR]], i1 false), !range [[RNG1:![0-9]+]] +; CHECK-NEXT: [[CTLZ:%.*]] = tail call range(i64 1, 65) i64 @llvm.ctlz.i64(i64 [[LSHR]], i1 false) ; CHECK-NEXT: [[SUB:%.*]] = sub nuw nsw i64 64, [[CTLZ]] ; CHECK-NEXT: [[SHL:%.*]] = shl nuw i64 1, [[SUB]] ; CHECK-NEXT: [[SEL:%.*]] = select i1 [[EQ0]], i64 0, i64 [[SHL]] @@ -44,7 +44,7 @@ define i32 @bit_floor_commuted_operands(i32 %x) { ; CHECK-LABEL: @bit_floor_commuted_operands( ; CHECK-NEXT: [[NE0_NOT:%.*]] = icmp eq i32 [[X:%.*]], 0 ; CHECK-NEXT: [[LSHR:%.*]] = lshr i32 [[X]], 1 -; CHECK-NEXT: [[CTLZ:%.*]] = tail call i32 @llvm.ctlz.i32(i32 [[LSHR]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[CTLZ:%.*]] = tail call range(i32 1, 33) i32 @llvm.ctlz.i32(i32 [[LSHR]], i1 false) ; CHECK-NEXT: [[SUB:%.*]] = sub nuw nsw i32 32, [[CTLZ]] ; CHECK-NEXT: [[SHL:%.*]] = shl nuw i32 1, [[SUB]] ; CHECK-NEXT: [[SEL:%.*]] = select i1 [[NE0_NOT]], i32 0, i32 [[SHL]] @@ -64,7 +64,7 @@ define i32 @bit_floor_lshr_used_twice(i32 %x, ptr %p) { ; CHECK-LABEL: @bit_floor_lshr_used_twice( ; CHECK-NEXT: [[EQ0:%.*]] = icmp eq i32 [[X:%.*]], 0 ; CHECK-NEXT: [[LSHR:%.*]] = lshr i32 [[X]], 1 -; CHECK-NEXT: [[CTLZ:%.*]] = tail call i32 @llvm.ctlz.i32(i32 [[LSHR]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[CTLZ:%.*]] = tail call range(i32 1, 33) i32 @llvm.ctlz.i32(i32 [[LSHR]], i1 false) ; CHECK-NEXT: [[SUB:%.*]] = sub nuw nsw i32 32, [[CTLZ]] ; CHECK-NEXT: [[SHL:%.*]] = shl nuw i32 1, [[SUB]] ; CHECK-NEXT: [[SEL:%.*]] = select i1 [[EQ0]], i32 0, i32 [[SHL]] @@ -86,7 +86,7 @@ define i32 @bit_floor_ctlz_used_twice(i32 %x, ptr %p) { ; CHECK-LABEL: @bit_floor_ctlz_used_twice( ; CHECK-NEXT: [[EQ0:%.*]] = icmp eq i32 [[X:%.*]], 0 ; CHECK-NEXT: [[LSHR:%.*]] = lshr i32 [[X]], 1 -; CHECK-NEXT: [[CTLZ:%.*]] = tail call i32 @llvm.ctlz.i32(i32 [[LSHR]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[CTLZ:%.*]] = tail call range(i32 1, 33) i32 @llvm.ctlz.i32(i32 [[LSHR]], i1 false) ; CHECK-NEXT: [[SUB:%.*]] = sub nuw nsw i32 32, [[CTLZ]] ; CHECK-NEXT: [[SHL:%.*]] = shl nuw i32 1, [[SUB]] ; CHECK-NEXT: [[SEL:%.*]] = select i1 [[EQ0]], i32 0, i32 [[SHL]] @@ -108,7 +108,7 @@ define i32 @bit_floor_sub_used_twice(i32 %x, ptr %p) { ; CHECK-LABEL: @bit_floor_sub_used_twice( ; CHECK-NEXT: [[EQ0:%.*]] = icmp eq i32 [[X:%.*]], 0 ; CHECK-NEXT: [[LSHR:%.*]] = lshr i32 [[X]], 1 -; CHECK-NEXT: [[CTLZ:%.*]] = tail call i32 @llvm.ctlz.i32(i32 [[LSHR]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[CTLZ:%.*]] = tail call range(i32 1, 33) i32 @llvm.ctlz.i32(i32 [[LSHR]], i1 false) ; CHECK-NEXT: [[SUB:%.*]] = sub nuw nsw i32 32, [[CTLZ]] ; CHECK-NEXT: [[SHL:%.*]] = shl nuw i32 1, [[SUB]] ; CHECK-NEXT: [[SEL:%.*]] = select i1 [[EQ0]], i32 0, i32 [[SHL]] @@ -130,7 +130,7 @@ define i32 @bit_floor_shl_used_twice(i32 %x, ptr %p) { ; CHECK-LABEL: @bit_floor_shl_used_twice( ; CHECK-NEXT: [[EQ0:%.*]] = icmp eq i32 [[X:%.*]], 0 ; CHECK-NEXT: [[LSHR:%.*]] = lshr i32 [[X]], 1 -; CHECK-NEXT: [[CTLZ:%.*]] = tail call i32 @llvm.ctlz.i32(i32 [[LSHR]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[CTLZ:%.*]] = tail call range(i32 1, 33) i32 @llvm.ctlz.i32(i32 [[LSHR]], i1 false) ; CHECK-NEXT: [[SUB:%.*]] = sub nuw nsw i32 32, [[CTLZ]] ; CHECK-NEXT: [[SHL:%.*]] = shl nuw i32 1, [[SUB]] ; CHECK-NEXT: [[SEL:%.*]] = select i1 [[EQ0]], i32 0, i32 [[SHL]] @@ -152,7 +152,7 @@ define <4 x i32> @bit_floor_v4i32(<4 x i32> %x) { ; CHECK-LABEL: @bit_floor_v4i32( ; CHECK-NEXT: [[EQ0:%.*]] = icmp eq <4 x i32> [[X:%.*]], zeroinitializer ; CHECK-NEXT: [[LSHR:%.*]] = lshr <4 x i32> [[X]], -; CHECK-NEXT: [[CTLZ:%.*]] = tail call <4 x i32> @llvm.ctlz.v4i32(<4 x i32> [[LSHR]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[CTLZ:%.*]] = tail call range(i32 1, 33) <4 x i32> @llvm.ctlz.v4i32(<4 x i32> [[LSHR]], i1 false) ; CHECK-NEXT: [[SUB:%.*]] = sub nuw nsw <4 x i32> , [[CTLZ]] ; CHECK-NEXT: [[SHL:%.*]] = shl nuw <4 x i32> , [[SUB]] ; CHECK-NEXT: [[SEL:%.*]] = select <4 x i1> [[EQ0]], <4 x i32> zeroinitializer, <4 x i32> [[SHL]] diff --git a/llvm/test/Transforms/InstCombine/cmp-intrinsic.ll b/llvm/test/Transforms/InstCombine/cmp-intrinsic.ll index 66cbb2636cbc2bc1d418076d370203dc3eaacaed..9a9f359fa80b4a2a6c32f0174e80dfe99f144290 100644 --- a/llvm/test/Transforms/InstCombine/cmp-intrinsic.ll +++ b/llvm/test/Transforms/InstCombine/cmp-intrinsic.ll @@ -125,7 +125,7 @@ define <2 x i1> @ctlz_ne_other_v2i32(<2 x i32> %a) { define i1 @ctlz_eq_other_i32_multiuse(i32 %x, ptr %p) { ; CHECK-LABEL: @ctlz_eq_other_i32_multiuse( -; CHECK-NEXT: [[LZ:%.*]] = tail call i32 @llvm.ctlz.i32(i32 [[X:%.*]], i1 false), !range [[RNG0:![0-9]+]] +; CHECK-NEXT: [[LZ:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[X:%.*]], i1 false) ; CHECK-NEXT: store i32 [[LZ]], ptr [[P:%.*]], align 4 ; CHECK-NEXT: [[CMP:%.*]] = icmp eq i32 [[LZ]], 24 ; CHECK-NEXT: ret i1 [[CMP]] @@ -178,7 +178,7 @@ define i1 @ctlz_ugt_other_i32(i32 %x) { define i1 @ctlz_ugt_other_multiuse_i32(i32 %x, ptr %p) { ; CHECK-LABEL: @ctlz_ugt_other_multiuse_i32( -; CHECK-NEXT: [[LZ:%.*]] = tail call i32 @llvm.ctlz.i32(i32 [[X:%.*]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[LZ:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[X:%.*]], i1 false) ; CHECK-NEXT: store i32 [[LZ]], ptr [[P:%.*]], align 4 ; CHECK-NEXT: [[CMP:%.*]] = icmp ult i32 [[X]], 32768 ; CHECK-NEXT: ret i1 [[CMP]] @@ -221,7 +221,7 @@ define <2 x i1> @ctlz_ult_other_v2i32(<2 x i32> %x) { define <2 x i1> @ctlz_ult_other_multiuse_v2i32(<2 x i32> %x, ptr %p) { ; CHECK-LABEL: @ctlz_ult_other_multiuse_v2i32( -; CHECK-NEXT: [[LZ:%.*]] = tail call <2 x i32> @llvm.ctlz.v2i32(<2 x i32> [[X:%.*]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[LZ:%.*]] = tail call range(i32 0, 33) <2 x i32> @llvm.ctlz.v2i32(<2 x i32> [[X:%.*]], i1 false) ; CHECK-NEXT: store <2 x i32> [[LZ]], ptr [[P:%.*]], align 8 ; CHECK-NEXT: [[CMP:%.*]] = icmp ugt <2 x i32> [[X]], ; CHECK-NEXT: ret <2 x i1> [[CMP]] @@ -338,7 +338,7 @@ define <2 x i1> @cttz_ne_other_v2i32(<2 x i32> %a) { define i1 @cttz_eq_other_i33_multiuse(i33 %x, ptr %p) { ; CHECK-LABEL: @cttz_eq_other_i33_multiuse( -; CHECK-NEXT: [[TZ:%.*]] = tail call i33 @llvm.cttz.i33(i33 [[X:%.*]], i1 false), !range [[RNG1:![0-9]+]] +; CHECK-NEXT: [[TZ:%.*]] = tail call range(i33 0, 34) i33 @llvm.cttz.i33(i33 [[X:%.*]], i1 false) ; CHECK-NEXT: store i33 [[TZ]], ptr [[P:%.*]], align 4 ; CHECK-NEXT: [[CMP:%.*]] = icmp eq i33 [[TZ]], 4 ; CHECK-NEXT: ret i1 [[CMP]] @@ -384,7 +384,7 @@ define i1 @cttz_ugt_other_i33(i33 %x) { define i1 @cttz_ugt_other_multiuse_i33(i33 %x, ptr %p) { ; CHECK-LABEL: @cttz_ugt_other_multiuse_i33( -; CHECK-NEXT: [[TZ:%.*]] = tail call i33 @llvm.cttz.i33(i33 [[X:%.*]], i1 false), !range [[RNG1]] +; CHECK-NEXT: [[TZ:%.*]] = tail call range(i33 0, 34) i33 @llvm.cttz.i33(i33 [[X:%.*]], i1 false) ; CHECK-NEXT: store i33 [[TZ]], ptr [[P:%.*]], align 4 ; CHECK-NEXT: [[CMP:%.*]] = icmp ugt i33 [[TZ]], 16 ; CHECK-NEXT: ret i1 [[CMP]] @@ -428,7 +428,7 @@ define <2 x i1> @cttz_ult_other_v2i32(<2 x i32> %x) { define <2 x i1> @cttz_ult_other_multiuse_v2i32(<2 x i32> %x, ptr %p) { ; CHECK-LABEL: @cttz_ult_other_multiuse_v2i32( -; CHECK-NEXT: [[TZ:%.*]] = tail call <2 x i32> @llvm.cttz.v2i32(<2 x i32> [[X:%.*]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[TZ:%.*]] = tail call range(i32 0, 33) <2 x i32> @llvm.cttz.v2i32(<2 x i32> [[X:%.*]], i1 false) ; CHECK-NEXT: store <2 x i32> [[TZ]], ptr [[P:%.*]], align 8 ; CHECK-NEXT: [[CMP:%.*]] = icmp ult <2 x i32> [[TZ]], ; CHECK-NEXT: ret <2 x i1> [[CMP]] @@ -502,7 +502,7 @@ define <2 x i1> @ctpop_ne_bitwidth_v2i32(<2 x i32> %x) { define i1 @ctpop_ugt_bitwidth_minus_one_i8(i8 %x, ptr %p) { ; CHECK-LABEL: @ctpop_ugt_bitwidth_minus_one_i8( -; CHECK-NEXT: [[POP:%.*]] = tail call i8 @llvm.ctpop.i8(i8 [[X:%.*]]), !range [[RNG2:![0-9]+]] +; CHECK-NEXT: [[POP:%.*]] = tail call range(i8 0, 9) i8 @llvm.ctpop.i8(i8 [[X:%.*]]) ; CHECK-NEXT: store i8 [[POP]], ptr [[P:%.*]], align 1 ; CHECK-NEXT: [[CMP:%.*]] = icmp eq i8 [[X]], -1 ; CHECK-NEXT: ret i1 [[CMP]] @@ -563,7 +563,7 @@ define i1 @trunc_cttz_ult_other_i33_i6(i33 %x) { define i1 @trunc_cttz_ult_other_i33_i5(i33 %x) { ; CHECK-LABEL: @trunc_cttz_ult_other_i33_i5( -; CHECK-NEXT: [[TZ:%.*]] = tail call i33 @llvm.cttz.i33(i33 [[X:%.*]], i1 true), !range [[RNG1]] +; CHECK-NEXT: [[TZ:%.*]] = tail call range(i33 0, 34) i33 @llvm.cttz.i33(i33 [[X:%.*]], i1 true) ; CHECK-NEXT: [[TRUNC:%.*]] = trunc i33 [[TZ]] to i5 ; CHECK-NEXT: [[CMP:%.*]] = icmp ult i5 [[TRUNC]], 7 ; CHECK-NEXT: ret i1 [[CMP]] @@ -590,7 +590,7 @@ define i1 @trunc_cttz_true_ult_other_i32_i5(i32 %x) { define i1 @trunc_cttz_false_ult_other_i32_i5(i32 %x) { ; CHECK-LABEL: @trunc_cttz_false_ult_other_i32_i5( -; CHECK-NEXT: [[TZ:%.*]] = tail call i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[TZ:%.*]] = tail call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 false) ; CHECK-NEXT: [[TRUNC:%.*]] = trunc i32 [[TZ]] to i5 ; CHECK-NEXT: [[CMP:%.*]] = icmp ult i5 [[TRUNC]], 7 ; CHECK-NEXT: ret i1 [[CMP]] @@ -617,7 +617,7 @@ define i1 @trunc_cttz_false_ult_other_i32_i6(i32 %x) { define i1 @trunc_cttz_false_ult_other_i32_i6_extra_use(i32 %x) { ; CHECK-LABEL: @trunc_cttz_false_ult_other_i32_i6_extra_use( -; CHECK-NEXT: [[TZ:%.*]] = tail call i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[TZ:%.*]] = tail call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 false) ; CHECK-NEXT: [[TRUNC:%.*]] = trunc nuw i32 [[TZ]] to i6 ; CHECK-NEXT: call void @use6(i6 [[TRUNC]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ult i6 [[TRUNC]], 7 @@ -667,7 +667,7 @@ define i1 @trunc_ctlz_ugt_other_i33_i6(i33 %x) { define i1 @trunc_ctlz_ugt_other_i33_i5(i33 %x) { ; CHECK-LABEL: @trunc_ctlz_ugt_other_i33_i5( -; CHECK-NEXT: [[LZ:%.*]] = tail call i33 @llvm.ctlz.i33(i33 [[X:%.*]], i1 true), !range [[RNG1]] +; CHECK-NEXT: [[LZ:%.*]] = tail call range(i33 0, 34) i33 @llvm.ctlz.i33(i33 [[X:%.*]], i1 true) ; CHECK-NEXT: [[TRUNC:%.*]] = trunc i33 [[LZ]] to i5 ; CHECK-NEXT: [[CMP:%.*]] = icmp ugt i5 [[TRUNC]], 4 ; CHECK-NEXT: ret i1 [[CMP]] @@ -693,7 +693,7 @@ define i1 @trunc_ctlz_true_ugt_other_i32_i5(i32 %x) { define i1 @trunc_ctlz_false_ugt_other_i32_i5(i32 %x) { ; CHECK-LABEL: @trunc_ctlz_false_ugt_other_i32_i5( -; CHECK-NEXT: [[LZ:%.*]] = tail call i32 @llvm.ctlz.i32(i32 [[X:%.*]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[LZ:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[X:%.*]], i1 false) ; CHECK-NEXT: [[TRUNC:%.*]] = trunc i32 [[LZ]] to i5 ; CHECK-NEXT: [[CMP:%.*]] = icmp ugt i5 [[TRUNC]], 4 ; CHECK-NEXT: ret i1 [[CMP]] @@ -719,7 +719,7 @@ define i1 @trunc_ctlz_false_ugt_other_i32_i6(i32 %x) { define i1 @trunc_ctlz_false_ugt_other_i32_i6_extra_use(i32 %x) { ; CHECK-LABEL: @trunc_ctlz_false_ugt_other_i32_i6_extra_use( -; CHECK-NEXT: [[LZ:%.*]] = tail call i32 @llvm.ctlz.i32(i32 [[X:%.*]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[LZ:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[X:%.*]], i1 false) ; CHECK-NEXT: [[TRUNC:%.*]] = trunc nuw i32 [[LZ]] to i6 ; CHECK-NEXT: call void @use6(i6 [[TRUNC]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ugt i6 [[TRUNC]], 4 @@ -758,7 +758,7 @@ define i1 @trunc_ctpop_eq_bitwidth_i8(i8 %x) { define i1 @trunc_negative_destbits_not_enough(i33 %x) { ; CHECK-LABEL: @trunc_negative_destbits_not_enough( -; CHECK-NEXT: [[TZ:%.*]] = tail call i33 @llvm.cttz.i33(i33 [[X:%.*]], i1 false), !range [[RNG1]] +; CHECK-NEXT: [[TZ:%.*]] = tail call range(i33 0, 34) i33 @llvm.cttz.i33(i33 [[X:%.*]], i1 false) ; CHECK-NEXT: [[TRUNC:%.*]] = trunc i33 [[TZ]] to i4 ; CHECK-NEXT: [[CMP:%.*]] = icmp ult i4 [[TRUNC]], 7 ; CHECK-NEXT: ret i1 [[CMP]] diff --git a/llvm/test/Transforms/InstCombine/ctlz-cttz-bitreverse.ll b/llvm/test/Transforms/InstCombine/ctlz-cttz-bitreverse.ll index a5189f47650569778cfdd8b3a7ebc9ea0658a9b3..ec822f4b8fb3a5d100abbf041ff79103bd928bfa 100644 --- a/llvm/test/Transforms/InstCombine/ctlz-cttz-bitreverse.ll +++ b/llvm/test/Transforms/InstCombine/ctlz-cttz-bitreverse.ll @@ -3,7 +3,7 @@ define i32 @ctlz_true_bitreverse(i32 %x) { ; CHECK-LABEL: @ctlz_true_bitreverse( -; CHECK-NEXT: [[B:%.*]] = call i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 true), !range [[RNG0:![0-9]+]] +; CHECK-NEXT: [[B:%.*]] = call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 true) ; CHECK-NEXT: ret i32 [[B]] ; %a = tail call i32 @llvm.bitreverse.i32(i32 %x) @@ -13,7 +13,7 @@ define i32 @ctlz_true_bitreverse(i32 %x) { define <2 x i64> @ctlz_true_bitreverse_vec(<2 x i64> %x) { ; CHECK-LABEL: @ctlz_true_bitreverse_vec( -; CHECK-NEXT: [[B:%.*]] = call <2 x i64> @llvm.cttz.v2i64(<2 x i64> [[X:%.*]], i1 true), !range [[RNG1:![0-9]+]] +; CHECK-NEXT: [[B:%.*]] = call range(i64 0, 65) <2 x i64> @llvm.cttz.v2i64(<2 x i64> [[X:%.*]], i1 true) ; CHECK-NEXT: ret <2 x i64> [[B]] ; %a = tail call <2 x i64> @llvm.bitreverse.v2i64(<2 x i64> %x) @@ -23,7 +23,7 @@ define <2 x i64> @ctlz_true_bitreverse_vec(<2 x i64> %x) { define i32 @ctlz_false_bitreverse(i32 %x) { ; CHECK-LABEL: @ctlz_false_bitreverse( -; CHECK-NEXT: [[B:%.*]] = call i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[B:%.*]] = call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 false) ; CHECK-NEXT: ret i32 [[B]] ; %a = tail call i32 @llvm.bitreverse.i32(i32 %x) @@ -33,7 +33,7 @@ define i32 @ctlz_false_bitreverse(i32 %x) { define i32 @cttz_true_bitreverse(i32 %x) { ; CHECK-LABEL: @cttz_true_bitreverse( -; CHECK-NEXT: [[B:%.*]] = call i32 @llvm.ctlz.i32(i32 [[X:%.*]], i1 true), !range [[RNG0]] +; CHECK-NEXT: [[B:%.*]] = call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[X:%.*]], i1 true) ; CHECK-NEXT: ret i32 [[B]] ; %a = tail call i32 @llvm.bitreverse.i32(i32 %x) @@ -43,7 +43,7 @@ define i32 @cttz_true_bitreverse(i32 %x) { define <2 x i64> @cttz_true_bitreverse_vec(<2 x i64> %x) { ; CHECK-LABEL: @cttz_true_bitreverse_vec( -; CHECK-NEXT: [[B:%.*]] = call <2 x i64> @llvm.ctlz.v2i64(<2 x i64> [[X:%.*]], i1 true), !range [[RNG1]] +; CHECK-NEXT: [[B:%.*]] = call range(i64 0, 65) <2 x i64> @llvm.ctlz.v2i64(<2 x i64> [[X:%.*]], i1 true) ; CHECK-NEXT: ret <2 x i64> [[B]] ; %a = tail call <2 x i64> @llvm.bitreverse.v2i64(<2 x i64> %x) @@ -53,7 +53,7 @@ define <2 x i64> @cttz_true_bitreverse_vec(<2 x i64> %x) { define i32 @cttz_false_bitreverse(i32 %x) { ; CHECK-LABEL: @cttz_false_bitreverse( -; CHECK-NEXT: [[B:%.*]] = call i32 @llvm.ctlz.i32(i32 [[X:%.*]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[B:%.*]] = call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[X:%.*]], i1 false) ; CHECK-NEXT: ret i32 [[B]] ; %a = tail call i32 @llvm.bitreverse.i32(i32 %x) diff --git a/llvm/test/Transforms/InstCombine/ctlz-cttz-shifts.ll b/llvm/test/Transforms/InstCombine/ctlz-cttz-shifts.ll index 86fef51872b1908685c27a24b60fc2ac2676c14a..15aa87f72c49a1a95ea9f0121cafcc22f4d5479c 100644 --- a/llvm/test/Transforms/InstCombine/ctlz-cttz-shifts.ll +++ b/llvm/test/Transforms/InstCombine/ctlz-cttz-shifts.ll @@ -122,7 +122,7 @@ define <2 x i32> @vec2_shl_nsw_ctlz_true_neg(<2 x i32>) { ; CHECK-LABEL: define <2 x i32> @vec2_shl_nsw_ctlz_true_neg( ; CHECK-SAME: <2 x i32> [[TMP0:%.*]]) { ; CHECK-NEXT: [[SHL:%.*]] = shl nsw <2 x i32> , [[TMP0]] -; CHECK-NEXT: [[CTLZ:%.*]] = call <2 x i32> @llvm.ctlz.v2i32(<2 x i32> [[SHL]], i1 true), !range [[RNG0:![0-9]+]] +; CHECK-NEXT: [[CTLZ:%.*]] = call range(i32 1, 33) <2 x i32> @llvm.ctlz.v2i32(<2 x i32> [[SHL]], i1 true) ; CHECK-NEXT: ret <2 x i32> [[CTLZ]] ; %shl = shl nsw <2 x i32> , %0 @@ -134,7 +134,7 @@ define <2 x i32> @vec2_lshr_ctlz_false_neg(<2 x i32>) { ; CHECK-LABEL: define <2 x i32> @vec2_lshr_ctlz_false_neg( ; CHECK-SAME: <2 x i32> [[TMP0:%.*]]) { ; CHECK-NEXT: [[DIV:%.*]] = lshr <2 x i32> , [[TMP0]] -; CHECK-NEXT: [[CTLZ:%.*]] = call <2 x i32> @llvm.ctlz.v2i32(<2 x i32> [[DIV]], i1 false), !range [[RNG1:![0-9]+]] +; CHECK-NEXT: [[CTLZ:%.*]] = call range(i32 9, 33) <2 x i32> @llvm.ctlz.v2i32(<2 x i32> [[DIV]], i1 false) ; CHECK-NEXT: ret <2 x i32> [[CTLZ]] ; %div = lshr <2 x i32> , %0 @@ -146,7 +146,7 @@ define <2 x i32> @vec2_shl_ctlz_false_neg(<2 x i32>) { ; CHECK-LABEL: define <2 x i32> @vec2_shl_ctlz_false_neg( ; CHECK-SAME: <2 x i32> [[TMP0:%.*]]) { ; CHECK-NEXT: [[SHL:%.*]] = shl <2 x i32> , [[TMP0]] -; CHECK-NEXT: [[CTLZ:%.*]] = call <2 x i32> @llvm.ctlz.v2i32(<2 x i32> [[SHL]], i1 false), !range [[RNG2:![0-9]+]] +; CHECK-NEXT: [[CTLZ:%.*]] = call range(i32 0, 33) <2 x i32> @llvm.ctlz.v2i32(<2 x i32> [[SHL]], i1 false) ; CHECK-NEXT: ret <2 x i32> [[CTLZ]] ; %shl = shl <2 x i32> , %0 @@ -158,7 +158,7 @@ define <2 x i32> @vec2_lshr_cttz_false_neg(<2 x i32>) { ; CHECK-LABEL: define <2 x i32> @vec2_lshr_cttz_false_neg( ; CHECK-SAME: <2 x i32> [[TMP0:%.*]]) { ; CHECK-NEXT: [[LSHR:%.*]] = lshr <2 x i32> , [[TMP0]] -; CHECK-NEXT: [[CTTZ:%.*]] = call <2 x i32> @llvm.cttz.v2i32(<2 x i32> [[LSHR]], i1 false), !range [[RNG2]] +; CHECK-NEXT: [[CTTZ:%.*]] = call range(i32 0, 33) <2 x i32> @llvm.cttz.v2i32(<2 x i32> [[LSHR]], i1 false) ; CHECK-NEXT: ret <2 x i32> [[CTTZ]] ; %lshr = lshr <2 x i32> , %0 @@ -170,7 +170,7 @@ define <2 x i32> @vec2_shl_cttz_false_neg(<2 x i32>) { ; CHECK-LABEL: define <2 x i32> @vec2_shl_cttz_false_neg( ; CHECK-SAME: <2 x i32> [[TMP0:%.*]]) { ; CHECK-NEXT: [[SHL:%.*]] = shl <2 x i32> , [[TMP0]] -; CHECK-NEXT: [[CTTZ:%.*]] = call <2 x i32> @llvm.cttz.v2i32(<2 x i32> [[SHL]], i1 false), !range [[RNG3:![0-9]+]] +; CHECK-NEXT: [[CTTZ:%.*]] = call range(i32 3, 33) <2 x i32> @llvm.cttz.v2i32(<2 x i32> [[SHL]], i1 false) ; CHECK-NEXT: ret <2 x i32> [[CTTZ]] ; %shl = shl <2 x i32> , %0 @@ -182,7 +182,7 @@ define i32 @lshr_ctlz_faslse_neg(i32) { ; CHECK-LABEL: define i32 @lshr_ctlz_faslse_neg( ; CHECK-SAME: i32 [[TMP0:%.*]]) { ; CHECK-NEXT: [[LSHR:%.*]] = lshr i32 8387584, [[TMP0]] -; CHECK-NEXT: [[CTLZ:%.*]] = call i32 @llvm.ctlz.i32(i32 [[LSHR]], i1 false), !range [[RNG1]] +; CHECK-NEXT: [[CTLZ:%.*]] = call range(i32 9, 33) i32 @llvm.ctlz.i32(i32 [[LSHR]], i1 false) ; CHECK-NEXT: ret i32 [[CTLZ]] ; %lshr = lshr i32 8387584, %0 @@ -194,7 +194,7 @@ define i32 @shl_ctlz_false_neg(i32) { ; CHECK-LABEL: define i32 @shl_ctlz_false_neg( ; CHECK-SAME: i32 [[TMP0:%.*]]) { ; CHECK-NEXT: [[SHL:%.*]] = shl i32 8387584, [[TMP0]] -; CHECK-NEXT: [[CTLZ:%.*]] = call i32 @llvm.ctlz.i32(i32 [[SHL]], i1 false), !range [[RNG2]] +; CHECK-NEXT: [[CTLZ:%.*]] = call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[SHL]], i1 false) ; CHECK-NEXT: ret i32 [[CTLZ]] ; %shl = shl i32 8387584, %0 @@ -206,7 +206,7 @@ define i32 @lshr_cttz_false_neg(i32) { ; CHECK-LABEL: define i32 @lshr_cttz_false_neg( ; CHECK-SAME: i32 [[TMP0:%.*]]) { ; CHECK-NEXT: [[LSHR:%.*]] = lshr i32 8387584, [[TMP0]] -; CHECK-NEXT: [[CTTZ:%.*]] = call i32 @llvm.cttz.i32(i32 [[LSHR]], i1 false), !range [[RNG2]] +; CHECK-NEXT: [[CTTZ:%.*]] = call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[LSHR]], i1 false) ; CHECK-NEXT: ret i32 [[CTTZ]] ; %lshr = lshr i32 8387584, %0 @@ -218,17 +218,10 @@ define i32 @shl_cttz_false_neg(i32) { ; CHECK-LABEL: define i32 @shl_cttz_false_neg( ; CHECK-SAME: i32 [[TMP0:%.*]]) { ; CHECK-NEXT: [[SHL:%.*]] = shl i32 8387584, [[TMP0]] -; CHECK-NEXT: [[CTTZ:%.*]] = call i32 @llvm.cttz.i32(i32 [[SHL]], i1 false), !range [[RNG4:![0-9]+]] +; CHECK-NEXT: [[CTTZ:%.*]] = call range(i32 10, 33) i32 @llvm.cttz.i32(i32 [[SHL]], i1 false) ; CHECK-NEXT: ret i32 [[CTTZ]] ; %shl = shl i32 8387584, %0 %cttz = call i32 @llvm.cttz.i32(i32 %shl, i1 false) ret i32 %cttz } -;. -; CHECK: [[RNG0]] = !{i32 1, i32 33} -; CHECK: [[RNG1]] = !{i32 9, i32 33} -; CHECK: [[RNG2]] = !{i32 0, i32 33} -; CHECK: [[RNG3]] = !{i32 3, i32 33} -; CHECK: [[RNG4]] = !{i32 10, i32 33} -;. diff --git a/llvm/test/Transforms/InstCombine/ctpop-bswap-bitreverse.ll b/llvm/test/Transforms/InstCombine/ctpop-bswap-bitreverse.ll index 2f523f90edda8871193f1ed38225cf50261fec24..7e4050873dc924b9f0765c6a4c1096b07fe2d352 100644 --- a/llvm/test/Transforms/InstCombine/ctpop-bswap-bitreverse.ll +++ b/llvm/test/Transforms/InstCombine/ctpop-bswap-bitreverse.ll @@ -3,7 +3,7 @@ define i32 @ctpop_bitreverse(i32 %x) { ; CHECK-LABEL: @ctpop_bitreverse( -; CHECK-NEXT: [[B:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0:![0-9]+]] +; CHECK-NEXT: [[B:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: ret i32 [[B]] ; %a = tail call i32 @llvm.bitreverse.i32(i32 %x) @@ -13,7 +13,7 @@ define i32 @ctpop_bitreverse(i32 %x) { define <2 x i64> @ctpop_bitreverse_vec(<2 x i64> %x) { ; CHECK-LABEL: @ctpop_bitreverse_vec( -; CHECK-NEXT: [[B:%.*]] = tail call <2 x i64> @llvm.ctpop.v2i64(<2 x i64> [[X:%.*]]), !range [[RNG1:![0-9]+]] +; CHECK-NEXT: [[B:%.*]] = tail call range(i64 0, 65) <2 x i64> @llvm.ctpop.v2i64(<2 x i64> [[X:%.*]]) ; CHECK-NEXT: ret <2 x i64> [[B]] ; %a = tail call <2 x i64> @llvm.bitreverse.v2i64(<2 x i64> %x) @@ -23,7 +23,7 @@ define <2 x i64> @ctpop_bitreverse_vec(<2 x i64> %x) { define i32 @ctpop_bswap(i32 %x) { ; CHECK-LABEL: @ctpop_bswap( -; CHECK-NEXT: [[B:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[B:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: ret i32 [[B]] ; %a = tail call i32 @llvm.bswap.i32(i32 %x) @@ -33,7 +33,7 @@ define i32 @ctpop_bswap(i32 %x) { define <2 x i64> @ctpop_bswap_vec(<2 x i64> %x) { ; CHECK-LABEL: @ctpop_bswap_vec( -; CHECK-NEXT: [[B:%.*]] = tail call <2 x i64> @llvm.ctpop.v2i64(<2 x i64> [[X:%.*]]), !range [[RNG1]] +; CHECK-NEXT: [[B:%.*]] = tail call range(i64 0, 65) <2 x i64> @llvm.ctpop.v2i64(<2 x i64> [[X:%.*]]) ; CHECK-NEXT: ret <2 x i64> [[B]] ; %a = tail call <2 x i64> @llvm.bswap.v2i64(<2 x i64> %x) diff --git a/llvm/test/Transforms/InstCombine/ctpop-cttz.ll b/llvm/test/Transforms/InstCombine/ctpop-cttz.ll index 70868554bdc1bbfacf662b70dd2a871713063a5c..a505654fa96e7fbb6e90fabf6c21059ca2189a7b 100644 --- a/llvm/test/Transforms/InstCombine/ctpop-cttz.ll +++ b/llvm/test/Transforms/InstCombine/ctpop-cttz.ll @@ -8,7 +8,7 @@ declare <2 x i32> @llvm.ctpop.v2i32(<2 x i32>) ; __builtin_popcount(i | -i) -> 32 - __builtin_cttz(i, false) define i32 @ctpop1(i32 %0) { ; CHECK-LABEL: @ctpop1( -; CHECK-NEXT: [[TMP2:%.*]] = call i32 @llvm.cttz.i32(i32 [[TMP0:%.*]], i1 false), !range [[RNG0:![0-9]+]] +; CHECK-NEXT: [[TMP2:%.*]] = call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[TMP0:%.*]], i1 false) ; CHECK-NEXT: ret i32 [[TMP2]] ; %2 = sub i32 0, %0 @@ -20,7 +20,7 @@ define i32 @ctpop1(i32 %0) { define <2 x i32> @ctpop1v(<2 x i32> %0) { ; CHECK-LABEL: @ctpop1v( -; CHECK-NEXT: [[TMP2:%.*]] = call <2 x i32> @llvm.cttz.v2i32(<2 x i32> [[TMP0:%.*]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[TMP2:%.*]] = call range(i32 0, 33) <2 x i32> @llvm.cttz.v2i32(<2 x i32> [[TMP0:%.*]], i1 false) ; CHECK-NEXT: [[TMP3:%.*]] = sub nuw nsw <2 x i32> , [[TMP2]] ; CHECK-NEXT: ret <2 x i32> [[TMP3]] ; @@ -35,7 +35,7 @@ define i32 @ctpop1_multiuse(i32 %0) { ; CHECK-NEXT: [[TMP2:%.*]] = sub i32 0, [[TMP0:%.*]] ; CHECK-NEXT: [[TMP3:%.*]] = or i32 [[TMP2]], [[TMP0]] ; CHECK-NEXT: [[TMP4:%.*]] = xor i32 [[TMP3]], -1 -; CHECK-NEXT: [[TMP5:%.*]] = call i32 @llvm.ctpop.i32(i32 [[TMP4]]), !range [[RNG0]] +; CHECK-NEXT: [[TMP5:%.*]] = call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[TMP4]]) ; CHECK-NEXT: [[TMP6:%.*]] = add i32 [[TMP5]], [[TMP3]] ; CHECK-NEXT: ret i32 [[TMP6]] ; @@ -51,7 +51,7 @@ define i32 @ctpop1_multiuse(i32 %0) { ; __builtin_popcount(~i & (i-1)) -> __builtin_cttz(i, false) define i32 @ctpop2(i32 %0) { ; CHECK-LABEL: @ctpop2( -; CHECK-NEXT: [[TMP2:%.*]] = call i32 @llvm.cttz.i32(i32 [[TMP0:%.*]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[TMP2:%.*]] = call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[TMP0:%.*]], i1 false) ; CHECK-NEXT: ret i32 [[TMP2]] ; %2 = xor i32 %0, -1 @@ -63,7 +63,7 @@ define i32 @ctpop2(i32 %0) { define <2 x i32> @ctpop2v(<2 x i32> %0) { ; CHECK-LABEL: @ctpop2v( -; CHECK-NEXT: [[TMP2:%.*]] = call <2 x i32> @llvm.cttz.v2i32(<2 x i32> [[TMP0:%.*]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[TMP2:%.*]] = call range(i32 0, 33) <2 x i32> @llvm.cttz.v2i32(<2 x i32> [[TMP0:%.*]], i1 false) ; CHECK-NEXT: ret <2 x i32> [[TMP2]] ; %2 = xor <2 x i32> %0, @@ -78,7 +78,7 @@ define i32 @ctpop2_multiuse(i32 %0) { ; CHECK-NEXT: [[TMP2:%.*]] = xor i32 [[TMP0:%.*]], -1 ; CHECK-NEXT: [[TMP3:%.*]] = add i32 [[TMP0]], -1 ; CHECK-NEXT: [[TMP4:%.*]] = and i32 [[TMP3]], [[TMP2]] -; CHECK-NEXT: [[TMP5:%.*]] = call i32 @llvm.cttz.i32(i32 [[TMP0]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[TMP5:%.*]] = call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[TMP0]], i1 false) ; CHECK-NEXT: [[TMP6:%.*]] = add i32 [[TMP5]], [[TMP4]] ; CHECK-NEXT: ret i32 [[TMP6]] ; @@ -94,7 +94,7 @@ define i32 @ctpop2_multiuse(i32 %0) { ; __builtin_popcount((i & -i) - 1) -> __builtin_cttz(i, false) define i32 @ctpop3(i32 %0) { ; CHECK-LABEL: @ctpop3( -; CHECK-NEXT: [[TMP2:%.*]] = call i32 @llvm.cttz.i32(i32 [[TMP0:%.*]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[TMP2:%.*]] = call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[TMP0:%.*]], i1 false) ; CHECK-NEXT: ret i32 [[TMP2]] ; %2 = sub i32 0, %0 @@ -106,7 +106,7 @@ define i32 @ctpop3(i32 %0) { define <2 x i32> @ctpop3v(<2 x i32> %0) { ; CHECK-LABEL: @ctpop3v( -; CHECK-NEXT: [[TMP2:%.*]] = call <2 x i32> @llvm.cttz.v2i32(<2 x i32> [[TMP0:%.*]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[TMP2:%.*]] = call range(i32 0, 33) <2 x i32> @llvm.cttz.v2i32(<2 x i32> [[TMP0:%.*]], i1 false) ; CHECK-NEXT: ret <2 x i32> [[TMP2]] ; %2 = sub <2 x i32> zeroinitializer, %0 @@ -118,7 +118,7 @@ define <2 x i32> @ctpop3v(<2 x i32> %0) { define <2 x i32> @ctpop3v_poison(<2 x i32> %0) { ; CHECK-LABEL: @ctpop3v_poison( -; CHECK-NEXT: [[TMP2:%.*]] = call <2 x i32> @llvm.cttz.v2i32(<2 x i32> [[TMP0:%.*]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[TMP2:%.*]] = call range(i32 0, 33) <2 x i32> @llvm.cttz.v2i32(<2 x i32> [[TMP0:%.*]], i1 false) ; CHECK-NEXT: ret <2 x i32> [[TMP2]] ; %2 = sub <2 x i32> zeroinitializer, %0 diff --git a/llvm/test/Transforms/InstCombine/ctpop-pow2.ll b/llvm/test/Transforms/InstCombine/ctpop-pow2.ll index f6757c2ff33cfaea99832a313c34219a22c0ce63..7facdaf7590d386c504e1630c0526a8630d63220 100644 --- a/llvm/test/Transforms/InstCombine/ctpop-pow2.ll +++ b/llvm/test/Transforms/InstCombine/ctpop-pow2.ll @@ -60,7 +60,7 @@ define i8 @ctpop_imin_plus1_lshr_nz(i8 %x) { ; CHECK-NEXT: [[CMP:%.*]] = icmp ne i8 [[X:%.*]], 0 ; CHECK-NEXT: call void @llvm.assume(i1 [[CMP]]) ; CHECK-NEXT: [[V:%.*]] = lshr i8 -127, [[X]] -; CHECK-NEXT: [[CNT:%.*]] = call i8 @llvm.ctpop.i8(i8 [[V]]), !range [[RNG0:![0-9]+]] +; CHECK-NEXT: [[CNT:%.*]] = call range(i8 0, 9) i8 @llvm.ctpop.i8(i8 [[V]]) ; CHECK-NEXT: ret i8 [[CNT]] ; %cmp = icmp ne i8 %x, 0 @@ -104,7 +104,7 @@ define <2 x i32> @ctpop_lshr_intmin_intmin_plus1_vec_nz(<2 x i32> %x) { ; CHECK-LABEL: @ctpop_lshr_intmin_intmin_plus1_vec_nz( ; CHECK-NEXT: [[X1:%.*]] = or <2 x i32> [[X:%.*]], ; CHECK-NEXT: [[SHR:%.*]] = lshr <2 x i32> , [[X1]] -; CHECK-NEXT: [[CNT:%.*]] = call <2 x i32> @llvm.ctpop.v2i32(<2 x i32> [[SHR]]), !range [[RNG1:![0-9]+]] +; CHECK-NEXT: [[CNT:%.*]] = call range(i32 0, 17) <2 x i32> @llvm.ctpop.v2i32(<2 x i32> [[SHR]]) ; CHECK-NEXT: ret <2 x i32> [[CNT]] ; %x1 = or <2 x i32> %x, diff --git a/llvm/test/Transforms/InstCombine/ctpop.ll b/llvm/test/Transforms/InstCombine/ctpop.ll index b3653e5071ba252e0ee41f3ade0aae637a309fc6..83700e72de080952b9314b10b30efbe5b5ef53bf 100644 --- a/llvm/test/Transforms/InstCombine/ctpop.ll +++ b/llvm/test/Transforms/InstCombine/ctpop.ll @@ -49,7 +49,7 @@ define i1 @test3(i32 %arg) { ; Negative test for when we know nothing define i1 @test4(i8 %arg) { ; CHECK-LABEL: @test4( -; CHECK-NEXT: [[CNT:%.*]] = call i8 @llvm.ctpop.i8(i8 [[ARG:%.*]]), !range [[RNG0:![0-9]+]] +; CHECK-NEXT: [[CNT:%.*]] = call range(i8 0, 9) i8 @llvm.ctpop.i8(i8 [[ARG:%.*]]) ; CHECK-NEXT: [[RES:%.*]] = icmp eq i8 [[CNT]], 2 ; CHECK-NEXT: ret i1 [[RES]] ; @@ -118,7 +118,7 @@ define <2 x i32> @mask_one_bit_splat(<2 x i32> %x, ptr %p) { define i32 @_parity_of_not(i32 %x) { ; CHECK-LABEL: @_parity_of_not( -; CHECK-NEXT: [[TMP1:%.*]] = call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG1:![0-9]+]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: [[R:%.*]] = and i32 [[TMP1]], 1 ; CHECK-NEXT: ret i32 [[R]] ; @@ -133,7 +133,7 @@ define i32 @_parity_of_not(i32 %x) { define i7 @_parity_of_not_odd_type(i7 %x) { ; CHECK-LABEL: @_parity_of_not_odd_type( ; CHECK-NEXT: [[NEG:%.*]] = xor i7 [[X:%.*]], -1 -; CHECK-NEXT: [[CNT:%.*]] = tail call i7 @llvm.ctpop.i7(i7 [[NEG]]), !range [[RNG2:![0-9]+]] +; CHECK-NEXT: [[CNT:%.*]] = tail call range(i7 0, 8) i7 @llvm.ctpop.i7(i7 [[NEG]]) ; CHECK-NEXT: [[R:%.*]] = and i7 [[CNT]], 1 ; CHECK-NEXT: ret i7 [[R]] ; @@ -145,7 +145,7 @@ define i7 @_parity_of_not_odd_type(i7 %x) { define <2 x i32> @_parity_of_not_vec(<2 x i32> %x) { ; CHECK-LABEL: @_parity_of_not_vec( -; CHECK-NEXT: [[TMP1:%.*]] = call <2 x i32> @llvm.ctpop.v2i32(<2 x i32> [[X:%.*]]), !range [[RNG1]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i32 0, 33) <2 x i32> @llvm.ctpop.v2i32(<2 x i32> [[X:%.*]]) ; CHECK-NEXT: [[R:%.*]] = and <2 x i32> [[TMP1]], ; CHECK-NEXT: ret <2 x i32> [[R]] ; @@ -157,7 +157,7 @@ define <2 x i32> @_parity_of_not_vec(<2 x i32> %x) { define <2 x i32> @_parity_of_not_poison(<2 x i32> %x) { ; CHECK-LABEL: @_parity_of_not_poison( -; CHECK-NEXT: [[TMP1:%.*]] = call <2 x i32> @llvm.ctpop.v2i32(<2 x i32> [[X:%.*]]), !range [[RNG1]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i32 0, 33) <2 x i32> @llvm.ctpop.v2i32(<2 x i32> [[X:%.*]]) ; CHECK-NEXT: [[R:%.*]] = and <2 x i32> [[TMP1]], ; CHECK-NEXT: ret <2 x i32> [[R]] ; @@ -169,7 +169,7 @@ define <2 x i32> @_parity_of_not_poison(<2 x i32> %x) { define <2 x i32> @_parity_of_not_poison2(<2 x i32> %x) { ; CHECK-LABEL: @_parity_of_not_poison2( -; CHECK-NEXT: [[CNT:%.*]] = call <2 x i32> @llvm.ctpop.v2i32(<2 x i32> [[X:%.*]]), !range [[RNG1]] +; CHECK-NEXT: [[CNT:%.*]] = call range(i32 0, 33) <2 x i32> @llvm.ctpop.v2i32(<2 x i32> [[X:%.*]]) ; CHECK-NEXT: [[R:%.*]] = and <2 x i32> [[CNT]], ; CHECK-NEXT: ret <2 x i32> [[R]] ; @@ -200,7 +200,7 @@ define i32 @ctpop_add(i32 %a, i32 %b) { define i32 @ctpop_add_no_common_bits(i32 %a, i32 %b) { ; CHECK-LABEL: @ctpop_add_no_common_bits( ; CHECK-NEXT: [[TMP1:%.*]] = call i32 @llvm.fshl.i32(i32 [[A:%.*]], i32 [[B:%.*]], i32 16) -; CHECK-NEXT: [[RES:%.*]] = call i32 @llvm.ctpop.i32(i32 [[TMP1]]), !range [[RNG1]] +; CHECK-NEXT: [[RES:%.*]] = call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[TMP1]]) ; CHECK-NEXT: ret i32 [[RES]] ; %shl16 = shl i32 %a, 16 @@ -214,7 +214,7 @@ define i32 @ctpop_add_no_common_bits(i32 %a, i32 %b) { define <2 x i32> @ctpop_add_no_common_bits_vec(<2 x i32> %a, <2 x i32> %b) { ; CHECK-LABEL: @ctpop_add_no_common_bits_vec( ; CHECK-NEXT: [[TMP1:%.*]] = call <2 x i32> @llvm.fshl.v2i32(<2 x i32> [[A:%.*]], <2 x i32> [[B:%.*]], <2 x i32> ) -; CHECK-NEXT: [[RES:%.*]] = call <2 x i32> @llvm.ctpop.v2i32(<2 x i32> [[TMP1]]), !range [[RNG1]] +; CHECK-NEXT: [[RES:%.*]] = call range(i32 0, 33) <2 x i32> @llvm.ctpop.v2i32(<2 x i32> [[TMP1]]) ; CHECK-NEXT: ret <2 x i32> [[RES]] ; %shl16 = shl <2 x i32> %a, @@ -228,9 +228,9 @@ define <2 x i32> @ctpop_add_no_common_bits_vec(<2 x i32> %a, <2 x i32> %b) { define <2 x i32> @ctpop_add_no_common_bits_vec_use(<2 x i32> %a, <2 x i32> %b, ptr %p) { ; CHECK-LABEL: @ctpop_add_no_common_bits_vec_use( ; CHECK-NEXT: [[SHL16:%.*]] = shl <2 x i32> [[A:%.*]], -; CHECK-NEXT: [[CTPOP1:%.*]] = tail call <2 x i32> @llvm.ctpop.v2i32(<2 x i32> [[SHL16]]), !range [[RNG3:![0-9]+]] +; CHECK-NEXT: [[CTPOP1:%.*]] = tail call range(i32 0, 17) <2 x i32> @llvm.ctpop.v2i32(<2 x i32> [[SHL16]]) ; CHECK-NEXT: [[LSHL16:%.*]] = lshr <2 x i32> [[B:%.*]], -; CHECK-NEXT: [[CTPOP2:%.*]] = tail call <2 x i32> @llvm.ctpop.v2i32(<2 x i32> [[LSHL16]]), !range [[RNG3]] +; CHECK-NEXT: [[CTPOP2:%.*]] = tail call range(i32 0, 17) <2 x i32> @llvm.ctpop.v2i32(<2 x i32> [[LSHL16]]) ; CHECK-NEXT: store <2 x i32> [[CTPOP2]], ptr [[P:%.*]], align 8 ; CHECK-NEXT: [[RES:%.*]] = add nuw nsw <2 x i32> [[CTPOP1]], [[CTPOP2]] ; CHECK-NEXT: ret <2 x i32> [[RES]] @@ -247,10 +247,10 @@ define <2 x i32> @ctpop_add_no_common_bits_vec_use(<2 x i32> %a, <2 x i32> %b, p define <2 x i32> @ctpop_add_no_common_bits_vec_use2(<2 x i32> %a, <2 x i32> %b, ptr %p) { ; CHECK-LABEL: @ctpop_add_no_common_bits_vec_use2( ; CHECK-NEXT: [[SHL16:%.*]] = shl <2 x i32> [[A:%.*]], -; CHECK-NEXT: [[CTPOP1:%.*]] = tail call <2 x i32> @llvm.ctpop.v2i32(<2 x i32> [[SHL16]]), !range [[RNG3]] +; CHECK-NEXT: [[CTPOP1:%.*]] = tail call range(i32 0, 17) <2 x i32> @llvm.ctpop.v2i32(<2 x i32> [[SHL16]]) ; CHECK-NEXT: store <2 x i32> [[CTPOP1]], ptr [[P:%.*]], align 8 ; CHECK-NEXT: [[LSHL16:%.*]] = lshr <2 x i32> [[B:%.*]], -; CHECK-NEXT: [[CTPOP2:%.*]] = tail call <2 x i32> @llvm.ctpop.v2i32(<2 x i32> [[LSHL16]]), !range [[RNG3]] +; CHECK-NEXT: [[CTPOP2:%.*]] = tail call range(i32 0, 17) <2 x i32> @llvm.ctpop.v2i32(<2 x i32> [[LSHL16]]) ; CHECK-NEXT: [[RES:%.*]] = add nuw nsw <2 x i32> [[CTPOP1]], [[CTPOP2]] ; CHECK-NEXT: ret <2 x i32> [[RES]] ; @@ -265,7 +265,7 @@ define <2 x i32> @ctpop_add_no_common_bits_vec_use2(<2 x i32> %a, <2 x i32> %b, define i8 @ctpop_rotate_left(i8 %a, i8 %amt) { ; CHECK-LABEL: @ctpop_rotate_left( -; CHECK-NEXT: [[RES:%.*]] = tail call i8 @llvm.ctpop.i8(i8 [[A:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[RES:%.*]] = tail call range(i8 0, 9) i8 @llvm.ctpop.i8(i8 [[A:%.*]]) ; CHECK-NEXT: ret i8 [[RES]] ; %rotl = tail call i8 @llvm.fshl.i8(i8 %a, i8 %a, i8 %amt) @@ -275,7 +275,7 @@ define i8 @ctpop_rotate_left(i8 %a, i8 %amt) { define i8 @ctpop_rotate_right(i8 %a, i8 %amt) { ; CHECK-LABEL: @ctpop_rotate_right( -; CHECK-NEXT: [[RES:%.*]] = tail call i8 @llvm.ctpop.i8(i8 [[A:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[RES:%.*]] = tail call range(i8 0, 9) i8 @llvm.ctpop.i8(i8 [[A:%.*]]) ; CHECK-NEXT: ret i8 [[RES]] ; %rotr = tail call i8 @llvm.fshr.i8(i8 %a, i8 %a, i8 %amt) @@ -289,7 +289,7 @@ declare i8 @llvm.fshr.i8(i8, i8, i8) define i8 @sub_ctpop(i8 %a) { ; CHECK-LABEL: @sub_ctpop( ; CHECK-NEXT: [[TMP1:%.*]] = xor i8 [[A:%.*]], -1 -; CHECK-NEXT: [[RES:%.*]] = call i8 @llvm.ctpop.i8(i8 [[TMP1]]), !range [[RNG0]] +; CHECK-NEXT: [[RES:%.*]] = call range(i8 0, 9) i8 @llvm.ctpop.i8(i8 [[TMP1]]) ; CHECK-NEXT: ret i8 [[RES]] ; %cnt = tail call i8 @llvm.ctpop.i8(i8 %a) @@ -299,7 +299,7 @@ define i8 @sub_ctpop(i8 %a) { define i8 @sub_ctpop_wrong_cst(i8 %a) { ; CHECK-LABEL: @sub_ctpop_wrong_cst( -; CHECK-NEXT: [[CNT:%.*]] = tail call i8 @llvm.ctpop.i8(i8 [[A:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[CNT:%.*]] = tail call range(i8 0, 9) i8 @llvm.ctpop.i8(i8 [[A:%.*]]) ; CHECK-NEXT: [[RES:%.*]] = sub nsw i8 5, [[CNT]] ; CHECK-NEXT: ret i8 [[RES]] ; @@ -310,7 +310,7 @@ define i8 @sub_ctpop_wrong_cst(i8 %a) { define i8 @sub_ctpop_unknown(i8 %a, i8 %b) { ; CHECK-LABEL: @sub_ctpop_unknown( -; CHECK-NEXT: [[CNT:%.*]] = tail call i8 @llvm.ctpop.i8(i8 [[A:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[CNT:%.*]] = tail call range(i8 0, 9) i8 @llvm.ctpop.i8(i8 [[A:%.*]]) ; CHECK-NEXT: [[RES:%.*]] = sub i8 [[B:%.*]], [[CNT]] ; CHECK-NEXT: ret i8 [[RES]] ; @@ -322,7 +322,7 @@ define i8 @sub_ctpop_unknown(i8 %a, i8 %b) { define <2 x i32> @sub_ctpop_vec(<2 x i32> %a) { ; CHECK-LABEL: @sub_ctpop_vec( ; CHECK-NEXT: [[TMP1:%.*]] = xor <2 x i32> [[A:%.*]], -; CHECK-NEXT: [[RES:%.*]] = call <2 x i32> @llvm.ctpop.v2i32(<2 x i32> [[TMP1]]), !range [[RNG1]] +; CHECK-NEXT: [[RES:%.*]] = call range(i32 0, 33) <2 x i32> @llvm.ctpop.v2i32(<2 x i32> [[TMP1]]) ; CHECK-NEXT: ret <2 x i32> [[RES]] ; %cnt = tail call <2 x i32> @llvm.ctpop.v2i32(<2 x i32> %a) @@ -332,7 +332,7 @@ define <2 x i32> @sub_ctpop_vec(<2 x i32> %a) { define <2 x i32> @sub_ctpop_vec_extra_use(<2 x i32> %a, ptr %p) { ; CHECK-LABEL: @sub_ctpop_vec_extra_use( -; CHECK-NEXT: [[CNT:%.*]] = tail call <2 x i32> @llvm.ctpop.v2i32(<2 x i32> [[A:%.*]]), !range [[RNG1]] +; CHECK-NEXT: [[CNT:%.*]] = tail call range(i32 0, 33) <2 x i32> @llvm.ctpop.v2i32(<2 x i32> [[A:%.*]]) ; CHECK-NEXT: store <2 x i32> [[CNT]], ptr [[P:%.*]], align 8 ; CHECK-NEXT: [[RES:%.*]] = sub nuw nsw <2 x i32> , [[CNT]] ; CHECK-NEXT: ret <2 x i32> [[RES]] @@ -345,7 +345,7 @@ define <2 x i32> @sub_ctpop_vec_extra_use(<2 x i32> %a, ptr %p) { define i32 @zext_ctpop(i16 %x) { ; CHECK-LABEL: @zext_ctpop( -; CHECK-NEXT: [[TMP1:%.*]] = call i16 @llvm.ctpop.i16(i16 [[X:%.*]]), !range [[RNG4:![0-9]+]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i16 0, 17) i16 @llvm.ctpop.i16(i16 [[X:%.*]]) ; CHECK-NEXT: [[P:%.*]] = zext nneg i16 [[TMP1]] to i32 ; CHECK-NEXT: ret i32 [[P]] ; @@ -356,7 +356,7 @@ define i32 @zext_ctpop(i16 %x) { define <2 x i32> @zext_ctpop_vec(<2 x i7> %x) { ; CHECK-LABEL: @zext_ctpop_vec( -; CHECK-NEXT: [[TMP1:%.*]] = call <2 x i7> @llvm.ctpop.v2i7(<2 x i7> [[X:%.*]]), !range [[RNG2]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i7 0, 8) <2 x i7> @llvm.ctpop.v2i7(<2 x i7> [[X:%.*]]) ; CHECK-NEXT: [[P:%.*]] = zext nneg <2 x i7> [[TMP1]] to <2 x i32> ; CHECK-NEXT: ret <2 x i32> [[P]] ; @@ -369,7 +369,7 @@ define i32 @zext_ctpop_extra_use(i16 %x, ptr %q) { ; CHECK-LABEL: @zext_ctpop_extra_use( ; CHECK-NEXT: [[Z:%.*]] = zext i16 [[X:%.*]] to i32 ; CHECK-NEXT: store i32 [[Z]], ptr [[Q:%.*]], align 4 -; CHECK-NEXT: [[P:%.*]] = call i32 @llvm.ctpop.i32(i32 [[Z]]), !range [[RNG3]] +; CHECK-NEXT: [[P:%.*]] = call range(i32 0, 17) i32 @llvm.ctpop.i32(i32 [[Z]]) ; CHECK-NEXT: ret i32 [[P]] ; %z = zext i16 %x to i32 @@ -381,7 +381,7 @@ define i32 @zext_ctpop_extra_use(i16 %x, ptr %q) { define i32 @parity_xor(i32 %arg, i32 %arg1) { ; CHECK-LABEL: @parity_xor( ; CHECK-NEXT: [[TMP1:%.*]] = xor i32 [[ARG1:%.*]], [[ARG:%.*]] -; CHECK-NEXT: [[TMP2:%.*]] = call i32 @llvm.ctpop.i32(i32 [[TMP1]]), !range [[RNG1]] +; CHECK-NEXT: [[TMP2:%.*]] = call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[TMP1]]) ; CHECK-NEXT: [[I4:%.*]] = and i32 [[TMP2]], 1 ; CHECK-NEXT: ret i32 [[I4]] ; @@ -395,7 +395,7 @@ define i32 @parity_xor(i32 %arg, i32 %arg1) { define i32 @parity_xor_trunc(i64 %arg, i64 %arg1) { ; CHECK-LABEL: @parity_xor_trunc( ; CHECK-NEXT: [[TMP1:%.*]] = xor i64 [[ARG1:%.*]], [[ARG:%.*]] -; CHECK-NEXT: [[TMP2:%.*]] = call i64 @llvm.ctpop.i64(i64 [[TMP1]]), !range [[RNG5:![0-9]+]] +; CHECK-NEXT: [[TMP2:%.*]] = call range(i64 0, 65) i64 @llvm.ctpop.i64(i64 [[TMP1]]) ; CHECK-NEXT: [[I4:%.*]] = trunc nuw nsw i64 [[TMP2]] to i32 ; CHECK-NEXT: [[I5:%.*]] = and i32 [[I4]], 1 ; CHECK-NEXT: ret i32 [[I5]] @@ -411,7 +411,7 @@ define i32 @parity_xor_trunc(i64 %arg, i64 %arg1) { define <2 x i32> @parity_xor_vec(<2 x i32> %arg, <2 x i32> %arg1) { ; CHECK-LABEL: @parity_xor_vec( ; CHECK-NEXT: [[TMP1:%.*]] = xor <2 x i32> [[ARG1:%.*]], [[ARG:%.*]] -; CHECK-NEXT: [[TMP2:%.*]] = call <2 x i32> @llvm.ctpop.v2i32(<2 x i32> [[TMP1]]), !range [[RNG1]] +; CHECK-NEXT: [[TMP2:%.*]] = call range(i32 0, 33) <2 x i32> @llvm.ctpop.v2i32(<2 x i32> [[TMP1]]) ; CHECK-NEXT: [[I4:%.*]] = and <2 x i32> [[TMP2]], ; CHECK-NEXT: ret <2 x i32> [[I4]] ; @@ -424,8 +424,8 @@ define <2 x i32> @parity_xor_vec(<2 x i32> %arg, <2 x i32> %arg1) { define i32 @parity_xor_wrong_cst(i32 %arg, i32 %arg1) { ; CHECK-LABEL: @parity_xor_wrong_cst( -; CHECK-NEXT: [[I:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[ARG:%.*]]), !range [[RNG1]] -; CHECK-NEXT: [[I2:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[ARG1:%.*]]), !range [[RNG1]] +; CHECK-NEXT: [[I:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[ARG:%.*]]) +; CHECK-NEXT: [[I2:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[ARG1:%.*]]) ; CHECK-NEXT: [[I3:%.*]] = xor i32 [[I2]], [[I]] ; CHECK-NEXT: [[I4:%.*]] = and i32 [[I3]], 3 ; CHECK-NEXT: ret i32 [[I4]] @@ -439,11 +439,11 @@ define i32 @parity_xor_wrong_cst(i32 %arg, i32 %arg1) { define i32 @parity_xor_extra_use(i32 %arg, i32 %arg1) { ; CHECK-LABEL: @parity_xor_extra_use( -; CHECK-NEXT: [[I:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[ARG:%.*]]), !range [[RNG1]] +; CHECK-NEXT: [[I:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[ARG:%.*]]) ; CHECK-NEXT: [[I2:%.*]] = and i32 [[I]], 1 ; CHECK-NEXT: tail call void @use(i32 [[I2]]) ; CHECK-NEXT: [[TMP1:%.*]] = xor i32 [[ARG1:%.*]], [[ARG]] -; CHECK-NEXT: [[TMP2:%.*]] = call i32 @llvm.ctpop.i32(i32 [[TMP1]]), !range [[RNG1]] +; CHECK-NEXT: [[TMP2:%.*]] = call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[TMP1]]) ; CHECK-NEXT: [[I5:%.*]] = and i32 [[TMP2]], 1 ; CHECK-NEXT: ret i32 [[I5]] ; @@ -458,11 +458,11 @@ define i32 @parity_xor_extra_use(i32 %arg, i32 %arg1) { define i32 @parity_xor_extra_use2(i32 %arg, i32 %arg1) { ; CHECK-LABEL: @parity_xor_extra_use2( -; CHECK-NEXT: [[I:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[ARG1:%.*]]), !range [[RNG1]] +; CHECK-NEXT: [[I:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[ARG1:%.*]]) ; CHECK-NEXT: [[I2:%.*]] = and i32 [[I]], 1 ; CHECK-NEXT: tail call void @use(i32 [[I2]]) ; CHECK-NEXT: [[TMP1:%.*]] = xor i32 [[ARG1]], [[ARG:%.*]] -; CHECK-NEXT: [[TMP2:%.*]] = call i32 @llvm.ctpop.i32(i32 [[TMP1]]), !range [[RNG1]] +; CHECK-NEXT: [[TMP2:%.*]] = call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[TMP1]]) ; CHECK-NEXT: [[I5:%.*]] = and i32 [[TMP2]], 1 ; CHECK-NEXT: ret i32 [[I5]] ; @@ -477,7 +477,7 @@ define i32 @parity_xor_extra_use2(i32 %arg, i32 %arg1) { define i32 @select_ctpop_zero(i32 %x) { ; CHECK-LABEL: @select_ctpop_zero( -; CHECK-NEXT: [[CTPOP:%.*]] = call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG1]] +; CHECK-NEXT: [[CTPOP:%.*]] = call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: ret i32 [[CTPOP]] ; %ctpop = call i32 @llvm.ctpop.i32(i32 %x) diff --git a/llvm/test/Transforms/InstCombine/cttz-abs.ll b/llvm/test/Transforms/InstCombine/cttz-abs.ll index 0141b2cd71cec9a5dfc7105a9d42883bf09bd39c..9d3b6168e710be1dbbdf9f7b45bd11e0c397068a 100644 --- a/llvm/test/Transforms/InstCombine/cttz-abs.ll +++ b/llvm/test/Transforms/InstCombine/cttz-abs.ll @@ -3,7 +3,7 @@ define i32 @cttz_abs(i32 %x) { ; CHECK-LABEL: @cttz_abs( -; CHECK-NEXT: [[R:%.*]] = tail call i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 true), !range [[RNG0:![0-9]+]] +; CHECK-NEXT: [[R:%.*]] = tail call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 true) ; CHECK-NEXT: ret i32 [[R]] ; %c = icmp slt i32 %x, 0 @@ -15,7 +15,7 @@ define i32 @cttz_abs(i32 %x) { define <2 x i64> @cttz_abs_vec(<2 x i64> %x) { ; CHECK-LABEL: @cttz_abs_vec( -; CHECK-NEXT: [[R:%.*]] = call <2 x i64> @llvm.cttz.v2i64(<2 x i64> [[X:%.*]], i1 false), !range [[RNG1:![0-9]+]] +; CHECK-NEXT: [[R:%.*]] = call range(i64 0, 65) <2 x i64> @llvm.cttz.v2i64(<2 x i64> [[X:%.*]], i1 false) ; CHECK-NEXT: ret <2 x i64> [[R]] ; %c = icmp slt <2 x i64> %x, zeroinitializer @@ -29,7 +29,7 @@ define i32 @cttz_abs2(i32 %x) { ; CHECK-LABEL: @cttz_abs2( ; CHECK-NEXT: [[C:%.*]] = icmp sgt i32 [[X:%.*]], 0 ; CHECK-NEXT: call void @use_cond(i1 [[C]]) -; CHECK-NEXT: [[R:%.*]] = tail call i32 @llvm.cttz.i32(i32 [[X]], i1 true), !range [[RNG0]] +; CHECK-NEXT: [[R:%.*]] = tail call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[X]], i1 true) ; CHECK-NEXT: ret i32 [[R]] ; %c = icmp sgt i32 %x, 0 @@ -44,7 +44,7 @@ define i32 @cttz_abs3(i32 %x) { ; CHECK-LABEL: @cttz_abs3( ; CHECK-NEXT: [[C:%.*]] = icmp sgt i32 [[X:%.*]], -1 ; CHECK-NEXT: call void @use_cond(i1 [[C]]) -; CHECK-NEXT: [[R:%.*]] = tail call i32 @llvm.cttz.i32(i32 [[X]], i1 true), !range [[RNG0]] +; CHECK-NEXT: [[R:%.*]] = tail call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[X]], i1 true) ; CHECK-NEXT: ret i32 [[R]] ; %c = icmp sgt i32 %x, -1 @@ -57,7 +57,7 @@ define i32 @cttz_abs3(i32 %x) { define i32 @cttz_abs4(i32 %x) { ; CHECK-LABEL: @cttz_abs4( -; CHECK-NEXT: [[R:%.*]] = tail call i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 true), !range [[RNG0]] +; CHECK-NEXT: [[R:%.*]] = tail call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 true) ; CHECK-NEXT: ret i32 [[R]] ; %c = icmp slt i32 %x, 1 @@ -69,7 +69,7 @@ define i32 @cttz_abs4(i32 %x) { define i32 @cttz_nabs(i32 %x) { ; CHECK-LABEL: @cttz_nabs( -; CHECK-NEXT: [[R:%.*]] = tail call i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[R:%.*]] = tail call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 false) ; CHECK-NEXT: ret i32 [[R]] ; %c = icmp slt i32 %x, 0 @@ -81,7 +81,7 @@ define i32 @cttz_nabs(i32 %x) { define <2 x i64> @cttz_nabs_vec(<2 x i64> %x) { ; CHECK-LABEL: @cttz_nabs_vec( -; CHECK-NEXT: [[R:%.*]] = call <2 x i64> @llvm.cttz.v2i64(<2 x i64> [[X:%.*]], i1 false), !range [[RNG1]] +; CHECK-NEXT: [[R:%.*]] = call range(i64 0, 65) <2 x i64> @llvm.cttz.v2i64(<2 x i64> [[X:%.*]], i1 false) ; CHECK-NEXT: ret <2 x i64> [[R]] ; %c = icmp slt <2 x i64> %x, zeroinitializer @@ -93,7 +93,7 @@ define <2 x i64> @cttz_nabs_vec(<2 x i64> %x) { define i64 @cttz_abs_64(i64 %x) { ; CHECK-LABEL: @cttz_abs_64( -; CHECK-NEXT: [[R:%.*]] = call i64 @llvm.cttz.i64(i64 [[X:%.*]], i1 false), !range [[RNG1]] +; CHECK-NEXT: [[R:%.*]] = call range(i64 0, 65) i64 @llvm.cttz.i64(i64 [[X:%.*]], i1 false) ; CHECK-NEXT: ret i64 [[R]] ; %c = icmp slt i64 %x, 0 @@ -107,7 +107,7 @@ define i32 @cttz_abs_multiuse(i32 %x) { ; CHECK-LABEL: @cttz_abs_multiuse( ; CHECK-NEXT: [[D:%.*]] = call i32 @llvm.abs.i32(i32 [[X:%.*]], i1 false) ; CHECK-NEXT: call void @use_abs(i32 [[D]]) -; CHECK-NEXT: [[R:%.*]] = tail call i32 @llvm.cttz.i32(i32 [[X]], i1 true), !range [[RNG0]] +; CHECK-NEXT: [[R:%.*]] = tail call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[X]], i1 true) ; CHECK-NEXT: ret i32 [[R]] ; %c = icmp slt i32 %x, 1 @@ -123,7 +123,7 @@ define i32 @cttz_nabs_multiuse(i32 %x) { ; CHECK-NEXT: [[TMP1:%.*]] = call i32 @llvm.abs.i32(i32 [[X:%.*]], i1 false) ; CHECK-NEXT: [[D:%.*]] = sub i32 0, [[TMP1]] ; CHECK-NEXT: call void @use_abs(i32 [[D]]) -; CHECK-NEXT: [[R:%.*]] = tail call i32 @llvm.cttz.i32(i32 [[X]], i1 true), !range [[RNG0]] +; CHECK-NEXT: [[R:%.*]] = tail call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[X]], i1 true) ; CHECK-NEXT: ret i32 [[R]] ; %c = icmp slt i32 %x, 1 @@ -141,7 +141,7 @@ define i32 @no_cttz_abs(i32 %x) { ; CHECK-NEXT: [[C:%.*]] = icmp slt i32 [[X:%.*]], 2 ; CHECK-NEXT: [[S:%.*]] = sub i32 0, [[X]] ; CHECK-NEXT: [[D:%.*]] = select i1 [[C]], i32 [[S]], i32 [[X]] -; CHECK-NEXT: [[R:%.*]] = tail call i32 @llvm.cttz.i32(i32 [[D]], i1 true), !range [[RNG0]] +; CHECK-NEXT: [[R:%.*]] = tail call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[D]], i1 true) ; CHECK-NEXT: ret i32 [[R]] ; %c = icmp slt i32 %x, 2 @@ -156,7 +156,7 @@ define i32 @no_cttz_abs2(i32 %x) { ; CHECK-NEXT: [[C:%.*]] = icmp slt i32 [[X:%.*]], 0 ; CHECK-NEXT: [[S:%.*]] = sub i32 1, [[X]] ; CHECK-NEXT: [[D:%.*]] = select i1 [[C]], i32 [[S]], i32 [[X]] -; CHECK-NEXT: [[R:%.*]] = tail call i32 @llvm.cttz.i32(i32 [[D]], i1 true), !range [[RNG0]] +; CHECK-NEXT: [[R:%.*]] = tail call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[D]], i1 true) ; CHECK-NEXT: ret i32 [[R]] ; %c = icmp slt i32 %x, 0 @@ -172,7 +172,7 @@ define i32 @no_cttz_abs3(i32 %x) { ; CHECK-NEXT: call void @use_cond(i1 [[C]]) ; CHECK-NEXT: [[S:%.*]] = sub i32 0, [[X]] ; CHECK-NEXT: [[D:%.*]] = select i1 [[C]], i32 [[X]], i32 [[S]] -; CHECK-NEXT: [[R:%.*]] = tail call i32 @llvm.cttz.i32(i32 [[D]], i1 true), !range [[RNG0]] +; CHECK-NEXT: [[R:%.*]] = tail call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[D]], i1 true) ; CHECK-NEXT: ret i32 [[R]] ; %c = icmp sgt i32 %x, -2 @@ -188,7 +188,7 @@ define <2 x i64> @no_cttz_abs_vec(<2 x i64> %x) { ; CHECK-NEXT: [[C:%.*]] = icmp slt <2 x i64> [[X:%.*]], ; CHECK-NEXT: [[S:%.*]] = sub <2 x i64> , [[X]] ; CHECK-NEXT: [[D:%.*]] = select <2 x i1> [[C]], <2 x i64> [[S]], <2 x i64> [[X]] -; CHECK-NEXT: [[R:%.*]] = call <2 x i64> @llvm.cttz.v2i64(<2 x i64> [[D]], i1 false), !range [[RNG1]] +; CHECK-NEXT: [[R:%.*]] = call range(i64 0, 65) <2 x i64> @llvm.cttz.v2i64(<2 x i64> [[D]], i1 false) ; CHECK-NEXT: ret <2 x i64> [[R]] ; %c = icmp slt <2 x i64> %x, @@ -203,7 +203,7 @@ define <2 x i64> @no_cttz_nabs_vec(<2 x i64> %x) { ; CHECK-NEXT: [[C:%.*]] = icmp slt <2 x i64> [[X:%.*]], ; CHECK-NEXT: [[S:%.*]] = sub <2 x i64> , [[X]] ; CHECK-NEXT: [[D:%.*]] = select <2 x i1> [[C]], <2 x i64> [[X]], <2 x i64> [[S]] -; CHECK-NEXT: [[R:%.*]] = call <2 x i64> @llvm.cttz.v2i64(<2 x i64> [[D]], i1 false), !range [[RNG1]] +; CHECK-NEXT: [[R:%.*]] = call range(i64 0, 65) <2 x i64> @llvm.cttz.v2i64(<2 x i64> [[D]], i1 false) ; CHECK-NEXT: ret <2 x i64> [[R]] ; %c = icmp slt <2 x i64> %x, @@ -215,7 +215,7 @@ define <2 x i64> @no_cttz_nabs_vec(<2 x i64> %x) { define i32 @cttz_abs_intrin(i32 %x) { ; CHECK-LABEL: @cttz_abs_intrin( -; CHECK-NEXT: [[R:%.*]] = call i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[R:%.*]] = call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 false) ; CHECK-NEXT: ret i32 [[R]] ; %a = call i32 @llvm.abs.i32(i32 %x, i1 false) @@ -225,7 +225,7 @@ define i32 @cttz_abs_intrin(i32 %x) { define i32 @cttz_nabs_intrin(i32 %x) { ; CHECK-LABEL: @cttz_nabs_intrin( -; CHECK-NEXT: [[R:%.*]] = call i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[R:%.*]] = call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 false) ; CHECK-NEXT: ret i32 [[R]] ; %a = call i32 @llvm.abs.i32(i32 %x, i1 false) diff --git a/llvm/test/Transforms/InstCombine/cttz-negative.ll b/llvm/test/Transforms/InstCombine/cttz-negative.ll index 139da840af9e4efb536de5cb89d3bf141b3c3d41..6f812e420935db9da70d3a1ff963ca12b692f6a7 100644 --- a/llvm/test/Transforms/InstCombine/cttz-negative.ll +++ b/llvm/test/Transforms/InstCombine/cttz-negative.ll @@ -3,7 +3,7 @@ define i32 @cttz_neg_value(i32 %x) { ; CHECK-LABEL: @cttz_neg_value( -; CHECK-NEXT: [[B:%.*]] = call i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 false), !range [[RNG0:![0-9]+]] +; CHECK-NEXT: [[B:%.*]] = call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 false) ; CHECK-NEXT: ret i32 [[B]] ; %a = sub i32 0, %x @@ -15,7 +15,7 @@ define i32 @cttz_neg_value_multiuse(i32 %x) { ; CHECK-LABEL: @cttz_neg_value_multiuse( ; CHECK-NEXT: [[A:%.*]] = sub i32 0, [[X:%.*]] ; CHECK-NEXT: call void @use(i32 [[A]]) -; CHECK-NEXT: [[B:%.*]] = call i32 @llvm.cttz.i32(i32 [[X]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[B:%.*]] = call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[X]], i1 false) ; CHECK-NEXT: ret i32 [[B]] ; %a = sub i32 0, %x @@ -26,7 +26,7 @@ define i32 @cttz_neg_value_multiuse(i32 %x) { define i64 @cttz_neg_value_64(i64 %x) { ; CHECK-LABEL: @cttz_neg_value_64( -; CHECK-NEXT: [[B:%.*]] = tail call i64 @llvm.cttz.i64(i64 [[X:%.*]], i1 true), !range [[RNG1:![0-9]+]] +; CHECK-NEXT: [[B:%.*]] = tail call range(i64 0, 65) i64 @llvm.cttz.i64(i64 [[X:%.*]], i1 true) ; CHECK-NEXT: ret i64 [[B]] ; %a = sub i64 0, %x @@ -36,7 +36,7 @@ define i64 @cttz_neg_value_64(i64 %x) { define i64 @cttz_neg_value2_64(i64 %x) { ; CHECK-LABEL: @cttz_neg_value2_64( -; CHECK-NEXT: [[B:%.*]] = tail call i64 @llvm.cttz.i64(i64 [[X:%.*]], i1 false), !range [[RNG1]] +; CHECK-NEXT: [[B:%.*]] = tail call range(i64 0, 65) i64 @llvm.cttz.i64(i64 [[X:%.*]], i1 false) ; CHECK-NEXT: ret i64 [[B]] ; %a = sub i64 0, %x @@ -46,7 +46,7 @@ define i64 @cttz_neg_value2_64(i64 %x) { define <2 x i64> @cttz_neg_value_vec(<2 x i64> %x) { ; CHECK-LABEL: @cttz_neg_value_vec( -; CHECK-NEXT: [[B:%.*]] = call <2 x i64> @llvm.cttz.v2i64(<2 x i64> [[X:%.*]], i1 false), !range [[RNG1]] +; CHECK-NEXT: [[B:%.*]] = call range(i64 0, 65) <2 x i64> @llvm.cttz.v2i64(<2 x i64> [[X:%.*]], i1 false) ; CHECK-NEXT: ret <2 x i64> [[B]] ; %a = sub <2 x i64> zeroinitializer, %x @@ -59,7 +59,7 @@ define <2 x i64> @cttz_neg_value_vec(<2 x i64> %x) { define i32 @cttz_nonneg_value(i32 %x) { ; CHECK-LABEL: @cttz_nonneg_value( ; CHECK-NEXT: [[A:%.*]] = sub i32 1, [[X:%.*]] -; CHECK-NEXT: [[B:%.*]] = call i32 @llvm.cttz.i32(i32 [[A]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[B:%.*]] = call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[A]], i1 false) ; CHECK-NEXT: ret i32 [[B]] ; %a = sub i32 1, %x @@ -70,7 +70,7 @@ define i32 @cttz_nonneg_value(i32 %x) { define <2 x i64> @cttz_nonneg_value_vec(<2 x i64> %x) { ; CHECK-LABEL: @cttz_nonneg_value_vec( ; CHECK-NEXT: [[A:%.*]] = sub <2 x i64> , [[X:%.*]] -; CHECK-NEXT: [[B:%.*]] = call <2 x i64> @llvm.cttz.v2i64(<2 x i64> [[A]], i1 false), !range [[RNG1]] +; CHECK-NEXT: [[B:%.*]] = call range(i64 0, 65) <2 x i64> @llvm.cttz.v2i64(<2 x i64> [[A]], i1 false) ; CHECK-NEXT: ret <2 x i64> [[B]] ; %a = sub <2 x i64> , %x diff --git a/llvm/test/Transforms/InstCombine/cttz.ll b/llvm/test/Transforms/InstCombine/cttz.ll index 6ea5e5e141b2edfe0bda80defb1e8f1bc6186c7e..3595cff5f1aed062c923989bb86e04483b00f640 100644 --- a/llvm/test/Transforms/InstCombine/cttz.ll +++ b/llvm/test/Transforms/InstCombine/cttz.ll @@ -8,7 +8,7 @@ declare void @use(i32) define i32 @cttz_zext_zero_undef(i16 %x) { ; CHECK-LABEL: @cttz_zext_zero_undef( -; CHECK-NEXT: [[TMP1:%.*]] = call i16 @llvm.cttz.i16(i16 [[X:%.*]], i1 true), !range [[RNG0:![0-9]+]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i16 0, 17) i16 @llvm.cttz.i16(i16 [[X:%.*]], i1 true) ; CHECK-NEXT: [[TZ:%.*]] = zext nneg i16 [[TMP1]] to i32 ; CHECK-NEXT: ret i32 [[TZ]] ; @@ -20,7 +20,7 @@ define i32 @cttz_zext_zero_undef(i16 %x) { define i32 @cttz_zext_zero_def(i16 %x) { ; CHECK-LABEL: @cttz_zext_zero_def( ; CHECK-NEXT: [[Z:%.*]] = zext i16 [[X:%.*]] to i32 -; CHECK-NEXT: [[TZ:%.*]] = call i32 @llvm.cttz.i32(i32 [[Z]], i1 false), !range [[RNG1:![0-9]+]] +; CHECK-NEXT: [[TZ:%.*]] = call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[Z]], i1 false) ; CHECK-NEXT: ret i32 [[TZ]] ; %z = zext i16 %x to i32 @@ -32,7 +32,7 @@ define i32 @cttz_zext_zero_undef_extra_use(i16 %x) { ; CHECK-LABEL: @cttz_zext_zero_undef_extra_use( ; CHECK-NEXT: [[Z:%.*]] = zext i16 [[X:%.*]] to i32 ; CHECK-NEXT: call void @use(i32 [[Z]]) -; CHECK-NEXT: [[TZ:%.*]] = call i32 @llvm.cttz.i32(i32 [[Z]], i1 true), !range [[RNG1]] +; CHECK-NEXT: [[TZ:%.*]] = call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[Z]], i1 true) ; CHECK-NEXT: ret i32 [[TZ]] ; %z = zext i16 %x to i32 @@ -43,7 +43,7 @@ define i32 @cttz_zext_zero_undef_extra_use(i16 %x) { define <2 x i64> @cttz_zext_zero_undef_vec(<2 x i32> %x) { ; CHECK-LABEL: @cttz_zext_zero_undef_vec( -; CHECK-NEXT: [[TMP1:%.*]] = call <2 x i32> @llvm.cttz.v2i32(<2 x i32> [[X:%.*]], i1 true), !range [[RNG1]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i32 0, 33) <2 x i32> @llvm.cttz.v2i32(<2 x i32> [[X:%.*]], i1 true) ; CHECK-NEXT: [[TZ:%.*]] = zext nneg <2 x i32> [[TMP1]] to <2 x i64> ; CHECK-NEXT: ret <2 x i64> [[TZ]] ; @@ -55,7 +55,7 @@ define <2 x i64> @cttz_zext_zero_undef_vec(<2 x i32> %x) { define <2 x i64> @cttz_zext_zero_def_vec(<2 x i32> %x) { ; CHECK-LABEL: @cttz_zext_zero_def_vec( ; CHECK-NEXT: [[Z:%.*]] = zext <2 x i32> [[X:%.*]] to <2 x i64> -; CHECK-NEXT: [[TZ:%.*]] = tail call <2 x i64> @llvm.cttz.v2i64(<2 x i64> [[Z]], i1 false), !range [[RNG2:![0-9]+]] +; CHECK-NEXT: [[TZ:%.*]] = tail call range(i64 0, 65) <2 x i64> @llvm.cttz.v2i64(<2 x i64> [[Z]], i1 false) ; CHECK-NEXT: ret <2 x i64> [[TZ]] ; %z = zext <2 x i32> %x to <2 x i64> @@ -65,7 +65,7 @@ define <2 x i64> @cttz_zext_zero_def_vec(<2 x i32> %x) { define i32 @cttz_sext_zero_undef(i16 %x) { ; CHECK-LABEL: @cttz_sext_zero_undef( -; CHECK-NEXT: [[TMP1:%.*]] = call i16 @llvm.cttz.i16(i16 [[X:%.*]], i1 true), !range [[RNG0]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i16 0, 17) i16 @llvm.cttz.i16(i16 [[X:%.*]], i1 true) ; CHECK-NEXT: [[TZ:%.*]] = zext nneg i16 [[TMP1]] to i32 ; CHECK-NEXT: ret i32 [[TZ]] ; @@ -77,7 +77,7 @@ define i32 @cttz_sext_zero_undef(i16 %x) { define i32 @cttz_sext_zero_def(i16 %x) { ; CHECK-LABEL: @cttz_sext_zero_def( ; CHECK-NEXT: [[TMP1:%.*]] = zext i16 [[X:%.*]] to i32 -; CHECK-NEXT: [[TZ:%.*]] = call i32 @llvm.cttz.i32(i32 [[TMP1]], i1 false), !range [[RNG1]] +; CHECK-NEXT: [[TZ:%.*]] = call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[TMP1]], i1 false) ; CHECK-NEXT: ret i32 [[TZ]] ; %s = sext i16 %x to i32 @@ -89,7 +89,7 @@ define i32 @cttz_sext_zero_undef_extra_use(i16 %x) { ; CHECK-LABEL: @cttz_sext_zero_undef_extra_use( ; CHECK-NEXT: [[S:%.*]] = sext i16 [[X:%.*]] to i32 ; CHECK-NEXT: call void @use(i32 [[S]]) -; CHECK-NEXT: [[TZ:%.*]] = call i32 @llvm.cttz.i32(i32 [[S]], i1 true), !range [[RNG1]] +; CHECK-NEXT: [[TZ:%.*]] = call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[S]], i1 true) ; CHECK-NEXT: ret i32 [[TZ]] ; %s = sext i16 %x to i32 @@ -100,7 +100,7 @@ define i32 @cttz_sext_zero_undef_extra_use(i16 %x) { define <2 x i64> @cttz_sext_zero_undef_vec(<2 x i32> %x) { ; CHECK-LABEL: @cttz_sext_zero_undef_vec( -; CHECK-NEXT: [[TMP1:%.*]] = call <2 x i32> @llvm.cttz.v2i32(<2 x i32> [[X:%.*]], i1 true), !range [[RNG1]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i32 0, 33) <2 x i32> @llvm.cttz.v2i32(<2 x i32> [[X:%.*]], i1 true) ; CHECK-NEXT: [[TZ:%.*]] = zext nneg <2 x i32> [[TMP1]] to <2 x i64> ; CHECK-NEXT: ret <2 x i64> [[TZ]] ; @@ -112,7 +112,7 @@ define <2 x i64> @cttz_sext_zero_undef_vec(<2 x i32> %x) { define <2 x i64> @cttz_sext_zero_def_vec(<2 x i32> %x) { ; CHECK-LABEL: @cttz_sext_zero_def_vec( ; CHECK-NEXT: [[TMP1:%.*]] = zext <2 x i32> [[X:%.*]] to <2 x i64> -; CHECK-NEXT: [[TZ:%.*]] = call <2 x i64> @llvm.cttz.v2i64(<2 x i64> [[TMP1]], i1 false), !range [[RNG2]] +; CHECK-NEXT: [[TZ:%.*]] = call range(i64 0, 65) <2 x i64> @llvm.cttz.v2i64(<2 x i64> [[TMP1]], i1 false) ; CHECK-NEXT: ret <2 x i64> [[TZ]] ; %s = sext <2 x i32> %x to <2 x i64> @@ -122,7 +122,7 @@ define <2 x i64> @cttz_sext_zero_def_vec(<2 x i32> %x) { define i32 @cttz_of_lowest_set_bit(i32 %x) { ; CHECK-LABEL: @cttz_of_lowest_set_bit( -; CHECK-NEXT: [[TZ:%.*]] = call i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 false), !range [[RNG1]] +; CHECK-NEXT: [[TZ:%.*]] = call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 false) ; CHECK-NEXT: ret i32 [[TZ]] ; %sub = sub i32 0, %x @@ -134,7 +134,7 @@ define i32 @cttz_of_lowest_set_bit(i32 %x) { define i32 @cttz_of_lowest_set_bit_commuted(i32 %xx) { ; CHECK-LABEL: @cttz_of_lowest_set_bit_commuted( ; CHECK-NEXT: [[X:%.*]] = udiv i32 42, [[XX:%.*]] -; CHECK-NEXT: [[TZ:%.*]] = call i32 @llvm.cttz.i32(i32 [[X]], i1 false), !range [[RNG1]] +; CHECK-NEXT: [[TZ:%.*]] = call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[X]], i1 false) ; CHECK-NEXT: ret i32 [[TZ]] ; %x = udiv i32 42, %xx ; thwart complexity-based canonicalization @@ -146,7 +146,7 @@ define i32 @cttz_of_lowest_set_bit_commuted(i32 %xx) { define i32 @cttz_of_lowest_set_bit_poison_flag(i32 %x) { ; CHECK-LABEL: @cttz_of_lowest_set_bit_poison_flag( -; CHECK-NEXT: [[TZ:%.*]] = call i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 true), !range [[RNG1]] +; CHECK-NEXT: [[TZ:%.*]] = call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 true) ; CHECK-NEXT: ret i32 [[TZ]] ; %sub = sub i32 0, %x @@ -157,7 +157,7 @@ define i32 @cttz_of_lowest_set_bit_poison_flag(i32 %x) { define <2 x i64> @cttz_of_lowest_set_bit_vec(<2 x i64> %x) { ; CHECK-LABEL: @cttz_of_lowest_set_bit_vec( -; CHECK-NEXT: [[TZ:%.*]] = call <2 x i64> @llvm.cttz.v2i64(<2 x i64> [[X:%.*]], i1 false), !range [[RNG2]] +; CHECK-NEXT: [[TZ:%.*]] = call range(i64 0, 65) <2 x i64> @llvm.cttz.v2i64(<2 x i64> [[X:%.*]], i1 false) ; CHECK-NEXT: ret <2 x i64> [[TZ]] ; %sub = sub <2 x i64> zeroinitializer, %x @@ -168,7 +168,7 @@ define <2 x i64> @cttz_of_lowest_set_bit_vec(<2 x i64> %x) { define <2 x i64> @cttz_of_lowest_set_bit_vec_undef(<2 x i64> %x) { ; CHECK-LABEL: @cttz_of_lowest_set_bit_vec_undef( -; CHECK-NEXT: [[TZ:%.*]] = call <2 x i64> @llvm.cttz.v2i64(<2 x i64> [[X:%.*]], i1 false), !range [[RNG2]] +; CHECK-NEXT: [[TZ:%.*]] = call range(i64 0, 65) <2 x i64> @llvm.cttz.v2i64(<2 x i64> [[X:%.*]], i1 false) ; CHECK-NEXT: ret <2 x i64> [[TZ]] ; %sub = sub <2 x i64> zeroinitializer, %x @@ -181,7 +181,7 @@ define i32 @cttz_of_lowest_set_bit_wrong_const(i32 %x) { ; CHECK-LABEL: @cttz_of_lowest_set_bit_wrong_const( ; CHECK-NEXT: [[SUB:%.*]] = sub i32 1, [[X:%.*]] ; CHECK-NEXT: [[AND:%.*]] = and i32 [[SUB]], [[X]] -; CHECK-NEXT: [[TZ:%.*]] = call i32 @llvm.cttz.i32(i32 [[AND]], i1 false), !range [[RNG3:![0-9]+]] +; CHECK-NEXT: [[TZ:%.*]] = call range(i32 1, 33) i32 @llvm.cttz.i32(i32 [[AND]], i1 false) ; CHECK-NEXT: ret i32 [[TZ]] ; %sub = sub i32 1, %x @@ -194,7 +194,7 @@ define i32 @cttz_of_lowest_set_bit_wrong_operand(i32 %x, i32 %y) { ; CHECK-LABEL: @cttz_of_lowest_set_bit_wrong_operand( ; CHECK-NEXT: [[SUB:%.*]] = sub i32 0, [[Y:%.*]] ; CHECK-NEXT: [[AND:%.*]] = and i32 [[SUB]], [[X:%.*]] -; CHECK-NEXT: [[TZ:%.*]] = call i32 @llvm.cttz.i32(i32 [[AND]], i1 false), !range [[RNG1]] +; CHECK-NEXT: [[TZ:%.*]] = call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[AND]], i1 false) ; CHECK-NEXT: ret i32 [[TZ]] ; %sub = sub i32 0, %y @@ -207,7 +207,7 @@ define i32 @cttz_of_lowest_set_bit_wrong_intrinsic(i32 %x) { ; CHECK-LABEL: @cttz_of_lowest_set_bit_wrong_intrinsic( ; CHECK-NEXT: [[SUB:%.*]] = sub i32 0, [[X:%.*]] ; CHECK-NEXT: [[AND:%.*]] = and i32 [[SUB]], [[X]] -; CHECK-NEXT: [[TZ:%.*]] = call i32 @llvm.ctlz.i32(i32 [[AND]], i1 false), !range [[RNG1]] +; CHECK-NEXT: [[TZ:%.*]] = call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[AND]], i1 false) ; CHECK-NEXT: ret i32 [[TZ]] ; %sub = sub i32 0, %x diff --git a/llvm/test/Transforms/InstCombine/ffs-1.ll b/llvm/test/Transforms/InstCombine/ffs-1.ll index 7cf080765bb1b6857f1dfee724ccef2056eaa01e..db01801b1225cd36c1073b473680c296ee383791 100644 --- a/llvm/test/Transforms/InstCombine/ffs-1.ll +++ b/llvm/test/Transforms/InstCombine/ffs-1.ll @@ -148,7 +148,7 @@ define i32 @test_simplify12() { define i32 @test_simplify13(i32 %x) { ; ALL-LABEL: @test_simplify13( -; ALL-NEXT: [[CTTZ:%.*]] = call i32 @llvm.cttz.i32(i32 %x, i1 true), !range !0 +; ALL-NEXT: [[CTTZ:%.*]] = call range(i32 0, 33) i32 @llvm.cttz.i32(i32 %x, i1 true) ; ALL-NEXT: [[TMP1:%.*]] = add nuw nsw i32 [[CTTZ]], 1 ; ALL-NEXT: [[TMP2:%.*]] = icmp eq i32 %x, 0 ; ALL-NEXT: [[TMP3:%.*]] = select i1 [[TMP2]], i32 0, i32 [[TMP1]] @@ -164,7 +164,7 @@ define i32 @test_simplify14(i32 %x) { ; GENERIC-NEXT: ret i32 [[RET]] ; ; TARGET-LABEL: @test_simplify14( -; TARGET-NEXT: [[CTTZ:%.*]] = call i32 @llvm.cttz.i32(i32 %x, i1 true), !range !0 +; TARGET-NEXT: [[CTTZ:%.*]] = call range(i32 0, 33) i32 @llvm.cttz.i32(i32 %x, i1 true) ; TARGET-NEXT: [[TMP1:%.*]] = add nuw nsw i32 [[CTTZ]], 1 ; TARGET-NEXT: [[TMP2:%.*]] = icmp eq i32 %x, 0 ; TARGET-NEXT: [[TMP3:%.*]] = select i1 [[TMP2]], i32 0, i32 [[TMP1]] @@ -180,7 +180,7 @@ define i32 @test_simplify15(i64 %x) { ; GENERIC-NEXT: ret i32 [[RET]] ; ; TARGET-LABEL: @test_simplify15( -; TARGET-NEXT: [[CTTZ:%.*]] = call i64 @llvm.cttz.i64(i64 %x, i1 true), !range !1 +; TARGET-NEXT: [[CTTZ:%.*]] = call range(i64 0, 65) i64 @llvm.cttz.i64(i64 %x, i1 true) ; TARGET-NEXT: [[TMP1:%.*]] = trunc nuw nsw i64 [[CTTZ]] to i32 ; TARGET-NEXT: [[TMP2:%.*]] = add nuw nsw i32 [[TMP1]], 1 ; TARGET-NEXT: [[TMP3:%.*]] = icmp eq i64 %x, 0 diff --git a/llvm/test/Transforms/InstCombine/ffs-i16.ll b/llvm/test/Transforms/InstCombine/ffs-i16.ll index f2b1f074f86d562d41aa8f047411ec2e65734132..ab5f1307f4d9d33e4acde3477be75e389233447e 100644 --- a/llvm/test/Transforms/InstCombine/ffs-i16.ll +++ b/llvm/test/Transforms/InstCombine/ffs-i16.ll @@ -17,7 +17,7 @@ define void @fold_ffs(i16 %x) { ; AVR-LABEL: @fold_ffs( ; AVR-NEXT: call addrspace(1) void @sink(i16 0) ; AVR-NEXT: call addrspace(1) void @sink(i16 1) -; AVR-NEXT: [[CTTZ:%.*]] = call addrspace(1) i16 @llvm.cttz.i16(i16 [[X:%.*]], i1 true), !range [[RNG0:![0-9]+]] +; AVR-NEXT: [[CTTZ:%.*]] = call range(i16 0, 17) addrspace(1) i16 @llvm.cttz.i16(i16 [[X:%.*]], i1 true) ; AVR-NEXT: [[TMP1:%.*]] = add nuw nsw i16 [[CTTZ]], 1 ; AVR-NEXT: [[DOTNOT:%.*]] = icmp eq i16 [[X]], 0 ; AVR-NEXT: [[NX:%.*]] = select i1 [[DOTNOT]], i16 0, i16 [[TMP1]] @@ -27,7 +27,7 @@ define void @fold_ffs(i16 %x) { ; MSP430-LABEL: @fold_ffs( ; MSP430-NEXT: call void @sink(i16 0) ; MSP430-NEXT: call void @sink(i16 1) -; MSP430-NEXT: [[CTTZ:%.*]] = call i16 @llvm.cttz.i16(i16 [[X:%.*]], i1 true), !range [[RNG0:![0-9]+]] +; MSP430-NEXT: [[CTTZ:%.*]] = call range(i16 0, 17) i16 @llvm.cttz.i16(i16 [[X:%.*]], i1 true) ; MSP430-NEXT: [[TMP1:%.*]] = add nuw nsw i16 [[CTTZ]], 1 ; MSP430-NEXT: [[DOTNOT:%.*]] = icmp eq i16 [[X]], 0 ; MSP430-NEXT: [[NX:%.*]] = select i1 [[DOTNOT]], i16 0, i16 [[TMP1]] diff --git a/llvm/test/Transforms/InstCombine/fls-i16.ll b/llvm/test/Transforms/InstCombine/fls-i16.ll index 54692fde5303ebcde85b2761b3460b05345b4461..e48397f5116a4b6c08c4070900608ba5c43efc81 100644 --- a/llvm/test/Transforms/InstCombine/fls-i16.ll +++ b/llvm/test/Transforms/InstCombine/fls-i16.ll @@ -17,7 +17,7 @@ define void @fold_fls(i16 %x) { ; AVR-LABEL: @fold_fls( ; AVR-NEXT: call addrspace(1) void @sink(i16 0) ; AVR-NEXT: call addrspace(1) void @sink(i16 1) -; AVR-NEXT: [[CTLZ:%.*]] = call addrspace(1) i16 @llvm.ctlz.i16(i16 [[X:%.*]], i1 false), !range [[RNG0:![0-9]+]] +; AVR-NEXT: [[CTLZ:%.*]] = call range(i16 0, 17) addrspace(1) i16 @llvm.ctlz.i16(i16 [[X:%.*]], i1 false) ; AVR-NEXT: [[NX:%.*]] = sub nuw nsw i16 16, [[CTLZ]] ; AVR-NEXT: call addrspace(1) void @sink(i16 [[NX]]) ; AVR-NEXT: ret void @@ -25,7 +25,7 @@ define void @fold_fls(i16 %x) { ; MSP430-LABEL: @fold_fls( ; MSP430-NEXT: call void @sink(i16 0) ; MSP430-NEXT: call void @sink(i16 1) -; MSP430-NEXT: [[CTLZ:%.*]] = call i16 @llvm.ctlz.i16(i16 [[X:%.*]], i1 false), !range [[RNG0:![0-9]+]] +; MSP430-NEXT: [[CTLZ:%.*]] = call range(i16 0, 17) i16 @llvm.ctlz.i16(i16 [[X:%.*]], i1 false) ; MSP430-NEXT: [[NX:%.*]] = sub nuw nsw i16 16, [[CTLZ]] ; MSP430-NEXT: call void @sink(i16 [[NX]]) ; MSP430-NEXT: ret void diff --git a/llvm/test/Transforms/InstCombine/fls.ll b/llvm/test/Transforms/InstCombine/fls.ll index 7710093e195a11f0c2ac53de84802ff4d53e7389..68bc0a2fc8a1d195e7b855c112a957e814605f96 100644 --- a/llvm/test/Transforms/InstCombine/fls.ll +++ b/llvm/test/Transforms/InstCombine/fls.ll @@ -31,7 +31,7 @@ define i32 @myflsll() { define i32 @flsnotconst(i64 %z) { ; CHECK-LABEL: @flsnotconst( -; CHECK-NEXT: [[CTLZ:%.*]] = call i64 @llvm.ctlz.i64(i64 [[Z:%.*]], i1 false), !range [[RNG0:![0-9]+]] +; CHECK-NEXT: [[CTLZ:%.*]] = call range(i64 0, 65) i64 @llvm.ctlz.i64(i64 [[Z:%.*]], i1 false) ; CHECK-NEXT: [[TMP1:%.*]] = trunc nuw nsw i64 [[CTLZ]] to i32 ; CHECK-NEXT: [[GOO:%.*]] = sub nsw i32 64, [[TMP1]] ; CHECK-NEXT: ret i32 [[GOO]] diff --git a/llvm/test/Transforms/InstCombine/fneg.ll b/llvm/test/Transforms/InstCombine/fneg.ll index 7c9289c447113fc42f025c62fd34e90ffe21dd99..3c4088832feaaa6ed29d64576529c686aa817a30 100644 --- a/llvm/test/Transforms/InstCombine/fneg.ll +++ b/llvm/test/Transforms/InstCombine/fneg.ll @@ -980,7 +980,7 @@ define float @fneg_ldexp_contract(float %x, i32 %n) { define float @fneg_ldexp_metadata(float %x, i32 %n) { ; CHECK-LABEL: @fneg_ldexp_metadata( ; CHECK-NEXT: [[TMP1:%.*]] = fneg float [[X:%.*]] -; CHECK-NEXT: [[NEG:%.*]] = call float @llvm.ldexp.f32.i32(float [[TMP1]], i32 [[N:%.*]]), !arst !0 +; CHECK-NEXT: [[NEG:%.*]] = call float @llvm.ldexp.f32.i32(float [[TMP1]], i32 [[N:%.*]]), !arst [[META0:![0-9]+]] ; CHECK-NEXT: ret float [[NEG]] ; %ldexp = call float @llvm.ldexp.f32.i32(float %x, i32 %n), !arst !0 @@ -988,4 +988,125 @@ define float @fneg_ldexp_metadata(float %x, i32 %n) { ret float %neg } +define float @test_fneg_select_constants(i1 %cond) { +; CHECK-LABEL: @test_fneg_select_constants( +; CHECK-NEXT: [[NEG:%.*]] = select i1 [[COND:%.*]], float -0.000000e+00, float 0.000000e+00 +; CHECK-NEXT: ret float [[NEG]] +; + %sel1 = select i1 %cond, float 0.0, float -0.0 + %neg = fneg float %sel1 + ret float %neg +} + +define <2 x float> @test_fneg_vec(<2 x i1> %cond) { +; CHECK-LABEL: @test_fneg_vec( +; CHECK-NEXT: [[NEG:%.*]] = select <2 x i1> [[COND:%.*]], <2 x float> , <2 x float> +; CHECK-NEXT: ret <2 x float> [[NEG]] +; + %sel1 = select <2 x i1> %cond, <2 x float> , <2 x float> + %neg = fneg <2 x float> %sel1 + ret <2 x float> %neg +} + +define float @test_fneg_select_var_constant(i1 %cond, float %x) { +; CHECK-LABEL: @test_fneg_select_var_constant( +; CHECK-NEXT: [[X_NEG:%.*]] = fneg float [[X:%.*]] +; CHECK-NEXT: [[NEG:%.*]] = select i1 [[COND:%.*]], float [[X_NEG]], float 0.000000e+00 +; CHECK-NEXT: ret float [[NEG]] +; + %sel1 = select i1 %cond, float %x, float -0.0 + %neg = fneg float %sel1 + ret float %neg +} + +; nsz can be preserved. + +define float @test_fneg_select_var_constant_fmf1(i1 %cond, float %x) { +; CHECK-LABEL: @test_fneg_select_var_constant_fmf1( +; CHECK-NEXT: [[X_NEG:%.*]] = fneg float [[X:%.*]] +; CHECK-NEXT: [[NEG:%.*]] = select nnan ninf nsz i1 [[COND:%.*]], float [[X_NEG]], float -1.000000e+00 +; CHECK-NEXT: ret float [[NEG]] +; + %sel1 = select nnan ninf nsz i1 %cond, float %x, float 1.0 + %neg = fneg float %sel1 + ret float %neg +} + +define float @test_fneg_select_var_constant_fmf2(i1 %cond, float %x) { +; CHECK-LABEL: @test_fneg_select_var_constant_fmf2( +; CHECK-NEXT: [[X_NEG:%.*]] = fneg nnan ninf nsz float [[X:%.*]] +; CHECK-NEXT: [[NEG:%.*]] = select nnan ninf nsz i1 [[COND:%.*]], float [[X_NEG]], float -1.000000e+00 +; CHECK-NEXT: ret float [[NEG]] +; + %sel1 = select i1 %cond, float %x, float 1.0 + %neg = fneg nnan ninf nsz float %sel1 + ret float %neg +} + +define float @test_fneg_select_constant_var(i1 %cond, float %x) { +; CHECK-LABEL: @test_fneg_select_constant_var( +; CHECK-NEXT: [[X_NEG:%.*]] = fneg float [[X:%.*]] +; CHECK-NEXT: [[NEG:%.*]] = select i1 [[COND:%.*]], float -0.000000e+00, float [[X_NEG]] +; CHECK-NEXT: ret float [[NEG]] +; + %sel1 = select i1 %cond, float 0.0, float %x + %neg = fneg float %sel1 + ret float %neg +} + +; Make sure nabs is generated. + +define float @test_fneg_select_abs(i1 %cond, float %x) { +; CHECK-LABEL: @test_fneg_select_abs( +; CHECK-NEXT: [[ABSX:%.*]] = call float @llvm.fabs.f32(float [[X:%.*]]) +; CHECK-NEXT: [[ABSX_NEG:%.*]] = fneg float [[ABSX]] +; CHECK-NEXT: [[NEG:%.*]] = select i1 [[COND:%.*]], float -0.000000e+00, float [[ABSX_NEG]] +; CHECK-NEXT: ret float [[NEG]] +; + %absx = call float @llvm.fabs.f32(float %x) + %sel1 = select i1 %cond, float 0.0, float %absx + %neg = fneg float %sel1 + ret float %neg +} + +define float @test_fneg_fabs_select(i1 %cond, float %x) { +; CHECK-LABEL: @test_fneg_fabs_select( +; CHECK-NEXT: [[TMP1:%.*]] = call float @llvm.fabs.f32(float [[X:%.*]]) +; CHECK-NEXT: [[DOTNEG:%.*]] = fneg float [[TMP1]] +; CHECK-NEXT: [[NEG:%.*]] = select i1 [[COND:%.*]], float -0.000000e+00, float [[DOTNEG]] +; CHECK-NEXT: ret float [[NEG]] +; + %sel1 = select i1 %cond, float 0.0, float %x + %abs = call float @llvm.fabs.f32(float %sel1) + %neg = fneg float %abs + ret float %neg +} + +define float @test_fneg_select_constant_var_multiuse(i1 %cond, float %x) { +; CHECK-LABEL: @test_fneg_select_constant_var_multiuse( +; CHECK-NEXT: [[SEL1:%.*]] = select i1 [[COND:%.*]], float 0.000000e+00, float [[X:%.*]] +; CHECK-NEXT: call void @use(float [[SEL1]]) +; CHECK-NEXT: [[NEG:%.*]] = fneg float [[SEL1]] +; CHECK-NEXT: ret float [[NEG]] +; + %sel1 = select i1 %cond, float 0.0, float %x + call void @use(float %sel1) + %neg = fneg float %sel1 + ret float %neg +} + +; Don't break fmax idioms. + +define float @test_fneg_select_maxnum(float %x) { +; CHECK-LABEL: @test_fneg_select_maxnum( +; CHECK-NEXT: [[SEL1:%.*]] = call nnan nsz float @llvm.maxnum.f32(float [[X:%.*]], float 1.000000e+00) +; CHECK-NEXT: [[NEG:%.*]] = fneg float [[SEL1]] +; CHECK-NEXT: ret float [[NEG]] +; + %cmp1 = fcmp ogt float %x, 1.0 + %sel1 = select nnan nsz i1 %cmp1, float %x, float 1.0 + %neg = fneg float %sel1 + ret float %neg +} + !0 = !{} diff --git a/llvm/test/Transforms/InstCombine/fold-ctpop-of-not.ll b/llvm/test/Transforms/InstCombine/fold-ctpop-of-not.ll index bbce5c2d625ec8d8eac5e2babfd024b220578986..4626d19bd2899ddde2579fa4ba93178191f28d66 100644 --- a/llvm/test/Transforms/InstCombine/fold-ctpop-of-not.ll +++ b/llvm/test/Transforms/InstCombine/fold-ctpop-of-not.ll @@ -8,7 +8,7 @@ declare <2 x i8> @llvm.ctpop.v2i8(<2 x i8>) define i8 @fold_sub_c_ctpop(i8 %x) { ; CHECK-LABEL: @fold_sub_c_ctpop( -; CHECK-NEXT: [[TMP1:%.*]] = call i8 @llvm.ctpop.i8(i8 [[X:%.*]]), !range [[RNG0:![0-9]+]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i8 0, 9) i8 @llvm.ctpop.i8(i8 [[X:%.*]]) ; CHECK-NEXT: [[R:%.*]] = add nuw nsw i8 [[TMP1]], 4 ; CHECK-NEXT: ret i8 [[R]] ; @@ -21,7 +21,7 @@ define i8 @fold_sub_c_ctpop(i8 %x) { define i8 @fold_sub_var_ctpop_fail(i8 %x, i8 %y) { ; CHECK-LABEL: @fold_sub_var_ctpop_fail( ; CHECK-NEXT: [[NX:%.*]] = xor i8 [[X:%.*]], -1 -; CHECK-NEXT: [[CNT:%.*]] = call i8 @llvm.ctpop.i8(i8 [[NX]]), !range [[RNG0]] +; CHECK-NEXT: [[CNT:%.*]] = call range(i8 0, 9) i8 @llvm.ctpop.i8(i8 [[NX]]) ; CHECK-NEXT: [[R:%.*]] = sub i8 [[Y:%.*]], [[CNT]] ; CHECK-NEXT: ret i8 [[R]] ; @@ -33,7 +33,7 @@ define i8 @fold_sub_var_ctpop_fail(i8 %x, i8 %y) { define <2 x i8> @fold_sub_ctpop_c(<2 x i8> %x) { ; CHECK-LABEL: @fold_sub_ctpop_c( -; CHECK-NEXT: [[TMP1:%.*]] = call <2 x i8> @llvm.ctpop.v2i8(<2 x i8> [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i8 0, 9) <2 x i8> @llvm.ctpop.v2i8(<2 x i8> [[X:%.*]]) ; CHECK-NEXT: [[R:%.*]] = sub nuw nsw <2 x i8> , [[TMP1]] ; CHECK-NEXT: ret <2 x i8> [[R]] ; @@ -45,7 +45,7 @@ define <2 x i8> @fold_sub_ctpop_c(<2 x i8> %x) { define i8 @fold_add_ctpop_c(i8 %x) { ; CHECK-LABEL: @fold_add_ctpop_c( -; CHECK-NEXT: [[TMP1:%.*]] = call i8 @llvm.ctpop.i8(i8 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i8 0, 9) i8 @llvm.ctpop.i8(i8 [[X:%.*]]) ; CHECK-NEXT: [[R:%.*]] = sub nuw nsw i8 71, [[TMP1]] ; CHECK-NEXT: ret i8 [[R]] ; @@ -57,7 +57,7 @@ define i8 @fold_add_ctpop_c(i8 %x) { define i8 @fold_distjoint_or_ctpop_c(i8 %x) { ; CHECK-LABEL: @fold_distjoint_or_ctpop_c( -; CHECK-NEXT: [[TMP1:%.*]] = call i8 @llvm.ctpop.i8(i8 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i8 0, 9) i8 @llvm.ctpop.i8(i8 [[X:%.*]]) ; CHECK-NEXT: [[R:%.*]] = sub nuw nsw i8 72, [[TMP1]] ; CHECK-NEXT: ret i8 [[R]] ; @@ -70,7 +70,7 @@ define i8 @fold_distjoint_or_ctpop_c(i8 %x) { define i8 @fold_or_ctpop_c_fail(i8 %x) { ; CHECK-LABEL: @fold_or_ctpop_c_fail( ; CHECK-NEXT: [[NX:%.*]] = xor i8 [[X:%.*]], -1 -; CHECK-NEXT: [[CNT:%.*]] = call i8 @llvm.ctpop.i8(i8 [[NX]]), !range [[RNG0]] +; CHECK-NEXT: [[CNT:%.*]] = call range(i8 0, 9) i8 @llvm.ctpop.i8(i8 [[NX]]) ; CHECK-NEXT: [[R:%.*]] = or i8 [[CNT]], 65 ; CHECK-NEXT: ret i8 [[R]] ; @@ -83,7 +83,7 @@ define i8 @fold_or_ctpop_c_fail(i8 %x) { define i8 @fold_add_ctpop_var_fail(i8 %x, i8 %y) { ; CHECK-LABEL: @fold_add_ctpop_var_fail( ; CHECK-NEXT: [[NX:%.*]] = xor i8 [[X:%.*]], -1 -; CHECK-NEXT: [[CNT:%.*]] = call i8 @llvm.ctpop.i8(i8 [[NX]]), !range [[RNG0]] +; CHECK-NEXT: [[CNT:%.*]] = call range(i8 0, 9) i8 @llvm.ctpop.i8(i8 [[NX]]) ; CHECK-NEXT: [[R:%.*]] = add i8 [[CNT]], [[Y:%.*]] ; CHECK-NEXT: ret i8 [[R]] ; @@ -105,7 +105,7 @@ define i1 @fold_icmp_sgt_ctpop_c_i2_fail(i2 %x, i2 %C) { define i1 @fold_cmp_eq_ctpop_c(i8 %x) { ; CHECK-LABEL: @fold_cmp_eq_ctpop_c( -; CHECK-NEXT: [[TMP1:%.*]] = call i8 @llvm.ctpop.i8(i8 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i8 0, 9) i8 @llvm.ctpop.i8(i8 [[X:%.*]]) ; CHECK-NEXT: [[R:%.*]] = icmp eq i8 [[TMP1]], 6 ; CHECK-NEXT: ret i1 [[R]] ; @@ -118,7 +118,7 @@ define i1 @fold_cmp_eq_ctpop_c(i8 %x) { define i1 @fold_cmp_eq_ctpop_c_multiuse_fail(i8 %x) { ; CHECK-LABEL: @fold_cmp_eq_ctpop_c_multiuse_fail( ; CHECK-NEXT: [[NX:%.*]] = xor i8 [[X:%.*]], -1 -; CHECK-NEXT: [[CNT:%.*]] = call i8 @llvm.ctpop.i8(i8 [[NX]]), !range [[RNG0]] +; CHECK-NEXT: [[CNT:%.*]] = call range(i8 0, 9) i8 @llvm.ctpop.i8(i8 [[NX]]) ; CHECK-NEXT: [[R:%.*]] = icmp eq i8 [[CNT]], 2 ; CHECK-NEXT: call void @use.i8(i8 [[CNT]]) ; CHECK-NEXT: ret i1 [[R]] @@ -132,7 +132,7 @@ define i1 @fold_cmp_eq_ctpop_c_multiuse_fail(i8 %x) { define <2 x i1> @fold_cmp_ne_ctpop_c(<2 x i8> %x) { ; CHECK-LABEL: @fold_cmp_ne_ctpop_c( -; CHECK-NEXT: [[TMP1:%.*]] = call <2 x i8> @llvm.ctpop.v2i8(<2 x i8> [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i8 0, 9) <2 x i8> @llvm.ctpop.v2i8(<2 x i8> [[X:%.*]]) ; CHECK-NEXT: [[R:%.*]] = icmp ne <2 x i8> [[TMP1]], ; CHECK-NEXT: ret <2 x i1> [[R]] ; @@ -145,7 +145,7 @@ define <2 x i1> @fold_cmp_ne_ctpop_c(<2 x i8> %x) { define <2 x i1> @fold_cmp_ne_ctpop_var_fail(<2 x i8> %x, <2 x i8> %y) { ; CHECK-LABEL: @fold_cmp_ne_ctpop_var_fail( ; CHECK-NEXT: [[NX:%.*]] = xor <2 x i8> [[X:%.*]], -; CHECK-NEXT: [[CNT:%.*]] = call <2 x i8> @llvm.ctpop.v2i8(<2 x i8> [[NX]]), !range [[RNG0]] +; CHECK-NEXT: [[CNT:%.*]] = call range(i8 0, 9) <2 x i8> @llvm.ctpop.v2i8(<2 x i8> [[NX]]) ; CHECK-NEXT: [[R:%.*]] = icmp ne <2 x i8> [[CNT]], [[Y:%.*]] ; CHECK-NEXT: ret <2 x i1> [[R]] ; @@ -159,7 +159,7 @@ define i1 @fold_cmp_ult_ctpop_c(i8 %x, i8 %y, i1 %cond) { ; CHECK-LABEL: @fold_cmp_ult_ctpop_c( ; CHECK-NEXT: [[TMP1:%.*]] = sub i8 -16, [[Y:%.*]] ; CHECK-NEXT: [[TMP2:%.*]] = select i1 [[COND:%.*]], i8 [[X:%.*]], i8 [[TMP1]] -; CHECK-NEXT: [[TMP3:%.*]] = call i8 @llvm.ctpop.i8(i8 [[TMP2]]), !range [[RNG0]] +; CHECK-NEXT: [[TMP3:%.*]] = call range(i8 0, 9) i8 @llvm.ctpop.i8(i8 [[TMP2]]) ; CHECK-NEXT: [[R:%.*]] = icmp ugt i8 [[TMP3]], 3 ; CHECK-NEXT: ret i1 [[R]] ; @@ -175,7 +175,7 @@ define i1 @fold_cmp_sle_ctpop_c(i8 %x, i8 %y, i1 %cond) { ; CHECK-LABEL: @fold_cmp_sle_ctpop_c( ; CHECK-NEXT: [[TMP1:%.*]] = sub i8 -16, [[Y:%.*]] ; CHECK-NEXT: [[TMP2:%.*]] = select i1 [[COND:%.*]], i8 [[X:%.*]], i8 [[TMP1]] -; CHECK-NEXT: [[TMP3:%.*]] = call i8 @llvm.ctpop.i8(i8 [[TMP2]]), !range [[RNG0]] +; CHECK-NEXT: [[TMP3:%.*]] = call range(i8 0, 9) i8 @llvm.ctpop.i8(i8 [[TMP2]]) ; CHECK-NEXT: [[R:%.*]] = icmp ugt i8 [[TMP3]], 4 ; CHECK-NEXT: ret i1 [[R]] ; @@ -190,7 +190,7 @@ define i1 @fold_cmp_sle_ctpop_c(i8 %x, i8 %y, i1 %cond) { define i1 @fold_cmp_ult_ctpop_c_no_not_inst_save_fail(i8 %x) { ; CHECK-LABEL: @fold_cmp_ult_ctpop_c_no_not_inst_save_fail( ; CHECK-NEXT: [[NX:%.*]] = xor i8 [[X:%.*]], -2 -; CHECK-NEXT: [[CNT:%.*]] = call i8 @llvm.ctpop.i8(i8 [[NX]]), !range [[RNG0]] +; CHECK-NEXT: [[CNT:%.*]] = call range(i8 0, 9) i8 @llvm.ctpop.i8(i8 [[NX]]) ; CHECK-NEXT: [[R:%.*]] = icmp ult i8 [[CNT]], 5 ; CHECK-NEXT: ret i1 [[R]] ; @@ -202,7 +202,7 @@ define i1 @fold_cmp_ult_ctpop_c_no_not_inst_save_fail(i8 %x) { define <2 x i1> @fold_cmp_ugt_ctpop_c(<2 x i8> %x) { ; CHECK-LABEL: @fold_cmp_ugt_ctpop_c( -; CHECK-NEXT: [[TMP1:%.*]] = call <2 x i8> @llvm.ctpop.v2i8(<2 x i8> [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i8 0, 9) <2 x i8> @llvm.ctpop.v2i8(<2 x i8> [[X:%.*]]) ; CHECK-NEXT: [[R:%.*]] = icmp ult <2 x i8> [[TMP1]], ; CHECK-NEXT: ret <2 x i1> [[R]] ; @@ -215,7 +215,7 @@ define <2 x i1> @fold_cmp_ugt_ctpop_c(<2 x i8> %x) { define <2 x i1> @fold_cmp_ugt_ctpop_c_out_of_range_fail(<2 x i8> %x) { ; CHECK-LABEL: @fold_cmp_ugt_ctpop_c_out_of_range_fail( ; CHECK-NEXT: [[NX:%.*]] = xor <2 x i8> [[X:%.*]], -; CHECK-NEXT: [[CNT:%.*]] = call <2 x i8> @llvm.ctpop.v2i8(<2 x i8> [[NX]]), !range [[RNG0]] +; CHECK-NEXT: [[CNT:%.*]] = call range(i8 0, 9) <2 x i8> @llvm.ctpop.v2i8(<2 x i8> [[NX]]) ; CHECK-NEXT: [[R:%.*]] = icmp ugt <2 x i8> [[CNT]], ; CHECK-NEXT: ret <2 x i1> [[R]] ; diff --git a/llvm/test/Transforms/InstCombine/fold-log2-ceil-idiom.ll b/llvm/test/Transforms/InstCombine/fold-log2-ceil-idiom.ll index a631aacd97ff947ab2fc89bc1f721c33d617d110..17e51e73201b168a240c55cf41115409cc636dd3 100644 --- a/llvm/test/Transforms/InstCombine/fold-log2-ceil-idiom.ll +++ b/llvm/test/Transforms/InstCombine/fold-log2-ceil-idiom.ll @@ -5,7 +5,7 @@ define i32 @log2_ceil_idiom(i32 %x) { ; CHECK-LABEL: define i32 @log2_ceil_idiom( ; CHECK-SAME: i32 [[X:%.*]]) { ; CHECK-NEXT: [[TMP1:%.*]] = add i32 [[X]], -1 -; CHECK-NEXT: [[TMP2:%.*]] = call i32 @llvm.ctlz.i32(i32 [[TMP1]], i1 false), !range [[RNG0:![0-9]+]] +; CHECK-NEXT: [[TMP2:%.*]] = call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[TMP1]], i1 false) ; CHECK-NEXT: [[RET:%.*]] = sub nuw nsw i32 32, [[TMP2]] ; CHECK-NEXT: ret i32 [[RET]] ; @@ -22,7 +22,7 @@ define i5 @log2_ceil_idiom_trunc(i32 %x) { ; CHECK-LABEL: define i5 @log2_ceil_idiom_trunc( ; CHECK-SAME: i32 [[X:%.*]]) { ; CHECK-NEXT: [[TMP1:%.*]] = add i32 [[X]], -1 -; CHECK-NEXT: [[TMP2:%.*]] = call i32 @llvm.ctlz.i32(i32 [[TMP1]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[TMP2:%.*]] = call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[TMP1]], i1 false) ; CHECK-NEXT: [[TMP3:%.*]] = sub nsw i32 0, [[TMP2]] ; CHECK-NEXT: [[RET:%.*]] = trunc i32 [[TMP3]] to i5 ; CHECK-NEXT: ret i5 [[RET]] @@ -41,7 +41,7 @@ define i64 @log2_ceil_idiom_zext(i32 %x) { ; CHECK-LABEL: define i64 @log2_ceil_idiom_zext( ; CHECK-SAME: i32 [[X:%.*]]) { ; CHECK-NEXT: [[TMP1:%.*]] = add i32 [[X]], -1 -; CHECK-NEXT: [[TMP2:%.*]] = call i32 @llvm.ctlz.i32(i32 [[TMP1]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[TMP2:%.*]] = call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[TMP1]], i1 false) ; CHECK-NEXT: [[TMP3:%.*]] = sub nuw nsw i32 32, [[TMP2]] ; CHECK-NEXT: [[RET:%.*]] = zext nneg i32 [[TMP3]] to i64 ; CHECK-NEXT: ret i64 [[RET]] @@ -60,7 +60,7 @@ define i32 @log2_ceil_idiom_power2_test2(i32 %x) { ; CHECK-LABEL: define i32 @log2_ceil_idiom_power2_test2( ; CHECK-SAME: i32 [[X:%.*]]) { ; CHECK-NEXT: [[TMP1:%.*]] = add i32 [[X]], -1 -; CHECK-NEXT: [[TMP2:%.*]] = call i32 @llvm.ctlz.i32(i32 [[TMP1]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[TMP2:%.*]] = call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[TMP1]], i1 false) ; CHECK-NEXT: [[RET:%.*]] = sub nuw nsw i32 32, [[TMP2]] ; CHECK-NEXT: ret i32 [[RET]] ; @@ -77,7 +77,7 @@ define i32 @log2_ceil_idiom_commuted(i32 %x) { ; CHECK-LABEL: define i32 @log2_ceil_idiom_commuted( ; CHECK-SAME: i32 [[X:%.*]]) { ; CHECK-NEXT: [[TMP1:%.*]] = add i32 [[X]], -1 -; CHECK-NEXT: [[TMP2:%.*]] = call i32 @llvm.ctlz.i32(i32 [[TMP1]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[TMP2:%.*]] = call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[TMP1]], i1 false) ; CHECK-NEXT: [[RET:%.*]] = sub nuw nsw i32 32, [[TMP2]] ; CHECK-NEXT: ret i32 [[RET]] ; @@ -93,10 +93,10 @@ define i32 @log2_ceil_idiom_commuted(i32 %x) { define i32 @log2_ceil_idiom_multiuse1(i32 %x) { ; CHECK-LABEL: define i32 @log2_ceil_idiom_multiuse1( ; CHECK-SAME: i32 [[X:%.*]]) { -; CHECK-NEXT: [[CTPOP:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X]]), !range [[RNG0]] +; CHECK-NEXT: [[CTPOP:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X]]) ; CHECK-NEXT: call void @use32(i32 [[CTPOP]]) ; CHECK-NEXT: [[TMP1:%.*]] = add i32 [[X]], -1 -; CHECK-NEXT: [[TMP2:%.*]] = call i32 @llvm.ctlz.i32(i32 [[TMP1]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[TMP2:%.*]] = call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[TMP1]], i1 false) ; CHECK-NEXT: [[RET:%.*]] = sub nuw nsw i32 32, [[TMP2]] ; CHECK-NEXT: ret i32 [[RET]] ; @@ -115,9 +115,9 @@ define i32 @log2_ceil_idiom_multiuse1(i32 %x) { define i32 @log2_ceil_idiom_x_may_be_zero(i32 %x) { ; CHECK-LABEL: define i32 @log2_ceil_idiom_x_may_be_zero( ; CHECK-SAME: i32 [[X:%.*]]) { -; CHECK-NEXT: [[CTLZ:%.*]] = tail call i32 @llvm.ctlz.i32(i32 [[X]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[CTLZ:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[X]], i1 false) ; CHECK-NEXT: [[XOR:%.*]] = xor i32 [[CTLZ]], 31 -; CHECK-NEXT: [[CTPOP:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X]]), !range [[RNG0]] +; CHECK-NEXT: [[CTPOP:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ugt i32 [[CTPOP]], 1 ; CHECK-NEXT: [[ZEXT:%.*]] = zext i1 [[CMP]] to i32 ; CHECK-NEXT: [[RET:%.*]] = add nuw nsw i32 [[XOR]], [[ZEXT]] @@ -135,10 +135,10 @@ define i32 @log2_ceil_idiom_x_may_be_zero(i32 %x) { define i4 @log2_ceil_idiom_trunc_too_short(i32 %x) { ; CHECK-LABEL: define i4 @log2_ceil_idiom_trunc_too_short( ; CHECK-SAME: i32 [[X:%.*]]) { -; CHECK-NEXT: [[CTLZ:%.*]] = tail call i32 @llvm.ctlz.i32(i32 [[X]], i1 true), !range [[RNG0]] +; CHECK-NEXT: [[CTLZ:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[X]], i1 true) ; CHECK-NEXT: [[TRUNC:%.*]] = trunc i32 [[CTLZ]] to i4 ; CHECK-NEXT: [[XOR:%.*]] = xor i4 [[TRUNC]], -1 -; CHECK-NEXT: [[CTPOP:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X]]), !range [[RNG0]] +; CHECK-NEXT: [[CTPOP:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ugt i32 [[CTPOP]], 1 ; CHECK-NEXT: [[ZEXT:%.*]] = zext i1 [[CMP]] to i4 ; CHECK-NEXT: [[RET:%.*]] = add i4 [[XOR]], [[ZEXT]] @@ -157,9 +157,9 @@ define i4 @log2_ceil_idiom_trunc_too_short(i32 %x) { define i32 @log2_ceil_idiom_mismatched_operands(i32 %x, i32 %y) { ; CHECK-LABEL: define i32 @log2_ceil_idiom_mismatched_operands( ; CHECK-SAME: i32 [[X:%.*]], i32 [[Y:%.*]]) { -; CHECK-NEXT: [[CTLZ:%.*]] = tail call i32 @llvm.ctlz.i32(i32 [[X]], i1 true), !range [[RNG0]] +; CHECK-NEXT: [[CTLZ:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[X]], i1 true) ; CHECK-NEXT: [[XOR:%.*]] = xor i32 [[CTLZ]], 31 -; CHECK-NEXT: [[CTPOP:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[Y]]), !range [[RNG0]] +; CHECK-NEXT: [[CTPOP:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[Y]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ugt i32 [[CTPOP]], 1 ; CHECK-NEXT: [[ZEXT:%.*]] = zext i1 [[CMP]] to i32 ; CHECK-NEXT: [[RET:%.*]] = add nuw nsw i32 [[XOR]], [[ZEXT]] @@ -177,9 +177,9 @@ define i32 @log2_ceil_idiom_mismatched_operands(i32 %x, i32 %y) { define i32 @log2_ceil_idiom_wrong_constant(i32 %x) { ; CHECK-LABEL: define i32 @log2_ceil_idiom_wrong_constant( ; CHECK-SAME: i32 [[X:%.*]]) { -; CHECK-NEXT: [[CTLZ:%.*]] = tail call i32 @llvm.ctlz.i32(i32 [[X]], i1 true), !range [[RNG0]] +; CHECK-NEXT: [[CTLZ:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[X]], i1 true) ; CHECK-NEXT: [[XOR:%.*]] = xor i32 [[CTLZ]], 30 -; CHECK-NEXT: [[CTPOP:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X]]), !range [[RNG0]] +; CHECK-NEXT: [[CTPOP:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ugt i32 [[CTPOP]], 1 ; CHECK-NEXT: [[ZEXT:%.*]] = zext i1 [[CMP]] to i32 ; CHECK-NEXT: [[RET:%.*]] = add nuw nsw i32 [[XOR]], [[ZEXT]] @@ -197,9 +197,9 @@ define i32 @log2_ceil_idiom_wrong_constant(i32 %x) { define i32 @log2_ceil_idiom_not_a_power2_test1(i32 %x) { ; CHECK-LABEL: define i32 @log2_ceil_idiom_not_a_power2_test1( ; CHECK-SAME: i32 [[X:%.*]]) { -; CHECK-NEXT: [[CTLZ:%.*]] = tail call i32 @llvm.ctlz.i32(i32 [[X]], i1 true), !range [[RNG0]] +; CHECK-NEXT: [[CTLZ:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[X]], i1 true) ; CHECK-NEXT: [[XOR:%.*]] = xor i32 [[CTLZ]], 31 -; CHECK-NEXT: [[CTPOP:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X]]), !range [[RNG0]] +; CHECK-NEXT: [[CTPOP:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp eq i32 [[CTPOP]], 1 ; CHECK-NEXT: [[ZEXT:%.*]] = zext i1 [[CMP]] to i32 ; CHECK-NEXT: [[RET:%.*]] = add nuw nsw i32 [[XOR]], [[ZEXT]] @@ -217,9 +217,9 @@ define i32 @log2_ceil_idiom_not_a_power2_test1(i32 %x) { define i32 @log2_ceil_idiom_not_a_power2_test2(i32 %x) { ; CHECK-LABEL: define i32 @log2_ceil_idiom_not_a_power2_test2( ; CHECK-SAME: i32 [[X:%.*]]) { -; CHECK-NEXT: [[CTLZ:%.*]] = tail call i32 @llvm.ctlz.i32(i32 [[X]], i1 true), !range [[RNG0]] +; CHECK-NEXT: [[CTLZ:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[X]], i1 true) ; CHECK-NEXT: [[XOR:%.*]] = xor i32 [[CTLZ]], 31 -; CHECK-NEXT: [[CTPOP:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X]]), !range [[RNG0]] +; CHECK-NEXT: [[CTPOP:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ugt i32 [[CTPOP]], 2 ; CHECK-NEXT: [[ZEXT:%.*]] = zext i1 [[CMP]] to i32 ; CHECK-NEXT: [[RET:%.*]] = add nuw nsw i32 [[XOR]], [[ZEXT]] @@ -237,10 +237,10 @@ define i32 @log2_ceil_idiom_not_a_power2_test2(i32 %x) { define i32 @log2_ceil_idiom_multiuse2(i32 %x) { ; CHECK-LABEL: define i32 @log2_ceil_idiom_multiuse2( ; CHECK-SAME: i32 [[X:%.*]]) { -; CHECK-NEXT: [[CTLZ:%.*]] = tail call i32 @llvm.ctlz.i32(i32 [[X]], i1 true), !range [[RNG0]] +; CHECK-NEXT: [[CTLZ:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[X]], i1 true) ; CHECK-NEXT: call void @use32(i32 [[CTLZ]]) ; CHECK-NEXT: [[XOR:%.*]] = xor i32 [[CTLZ]], 31 -; CHECK-NEXT: [[CTPOP:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X]]), !range [[RNG0]] +; CHECK-NEXT: [[CTPOP:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ugt i32 [[CTPOP]], 1 ; CHECK-NEXT: [[ZEXT:%.*]] = zext i1 [[CMP]] to i32 ; CHECK-NEXT: [[RET:%.*]] = add nuw nsw i32 [[XOR]], [[ZEXT]] @@ -259,10 +259,10 @@ define i32 @log2_ceil_idiom_multiuse2(i32 %x) { define i32 @log2_ceil_idiom_multiuse3(i32 %x) { ; CHECK-LABEL: define i32 @log2_ceil_idiom_multiuse3( ; CHECK-SAME: i32 [[X:%.*]]) { -; CHECK-NEXT: [[CTLZ:%.*]] = tail call i32 @llvm.ctlz.i32(i32 [[X]], i1 true), !range [[RNG0]] +; CHECK-NEXT: [[CTLZ:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[X]], i1 true) ; CHECK-NEXT: [[XOR:%.*]] = xor i32 [[CTLZ]], 31 ; CHECK-NEXT: call void @use32(i32 [[XOR]]) -; CHECK-NEXT: [[CTPOP:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X]]), !range [[RNG0]] +; CHECK-NEXT: [[CTPOP:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ugt i32 [[CTPOP]], 1 ; CHECK-NEXT: [[ZEXT:%.*]] = zext i1 [[CMP]] to i32 ; CHECK-NEXT: [[RET:%.*]] = add nuw nsw i32 [[XOR]], [[ZEXT]] @@ -281,11 +281,11 @@ define i32 @log2_ceil_idiom_multiuse3(i32 %x) { define i5 @log2_ceil_idiom_trunc_multiuse4(i32 %x) { ; CHECK-LABEL: define i5 @log2_ceil_idiom_trunc_multiuse4( ; CHECK-SAME: i32 [[X:%.*]]) { -; CHECK-NEXT: [[CTLZ:%.*]] = tail call i32 @llvm.ctlz.i32(i32 [[X]], i1 true), !range [[RNG0]] +; CHECK-NEXT: [[CTLZ:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[X]], i1 true) ; CHECK-NEXT: [[TRUNC:%.*]] = trunc nuw i32 [[CTLZ]] to i5 ; CHECK-NEXT: call void @use5(i5 [[TRUNC]]) ; CHECK-NEXT: [[XOR:%.*]] = xor i5 [[TRUNC]], -1 -; CHECK-NEXT: [[CTPOP:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X]]), !range [[RNG0]] +; CHECK-NEXT: [[CTPOP:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ugt i32 [[CTPOP]], 1 ; CHECK-NEXT: [[ZEXT:%.*]] = zext i1 [[CMP]] to i5 ; CHECK-NEXT: [[RET:%.*]] = add i5 [[XOR]], [[ZEXT]] @@ -305,11 +305,11 @@ define i5 @log2_ceil_idiom_trunc_multiuse4(i32 %x) { define i64 @log2_ceil_idiom_zext_multiuse5(i32 %x) { ; CHECK-LABEL: define i64 @log2_ceil_idiom_zext_multiuse5( ; CHECK-SAME: i32 [[X:%.*]]) { -; CHECK-NEXT: [[CTLZ:%.*]] = tail call i32 @llvm.ctlz.i32(i32 [[X]], i1 true), !range [[RNG0]] +; CHECK-NEXT: [[CTLZ:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[X]], i1 true) ; CHECK-NEXT: [[XOR:%.*]] = xor i32 [[CTLZ]], 31 ; CHECK-NEXT: [[EXT:%.*]] = zext nneg i32 [[XOR]] to i64 ; CHECK-NEXT: call void @use64(i64 [[EXT]]) -; CHECK-NEXT: [[CTPOP:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X]]), !range [[RNG0]] +; CHECK-NEXT: [[CTPOP:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ugt i32 [[CTPOP]], 1 ; CHECK-NEXT: [[ZEXT:%.*]] = zext i1 [[CMP]] to i64 ; CHECK-NEXT: [[RET:%.*]] = add nuw nsw i64 [[EXT]], [[ZEXT]] @@ -332,6 +332,3 @@ declare void @use64(i64) declare i32 @llvm.ctlz.i32(i32, i1) declare i32 @llvm.ctpop.i32(i32) -;. -; CHECK: [[RNG0]] = !{i32 0, i32 33} -;. diff --git a/llvm/test/Transforms/InstCombine/freeze-integer-intrinsics.ll b/llvm/test/Transforms/InstCombine/freeze-integer-intrinsics.ll index 105bd28fb052e8c76e22187ff86f22fc8969663c..c4a590e1a12bfaa475531bfa5916def66db807af 100644 --- a/llvm/test/Transforms/InstCombine/freeze-integer-intrinsics.ll +++ b/llvm/test/Transforms/InstCombine/freeze-integer-intrinsics.ll @@ -3,7 +3,7 @@ define i32 @ctlz_true_freeze(i32 %arg) { ; CHECK-LABEL: @ctlz_true_freeze( -; CHECK-NEXT: [[CALL:%.*]] = call i32 @llvm.ctlz.i32(i32 [[ARG:%.*]], i1 true), !range [[RNG0:![0-9]+]] +; CHECK-NEXT: [[CALL:%.*]] = call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[ARG:%.*]], i1 true) ; CHECK-NEXT: [[FREEZE:%.*]] = freeze i32 [[CALL]] ; CHECK-NEXT: ret i32 [[FREEZE]] ; @@ -15,7 +15,7 @@ define i32 @ctlz_true_freeze(i32 %arg) { define i32 @ctlz_false_freeze(i32 %arg) { ; CHECK-LABEL: @ctlz_false_freeze( ; CHECK-NEXT: [[ARG_FR:%.*]] = freeze i32 [[ARG:%.*]] -; CHECK-NEXT: [[CALL:%.*]] = call i32 @llvm.ctlz.i32(i32 [[ARG_FR]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[CALL:%.*]] = call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[ARG_FR]], i1 false) ; CHECK-NEXT: ret i32 [[CALL]] ; %call = call i32 @llvm.ctlz.i32(i32 %arg, i1 false) @@ -25,7 +25,7 @@ define i32 @ctlz_false_freeze(i32 %arg) { define i32 @ctlz_true_noundef_freeze(i32 %arg) { ; CHECK-LABEL: @ctlz_true_noundef_freeze( -; CHECK-NEXT: [[CALL:%.*]] = call noundef i32 @llvm.ctlz.i32(i32 [[ARG:%.*]], i1 true), !range [[RNG0]] +; CHECK-NEXT: [[CALL:%.*]] = call noundef range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[ARG:%.*]], i1 true) ; CHECK-NEXT: ret i32 [[CALL]] ; %call = call noundef i32 @llvm.ctlz.i32(i32 %arg, i1 true) @@ -35,7 +35,7 @@ define i32 @ctlz_true_noundef_freeze(i32 %arg) { define i32 @cttz_true_freeze(i32 %arg) { ; CHECK-LABEL: @cttz_true_freeze( -; CHECK-NEXT: [[CALL:%.*]] = call i32 @llvm.cttz.i32(i32 [[ARG:%.*]], i1 true), !range [[RNG0]] +; CHECK-NEXT: [[CALL:%.*]] = call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[ARG:%.*]], i1 true) ; CHECK-NEXT: [[FREEZE:%.*]] = freeze i32 [[CALL]] ; CHECK-NEXT: ret i32 [[FREEZE]] ; @@ -46,7 +46,7 @@ define i32 @cttz_true_freeze(i32 %arg) { define i32 @cttz_true_noundef_freeze(i32 %arg) { ; CHECK-LABEL: @cttz_true_noundef_freeze( -; CHECK-NEXT: [[CALL:%.*]] = call noundef i32 @llvm.cttz.i32(i32 [[ARG:%.*]], i1 true), !range [[RNG0]] +; CHECK-NEXT: [[CALL:%.*]] = call noundef range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[ARG:%.*]], i1 true) ; CHECK-NEXT: ret i32 [[CALL]] ; %call = call noundef i32 @llvm.cttz.i32(i32 %arg, i1 true) @@ -57,7 +57,7 @@ define i32 @cttz_true_noundef_freeze(i32 %arg) { define i32 @freeze_cttz_true(i32 %arg) { ; CHECK-LABEL: @freeze_cttz_true( ; CHECK-NEXT: [[FREEZE:%.*]] = freeze i32 [[ARG:%.*]] -; CHECK-NEXT: [[CALL:%.*]] = call i32 @llvm.cttz.i32(i32 [[FREEZE]], i1 true), !range [[RNG0]] +; CHECK-NEXT: [[CALL:%.*]] = call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[FREEZE]], i1 true) ; CHECK-NEXT: ret i32 [[CALL]] ; %freeze = freeze i32 %arg @@ -68,7 +68,7 @@ define i32 @freeze_cttz_true(i32 %arg) { define i32 @cttz_false_freeze(i32 %arg) { ; CHECK-LABEL: @cttz_false_freeze( ; CHECK-NEXT: [[ARG_FR:%.*]] = freeze i32 [[ARG:%.*]] -; CHECK-NEXT: [[CALL:%.*]] = call i32 @llvm.cttz.i32(i32 [[ARG_FR]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[CALL:%.*]] = call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[ARG_FR]], i1 false) ; CHECK-NEXT: ret i32 [[CALL]] ; %call = call i32 @llvm.cttz.i32(i32 %arg, i1 false) @@ -79,7 +79,7 @@ define i32 @cttz_false_freeze(i32 %arg) { define i32 @freeze_cttz_false(i32 %arg) { ; CHECK-LABEL: @freeze_cttz_false( ; CHECK-NEXT: [[FREEZE:%.*]] = freeze i32 [[ARG:%.*]] -; CHECK-NEXT: [[CALL:%.*]] = call i32 @llvm.cttz.i32(i32 [[FREEZE]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[CALL:%.*]] = call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[FREEZE]], i1 false) ; CHECK-NEXT: ret i32 [[CALL]] ; %freeze = freeze i32 %arg diff --git a/llvm/test/Transforms/InstCombine/freeze.ll b/llvm/test/Transforms/InstCombine/freeze.ll index adcf7d50f413bea83eeb010010924d6d49c7496e..391d626a795c7d06b7b355878dfbd006ee1f7b5c 100644 --- a/llvm/test/Transforms/InstCombine/freeze.ll +++ b/llvm/test/Transforms/InstCombine/freeze.ll @@ -1107,7 +1107,7 @@ define i32 @freeze_ctpop(i32 %x) { ; CHECK-LABEL: @freeze_ctpop( ; CHECK-NEXT: [[Y:%.*]] = lshr i32 2047, [[X:%.*]] ; CHECK-NEXT: [[Y_FR:%.*]] = freeze i32 [[Y]] -; CHECK-NEXT: [[CTPOP:%.*]] = call i32 @llvm.ctpop.i32(i32 [[Y_FR]]), !range [[RNG3:![0-9]+]] +; CHECK-NEXT: [[CTPOP:%.*]] = call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[Y_FR]]) ; CHECK-NEXT: ret i32 [[CTPOP]] ; %y = lshr i32 2047, %x @@ -1209,5 +1209,4 @@ define ptr @freeze_ptrmask_nonnull(ptr %p, i64 noundef %m) { ; CHECK: [[META0]] = !{} ; CHECK: [[META1]] = !{i64 4} ; CHECK: [[RNG2]] = !{i32 0, i32 100} -; CHECK: [[RNG3]] = !{i32 0, i32 33} ;. diff --git a/llvm/test/Transforms/InstCombine/gepofconstgepi8.ll b/llvm/test/Transforms/InstCombine/gepofconstgepi8.ll new file mode 100644 index 0000000000000000000000000000000000000000..7b7c6fba699c219091b2dbf3b8ab7033513a832f --- /dev/null +++ b/llvm/test/Transforms/InstCombine/gepofconstgepi8.ll @@ -0,0 +1,292 @@ +; NOTE: Assertions have been autogenerated by utils/update_test_checks.py UTC_ARGS: --version 4 +; RUN: opt < %s -S -passes=instcombine | FileCheck %s + +declare void @use64(i64) +declare void @useptr(ptr) + +define ptr @test_zero(ptr %base, i64 %a) { +; CHECK-LABEL: define ptr @test_zero( +; CHECK-SAME: ptr [[BASE:%.*]], i64 [[A:%.*]]) { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[P2:%.*]] = getelementptr i32, ptr [[BASE]], i64 [[A]] +; CHECK-NEXT: ret ptr [[P2]] +; +entry: + %p1 = getelementptr i8, ptr %base, i64 -4 + %index = add i64 %a, 1 + %p2 = getelementptr i32, ptr %p1, i64 %index + ret ptr %p2 +} + +define ptr @test_nonzero(ptr %base, i64 %a) { +; CHECK-LABEL: define ptr @test_nonzero( +; CHECK-SAME: ptr [[BASE:%.*]], i64 [[A:%.*]]) { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP0:%.*]] = getelementptr i8, ptr [[BASE]], i64 4 +; CHECK-NEXT: [[P2:%.*]] = getelementptr i32, ptr [[TMP0]], i64 [[A]] +; CHECK-NEXT: ret ptr [[P2]] +; +entry: + %p1 = getelementptr i8, ptr %base, i64 -4 + %index = add i64 %a, 2 + %p2 = getelementptr i32, ptr %p1, i64 %index + ret ptr %p2 +} + +define ptr @test_or_disjoint(ptr %base, i64 %a) { +; CHECK-LABEL: define ptr @test_or_disjoint( +; CHECK-SAME: ptr [[BASE:%.*]], i64 [[A:%.*]]) { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[P2:%.*]] = getelementptr i32, ptr [[BASE]], i64 [[A]] +; CHECK-NEXT: ret ptr [[P2]] +; +entry: + %p1 = getelementptr i8, ptr %base, i64 -4 + %index = or disjoint i64 %a, 1 + %p2 = getelementptr i32, ptr %p1, i64 %index + ret ptr %p2 +} + +define ptr @test_zero_multiuse_index(ptr %base, i64 %a) { +; CHECK-LABEL: define ptr @test_zero_multiuse_index( +; CHECK-SAME: ptr [[BASE:%.*]], i64 [[A:%.*]]) { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[INDEX:%.*]] = add i64 [[A]], 1 +; CHECK-NEXT: call void @use64(i64 [[INDEX]]) +; CHECK-NEXT: [[P2:%.*]] = getelementptr i32, ptr [[BASE]], i64 [[A]] +; CHECK-NEXT: ret ptr [[P2]] +; +entry: + %p1 = getelementptr i8, ptr %base, i64 -4 + %index = add i64 %a, 1 + call void @use64(i64 %index) + %p2 = getelementptr i32, ptr %p1, i64 %index + ret ptr %p2 +} + +define ptr @test_zero_multiuse_ptr(ptr %base, i64 %a) { +; CHECK-LABEL: define ptr @test_zero_multiuse_ptr( +; CHECK-SAME: ptr [[BASE:%.*]], i64 [[A:%.*]]) { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[P1:%.*]] = getelementptr i8, ptr [[BASE]], i64 -4 +; CHECK-NEXT: call void @useptr(ptr [[P1]]) +; CHECK-NEXT: [[P2:%.*]] = getelementptr i32, ptr [[BASE]], i64 [[A]] +; CHECK-NEXT: ret ptr [[P2]] +; +entry: + %p1 = getelementptr i8, ptr %base, i64 -4 + call void @useptr(ptr %p1) + %index = add i64 %a, 1 + %p2 = getelementptr i32, ptr %p1, i64 %index + ret ptr %p2 +} + +define ptr @test_zero_sext_add_nsw(ptr %base, i32 %a) { +; CHECK-LABEL: define ptr @test_zero_sext_add_nsw( +; CHECK-SAME: ptr [[BASE:%.*]], i32 [[A:%.*]]) { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[P1:%.*]] = getelementptr i8, ptr [[BASE]], i64 -4 +; CHECK-NEXT: [[TMP0:%.*]] = sext i32 [[A]] to i64 +; CHECK-NEXT: [[TMP1:%.*]] = getelementptr i32, ptr [[P1]], i64 [[TMP0]] +; CHECK-NEXT: [[P2:%.*]] = getelementptr i8, ptr [[TMP1]], i64 4 +; CHECK-NEXT: ret ptr [[P2]] +; +entry: + %p1 = getelementptr i8, ptr %base, i64 -4 + %index = add nsw i32 %a, 1 + %p2 = getelementptr i32, ptr %p1, i32 %index + ret ptr %p2 +} + +define ptr @test_zero_trunc_add(ptr %base, i128 %a) { +; CHECK-LABEL: define ptr @test_zero_trunc_add( +; CHECK-SAME: ptr [[BASE:%.*]], i128 [[A:%.*]]) { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP0:%.*]] = trunc i128 [[A]] to i64 +; CHECK-NEXT: [[P2:%.*]] = getelementptr i32, ptr [[BASE]], i64 [[TMP0]] +; CHECK-NEXT: ret ptr [[P2]] +; +entry: + %p1 = getelementptr i8, ptr %base, i64 -4 + %index = add i128 %a, 1 + %p2 = getelementptr i32, ptr %p1, i128 %index + ret ptr %p2 +} + +define ptr @test_non_i8(ptr %base, i64 %a) { +; CHECK-LABEL: define ptr @test_non_i8( +; CHECK-SAME: ptr [[BASE:%.*]], i64 [[A:%.*]]) { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[P1:%.*]] = getelementptr i8, ptr [[BASE]], i64 -4 +; CHECK-NEXT: [[TMP0:%.*]] = getelementptr i32, ptr [[P1]], i64 [[A]] +; CHECK-NEXT: ret ptr [[TMP0]] +; +entry: + %p1 = getelementptr i16, ptr %base, i64 -4 + %index = add i64 %a, 1 + %p2 = getelementptr i32, ptr %p1, i64 %index + ret ptr %p2 +} + +define ptr @test_non_const(ptr %base, i64 %a, i64 %b) { +; CHECK-LABEL: define ptr @test_non_const( +; CHECK-SAME: ptr [[BASE:%.*]], i64 [[A:%.*]], i64 [[B:%.*]]) { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[P1:%.*]] = getelementptr i8, ptr [[BASE]], i64 [[B]] +; CHECK-NEXT: [[TMP0:%.*]] = getelementptr i32, ptr [[P1]], i64 [[A]] +; CHECK-NEXT: [[P2:%.*]] = getelementptr i8, ptr [[TMP0]], i64 4 +; CHECK-NEXT: ret ptr [[P2]] +; +entry: + %p1 = getelementptr i8, ptr %base, i64 %b + %index = add i64 %a, 1 + %p2 = getelementptr i32, ptr %p1, i64 %index + ret ptr %p2 +} + +define ptr @test_too_many_indices(ptr %base, i64 %a, i64 %b) { +; CHECK-LABEL: define ptr @test_too_many_indices( +; CHECK-SAME: ptr [[BASE:%.*]], i64 [[A:%.*]], i64 [[B:%.*]]) { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[P1:%.*]] = getelementptr i8, ptr [[BASE]], i64 [[B]] +; CHECK-NEXT: [[INDEX:%.*]] = add i64 [[A]], 1 +; CHECK-NEXT: [[P2:%.*]] = getelementptr [8 x i32], ptr [[P1]], i64 1, i64 [[INDEX]] +; CHECK-NEXT: ret ptr [[P2]] +; +entry: + %p1 = getelementptr i8, ptr %base, i64 %b + %index = add i64 %a, 1 + %p2 = getelementptr [8 x i32], ptr %p1, i64 1, i64 %index + ret ptr %p2 +} + +define ptr @test_wrong_op(ptr %base, i64 %a) { +; CHECK-LABEL: define ptr @test_wrong_op( +; CHECK-SAME: ptr [[BASE:%.*]], i64 [[A:%.*]]) { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[P1:%.*]] = getelementptr i8, ptr [[BASE]], i64 -4 +; CHECK-NEXT: [[INDEX:%.*]] = xor i64 [[A]], 1 +; CHECK-NEXT: [[P2:%.*]] = getelementptr i32, ptr [[P1]], i64 [[INDEX]] +; CHECK-NEXT: ret ptr [[P2]] +; +entry: + %p1 = getelementptr i8, ptr %base, i64 -4 + %index = xor i64 %a, 1 + %p2 = getelementptr i32, ptr %p1, i64 %index + ret ptr %p2 +} + +define ptr @test_sext_add_without_nsw(ptr %base, i32 %a) { +; CHECK-LABEL: define ptr @test_sext_add_without_nsw( +; CHECK-SAME: ptr [[BASE:%.*]], i32 [[A:%.*]]) { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[P1:%.*]] = getelementptr i8, ptr [[BASE]], i64 -4 +; CHECK-NEXT: [[INDEX:%.*]] = add i32 [[A]], 1 +; CHECK-NEXT: [[TMP0:%.*]] = sext i32 [[INDEX]] to i64 +; CHECK-NEXT: [[P2:%.*]] = getelementptr i32, ptr [[P1]], i64 [[TMP0]] +; CHECK-NEXT: ret ptr [[P2]] +; +entry: + %p1 = getelementptr i8, ptr %base, i64 -4 + %index = add i32 %a, 1 + %p2 = getelementptr i32, ptr %p1, i32 %index + ret ptr %p2 +} + +define ptr @test_or_without_disjoint(ptr %base, i64 %a) { +; CHECK-LABEL: define ptr @test_or_without_disjoint( +; CHECK-SAME: ptr [[BASE:%.*]], i64 [[A:%.*]]) { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[P1:%.*]] = getelementptr i8, ptr [[BASE]], i64 -4 +; CHECK-NEXT: [[INDEX:%.*]] = or i64 [[A]], 1 +; CHECK-NEXT: [[P2:%.*]] = getelementptr i32, ptr [[P1]], i64 [[INDEX]] +; CHECK-NEXT: ret ptr [[P2]] +; +entry: + %p1 = getelementptr i8, ptr %base, i64 -4 + %index = or i64 %a, 1 + %p2 = getelementptr i32, ptr %p1, i64 %index + ret ptr %p2 +} + +define ptr @test_smul_overflow(ptr %base, i64 %a) { +; CHECK-LABEL: define ptr @test_smul_overflow( +; CHECK-SAME: ptr [[BASE:%.*]], i64 [[A:%.*]]) { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[P1:%.*]] = getelementptr i8, ptr [[BASE]], i64 -12 +; CHECK-NEXT: [[TMP0:%.*]] = getelementptr i32, ptr [[P1]], i64 [[A]] +; CHECK-NEXT: ret ptr [[TMP0]] +; +entry: + %p1 = getelementptr i8, ptr %base, i64 -4 + %index = add i64 %a, 9223372036854775806 + %p2 = getelementptr i32, ptr %p1, i64 %index + ret ptr %p2 +} + +define ptr @test_sadd_overflow(ptr %base, i64 %a) { +; CHECK-LABEL: define ptr @test_sadd_overflow( +; CHECK-SAME: ptr [[BASE:%.*]], i64 [[A:%.*]]) { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[P1:%.*]] = getelementptr i8, ptr [[BASE]], i64 -9223372036854775808 +; CHECK-NEXT: [[TMP0:%.*]] = getelementptr i32, ptr [[P1]], i64 [[A]] +; CHECK-NEXT: ret ptr [[TMP0]] +; +entry: + %p1 = getelementptr i8, ptr %base, i64 9223372036854775804 + %index = add i64 %a, 1 + %p2 = getelementptr i32, ptr %p1, i64 %index + ret ptr %p2 +} + +define ptr @test_nonzero_multiuse_index(ptr %base, i64 %a) { +; CHECK-LABEL: define ptr @test_nonzero_multiuse_index( +; CHECK-SAME: ptr [[BASE:%.*]], i64 [[A:%.*]]) { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[P1:%.*]] = getelementptr i8, ptr [[BASE]], i64 -4 +; CHECK-NEXT: [[INDEX:%.*]] = add i64 [[A]], 2 +; CHECK-NEXT: call void @use64(i64 [[INDEX]]) +; CHECK-NEXT: [[P2:%.*]] = getelementptr i32, ptr [[P1]], i64 [[INDEX]] +; CHECK-NEXT: ret ptr [[P2]] +; +entry: + %p1 = getelementptr i8, ptr %base, i64 -4 + %index = add i64 %a, 2 + call void @use64(i64 %index) + %p2 = getelementptr i32, ptr %p1, i64 %index + ret ptr %p2 +} + +define ptr @test_nonzero_multiuse_ptr(ptr %base, i64 %a) { +; CHECK-LABEL: define ptr @test_nonzero_multiuse_ptr( +; CHECK-SAME: ptr [[BASE:%.*]], i64 [[A:%.*]]) { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[P1:%.*]] = getelementptr i8, ptr [[BASE]], i64 -4 +; CHECK-NEXT: call void @useptr(ptr [[P1]]) +; CHECK-NEXT: [[TMP0:%.*]] = getelementptr i32, ptr [[P1]], i64 [[A]] +; CHECK-NEXT: [[P2:%.*]] = getelementptr i8, ptr [[TMP0]], i64 8 +; CHECK-NEXT: ret ptr [[P2]] +; +entry: + %p1 = getelementptr i8, ptr %base, i64 -4 + call void @useptr(ptr %p1) + %index = add i64 %a, 2 + %p2 = getelementptr i32, ptr %p1, i64 %index + ret ptr %p2 +} + +define ptr @test_scalable(ptr %base, i64 %a) { +; CHECK-LABEL: define ptr @test_scalable( +; CHECK-SAME: ptr [[BASE:%.*]], i64 [[A:%.*]]) { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[P1:%.*]] = getelementptr i8, ptr [[BASE]], i64 -4 +; CHECK-NEXT: [[TMP0:%.*]] = getelementptr , ptr [[P1]], i64 [[A]] +; CHECK-NEXT: [[P2:%.*]] = getelementptr , ptr [[TMP0]], i64 1 +; CHECK-NEXT: ret ptr [[P2]] +; +entry: + %p1 = getelementptr i8, ptr %base, i64 -4 + %index = add i64 %a, 1 + %p2 = getelementptr , ptr %p1, i64 %index + ret ptr %p2 +} diff --git a/llvm/test/Transforms/InstCombine/icmp-ne-pow2.ll b/llvm/test/Transforms/InstCombine/icmp-ne-pow2.ll index 70a2b33d17dd7caa533133092bd2bcf833a3ec5c..e9ec6b415d4621251491b15124cf8a6689f6be95 100644 --- a/llvm/test/Transforms/InstCombine/icmp-ne-pow2.ll +++ b/llvm/test/Transforms/InstCombine/icmp-ne-pow2.ll @@ -284,7 +284,7 @@ False: define i32 @pow2_32_nonconst_assume(i32 %x, i32 %y) { ; CHECK-LABEL: @pow2_32_nonconst_assume( -; CHECK-NEXT: [[CTPOP:%.*]] = call i32 @llvm.ctpop.i32(i32 [[Y:%.*]]), !range [[RNG0:![0-9]+]] +; CHECK-NEXT: [[CTPOP:%.*]] = call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[Y:%.*]]) ; CHECK-NEXT: [[YP2:%.*]] = icmp eq i32 [[CTPOP]], 1 ; CHECK-NEXT: call void @llvm.assume(i1 [[YP2]]) ; CHECK-NEXT: [[AND:%.*]] = and i32 [[X:%.*]], [[Y]] @@ -306,7 +306,7 @@ define i32 @pow2_32_nonconst_assume(i32 %x, i32 %y) { define i32 @pow2_32_gtnonconst_assume(i32 %x, i32 %y) { ; CHECK-LABEL: @pow2_32_gtnonconst_assume( -; CHECK-NEXT: [[CTPOP:%.*]] = call i32 @llvm.ctpop.i32(i32 [[Y:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[CTPOP:%.*]] = call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[Y:%.*]]) ; CHECK-NEXT: [[YP2:%.*]] = icmp eq i32 [[CTPOP]], 1 ; CHECK-NEXT: call void @llvm.assume(i1 [[YP2]]) ; CHECK-NEXT: [[YGT:%.*]] = icmp ugt i32 [[Y]], [[X:%.*]] @@ -327,7 +327,7 @@ define i32 @pow2_32_gtnonconst_assume(i32 %x, i32 %y) { define i32 @not_pow2_32_nonconst_assume(i32 %x, i32 %y) { ; CHECK-LABEL: @not_pow2_32_nonconst_assume( -; CHECK-NEXT: [[CTPOP:%.*]] = call i32 @llvm.ctpop.i32(i32 [[Y:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[CTPOP:%.*]] = call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[Y:%.*]]) ; CHECK-NEXT: [[YP2:%.*]] = icmp ne i32 [[CTPOP]], 1 ; CHECK-NEXT: call void @llvm.assume(i1 [[YP2]]) ; CHECK-NEXT: [[AND:%.*]] = and i32 [[X:%.*]], [[Y]] @@ -349,7 +349,7 @@ define i32 @not_pow2_32_nonconst_assume(i32 %x, i32 %y) { define i32 @pow2_or_zero_32_nonconst_assume(i32 %x, i32 %y) { ; CHECK-LABEL: @pow2_or_zero_32_nonconst_assume( -; CHECK-NEXT: [[CTPOP:%.*]] = call i32 @llvm.ctpop.i32(i32 [[Y:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[CTPOP:%.*]] = call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[Y:%.*]]) ; CHECK-NEXT: [[YP2:%.*]] = icmp ult i32 [[CTPOP]], 2 ; CHECK-NEXT: call void @llvm.assume(i1 [[YP2]]) ; CHECK-NEXT: [[AND:%.*]] = and i32 [[X:%.*]], [[Y]] @@ -371,7 +371,7 @@ define i32 @pow2_or_zero_32_nonconst_assume(i32 %x, i32 %y) { define i32 @pow2_32_nonconst_assume_br(i32 %x, i32 %y) { ; CHECK-LABEL: @pow2_32_nonconst_assume_br( -; CHECK-NEXT: [[CTPOP:%.*]] = call i32 @llvm.ctpop.i32(i32 [[Y:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[CTPOP:%.*]] = call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[Y:%.*]]) ; CHECK-NEXT: [[YP2:%.*]] = icmp eq i32 [[CTPOP]], 1 ; CHECK-NEXT: call void @llvm.assume(i1 [[YP2]]) ; CHECK-NEXT: [[AND:%.*]] = and i32 [[X:%.*]], [[Y]] @@ -398,7 +398,7 @@ False: define i32 @not_pow2_32_nonconst_assume_br(i32 %x, i32 %y) { ; CHECK-LABEL: @not_pow2_32_nonconst_assume_br( -; CHECK-NEXT: [[CTPOP:%.*]] = call i32 @llvm.ctpop.i32(i32 [[Y:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[CTPOP:%.*]] = call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[Y:%.*]]) ; CHECK-NEXT: [[YP2:%.*]] = icmp ne i32 [[CTPOP]], 1 ; CHECK-NEXT: call void @llvm.assume(i1 [[YP2]]) ; CHECK-NEXT: [[AND:%.*]] = and i32 [[X:%.*]], [[Y]] @@ -425,7 +425,7 @@ False: define i32 @pow2_or_zero_32_nonconst_assume_br(i32 %x, i32 %y) { ; CHECK-LABEL: @pow2_or_zero_32_nonconst_assume_br( -; CHECK-NEXT: [[CTPOP:%.*]] = call i32 @llvm.ctpop.i32(i32 [[Y:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[CTPOP:%.*]] = call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[Y:%.*]]) ; CHECK-NEXT: [[YP2:%.*]] = icmp ult i32 [[CTPOP]], 2 ; CHECK-NEXT: call void @llvm.assume(i1 [[YP2]]) ; CHECK-NEXT: [[AND:%.*]] = and i32 [[X:%.*]], [[Y]] @@ -452,7 +452,7 @@ False: define i32 @pow2_32_nonconst_br1_br(i32 %x, i32 %y) { ; CHECK-LABEL: @pow2_32_nonconst_br1_br( -; CHECK-NEXT: [[CTPOP:%.*]] = call i32 @llvm.ctpop.i32(i32 [[Y:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[CTPOP:%.*]] = call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[Y:%.*]]) ; CHECK-NEXT: [[YP2:%.*]] = icmp eq i32 [[CTPOP]], 1 ; CHECK-NEXT: br i1 [[YP2]], label [[CONT:%.*]], label [[FALSE:%.*]] ; CHECK: Cont: @@ -481,7 +481,7 @@ False: define i32 @not_pow2_32_nonconst_br1_br(i32 %x, i32 %y) { ; CHECK-LABEL: @not_pow2_32_nonconst_br1_br( -; CHECK-NEXT: [[CTPOP:%.*]] = call i32 @llvm.ctpop.i32(i32 [[Y:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[CTPOP:%.*]] = call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[Y:%.*]]) ; CHECK-NEXT: [[YP2_NOT:%.*]] = icmp eq i32 [[CTPOP]], 1 ; CHECK-NEXT: br i1 [[YP2_NOT]], label [[FALSE:%.*]], label [[CONT:%.*]] ; CHECK: Cont: @@ -513,7 +513,7 @@ define i32 @maybe_pow2_32_noncont(i32 %x, i32 %y) { ; CHECK-NEXT: [[YGT8:%.*]] = icmp ugt i32 [[Y:%.*]], 8 ; CHECK-NEXT: br i1 [[YGT8]], label [[CONT1:%.*]], label [[CONT2:%.*]] ; CHECK: Cont1: -; CHECK-NEXT: [[CTPOP:%.*]] = call i32 @llvm.ctpop.i32(i32 [[Y]]), !range [[RNG0]] +; CHECK-NEXT: [[CTPOP:%.*]] = call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[Y]]) ; CHECK-NEXT: [[YP2:%.*]] = icmp eq i32 [[CTPOP]], 1 ; CHECK-NEXT: call void @llvm.assume(i1 [[YP2]]) ; CHECK-NEXT: br i1 true, label [[CONT2]], label [[FALSE:%.*]] diff --git a/llvm/test/Transforms/InstCombine/intrinsic-select.ll b/llvm/test/Transforms/InstCombine/intrinsic-select.ll index 1727d8f2758b01a3ea2292af2a3de3ed32bd71eb..f110d7765830efa3b594bd3fe950200c250cb19a 100644 --- a/llvm/test/Transforms/InstCombine/intrinsic-select.ll +++ b/llvm/test/Transforms/InstCombine/intrinsic-select.ll @@ -26,7 +26,7 @@ define i32 @ctlz_sel_const_true_false(i1 %b) { define i32 @ctlz_sel_const_true(i1 %b, i32 %x) { ; CHECK-LABEL: @ctlz_sel_const_true( -; CHECK-NEXT: [[TMP1:%.*]] = call i32 @llvm.ctlz.i32(i32 [[X:%.*]], i1 false), !range [[RNG0:![0-9]+]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[X:%.*]], i1 false) ; CHECK-NEXT: [[C:%.*]] = select i1 [[B:%.*]], i32 29, i32 [[TMP1]] ; CHECK-NEXT: ret i32 [[C]] ; @@ -37,7 +37,7 @@ define i32 @ctlz_sel_const_true(i1 %b, i32 %x) { define <3 x i17> @ctlz_sel_const_false(<3 x i1> %b, <3 x i17> %x) { ; CHECK-LABEL: @ctlz_sel_const_false( -; CHECK-NEXT: [[TMP1:%.*]] = call <3 x i17> @llvm.ctlz.v3i17(<3 x i17> [[X:%.*]], i1 true), !range [[RNG1:![0-9]+]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i17 0, 18) <3 x i17> @llvm.ctlz.v3i17(<3 x i17> [[X:%.*]], i1 true) ; CHECK-NEXT: [[C:%.*]] = select <3 x i1> [[B:%.*]], <3 x i17> [[TMP1]], <3 x i17> ; CHECK-NEXT: ret <3 x i17> [[C]] ; @@ -50,7 +50,7 @@ define i32 @ctlz_sel_const_true_false_extra_use(i1 %b) { ; CHECK-LABEL: @ctlz_sel_const_true_false_extra_use( ; CHECK-NEXT: [[S:%.*]] = select i1 [[B:%.*]], i32 -1, i32 7 ; CHECK-NEXT: call void @use(i32 [[S]]) -; CHECK-NEXT: [[C:%.*]] = call i32 @llvm.ctlz.i32(i32 [[S]], i1 true), !range [[RNG2:![0-9]+]] +; CHECK-NEXT: [[C:%.*]] = call range(i32 0, 30) i32 @llvm.ctlz.i32(i32 [[S]], i1 true) ; CHECK-NEXT: ret i32 [[C]] ; %s = select i1 %b, i32 -1, i32 7 @@ -71,7 +71,7 @@ define i32 @cttz_sel_const_true_false(i1 %b) { define i32 @cttz_sel_const_true(i1 %b, i32 %x) { ; CHECK-LABEL: @cttz_sel_const_true( -; CHECK-NEXT: [[TMP1:%.*]] = call i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 true), !range [[RNG0]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 true) ; CHECK-NEXT: [[C:%.*]] = select i1 [[B:%.*]], i32 0, i32 [[TMP1]] ; CHECK-NEXT: ret i32 [[C]] ; @@ -82,7 +82,7 @@ define i32 @cttz_sel_const_true(i1 %b, i32 %x) { define <3 x i5> @cttz_sel_const_false(<3 x i1> %b, <3 x i5> %x) { ; CHECK-LABEL: @cttz_sel_const_false( -; CHECK-NEXT: [[TMP1:%.*]] = call <3 x i5> @llvm.cttz.v3i5(<3 x i5> [[X:%.*]], i1 false), !range [[RNG3:![0-9]+]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i5 0, 6) <3 x i5> @llvm.cttz.v3i5(<3 x i5> [[X:%.*]], i1 false) ; CHECK-NEXT: [[C:%.*]] = select <3 x i1> [[B:%.*]], <3 x i5> [[TMP1]], <3 x i5> ; CHECK-NEXT: ret <3 x i5> [[C]] ; @@ -95,7 +95,7 @@ define i32 @cttz_sel_const_true_false_extra_use(i1 %b) { ; CHECK-LABEL: @cttz_sel_const_true_false_extra_use( ; CHECK-NEXT: [[S:%.*]] = select i1 [[B:%.*]], i32 5, i32 -8 ; CHECK-NEXT: call void @use(i32 [[S]]) -; CHECK-NEXT: [[C:%.*]] = call i32 @llvm.cttz.i32(i32 [[S]], i1 true), !range [[RNG0]] +; CHECK-NEXT: [[C:%.*]] = call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[S]], i1 true) ; CHECK-NEXT: ret i32 [[C]] ; %s = select i1 %b, i32 5, i32 -8 @@ -116,7 +116,7 @@ define i32 @ctpop_sel_const_true_false(i1 %b) { define i32 @ctpop_sel_const_true(i1 %b, i32 %x) { ; CHECK-LABEL: @ctpop_sel_const_true( -; CHECK-NEXT: [[TMP1:%.*]] = call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: [[C:%.*]] = select i1 [[B:%.*]], i32 2, i32 [[TMP1]] ; CHECK-NEXT: ret i32 [[C]] ; @@ -127,7 +127,7 @@ define i32 @ctpop_sel_const_true(i1 %b, i32 %x) { define <3 x i7> @ctpop_sel_const_false(<3 x i1> %b, <3 x i7> %x) { ; CHECK-LABEL: @ctpop_sel_const_false( -; CHECK-NEXT: [[TMP1:%.*]] = call <3 x i7> @llvm.ctpop.v3i7(<3 x i7> [[X:%.*]]), !range [[RNG4:![0-9]+]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i7 0, 8) <3 x i7> @llvm.ctpop.v3i7(<3 x i7> [[X:%.*]]) ; CHECK-NEXT: [[C:%.*]] = select <3 x i1> [[B:%.*]], <3 x i7> [[TMP1]], <3 x i7> ; CHECK-NEXT: ret <3 x i7> [[C]] ; @@ -140,7 +140,7 @@ define i32 @ctpop_sel_const_true_false_extra_use(i1 %b) { ; CHECK-LABEL: @ctpop_sel_const_true_false_extra_use( ; CHECK-NEXT: [[S:%.*]] = select i1 [[B:%.*]], i32 5, i32 7 ; CHECK-NEXT: call void @use(i32 [[S]]) -; CHECK-NEXT: [[C:%.*]] = call i32 @llvm.ctpop.i32(i32 [[S]]), !range [[RNG5:![0-9]+]] +; CHECK-NEXT: [[C:%.*]] = call range(i32 2, 4) i32 @llvm.ctpop.i32(i32 [[S]]) ; CHECK-NEXT: ret i32 [[C]] ; %s = select i1 %b, i32 5, i32 7 diff --git a/llvm/test/Transforms/InstCombine/intrinsics.ll b/llvm/test/Transforms/InstCombine/intrinsics.ll index d90b0ebd400c721ded351f65a9eca6679c2d1b58..c8d70e17cd392112e96bd52a937d569c6bc1be39 100644 --- a/llvm/test/Transforms/InstCombine/intrinsics.ll +++ b/llvm/test/Transforms/InstCombine/intrinsics.ll @@ -139,7 +139,7 @@ define @cttz_knownbits_scalable_vec( %arg) { define i32 @cttz_knownbits2(i32 %arg) { ; CHECK-LABEL: @cttz_knownbits2( ; CHECK-NEXT: [[OR:%.*]] = or i32 [[ARG:%.*]], 4 -; CHECK-NEXT: [[CNT:%.*]] = call i32 @llvm.cttz.i32(i32 [[OR]], i1 true) #[[ATTR2:[0-9]+]], !range [[RNG0:![0-9]+]] +; CHECK-NEXT: [[CNT:%.*]] = call range(i32 0, 3) i32 @llvm.cttz.i32(i32 [[OR]], i1 true) #[[ATTR2:[0-9]+]] ; CHECK-NEXT: ret i32 [[CNT]] ; %or = or i32 %arg, 4 @@ -150,7 +150,7 @@ define i32 @cttz_knownbits2(i32 %arg) { define <2 x i32> @cttz_knownbits2_vec(<2 x i32> %arg) { ; CHECK-LABEL: @cttz_knownbits2_vec( ; CHECK-NEXT: [[OR:%.*]] = or <2 x i32> [[ARG:%.*]], -; CHECK-NEXT: [[CNT:%.*]] = call <2 x i32> @llvm.cttz.v2i32(<2 x i32> [[OR]], i1 true) #[[ATTR2]], !range [[RNG0]] +; CHECK-NEXT: [[CNT:%.*]] = call range(i32 0, 3) <2 x i32> @llvm.cttz.v2i32(<2 x i32> [[OR]], i1 true) #[[ATTR2]] ; CHECK-NEXT: ret <2 x i32> [[CNT]] ; %or = or <2 x i32> %arg, @@ -256,7 +256,7 @@ define <2 x i1> @ctlz_knownbits_vec(<2 x i8> %arg) { define i8 @ctlz_knownbits2(i8 %arg) { ; CHECK-LABEL: @ctlz_knownbits2( ; CHECK-NEXT: [[OR:%.*]] = or i8 [[ARG:%.*]], 32 -; CHECK-NEXT: [[CNT:%.*]] = call i8 @llvm.ctlz.i8(i8 [[OR]], i1 true) #[[ATTR2]], !range [[RNG1:![0-9]+]] +; CHECK-NEXT: [[CNT:%.*]] = call range(i8 0, 3) i8 @llvm.ctlz.i8(i8 [[OR]], i1 true) #[[ATTR2]] ; CHECK-NEXT: ret i8 [[CNT]] ; %or = or i8 %arg, 32 @@ -267,7 +267,7 @@ define i8 @ctlz_knownbits2(i8 %arg) { define <2 x i8> @ctlz_knownbits2_vec(<2 x i8> %arg) { ; CHECK-LABEL: @ctlz_knownbits2_vec( ; CHECK-NEXT: [[OR:%.*]] = or <2 x i8> [[ARG:%.*]], -; CHECK-NEXT: [[CNT:%.*]] = call <2 x i8> @llvm.ctlz.v2i8(<2 x i8> [[OR]], i1 true) #[[ATTR2]], !range [[RNG1]] +; CHECK-NEXT: [[CNT:%.*]] = call range(i8 0, 3) <2 x i8> @llvm.ctlz.v2i8(<2 x i8> [[OR]], i1 true) #[[ATTR2]] ; CHECK-NEXT: ret <2 x i8> [[CNT]] ; %or = or <2 x i8> %arg, @@ -314,7 +314,7 @@ define <2 x i32> @ctlz_poison_vec(<2 x i32> %Value) { define i32 @ctlz_no_zero(i32 %a) { ; CHECK-LABEL: @ctlz_no_zero( ; CHECK-NEXT: [[OR:%.*]] = or i32 [[A:%.*]], 8 -; CHECK-NEXT: [[CTLZ:%.*]] = tail call i32 @llvm.ctlz.i32(i32 [[OR]], i1 true), !range [[RNG2:![0-9]+]] +; CHECK-NEXT: [[CTLZ:%.*]] = tail call range(i32 0, 29) i32 @llvm.ctlz.i32(i32 [[OR]], i1 true) ; CHECK-NEXT: ret i32 [[CTLZ]] ; %or = or i32 %a, 8 @@ -325,7 +325,7 @@ define i32 @ctlz_no_zero(i32 %a) { define <2 x i32> @ctlz_no_zero_vec(<2 x i32> %a) { ; CHECK-LABEL: @ctlz_no_zero_vec( ; CHECK-NEXT: [[OR:%.*]] = or <2 x i32> [[A:%.*]], -; CHECK-NEXT: [[CTLZ:%.*]] = tail call <2 x i32> @llvm.ctlz.v2i32(<2 x i32> [[OR]], i1 true), !range [[RNG2]] +; CHECK-NEXT: [[CTLZ:%.*]] = tail call range(i32 0, 29) <2 x i32> @llvm.ctlz.v2i32(<2 x i32> [[OR]], i1 true) ; CHECK-NEXT: ret <2 x i32> [[CTLZ]] ; %or = or <2 x i32> %a, @@ -352,7 +352,7 @@ define <2 x i32> @cttz_poison_vec(<2 x i32> %Value) { define i32 @cttz_no_zero(i32 %a) { ; CHECK-LABEL: @cttz_no_zero( ; CHECK-NEXT: [[OR:%.*]] = or i32 [[A:%.*]], 8 -; CHECK-NEXT: [[CTTZ:%.*]] = tail call i32 @llvm.cttz.i32(i32 [[OR]], i1 true), !range [[RNG3:![0-9]+]] +; CHECK-NEXT: [[CTTZ:%.*]] = tail call range(i32 0, 4) i32 @llvm.cttz.i32(i32 [[OR]], i1 true) ; CHECK-NEXT: ret i32 [[CTTZ]] ; %or = or i32 %a, 8 @@ -363,7 +363,7 @@ define i32 @cttz_no_zero(i32 %a) { define <2 x i32> @cttz_no_zero_vec(<2 x i32> %a) { ; CHECK-LABEL: @cttz_no_zero_vec( ; CHECK-NEXT: [[OR:%.*]] = or <2 x i32> [[A:%.*]], -; CHECK-NEXT: [[CTTZ:%.*]] = tail call <2 x i32> @llvm.cttz.v2i32(<2 x i32> [[OR]], i1 true), !range [[RNG3]] +; CHECK-NEXT: [[CTTZ:%.*]] = tail call range(i32 0, 4) <2 x i32> @llvm.cttz.v2i32(<2 x i32> [[OR]], i1 true) ; CHECK-NEXT: ret <2 x i32> [[CTTZ]] ; %or = or <2 x i32> %a, @@ -373,7 +373,7 @@ define <2 x i32> @cttz_no_zero_vec(<2 x i32> %a) { define i32 @ctlz_select(i32 %Value) nounwind { ; CHECK-LABEL: @ctlz_select( -; CHECK-NEXT: [[CTLZ:%.*]] = call i32 @llvm.ctlz.i32(i32 [[VALUE:%.*]], i1 false), !range [[RNG4:![0-9]+]] +; CHECK-NEXT: [[CTLZ:%.*]] = call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[VALUE:%.*]], i1 false) ; CHECK-NEXT: ret i32 [[CTLZ]] ; %tobool = icmp ne i32 %Value, 0 @@ -384,7 +384,7 @@ define i32 @ctlz_select(i32 %Value) nounwind { define <2 x i32> @ctlz_select_vec(<2 x i32> %Value) nounwind { ; CHECK-LABEL: @ctlz_select_vec( -; CHECK-NEXT: [[CTLZ:%.*]] = call <2 x i32> @llvm.ctlz.v2i32(<2 x i32> [[VALUE:%.*]], i1 false), !range [[RNG4]] +; CHECK-NEXT: [[CTLZ:%.*]] = call range(i32 0, 33) <2 x i32> @llvm.ctlz.v2i32(<2 x i32> [[VALUE:%.*]], i1 false) ; CHECK-NEXT: ret <2 x i32> [[CTLZ]] ; %tobool = icmp ne <2 x i32> %Value, zeroinitializer @@ -395,7 +395,7 @@ define <2 x i32> @ctlz_select_vec(<2 x i32> %Value) nounwind { define i32 @cttz_select(i32 %Value) nounwind { ; CHECK-LABEL: @cttz_select( -; CHECK-NEXT: [[CTTZ:%.*]] = call i32 @llvm.cttz.i32(i32 [[VALUE:%.*]], i1 false), !range [[RNG4]] +; CHECK-NEXT: [[CTTZ:%.*]] = call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[VALUE:%.*]], i1 false) ; CHECK-NEXT: ret i32 [[CTTZ]] ; %tobool = icmp ne i32 %Value, 0 @@ -406,7 +406,7 @@ define i32 @cttz_select(i32 %Value) nounwind { define <2 x i32> @cttz_select_vec(<2 x i32> %Value) nounwind { ; CHECK-LABEL: @cttz_select_vec( -; CHECK-NEXT: [[CTTZ:%.*]] = call <2 x i32> @llvm.cttz.v2i32(<2 x i32> [[VALUE:%.*]], i1 false), !range [[RNG4]] +; CHECK-NEXT: [[CTTZ:%.*]] = call range(i32 0, 33) <2 x i32> @llvm.cttz.v2i32(<2 x i32> [[VALUE:%.*]], i1 false) ; CHECK-NEXT: ret <2 x i32> [[CTTZ]] ; %tobool = icmp ne <2 x i32> %Value, zeroinitializer diff --git a/llvm/test/Transforms/InstCombine/ispow2.ll b/llvm/test/Transforms/InstCombine/ispow2.ll index cc50c5cd1e6680a8353087ddfaa3c50f49c76808..a143b1347ccee5b85c2f366705f4b9b29218edab 100644 --- a/llvm/test/Transforms/InstCombine/ispow2.ll +++ b/llvm/test/Transforms/InstCombine/ispow2.ll @@ -3,7 +3,7 @@ define i1 @is_pow2or0_negate_op(i32 %x) { ; CHECK-LABEL: @is_pow2or0_negate_op( -; CHECK-NEXT: [[TMP1:%.*]] = call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0:![0-9]+]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ult i32 [[TMP1]], 2 ; CHECK-NEXT: ret i1 [[CMP]] ; @@ -15,7 +15,7 @@ define i1 @is_pow2or0_negate_op(i32 %x) { define <2 x i1> @is_pow2or0_negate_op_vec(<2 x i32> %x) { ; CHECK-LABEL: @is_pow2or0_negate_op_vec( -; CHECK-NEXT: [[TMP1:%.*]] = call <2 x i32> @llvm.ctpop.v2i32(<2 x i32> [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i32 0, 33) <2 x i32> @llvm.ctpop.v2i32(<2 x i32> [[X:%.*]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ult <2 x i32> [[TMP1]], ; CHECK-NEXT: ret <2 x i1> [[CMP]] ; @@ -27,7 +27,7 @@ define <2 x i1> @is_pow2or0_negate_op_vec(<2 x i32> %x) { define i1 @is_pow2or0_decrement_op(i8 %x) { ; CHECK-LABEL: @is_pow2or0_decrement_op( -; CHECK-NEXT: [[TMP1:%.*]] = call i8 @llvm.ctpop.i8(i8 [[X:%.*]]), !range [[RNG1:![0-9]+]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i8 0, 9) i8 @llvm.ctpop.i8(i8 [[X:%.*]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ult i8 [[TMP1]], 2 ; CHECK-NEXT: ret i1 [[CMP]] ; @@ -39,7 +39,7 @@ define i1 @is_pow2or0_decrement_op(i8 %x) { define <2 x i1> @is_pow2or0_decrement_op_vec(<2 x i8> %x) { ; CHECK-LABEL: @is_pow2or0_decrement_op_vec( -; CHECK-NEXT: [[TMP1:%.*]] = call <2 x i8> @llvm.ctpop.v2i8(<2 x i8> [[X:%.*]]), !range [[RNG1]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i8 0, 9) <2 x i8> @llvm.ctpop.v2i8(<2 x i8> [[X:%.*]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ult <2 x i8> [[TMP1]], ; CHECK-NEXT: ret <2 x i1> [[CMP]] ; @@ -51,7 +51,7 @@ define <2 x i1> @is_pow2or0_decrement_op_vec(<2 x i8> %x) { define i1 @isnot_pow2or0_negate_op(i32 %x) { ; CHECK-LABEL: @isnot_pow2or0_negate_op( -; CHECK-NEXT: [[TMP1:%.*]] = call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ugt i32 [[TMP1]], 1 ; CHECK-NEXT: ret i1 [[CMP]] ; @@ -63,7 +63,7 @@ define i1 @isnot_pow2or0_negate_op(i32 %x) { define <2 x i1> @isnot_pow2or0_negate_op_vec(<2 x i32> %x) { ; CHECK-LABEL: @isnot_pow2or0_negate_op_vec( -; CHECK-NEXT: [[TMP1:%.*]] = call <2 x i32> @llvm.ctpop.v2i32(<2 x i32> [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i32 0, 33) <2 x i32> @llvm.ctpop.v2i32(<2 x i32> [[X:%.*]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ugt <2 x i32> [[TMP1]], ; CHECK-NEXT: ret <2 x i1> [[CMP]] ; @@ -75,7 +75,7 @@ define <2 x i1> @isnot_pow2or0_negate_op_vec(<2 x i32> %x) { define i1 @isnot_pow2or0_decrement_op(i8 %x) { ; CHECK-LABEL: @isnot_pow2or0_decrement_op( -; CHECK-NEXT: [[TMP1:%.*]] = call i8 @llvm.ctpop.i8(i8 [[X:%.*]]), !range [[RNG1]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i8 0, 9) i8 @llvm.ctpop.i8(i8 [[X:%.*]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ugt i8 [[TMP1]], 1 ; CHECK-NEXT: ret i1 [[CMP]] ; @@ -87,7 +87,7 @@ define i1 @isnot_pow2or0_decrement_op(i8 %x) { define <2 x i1> @isnot_pow2or0_decrement_op_vec(<2 x i8> %x) { ; CHECK-LABEL: @isnot_pow2or0_decrement_op_vec( -; CHECK-NEXT: [[TMP1:%.*]] = call <2 x i8> @llvm.ctpop.v2i8(<2 x i8> [[X:%.*]]), !range [[RNG1]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i8 0, 9) <2 x i8> @llvm.ctpop.v2i8(<2 x i8> [[X:%.*]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ugt <2 x i8> [[TMP1]], ; CHECK-NEXT: ret <2 x i1> [[CMP]] ; @@ -100,7 +100,7 @@ define <2 x i1> @isnot_pow2or0_decrement_op_vec(<2 x i8> %x) { define i1 @is_pow2or0_negate_op_commute1(i32 %p) { ; CHECK-LABEL: @is_pow2or0_negate_op_commute1( ; CHECK-NEXT: [[X:%.*]] = srem i32 42, [[P:%.*]] -; CHECK-NEXT: [[TMP1:%.*]] = call i32 @llvm.ctpop.i32(i32 [[X]]), !range [[RNG2:![0-9]+]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i32 0, 7) i32 @llvm.ctpop.i32(i32 [[X]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ult i32 [[TMP1]], 2 ; CHECK-NEXT: ret i1 [[CMP]] ; @@ -116,7 +116,7 @@ define i1 @is_pow2or0_negate_op_commute1(i32 %p) { define i1 @isnot_pow2or0_negate_op_commute2(i32 %p) { ; CHECK-LABEL: @isnot_pow2or0_negate_op_commute2( ; CHECK-NEXT: [[X:%.*]] = urem i32 42, [[P:%.*]] -; CHECK-NEXT: [[TMP1:%.*]] = call i32 @llvm.ctpop.i32(i32 [[X]]), !range [[RNG2]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i32 0, 7) i32 @llvm.ctpop.i32(i32 [[X]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ugt i32 [[TMP1]], 1 ; CHECK-NEXT: ret i1 [[CMP]] ; @@ -130,7 +130,7 @@ define i1 @isnot_pow2or0_negate_op_commute2(i32 %p) { define i1 @isnot_pow2or0_negate_op_commute3(i32 %p) { ; CHECK-LABEL: @isnot_pow2or0_negate_op_commute3( ; CHECK-NEXT: [[X:%.*]] = urem i32 42, [[P:%.*]] -; CHECK-NEXT: [[TMP1:%.*]] = call i32 @llvm.ctpop.i32(i32 [[X]]), !range [[RNG2]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i32 0, 7) i32 @llvm.ctpop.i32(i32 [[X]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ugt i32 [[TMP1]], 1 ; CHECK-NEXT: ret i1 [[CMP]] ; @@ -147,7 +147,7 @@ define i1 @is_pow2or0_negate_op_extra_use1(i32 %x) { ; CHECK-LABEL: @is_pow2or0_negate_op_extra_use1( ; CHECK-NEXT: [[NEG:%.*]] = sub i32 0, [[X:%.*]] ; CHECK-NEXT: call void @use(i32 [[NEG]]) -; CHECK-NEXT: [[TMP1:%.*]] = call i32 @llvm.ctpop.i32(i32 [[X]]), !range [[RNG0]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ult i32 [[TMP1]], 2 ; CHECK-NEXT: ret i1 [[CMP]] ; @@ -181,7 +181,7 @@ declare void @llvm.assume(i1) define i1 @is_pow2_ctpop(i32 %x) { ; CHECK-LABEL: @is_pow2_ctpop( -; CHECK-NEXT: [[T0:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: [[R:%.*]] = icmp eq i32 [[T0]], 1 ; CHECK-NEXT: ret i1 [[R]] ; @@ -197,7 +197,7 @@ define i1 @is_pow2_non_zero_ult_2(i32 %x) { ; CHECK-LABEL: @is_pow2_non_zero_ult_2( ; CHECK-NEXT: [[NOTZERO:%.*]] = icmp ne i32 [[X:%.*]], 0 ; CHECK-NEXT: call void @llvm.assume(i1 [[NOTZERO]]) -; CHECK-NEXT: [[T0:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X]]), !range [[RNG0]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ult i32 [[T0]], 2 ; CHECK-NEXT: ret i1 [[CMP]] ; @@ -212,7 +212,7 @@ define i1 @is_pow2_non_zero_eq_1(i32 %x) { ; CHECK-LABEL: @is_pow2_non_zero_eq_1( ; CHECK-NEXT: [[NOTZERO:%.*]] = icmp ne i32 [[X:%.*]], 0 ; CHECK-NEXT: call void @llvm.assume(i1 [[NOTZERO]]) -; CHECK-NEXT: [[T0:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X]]), !range [[RNG0]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp eq i32 [[T0]], 1 ; CHECK-NEXT: ret i1 [[CMP]] ; @@ -227,7 +227,7 @@ define i1 @is_pow2_non_zero_ugt_1(i32 %x) { ; CHECK-LABEL: @is_pow2_non_zero_ugt_1( ; CHECK-NEXT: [[NOTZERO:%.*]] = icmp ne i32 [[X:%.*]], 0 ; CHECK-NEXT: call void @llvm.assume(i1 [[NOTZERO]]) -; CHECK-NEXT: [[T0:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X]]), !range [[RNG0]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ugt i32 [[T0]], 1 ; CHECK-NEXT: ret i1 [[CMP]] ; @@ -242,7 +242,7 @@ define i1 @is_pow2_non_zero_ne_1(i32 %x) { ; CHECK-LABEL: @is_pow2_non_zero_ne_1( ; CHECK-NEXT: [[NOTZERO:%.*]] = icmp ne i32 [[X:%.*]], 0 ; CHECK-NEXT: call void @llvm.assume(i1 [[NOTZERO]]) -; CHECK-NEXT: [[T0:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X]]), !range [[RNG0]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ne i32 [[T0]], 1 ; CHECK-NEXT: ret i1 [[CMP]] ; @@ -255,7 +255,7 @@ define i1 @is_pow2_non_zero_ne_1(i32 %x) { define i1 @is_pow2_ctpop_logical(i32 %x) { ; CHECK-LABEL: @is_pow2_ctpop_logical( -; CHECK-NEXT: [[T0:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: [[R:%.*]] = icmp eq i32 [[T0]], 1 ; CHECK-NEXT: ret i1 [[R]] ; @@ -271,7 +271,7 @@ declare void @use_i1(i1) define i1 @is_pow2_ctpop_extra_uses(i32 %x) { ; CHECK-LABEL: @is_pow2_ctpop_extra_uses( -; CHECK-NEXT: [[T0:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ult i32 [[T0]], 2 ; CHECK-NEXT: call void @use_i1(i1 [[CMP]]) ; CHECK-NEXT: [[NOTZERO:%.*]] = icmp ne i32 [[X]], 0 @@ -290,7 +290,7 @@ define i1 @is_pow2_ctpop_extra_uses(i32 %x) { define i1 @is_pow2_ctpop_extra_uses_logical(i32 %x) { ; CHECK-LABEL: @is_pow2_ctpop_extra_uses_logical( -; CHECK-NEXT: [[T0:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ult i32 [[T0]], 2 ; CHECK-NEXT: call void @use_i1(i1 [[CMP]]) ; CHECK-NEXT: [[NOTZERO:%.*]] = icmp ne i32 [[X]], 0 @@ -311,7 +311,7 @@ define i1 @is_pow2_ctpop_extra_uses_logical(i32 %x) { define <2 x i1> @is_pow2_ctpop_commute_vec(<2 x i8> %x) { ; CHECK-LABEL: @is_pow2_ctpop_commute_vec( -; CHECK-NEXT: [[T0:%.*]] = tail call <2 x i8> @llvm.ctpop.v2i8(<2 x i8> [[X:%.*]]), !range [[RNG1]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i8 0, 9) <2 x i8> @llvm.ctpop.v2i8(<2 x i8> [[X:%.*]]) ; CHECK-NEXT: [[R:%.*]] = icmp eq <2 x i8> [[T0]], ; CHECK-NEXT: ret <2 x i1> [[R]] ; @@ -326,7 +326,7 @@ define <2 x i1> @is_pow2_ctpop_commute_vec(<2 x i8> %x) { define i1 @is_pow2_ctpop_wrong_cmp_op1(i32 %x) { ; CHECK-LABEL: @is_pow2_ctpop_wrong_cmp_op1( -; CHECK-NEXT: [[T0:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ult i32 [[T0]], 3 ; CHECK-NEXT: [[NOTZERO:%.*]] = icmp ne i32 [[X]], 0 ; CHECK-NEXT: [[R:%.*]] = and i1 [[NOTZERO]], [[CMP]] @@ -341,7 +341,7 @@ define i1 @is_pow2_ctpop_wrong_cmp_op1(i32 %x) { define i1 @is_pow2_ctpop_wrong_cmp_op1_logical(i32 %x) { ; CHECK-LABEL: @is_pow2_ctpop_wrong_cmp_op1_logical( -; CHECK-NEXT: [[T0:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ult i32 [[T0]], 3 ; CHECK-NEXT: [[NOTZERO:%.*]] = icmp ne i32 [[X]], 0 ; CHECK-NEXT: [[R:%.*]] = select i1 [[NOTZERO]], i1 [[CMP]], i1 false @@ -358,7 +358,7 @@ define i1 @is_pow2_ctpop_wrong_cmp_op1_logical(i32 %x) { define i1 @is_pow2_ctpop_wrong_cmp_op2(i32 %x) { ; CHECK-LABEL: @is_pow2_ctpop_wrong_cmp_op2( -; CHECK-NEXT: [[T0:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ult i32 [[T0]], 2 ; CHECK-NEXT: [[NOTZERO:%.*]] = icmp ne i32 [[X]], 1 ; CHECK-NEXT: [[R:%.*]] = and i1 [[NOTZERO]], [[CMP]] @@ -373,7 +373,7 @@ define i1 @is_pow2_ctpop_wrong_cmp_op2(i32 %x) { define i1 @is_pow2_ctpop_wrong_cmp_op2_logical(i32 %x) { ; CHECK-LABEL: @is_pow2_ctpop_wrong_cmp_op2_logical( -; CHECK-NEXT: [[T0:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ult i32 [[T0]], 2 ; CHECK-NEXT: [[NOTZERO:%.*]] = icmp ne i32 [[X]], 1 ; CHECK-NEXT: [[R:%.*]] = select i1 [[NOTZERO]], i1 [[CMP]], i1 false @@ -390,7 +390,7 @@ define i1 @is_pow2_ctpop_wrong_cmp_op2_logical(i32 %x) { define i1 @is_pow2_ctpop_wrong_pred1(i32 %x) { ; CHECK-LABEL: @is_pow2_ctpop_wrong_pred1( -; CHECK-NEXT: [[T0:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ugt i32 [[T0]], 2 ; CHECK-NEXT: ret i1 [[CMP]] ; @@ -403,7 +403,7 @@ define i1 @is_pow2_ctpop_wrong_pred1(i32 %x) { define i1 @is_pow2_ctpop_wrong_pred1_logical(i32 %x) { ; CHECK-LABEL: @is_pow2_ctpop_wrong_pred1_logical( -; CHECK-NEXT: [[T0:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ugt i32 [[T0]], 2 ; CHECK-NEXT: ret i1 [[CMP]] ; @@ -418,7 +418,7 @@ define i1 @is_pow2_ctpop_wrong_pred1_logical(i32 %x) { define i1 @is_pow2_ctpop_wrong_pred2(i32 %x) { ; CHECK-LABEL: @is_pow2_ctpop_wrong_pred2( -; CHECK-NEXT: [[T0:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ult i32 [[T0]], 2 ; CHECK-NEXT: [[CMP2:%.*]] = icmp sgt i32 [[X]], 0 ; CHECK-NEXT: [[R:%.*]] = and i1 [[CMP2]], [[CMP]] @@ -433,7 +433,7 @@ define i1 @is_pow2_ctpop_wrong_pred2(i32 %x) { define i1 @is_pow2_ctpop_wrong_pred2_logical(i32 %x) { ; CHECK-LABEL: @is_pow2_ctpop_wrong_pred2_logical( -; CHECK-NEXT: [[T0:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ult i32 [[T0]], 2 ; CHECK-NEXT: [[CMP2:%.*]] = icmp sgt i32 [[X]], 0 ; CHECK-NEXT: [[R:%.*]] = select i1 [[CMP2]], i1 [[CMP]], i1 false @@ -450,7 +450,7 @@ define i1 @is_pow2_ctpop_wrong_pred2_logical(i32 %x) { define i1 @isnot_pow2_ctpop(i32 %x) { ; CHECK-LABEL: @isnot_pow2_ctpop( -; CHECK-NEXT: [[T0:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: [[R:%.*]] = icmp ne i32 [[T0]], 1 ; CHECK-NEXT: ret i1 [[R]] ; @@ -463,7 +463,7 @@ define i1 @isnot_pow2_ctpop(i32 %x) { define i1 @isnot_pow2_ctpop_logical(i32 %x) { ; CHECK-LABEL: @isnot_pow2_ctpop_logical( -; CHECK-NEXT: [[T0:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: [[R:%.*]] = icmp ne i32 [[T0]], 1 ; CHECK-NEXT: ret i1 [[R]] ; @@ -478,7 +478,7 @@ define i1 @isnot_pow2_ctpop_logical(i32 %x) { define i1 @isnot_pow2_ctpop_extra_uses(i32 %x) { ; CHECK-LABEL: @isnot_pow2_ctpop_extra_uses( -; CHECK-NEXT: [[T0:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ugt i32 [[T0]], 1 ; CHECK-NEXT: call void @use_i1(i1 [[CMP]]) ; CHECK-NEXT: [[ISZERO:%.*]] = icmp eq i32 [[X]], 0 @@ -497,7 +497,7 @@ define i1 @isnot_pow2_ctpop_extra_uses(i32 %x) { define i1 @isnot_pow2_ctpop_extra_uses_logical(i32 %x) { ; CHECK-LABEL: @isnot_pow2_ctpop_extra_uses_logical( -; CHECK-NEXT: [[T0:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ugt i32 [[T0]], 1 ; CHECK-NEXT: call void @use_i1(i1 [[CMP]]) ; CHECK-NEXT: [[ISZERO:%.*]] = icmp eq i32 [[X]], 0 @@ -518,7 +518,7 @@ define i1 @isnot_pow2_ctpop_extra_uses_logical(i32 %x) { define <2 x i1> @isnot_pow2_ctpop_commute_vec(<2 x i8> %x) { ; CHECK-LABEL: @isnot_pow2_ctpop_commute_vec( -; CHECK-NEXT: [[T0:%.*]] = tail call <2 x i8> @llvm.ctpop.v2i8(<2 x i8> [[X:%.*]]), !range [[RNG1]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i8 0, 9) <2 x i8> @llvm.ctpop.v2i8(<2 x i8> [[X:%.*]]) ; CHECK-NEXT: [[R:%.*]] = icmp ne <2 x i8> [[T0]], ; CHECK-NEXT: ret <2 x i1> [[R]] ; @@ -533,7 +533,7 @@ define <2 x i1> @isnot_pow2_ctpop_commute_vec(<2 x i8> %x) { define i1 @isnot_pow2_ctpop_wrong_cmp_op1(i32 %x) { ; CHECK-LABEL: @isnot_pow2_ctpop_wrong_cmp_op1( -; CHECK-NEXT: [[T0:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ugt i32 [[T0]], 2 ; CHECK-NEXT: [[ISZERO:%.*]] = icmp eq i32 [[X]], 0 ; CHECK-NEXT: [[R:%.*]] = or i1 [[ISZERO]], [[CMP]] @@ -548,7 +548,7 @@ define i1 @isnot_pow2_ctpop_wrong_cmp_op1(i32 %x) { define i1 @isnot_pow2_ctpop_wrong_cmp_op1_logical(i32 %x) { ; CHECK-LABEL: @isnot_pow2_ctpop_wrong_cmp_op1_logical( -; CHECK-NEXT: [[T0:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ugt i32 [[T0]], 2 ; CHECK-NEXT: [[ISZERO:%.*]] = icmp eq i32 [[X]], 0 ; CHECK-NEXT: [[R:%.*]] = select i1 [[ISZERO]], i1 true, i1 [[CMP]] @@ -565,7 +565,7 @@ define i1 @isnot_pow2_ctpop_wrong_cmp_op1_logical(i32 %x) { define i1 @isnot_pow2_ctpop_wrong_cmp_op2(i32 %x) { ; CHECK-LABEL: @isnot_pow2_ctpop_wrong_cmp_op2( -; CHECK-NEXT: [[T0:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ugt i32 [[T0]], 1 ; CHECK-NEXT: [[ISZERO:%.*]] = icmp eq i32 [[X]], 1 ; CHECK-NEXT: [[R:%.*]] = or i1 [[ISZERO]], [[CMP]] @@ -580,7 +580,7 @@ define i1 @isnot_pow2_ctpop_wrong_cmp_op2(i32 %x) { define i1 @isnot_pow2_ctpop_wrong_cmp_op2_logical(i32 %x) { ; CHECK-LABEL: @isnot_pow2_ctpop_wrong_cmp_op2_logical( -; CHECK-NEXT: [[T0:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ugt i32 [[T0]], 1 ; CHECK-NEXT: [[ISZERO:%.*]] = icmp eq i32 [[X]], 1 ; CHECK-NEXT: [[R:%.*]] = select i1 [[ISZERO]], i1 true, i1 [[CMP]] @@ -597,7 +597,7 @@ define i1 @isnot_pow2_ctpop_wrong_cmp_op2_logical(i32 %x) { define i1 @isnot_pow2_ctpop_wrong_pred2(i32 %x) { ; CHECK-LABEL: @isnot_pow2_ctpop_wrong_pred2( -; CHECK-NEXT: [[T0:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ugt i32 [[T0]], 1 ; CHECK-NEXT: [[CMP2:%.*]] = icmp slt i32 [[X]], 0 ; CHECK-NEXT: [[R:%.*]] = or i1 [[CMP2]], [[CMP]] @@ -612,7 +612,7 @@ define i1 @isnot_pow2_ctpop_wrong_pred2(i32 %x) { define i1 @isnot_pow2_ctpop_wrong_pred2_logical(i32 %x) { ; CHECK-LABEL: @isnot_pow2_ctpop_wrong_pred2_logical( -; CHECK-NEXT: [[T0:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ugt i32 [[T0]], 1 ; CHECK-NEXT: [[CMP2:%.*]] = icmp slt i32 [[X]], 0 ; CHECK-NEXT: [[R:%.*]] = select i1 [[CMP2]], i1 true, i1 [[CMP]] @@ -627,7 +627,7 @@ define i1 @isnot_pow2_ctpop_wrong_pred2_logical(i32 %x) { define i1 @is_pow2_negate_op(i32 %x) { ; CHECK-LABEL: @is_pow2_negate_op( -; CHECK-NEXT: [[TMP1:%.*]] = call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: [[R:%.*]] = icmp eq i32 [[TMP1]], 1 ; CHECK-NEXT: ret i1 [[R]] ; @@ -641,7 +641,7 @@ define i1 @is_pow2_negate_op(i32 %x) { define i1 @is_pow2_negate_op_logical(i32 %x) { ; CHECK-LABEL: @is_pow2_negate_op_logical( -; CHECK-NEXT: [[TMP1:%.*]] = call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: [[R:%.*]] = icmp eq i32 [[TMP1]], 1 ; CHECK-NEXT: ret i1 [[R]] ; @@ -655,7 +655,7 @@ define i1 @is_pow2_negate_op_logical(i32 %x) { define <2 x i1> @is_pow2_negate_op_vec(<2 x i32> %x) { ; CHECK-LABEL: @is_pow2_negate_op_vec( -; CHECK-NEXT: [[TMP1:%.*]] = call <2 x i32> @llvm.ctpop.v2i32(<2 x i32> [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i32 0, 33) <2 x i32> @llvm.ctpop.v2i32(<2 x i32> [[X:%.*]]) ; CHECK-NEXT: [[R:%.*]] = icmp eq <2 x i32> [[TMP1]], ; CHECK-NEXT: ret <2 x i1> [[R]] ; @@ -669,7 +669,7 @@ define <2 x i1> @is_pow2_negate_op_vec(<2 x i32> %x) { define i1 @is_pow2_decrement_op(i8 %x) { ; CHECK-LABEL: @is_pow2_decrement_op( -; CHECK-NEXT: [[TMP1:%.*]] = call i8 @llvm.ctpop.i8(i8 [[X:%.*]]), !range [[RNG1]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i8 0, 9) i8 @llvm.ctpop.i8(i8 [[X:%.*]]) ; CHECK-NEXT: [[R:%.*]] = icmp eq i8 [[TMP1]], 1 ; CHECK-NEXT: ret i1 [[R]] ; @@ -683,7 +683,7 @@ define i1 @is_pow2_decrement_op(i8 %x) { define i1 @is_pow2_decrement_op_logical(i8 %x) { ; CHECK-LABEL: @is_pow2_decrement_op_logical( -; CHECK-NEXT: [[TMP1:%.*]] = call i8 @llvm.ctpop.i8(i8 [[X:%.*]]), !range [[RNG1]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i8 0, 9) i8 @llvm.ctpop.i8(i8 [[X:%.*]]) ; CHECK-NEXT: [[R:%.*]] = icmp eq i8 [[TMP1]], 1 ; CHECK-NEXT: ret i1 [[R]] ; @@ -697,7 +697,7 @@ define i1 @is_pow2_decrement_op_logical(i8 %x) { define <2 x i1> @is_pow2_decrement_op_vec(<2 x i8> %x) { ; CHECK-LABEL: @is_pow2_decrement_op_vec( -; CHECK-NEXT: [[TMP1:%.*]] = call <2 x i8> @llvm.ctpop.v2i8(<2 x i8> [[X:%.*]]), !range [[RNG1]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i8 0, 9) <2 x i8> @llvm.ctpop.v2i8(<2 x i8> [[X:%.*]]) ; CHECK-NEXT: [[R:%.*]] = icmp eq <2 x i8> [[TMP1]], ; CHECK-NEXT: ret <2 x i1> [[R]] ; @@ -711,7 +711,7 @@ define <2 x i1> @is_pow2_decrement_op_vec(<2 x i8> %x) { define i1 @isnot_pow2_negate_op(i32 %x) { ; CHECK-LABEL: @isnot_pow2_negate_op( -; CHECK-NEXT: [[TMP1:%.*]] = call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: [[R:%.*]] = icmp ne i32 [[TMP1]], 1 ; CHECK-NEXT: ret i1 [[R]] ; @@ -725,7 +725,7 @@ define i1 @isnot_pow2_negate_op(i32 %x) { define i1 @isnot_pow2_negate_op_logical(i32 %x) { ; CHECK-LABEL: @isnot_pow2_negate_op_logical( -; CHECK-NEXT: [[TMP1:%.*]] = call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: [[R:%.*]] = icmp ne i32 [[TMP1]], 1 ; CHECK-NEXT: ret i1 [[R]] ; @@ -739,7 +739,7 @@ define i1 @isnot_pow2_negate_op_logical(i32 %x) { define <2 x i1> @isnot_pow2_negate_op_vec(<2 x i32> %x) { ; CHECK-LABEL: @isnot_pow2_negate_op_vec( -; CHECK-NEXT: [[TMP1:%.*]] = call <2 x i32> @llvm.ctpop.v2i32(<2 x i32> [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i32 0, 33) <2 x i32> @llvm.ctpop.v2i32(<2 x i32> [[X:%.*]]) ; CHECK-NEXT: [[R:%.*]] = icmp ne <2 x i32> [[TMP1]], ; CHECK-NEXT: ret <2 x i1> [[R]] ; @@ -753,7 +753,7 @@ define <2 x i1> @isnot_pow2_negate_op_vec(<2 x i32> %x) { define i1 @isnot_pow2_decrement_op(i8 %x) { ; CHECK-LABEL: @isnot_pow2_decrement_op( -; CHECK-NEXT: [[TMP1:%.*]] = call i8 @llvm.ctpop.i8(i8 [[X:%.*]]), !range [[RNG1]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i8 0, 9) i8 @llvm.ctpop.i8(i8 [[X:%.*]]) ; CHECK-NEXT: [[R:%.*]] = icmp ne i8 [[TMP1]], 1 ; CHECK-NEXT: ret i1 [[R]] ; @@ -767,7 +767,7 @@ define i1 @isnot_pow2_decrement_op(i8 %x) { define i1 @isnot_pow2_decrement_op_logical(i8 %x) { ; CHECK-LABEL: @isnot_pow2_decrement_op_logical( -; CHECK-NEXT: [[TMP1:%.*]] = call i8 @llvm.ctpop.i8(i8 [[X:%.*]]), !range [[RNG1]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i8 0, 9) i8 @llvm.ctpop.i8(i8 [[X:%.*]]) ; CHECK-NEXT: [[R:%.*]] = icmp ne i8 [[TMP1]], 1 ; CHECK-NEXT: ret i1 [[R]] ; @@ -781,7 +781,7 @@ define i1 @isnot_pow2_decrement_op_logical(i8 %x) { define <2 x i1> @isnot_pow2_decrement_op_vec(<2 x i8> %x) { ; CHECK-LABEL: @isnot_pow2_decrement_op_vec( -; CHECK-NEXT: [[TMP1:%.*]] = call <2 x i8> @llvm.ctpop.v2i8(<2 x i8> [[X:%.*]]), !range [[RNG1]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i8 0, 9) <2 x i8> @llvm.ctpop.v2i8(<2 x i8> [[X:%.*]]) ; CHECK-NEXT: [[R:%.*]] = icmp ne <2 x i8> [[TMP1]], ; CHECK-NEXT: ret <2 x i1> [[R]] ; @@ -797,7 +797,7 @@ define <2 x i1> @isnot_pow2_decrement_op_vec(<2 x i8> %x) { define i1 @is_pow2or0_ctpop(i32 %x) { ; CHECK-LABEL: @is_pow2or0_ctpop( -; CHECK-NEXT: [[T0:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: [[R:%.*]] = icmp ult i32 [[T0]], 2 ; CHECK-NEXT: ret i1 [[R]] ; @@ -810,7 +810,7 @@ define i1 @is_pow2or0_ctpop(i32 %x) { define i1 @is_pow2or0_ctpop_swap_cmp(i32 %x) { ; CHECK-LABEL: @is_pow2or0_ctpop_swap_cmp( -; CHECK-NEXT: [[T0:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: [[R:%.*]] = icmp ult i32 [[T0]], 2 ; CHECK-NEXT: ret i1 [[R]] ; @@ -823,7 +823,7 @@ define i1 @is_pow2or0_ctpop_swap_cmp(i32 %x) { define i1 @is_pow2or0_ctpop_logical(i32 %x) { ; CHECK-LABEL: @is_pow2or0_ctpop_logical( -; CHECK-NEXT: [[T0:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: [[R:%.*]] = icmp ult i32 [[T0]], 2 ; CHECK-NEXT: ret i1 [[R]] ; @@ -836,7 +836,7 @@ define i1 @is_pow2or0_ctpop_logical(i32 %x) { define <2 x i1> @is_pow2or0_ctpop_commute_vec(<2 x i8> %x) { ; CHECK-LABEL: @is_pow2or0_ctpop_commute_vec( -; CHECK-NEXT: [[T0:%.*]] = tail call <2 x i8> @llvm.ctpop.v2i8(<2 x i8> [[X:%.*]]), !range [[RNG1]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i8 0, 9) <2 x i8> @llvm.ctpop.v2i8(<2 x i8> [[X:%.*]]) ; CHECK-NEXT: [[R:%.*]] = icmp ult <2 x i8> [[T0]], ; CHECK-NEXT: ret <2 x i1> [[R]] ; @@ -851,7 +851,7 @@ define <2 x i1> @is_pow2or0_ctpop_commute_vec(<2 x i8> %x) { define i1 @is_pow2or0_ctpop_extra_uses(i32 %x) { ; CHECK-LABEL: @is_pow2or0_ctpop_extra_uses( -; CHECK-NEXT: [[T0:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: call void @use(i32 [[T0]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp eq i32 [[T0]], 1 ; CHECK-NEXT: call void @use_i1(i1 [[CMP]]) @@ -872,7 +872,7 @@ define i1 @is_pow2or0_ctpop_extra_uses(i32 %x) { define i1 @is_pow2or0_ctpop_logical_extra_uses(i32 %x) { ; CHECK-LABEL: @is_pow2or0_ctpop_logical_extra_uses( -; CHECK-NEXT: [[T0:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: call void @use(i32 [[T0]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp eq i32 [[T0]], 1 ; CHECK-NEXT: call void @use_i1(i1 [[CMP]]) @@ -895,7 +895,7 @@ define i1 @is_pow2or0_ctpop_logical_extra_uses(i32 %x) { define i1 @is_pow2or0_ctpop_wrong_cmp_op1(i32 %x) { ; CHECK-LABEL: @is_pow2or0_ctpop_wrong_cmp_op1( -; CHECK-NEXT: [[T0:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp eq i32 [[T0]], 2 ; CHECK-NEXT: [[ISZERO:%.*]] = icmp eq i32 [[X]], 0 ; CHECK-NEXT: [[R:%.*]] = or i1 [[ISZERO]], [[CMP]] @@ -910,7 +910,7 @@ define i1 @is_pow2or0_ctpop_wrong_cmp_op1(i32 %x) { define i1 @is_pow2or0_ctpop_wrong_cmp_op1_logical(i32 %x) { ; CHECK-LABEL: @is_pow2or0_ctpop_wrong_cmp_op1_logical( -; CHECK-NEXT: [[T0:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp eq i32 [[T0]], 3 ; CHECK-NEXT: [[ISZERO:%.*]] = icmp eq i32 [[X]], 0 ; CHECK-NEXT: [[R:%.*]] = select i1 [[ISZERO]], i1 true, i1 [[CMP]] @@ -925,7 +925,7 @@ define i1 @is_pow2or0_ctpop_wrong_cmp_op1_logical(i32 %x) { define <2 x i1> @is_pow2or0_ctpop_commute_vec_wrong_cmp_op1(<2 x i8> %x) { ; CHECK-LABEL: @is_pow2or0_ctpop_commute_vec_wrong_cmp_op1( -; CHECK-NEXT: [[T0:%.*]] = tail call <2 x i8> @llvm.ctpop.v2i8(<2 x i8> [[X:%.*]]), !range [[RNG1]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i8 0, 9) <2 x i8> @llvm.ctpop.v2i8(<2 x i8> [[X:%.*]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp eq <2 x i8> [[T0]], ; CHECK-NEXT: [[ISZERO:%.*]] = icmp eq <2 x i8> [[X]], zeroinitializer ; CHECK-NEXT: [[R:%.*]] = or <2 x i1> [[CMP]], [[ISZERO]] @@ -942,7 +942,7 @@ define <2 x i1> @is_pow2or0_ctpop_commute_vec_wrong_cmp_op1(<2 x i8> %x) { define i1 @is_pow2or0_ctpop_wrong_pred1(i32 %x) { ; CHECK-LABEL: @is_pow2or0_ctpop_wrong_pred1( -; CHECK-NEXT: [[T0:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ne i32 [[T0]], 1 ; CHECK-NEXT: ret i1 [[CMP]] ; @@ -977,7 +977,7 @@ define i1 @is_pow2or0_ctpop_wrong_pred2_logical(i32 %x) { define <2 x i1> @is_pow2or0_ctpop_commute_vec_wrong_pred3(<2 x i8> %x) { ; CHECK-LABEL: @is_pow2or0_ctpop_commute_vec_wrong_pred3( -; CHECK-NEXT: [[T0:%.*]] = tail call <2 x i8> @llvm.ctpop.v2i8(<2 x i8> [[X:%.*]]), !range [[RNG1]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i8 0, 9) <2 x i8> @llvm.ctpop.v2i8(<2 x i8> [[X:%.*]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp eq <2 x i8> [[T0]], ; CHECK-NEXT: [[ISZERO:%.*]] = icmp eq <2 x i8> [[X]], zeroinitializer ; CHECK-NEXT: [[R:%.*]] = and <2 x i1> [[CMP]], [[ISZERO]] @@ -994,7 +994,7 @@ define <2 x i1> @is_pow2or0_ctpop_commute_vec_wrong_pred3(<2 x i8> %x) { define i1 @isnot_pow2nor0_ctpop(i32 %x) { ; CHECK-LABEL: @isnot_pow2nor0_ctpop( -; CHECK-NEXT: [[T0:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: [[R:%.*]] = icmp ugt i32 [[T0]], 1 ; CHECK-NEXT: ret i1 [[R]] ; @@ -1007,7 +1007,7 @@ define i1 @isnot_pow2nor0_ctpop(i32 %x) { define i1 @isnot_pow2nor0_ctpop_swap_cmp(i32 %x) { ; CHECK-LABEL: @isnot_pow2nor0_ctpop_swap_cmp( -; CHECK-NEXT: [[T0:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: [[R:%.*]] = icmp ugt i32 [[T0]], 1 ; CHECK-NEXT: ret i1 [[R]] ; @@ -1020,7 +1020,7 @@ define i1 @isnot_pow2nor0_ctpop_swap_cmp(i32 %x) { define i1 @isnot_pow2nor0_ctpop_logical(i32 %x) { ; CHECK-LABEL: @isnot_pow2nor0_ctpop_logical( -; CHECK-NEXT: [[T0:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: [[R:%.*]] = icmp ugt i32 [[T0]], 1 ; CHECK-NEXT: ret i1 [[R]] ; @@ -1033,7 +1033,7 @@ define i1 @isnot_pow2nor0_ctpop_logical(i32 %x) { define <2 x i1> @isnot_pow2nor0_ctpop_commute_vec(<2 x i8> %x) { ; CHECK-LABEL: @isnot_pow2nor0_ctpop_commute_vec( -; CHECK-NEXT: [[T0:%.*]] = tail call <2 x i8> @llvm.ctpop.v2i8(<2 x i8> [[X:%.*]]), !range [[RNG1]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i8 0, 9) <2 x i8> @llvm.ctpop.v2i8(<2 x i8> [[X:%.*]]) ; CHECK-NEXT: [[R:%.*]] = icmp ugt <2 x i8> [[T0]], ; CHECK-NEXT: ret <2 x i1> [[R]] ; @@ -1048,7 +1048,7 @@ define <2 x i1> @isnot_pow2nor0_ctpop_commute_vec(<2 x i8> %x) { define i1 @isnot_pow2nor0_ctpop_extra_uses(i32 %x) { ; CHECK-LABEL: @isnot_pow2nor0_ctpop_extra_uses( -; CHECK-NEXT: [[T0:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: call void @use(i32 [[T0]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ne i32 [[T0]], 1 ; CHECK-NEXT: call void @use_i1(i1 [[CMP]]) @@ -1069,7 +1069,7 @@ define i1 @isnot_pow2nor0_ctpop_extra_uses(i32 %x) { define i1 @isnot_pow2nor0_ctpop_logical_extra_uses(i32 %x) { ; CHECK-LABEL: @isnot_pow2nor0_ctpop_logical_extra_uses( -; CHECK-NEXT: [[T0:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: call void @use(i32 [[T0]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ne i32 [[T0]], 1 ; CHECK-NEXT: call void @use_i1(i1 [[CMP]]) @@ -1092,7 +1092,7 @@ define i1 @isnot_pow2nor0_ctpop_logical_extra_uses(i32 %x) { define i1 @isnot_pow2nor0_ctpop_wrong_cmp_op1(i32 %x) { ; CHECK-LABEL: @isnot_pow2nor0_ctpop_wrong_cmp_op1( -; CHECK-NEXT: [[T0:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ne i32 [[T0]], 4 ; CHECK-NEXT: [[NOTZERO:%.*]] = icmp ne i32 [[X]], 0 ; CHECK-NEXT: [[R:%.*]] = and i1 [[NOTZERO]], [[CMP]] @@ -1107,7 +1107,7 @@ define i1 @isnot_pow2nor0_ctpop_wrong_cmp_op1(i32 %x) { define i1 @isnot_pow2nor0_ctpop_wrong_cmp_op1_logical(i32 %x) { ; CHECK-LABEL: @isnot_pow2nor0_ctpop_wrong_cmp_op1_logical( -; CHECK-NEXT: [[T0:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ne i32 [[T0]], 5 ; CHECK-NEXT: [[NOTZERO:%.*]] = icmp ne i32 [[X]], 0 ; CHECK-NEXT: [[R:%.*]] = select i1 [[NOTZERO]], i1 [[CMP]], i1 false @@ -1122,7 +1122,7 @@ define i1 @isnot_pow2nor0_ctpop_wrong_cmp_op1_logical(i32 %x) { define <2 x i1> @isnot_pow2nor0_ctpop_commute_vec_wrong_cmp_op1(<2 x i8> %x) { ; CHECK-LABEL: @isnot_pow2nor0_ctpop_commute_vec_wrong_cmp_op1( -; CHECK-NEXT: [[T0:%.*]] = tail call <2 x i8> @llvm.ctpop.v2i8(<2 x i8> [[X:%.*]]), !range [[RNG1]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i8 0, 9) <2 x i8> @llvm.ctpop.v2i8(<2 x i8> [[X:%.*]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ne <2 x i8> [[T0]], ; CHECK-NEXT: [[NOTZERO:%.*]] = icmp ne <2 x i8> [[X]], zeroinitializer ; CHECK-NEXT: [[R:%.*]] = and <2 x i1> [[CMP]], [[NOTZERO]] @@ -1139,7 +1139,7 @@ define <2 x i1> @isnot_pow2nor0_ctpop_commute_vec_wrong_cmp_op1(<2 x i8> %x) { define i1 @isnot_pow2nor0_ctpop_wrong_pred1(i32 %x) { ; CHECK-LABEL: @isnot_pow2nor0_ctpop_wrong_pred1( -; CHECK-NEXT: [[T0:%.*]] = tail call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp eq i32 [[T0]], 1 ; CHECK-NEXT: ret i1 [[CMP]] ; @@ -1174,7 +1174,7 @@ define i1 @isnot_pow2nor0_ctpop_wrong_pred2_logical(i32 %x) { define <2 x i1> @isnot_pow2nor0_wrong_pred3_ctpop_commute_vec(<2 x i8> %x) { ; CHECK-LABEL: @isnot_pow2nor0_wrong_pred3_ctpop_commute_vec( -; CHECK-NEXT: [[T0:%.*]] = tail call <2 x i8> @llvm.ctpop.v2i8(<2 x i8> [[X:%.*]]), !range [[RNG1]] +; CHECK-NEXT: [[T0:%.*]] = tail call range(i8 0, 9) <2 x i8> @llvm.ctpop.v2i8(<2 x i8> [[X:%.*]]) ; CHECK-NEXT: [[CMP:%.*]] = icmp ne <2 x i8> [[T0]], ; CHECK-NEXT: [[NOTZERO:%.*]] = icmp ne <2 x i8> [[X]], zeroinitializer ; CHECK-NEXT: [[R:%.*]] = or <2 x i1> [[CMP]], [[NOTZERO]] @@ -1217,7 +1217,7 @@ define i1 @blsmsk_is_p2_or_z(i32 %xx, i32 %yy) { define i1 @blsmsk_isnt_p2_or_z(i32 %x) { ; CHECK-LABEL: @blsmsk_isnt_p2_or_z( -; CHECK-NEXT: [[TMP1:%.*]] = call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: [[R:%.*]] = icmp ugt i32 [[TMP1]], 1 ; CHECK-NEXT: ret i1 [[R]] ; @@ -1230,7 +1230,7 @@ define i1 @blsmsk_isnt_p2_or_z(i32 %x) { define i1 @blsmsk_is_p2_or_z_fail(i32 %xx, i32 %yy) { ; CHECK-LABEL: @blsmsk_is_p2_or_z_fail( ; CHECK-NEXT: [[X:%.*]] = or i32 [[XX:%.*]], [[YY:%.*]] -; CHECK-NEXT: [[TMP1:%.*]] = call i32 @llvm.ctpop.i32(i32 [[X]]), !range [[RNG0]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X]]) ; CHECK-NEXT: [[R:%.*]] = icmp ugt i32 [[TMP1]], 1 ; CHECK-NEXT: ret i1 [[R]] ; @@ -1315,7 +1315,7 @@ define i1 @blsmsk_is_p2_or_z_fail_bad_cmp(i32 %x, i32 %z) { define i1 @blsmsk_is_p2_or_z_ule_xy(i8 %xx, i8 %yy) { ; CHECK-LABEL: @blsmsk_is_p2_or_z_ule_xy( ; CHECK-NEXT: [[X:%.*]] = or i8 [[XX:%.*]], [[YY:%.*]] -; CHECK-NEXT: [[TMP1:%.*]] = call i8 @llvm.ctpop.i8(i8 [[X]]), !range [[RNG1]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i8 0, 9) i8 @llvm.ctpop.i8(i8 [[X]]) ; CHECK-NEXT: [[R:%.*]] = icmp ult i8 [[TMP1]], 2 ; CHECK-NEXT: ret i1 [[R]] ; @@ -1346,7 +1346,7 @@ define i1 @blsmsk_is_p2_or_z_ule_yx_fail(i8 %xx, i8 %yy) { define i1 @blsmsk_is_p2_or_z_uge_yx(i8 %xx, i8 %yy) { ; CHECK-LABEL: @blsmsk_is_p2_or_z_uge_yx( ; CHECK-NEXT: [[X:%.*]] = or i8 [[XX:%.*]], [[YY:%.*]] -; CHECK-NEXT: [[TMP1:%.*]] = call i8 @llvm.ctpop.i8(i8 [[X]]), !range [[RNG1]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i8 0, 9) i8 @llvm.ctpop.i8(i8 [[X]]) ; CHECK-NEXT: [[R:%.*]] = icmp ult i8 [[TMP1]], 2 ; CHECK-NEXT: ret i1 [[R]] ; @@ -1376,7 +1376,7 @@ define i1 @blsmsk_is_p2_or_z_uge_xy_fail(i8 %xx, i8 %yy) { define i1 @blsmsk_isnt_p2_or_z_ugt_xy(i8 %xx, i8 %yy) { ; CHECK-LABEL: @blsmsk_isnt_p2_or_z_ugt_xy( ; CHECK-NEXT: [[X:%.*]] = or i8 [[XX:%.*]], [[YY:%.*]] -; CHECK-NEXT: [[TMP1:%.*]] = call i8 @llvm.ctpop.i8(i8 [[X]]), !range [[RNG1]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i8 0, 9) i8 @llvm.ctpop.i8(i8 [[X]]) ; CHECK-NEXT: [[R:%.*]] = icmp ugt i8 [[TMP1]], 1 ; CHECK-NEXT: ret i1 [[R]] ; @@ -1407,7 +1407,7 @@ define i1 @blsmsk_isnt_p2_or_z_ugt_yx_fail(i8 %xx, i8 %yy) { define i1 @blsmsk_isnt_p2_or_z_ult_yx(i8 %xx, i8 %yy) { ; CHECK-LABEL: @blsmsk_isnt_p2_or_z_ult_yx( ; CHECK-NEXT: [[X:%.*]] = or i8 [[XX:%.*]], [[YY:%.*]] -; CHECK-NEXT: [[TMP1:%.*]] = call i8 @llvm.ctpop.i8(i8 [[X]]), !range [[RNG1]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i8 0, 9) i8 @llvm.ctpop.i8(i8 [[X]]) ; CHECK-NEXT: [[R:%.*]] = icmp ugt i8 [[TMP1]], 1 ; CHECK-NEXT: ret i1 [[R]] ; @@ -1450,7 +1450,7 @@ define i1 @is_pow2_nz_known_bits(i32 %xin) { define i1 @is_pow2_nz_known_bits_fail_multiuse(i32 %xin) { ; CHECK-LABEL: @is_pow2_nz_known_bits_fail_multiuse( ; CHECK-NEXT: [[X:%.*]] = or i32 [[XIN:%.*]], 64 -; CHECK-NEXT: [[CNT:%.*]] = call i32 @llvm.ctpop.i32(i32 [[X]]), !range [[RNG3:![0-9]+]] +; CHECK-NEXT: [[CNT:%.*]] = call range(i32 1, 33) i32 @llvm.ctpop.i32(i32 [[X]]) ; CHECK-NEXT: call void @use.i32(i32 [[CNT]]) ; CHECK-NEXT: [[R:%.*]] = icmp eq i32 [[CNT]], 1 ; CHECK-NEXT: ret i1 [[R]] @@ -1476,7 +1476,7 @@ define i1 @not_pow2_nz_known_bits(i32 %xin) { define i1 @not_pow2_nz_known_bits_fail_not_p2_test(i32 %xin) { ; CHECK-LABEL: @not_pow2_nz_known_bits_fail_not_p2_test( ; CHECK-NEXT: [[X:%.*]] = or i32 [[XIN:%.*]], 1 -; CHECK-NEXT: [[CNT:%.*]] = call i32 @llvm.ctpop.i32(i32 [[X]]), !range [[RNG3]] +; CHECK-NEXT: [[CNT:%.*]] = call range(i32 1, 33) i32 @llvm.ctpop.i32(i32 [[X]]) ; CHECK-NEXT: [[R:%.*]] = icmp ne i32 [[CNT]], 2 ; CHECK-NEXT: ret i1 [[R]] ; @@ -1513,7 +1513,7 @@ define <2 x i1> @not_pow2_or_z_known_bits(<2 x i32> %xin) { define <2 x i1> @not_pow2_or_z_known_bits_fail_wrong_cmp(<2 x i32> %xin) { ; CHECK-LABEL: @not_pow2_or_z_known_bits_fail_wrong_cmp( ; CHECK-NEXT: [[X:%.*]] = or <2 x i32> [[XIN:%.*]], -; CHECK-NEXT: [[CNT:%.*]] = call <2 x i32> @llvm.ctpop.v2i32(<2 x i32> [[X]]), !range [[RNG3]] +; CHECK-NEXT: [[CNT:%.*]] = call range(i32 1, 33) <2 x i32> @llvm.ctpop.v2i32(<2 x i32> [[X]]) ; CHECK-NEXT: [[R:%.*]] = icmp ugt <2 x i32> [[CNT]], ; CHECK-NEXT: ret <2 x i1> [[R]] ; diff --git a/llvm/test/Transforms/InstCombine/known-non-zero.ll b/llvm/test/Transforms/InstCombine/known-non-zero.ll index f1c757cafefb0fd54a269440662f8318a8f11f1a..b77c04eb81475a4534ae7a87b041a544ad995adf 100644 --- a/llvm/test/Transforms/InstCombine/known-non-zero.ll +++ b/llvm/test/Transforms/InstCombine/known-non-zero.ll @@ -13,7 +13,7 @@ define i32 @test0(i64 %x) { ; CHECK-NEXT: [[C:%.*]] = icmp eq i64 [[X:%.*]], 0 ; CHECK-NEXT: br i1 [[C]], label [[EXIT:%.*]], label [[NON_ZERO:%.*]] ; CHECK: non_zero: -; CHECK-NEXT: [[CTZ:%.*]] = call i64 @llvm.cttz.i64(i64 [[X]], i1 true), !range [[RNG0:![0-9]+]] +; CHECK-NEXT: [[CTZ:%.*]] = call range(i64 0, 65) i64 @llvm.cttz.i64(i64 [[X]], i1 true) ; CHECK-NEXT: [[CTZ32:%.*]] = trunc nuw nsw i64 [[CTZ]] to i32 ; CHECK-NEXT: br label [[EXIT]] ; CHECK: exit: @@ -40,7 +40,7 @@ define i32 @test1(i64 %x) { ; CHECK-NEXT: [[C:%.*]] = icmp eq i64 [[X:%.*]], 0 ; CHECK-NEXT: br i1 [[C]], label [[EXIT:%.*]], label [[NON_ZERO:%.*]] ; CHECK: non_zero: -; CHECK-NEXT: [[CTZ:%.*]] = call i64 @llvm.ctlz.i64(i64 [[X]], i1 true), !range [[RNG0]] +; CHECK-NEXT: [[CTZ:%.*]] = call range(i64 0, 65) i64 @llvm.ctlz.i64(i64 [[X]], i1 true) ; CHECK-NEXT: [[CTZ32:%.*]] = trunc nuw nsw i64 [[CTZ]] to i32 ; CHECK-NEXT: br label [[EXIT]] ; CHECK: exit: @@ -69,7 +69,7 @@ define <8 x i64> @test2(<8 x i64> %x) { ; CHECK-NEXT: [[C:%.*]] = icmp eq i8 [[B]], 0 ; CHECK-NEXT: br i1 [[C]], label [[EXIT:%.*]], label [[NON_ZERO:%.*]] ; CHECK: non_zero: -; CHECK-NEXT: [[CTZ:%.*]] = call <8 x i64> @llvm.cttz.v8i64(<8 x i64> [[X]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[CTZ:%.*]] = call range(i64 0, 65) <8 x i64> @llvm.cttz.v8i64(<8 x i64> [[X]], i1 false) ; CHECK-NEXT: br label [[EXIT]] ; CHECK: exit: ; CHECK-NEXT: [[RES:%.*]] = phi <8 x i64> [ [[CTZ]], [[NON_ZERO]] ], [ zeroinitializer, [[START:%.*]] ] @@ -140,7 +140,7 @@ define i64 @test_sgt_zero(i64 %x) { ; CHECK-NEXT: [[C:%.*]] = icmp sgt i64 [[X:%.*]], 0 ; CHECK-NEXT: br i1 [[C]], label [[NON_ZERO:%.*]], label [[EXIT:%.*]] ; CHECK: non_zero: -; CHECK-NEXT: [[CTZ:%.*]] = call i64 @llvm.ctlz.i64(i64 [[X]], i1 true), !range [[RNG1:![0-9]+]] +; CHECK-NEXT: [[CTZ:%.*]] = call range(i64 1, 65) i64 @llvm.ctlz.i64(i64 [[X]], i1 true) ; CHECK-NEXT: ret i64 [[CTZ]] ; CHECK: exit: ; CHECK-NEXT: ret i64 -1 @@ -185,7 +185,7 @@ define i64 @test_slt_ten(i64 %x) { ; CHECK-NEXT: [[C:%.*]] = icmp slt i64 [[X:%.*]], 10 ; CHECK-NEXT: br i1 [[C]], label [[MAYBE_ZERO:%.*]], label [[EXIT:%.*]] ; CHECK: maybe_zero: -; CHECK-NEXT: [[CTZ:%.*]] = call i64 @llvm.ctlz.i64(i64 [[X]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[CTZ:%.*]] = call range(i64 0, 65) i64 @llvm.ctlz.i64(i64 [[X]], i1 false) ; CHECK-NEXT: ret i64 [[CTZ]] ; CHECK: exit: ; CHECK-NEXT: ret i64 -1 @@ -208,7 +208,7 @@ define i64 @test_ugt_unknown(i64 %x, i64 %y) { ; CHECK-NEXT: [[C:%.*]] = icmp ugt i64 [[X:%.*]], [[Y:%.*]] ; CHECK-NEXT: br i1 [[C]], label [[NON_ZERO:%.*]], label [[EXIT:%.*]] ; CHECK: non_zero: -; CHECK-NEXT: [[CTZ:%.*]] = call i64 @llvm.ctlz.i64(i64 [[X]], i1 true), !range [[RNG0]] +; CHECK-NEXT: [[CTZ:%.*]] = call range(i64 0, 65) i64 @llvm.ctlz.i64(i64 [[X]], i1 true) ; CHECK-NEXT: ret i64 [[CTZ]] ; CHECK: exit: ; CHECK-NEXT: ret i64 -1 @@ -231,7 +231,7 @@ define i64 @test_sle_zero(i64 %x) { ; CHECK-NEXT: [[C:%.*]] = icmp slt i64 [[X:%.*]], 1 ; CHECK-NEXT: br i1 [[C]], label [[EXIT:%.*]], label [[NON_ZERO:%.*]] ; CHECK: non_zero: -; CHECK-NEXT: [[CTZ:%.*]] = call i64 @llvm.ctlz.i64(i64 [[X]], i1 true), !range [[RNG1]] +; CHECK-NEXT: [[CTZ:%.*]] = call range(i64 1, 65) i64 @llvm.ctlz.i64(i64 [[X]], i1 true) ; CHECK-NEXT: ret i64 [[CTZ]] ; CHECK: exit: ; CHECK-NEXT: ret i64 -1 @@ -276,7 +276,7 @@ define i64 @test_sge_ten(i64 %x) { ; CHECK-NEXT: [[C:%.*]] = icmp sgt i64 [[X:%.*]], 9 ; CHECK-NEXT: br i1 [[C]], label [[EXIT:%.*]], label [[MAYBE_ZERO:%.*]] ; CHECK: maybe_zero: -; CHECK-NEXT: [[CTZ:%.*]] = call i64 @llvm.ctlz.i64(i64 [[X]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[CTZ:%.*]] = call range(i64 0, 65) i64 @llvm.ctlz.i64(i64 [[X]], i1 false) ; CHECK-NEXT: ret i64 [[CTZ]] ; CHECK: exit: ; CHECK-NEXT: ret i64 -1 @@ -299,7 +299,7 @@ define i64 @test_ule_unknown(i64 %x, i64 %y) { ; CHECK-NEXT: [[C_NOT:%.*]] = icmp ugt i64 [[X:%.*]], [[Y:%.*]] ; CHECK-NEXT: br i1 [[C_NOT]], label [[NON_ZERO:%.*]], label [[EXIT:%.*]] ; CHECK: non_zero: -; CHECK-NEXT: [[CTZ:%.*]] = call i64 @llvm.ctlz.i64(i64 [[X]], i1 true), !range [[RNG0]] +; CHECK-NEXT: [[CTZ:%.*]] = call range(i64 0, 65) i64 @llvm.ctlz.i64(i64 [[X]], i1 true) ; CHECK-NEXT: ret i64 [[CTZ]] ; CHECK: exit: ; CHECK-NEXT: ret i64 -1 diff --git a/llvm/test/Transforms/InstCombine/known-phi-recurse.ll b/llvm/test/Transforms/InstCombine/known-phi-recurse.ll index d33e08ffaf9b77d40d2534714d768f32fd6c636a..c2007d16ae93be0e18da35caacb00385f585d7a6 100644 --- a/llvm/test/Transforms/InstCombine/known-phi-recurse.ll +++ b/llvm/test/Transforms/InstCombine/known-phi-recurse.ll @@ -16,7 +16,7 @@ define i32 @single_entry_phi(i64 %x, i1 %c) { ; CHECK: body: ; CHECK-NEXT: br i1 [[C:%.*]], label [[END:%.*]], label [[BODY]] ; CHECK: end: -; CHECK-NEXT: [[Y:%.*]] = call i64 @llvm.ctpop.i64(i64 [[X:%.*]]), !range [[RNG0:![0-9]+]] +; CHECK-NEXT: [[Y:%.*]] = call range(i64 0, 65) i64 @llvm.ctpop.i64(i64 [[X:%.*]]) ; CHECK-NEXT: [[TRUNC:%.*]] = trunc nuw nsw i64 [[Y]] to i32 ; CHECK-NEXT: ret i32 [[TRUNC]] ; @@ -36,7 +36,7 @@ end: define i32 @two_entry_phi_with_constant(i64 %x, i1 %c) { ; CHECK-LABEL: @two_entry_phi_with_constant( ; CHECK-NEXT: entry: -; CHECK-NEXT: [[Y:%.*]] = call i64 @llvm.ctpop.i64(i64 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[Y:%.*]] = call range(i64 0, 65) i64 @llvm.ctpop.i64(i64 [[X:%.*]]) ; CHECK-NEXT: [[TRUNC:%.*]] = trunc nuw nsw i64 [[Y]] to i32 ; CHECK-NEXT: br i1 [[C:%.*]], label [[END:%.*]], label [[BODY:%.*]] ; CHECK: body: @@ -61,11 +61,11 @@ end: define i32 @two_entry_phi_non_constant(i64 %x, i64 %x2, i1 %c) { ; CHECK-LABEL: @two_entry_phi_non_constant( ; CHECK-NEXT: entry: -; CHECK-NEXT: [[Y:%.*]] = call i64 @llvm.ctpop.i64(i64 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[Y:%.*]] = call range(i64 0, 65) i64 @llvm.ctpop.i64(i64 [[X:%.*]]) ; CHECK-NEXT: [[TRUNC:%.*]] = trunc nuw nsw i64 [[Y]] to i32 ; CHECK-NEXT: br i1 [[C:%.*]], label [[END:%.*]], label [[BODY:%.*]] ; CHECK: body: -; CHECK-NEXT: [[Y2:%.*]] = call i64 @llvm.ctpop.i64(i64 [[X2:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[Y2:%.*]] = call range(i64 0, 65) i64 @llvm.ctpop.i64(i64 [[X2:%.*]]) ; CHECK-NEXT: [[TRUNC2:%.*]] = trunc nuw nsw i64 [[Y2]] to i32 ; CHECK-NEXT: br label [[END]] ; CHECK: end: @@ -90,7 +90,7 @@ end: define i32 @neg_many_branches(i64 %x) { ; CHECK-LABEL: @neg_many_branches( ; CHECK-NEXT: entry: -; CHECK-NEXT: [[Y:%.*]] = call i64 @llvm.ctpop.i64(i64 [[X:%.*]]), !range [[RNG0]] +; CHECK-NEXT: [[Y:%.*]] = call range(i64 0, 65) i64 @llvm.ctpop.i64(i64 [[X:%.*]]) ; CHECK-NEXT: [[TRUNC:%.*]] = trunc nuw nsw i64 [[Y]] to i32 ; CHECK-NEXT: switch i32 [[TRUNC]], label [[END:%.*]] [ ; CHECK-NEXT: i32 1, label [[ONE:%.*]] diff --git a/llvm/test/Transforms/InstCombine/loadstore-alignment.ll b/llvm/test/Transforms/InstCombine/loadstore-alignment.ll index 0fc82a1d5343699cacb8c600a86a144e515f72af..1027468d6715e8096e4d3031d77f74cc6fd4287c 100644 --- a/llvm/test/Transforms/InstCombine/loadstore-alignment.ll +++ b/llvm/test/Transforms/InstCombine/loadstore-alignment.ll @@ -9,24 +9,24 @@ target datalayout = "E-p:64:64:64-p1:64:64:64-p2:32:32:32-a0:0:8-f32:32:32-f64:6 define <2 x i64> @static_hem() { ; CHECK-LABEL: @static_hem( -; CHECK-NEXT: [[TMP1:%.*]] = load <2 x i64>, ptr getelementptr (<2 x i64>, ptr @x, i64 7), align 1 -; CHECK-NEXT: ret <2 x i64> [[TMP1]] +; CHECK-NEXT: [[L:%.*]] = load <2 x i64>, ptr getelementptr (<2 x i64>, ptr @x, i64 7), align 1 +; CHECK-NEXT: ret <2 x i64> [[L]] ; %t = getelementptr <2 x i64>, ptr @x, i32 7 - %tmp1 = load <2 x i64>, ptr %t, align 1 - ret <2 x i64> %tmp1 + %l = load <2 x i64>, ptr %t, align 1 + ret <2 x i64> %l } define <2 x i64> @hem(i32 %i) { ; CHECK-LABEL: @hem( ; CHECK-NEXT: [[TMP1:%.*]] = sext i32 [[I:%.*]] to i64 ; CHECK-NEXT: [[T:%.*]] = getelementptr <2 x i64>, ptr @x, i64 [[TMP1]] -; CHECK-NEXT: [[TMP1:%.*]] = load <2 x i64>, ptr [[T]], align 1 -; CHECK-NEXT: ret <2 x i64> [[TMP1]] +; CHECK-NEXT: [[L:%.*]] = load <2 x i64>, ptr [[T]], align 1 +; CHECK-NEXT: ret <2 x i64> [[L]] ; %t = getelementptr <2 x i64>, ptr @x, i32 %i - %tmp1 = load <2 x i64>, ptr %t, align 1 - ret <2 x i64> %tmp1 + %l = load <2 x i64>, ptr %t, align 1 + ret <2 x i64> %l } define <2 x i64> @hem_2d(i32 %i, i32 %j) { @@ -34,34 +34,34 @@ define <2 x i64> @hem_2d(i32 %i, i32 %j) { ; CHECK-NEXT: [[TMP1:%.*]] = sext i32 [[I:%.*]] to i64 ; CHECK-NEXT: [[TMP2:%.*]] = sext i32 [[J:%.*]] to i64 ; CHECK-NEXT: [[T:%.*]] = getelementptr [13 x <2 x i64>], ptr @xx, i64 [[TMP1]], i64 [[TMP2]] -; CHECK-NEXT: [[TMP1:%.*]] = load <2 x i64>, ptr [[T]], align 1 -; CHECK-NEXT: ret <2 x i64> [[TMP1]] +; CHECK-NEXT: [[L:%.*]] = load <2 x i64>, ptr [[T]], align 1 +; CHECK-NEXT: ret <2 x i64> [[L]] ; %t = getelementptr [13 x <2 x i64>], ptr @xx, i32 %i, i32 %j - %tmp1 = load <2 x i64>, ptr %t, align 1 - ret <2 x i64> %tmp1 + %l = load <2 x i64>, ptr %t, align 1 + ret <2 x i64> %l } define <2 x i64> @foo() { ; CHECK-LABEL: @foo( -; CHECK-NEXT: [[TMP1:%.*]] = load <2 x i64>, ptr @x, align 1 -; CHECK-NEXT: ret <2 x i64> [[TMP1]] +; CHECK-NEXT: [[L:%.*]] = load <2 x i64>, ptr @x, align 1 +; CHECK-NEXT: ret <2 x i64> [[L]] ; - %tmp1 = load <2 x i64>, ptr @x, align 1 - ret <2 x i64> %tmp1 + %l = load <2 x i64>, ptr @x, align 1 + ret <2 x i64> %l } define <2 x i64> @bar() { ; CHECK-LABEL: @bar( ; CHECK-NEXT: [[T:%.*]] = alloca <2 x i64>, align 16 ; CHECK-NEXT: call void @kip(ptr nonnull [[T]]) -; CHECK-NEXT: [[TMP1:%.*]] = load <2 x i64>, ptr [[T]], align 1 -; CHECK-NEXT: ret <2 x i64> [[TMP1]] +; CHECK-NEXT: [[L:%.*]] = load <2 x i64>, ptr [[T]], align 1 +; CHECK-NEXT: ret <2 x i64> [[L]] ; %t = alloca <2 x i64> call void @kip(ptr %t) - %tmp1 = load <2 x i64>, ptr %t, align 1 - ret <2 x i64> %tmp1 + %l = load <2 x i64>, ptr %t, align 1 + ret <2 x i64> %l } define void @static_hem_store(<2 x i64> %y) { diff --git a/llvm/test/Transforms/InstCombine/memcpy-from-global.ll b/llvm/test/Transforms/InstCombine/memcpy-from-global.ll index aeca0cd2924ea5c39b524e0dd27579db56c187b8..e9ff34735f1cf1194ce6ce90f63d86d51e3e478e 100644 --- a/llvm/test/Transforms/InstCombine/memcpy-from-global.ll +++ b/llvm/test/Transforms/InstCombine/memcpy-from-global.ll @@ -6,60 +6,60 @@ target datalayout = "E-p:64:64:64-i1:8:8-i8:8:8-i16:16:16-i32:32:32-i64:32:64-f3 define float @test1(i32 %hash, float %x, float %y, float %z, float %w) { ; CHECK-LABEL: @test1( ; CHECK-NEXT: entry: -; CHECK-NEXT: [[TMP3:%.*]] = shl i32 [[HASH:%.*]], 2 -; CHECK-NEXT: [[TMP5:%.*]] = and i32 [[TMP3]], 124 -; CHECK-NEXT: [[TMP0:%.*]] = zext nneg i32 [[TMP5]] to i64 -; CHECK-NEXT: [[TMP753:%.*]] = getelementptr [128 x float], ptr @C.0.1248, i64 0, i64 [[TMP0]] -; CHECK-NEXT: [[TMP9:%.*]] = load float, ptr [[TMP753]], align 4 -; CHECK-NEXT: [[TMP11:%.*]] = fmul float [[TMP9]], [[X:%.*]] -; CHECK-NEXT: [[TMP13:%.*]] = fadd float [[TMP11]], 0.000000e+00 -; CHECK-NEXT: [[TMP17_SUM52:%.*]] = or disjoint i32 [[TMP5]], 1 -; CHECK-NEXT: [[TMP1:%.*]] = zext nneg i32 [[TMP17_SUM52]] to i64 -; CHECK-NEXT: [[TMP1851:%.*]] = getelementptr [128 x float], ptr @C.0.1248, i64 0, i64 [[TMP1]] -; CHECK-NEXT: [[TMP19:%.*]] = load float, ptr [[TMP1851]], align 4 -; CHECK-NEXT: [[TMP21:%.*]] = fmul float [[TMP19]], [[Y:%.*]] -; CHECK-NEXT: [[TMP23:%.*]] = fadd float [[TMP21]], [[TMP13]] -; CHECK-NEXT: [[TMP27_SUM50:%.*]] = or disjoint i32 [[TMP5]], 2 -; CHECK-NEXT: [[TMP2:%.*]] = zext nneg i32 [[TMP27_SUM50]] to i64 -; CHECK-NEXT: [[TMP2849:%.*]] = getelementptr [128 x float], ptr @C.0.1248, i64 0, i64 [[TMP2]] -; CHECK-NEXT: [[TMP29:%.*]] = load float, ptr [[TMP2849]], align 4 -; CHECK-NEXT: [[TMP31:%.*]] = fmul float [[TMP29]], [[Z:%.*]] -; CHECK-NEXT: [[TMP33:%.*]] = fadd float [[TMP31]], [[TMP23]] -; CHECK-NEXT: [[TMP37_SUM48:%.*]] = or disjoint i32 [[TMP5]], 3 -; CHECK-NEXT: [[TMP3:%.*]] = zext nneg i32 [[TMP37_SUM48]] to i64 -; CHECK-NEXT: [[TMP3847:%.*]] = getelementptr [128 x float], ptr @C.0.1248, i64 0, i64 [[TMP3]] -; CHECK-NEXT: [[TMP39:%.*]] = load float, ptr [[TMP3847]], align 4 -; CHECK-NEXT: [[TMP41:%.*]] = fmul float [[TMP39]], [[W:%.*]] -; CHECK-NEXT: [[TMP43:%.*]] = fadd float [[TMP41]], [[TMP33]] -; CHECK-NEXT: ret float [[TMP43]] +; CHECK-NEXT: [[T3:%.*]] = shl i32 [[HASH:%.*]], 2 +; CHECK-NEXT: [[T5:%.*]] = and i32 [[T3]], 124 +; CHECK-NEXT: [[TMP0:%.*]] = zext nneg i32 [[T5]] to i64 +; CHECK-NEXT: [[T753:%.*]] = getelementptr [128 x float], ptr @C.0.1248, i64 0, i64 [[TMP0]] +; CHECK-NEXT: [[T9:%.*]] = load float, ptr [[T753]], align 4 +; CHECK-NEXT: [[T11:%.*]] = fmul float [[T9]], [[X:%.*]] +; CHECK-NEXT: [[T13:%.*]] = fadd float [[T11]], 0.000000e+00 +; CHECK-NEXT: [[T17_SUM52:%.*]] = or disjoint i32 [[T5]], 1 +; CHECK-NEXT: [[TMP1:%.*]] = zext nneg i32 [[T17_SUM52]] to i64 +; CHECK-NEXT: [[T1851:%.*]] = getelementptr [128 x float], ptr @C.0.1248, i64 0, i64 [[TMP1]] +; CHECK-NEXT: [[T19:%.*]] = load float, ptr [[T1851]], align 4 +; CHECK-NEXT: [[T21:%.*]] = fmul float [[T19]], [[Y:%.*]] +; CHECK-NEXT: [[T23:%.*]] = fadd float [[T21]], [[T13]] +; CHECK-NEXT: [[T27_SUM50:%.*]] = or disjoint i32 [[T5]], 2 +; CHECK-NEXT: [[TMP2:%.*]] = zext nneg i32 [[T27_SUM50]] to i64 +; CHECK-NEXT: [[T2849:%.*]] = getelementptr [128 x float], ptr @C.0.1248, i64 0, i64 [[TMP2]] +; CHECK-NEXT: [[T29:%.*]] = load float, ptr [[T2849]], align 4 +; CHECK-NEXT: [[T31:%.*]] = fmul float [[T29]], [[Z:%.*]] +; CHECK-NEXT: [[T33:%.*]] = fadd float [[T31]], [[T23]] +; CHECK-NEXT: [[T37_SUM48:%.*]] = or disjoint i32 [[T5]], 3 +; CHECK-NEXT: [[TMP3:%.*]] = zext nneg i32 [[T37_SUM48]] to i64 +; CHECK-NEXT: [[T3847:%.*]] = getelementptr [128 x float], ptr @C.0.1248, i64 0, i64 [[TMP3]] +; CHECK-NEXT: [[T39:%.*]] = load float, ptr [[T3847]], align 4 +; CHECK-NEXT: [[T41:%.*]] = fmul float [[T39]], [[W:%.*]] +; CHECK-NEXT: [[T43:%.*]] = fadd float [[T41]], [[T33]] +; CHECK-NEXT: ret float [[T43]] ; entry: - %lookupTable = alloca [128 x float], align 16 ; [#uses=5] + %lookupTable = alloca [128 x float], align 16 call void @llvm.memcpy.p0.p0.i64(ptr align 16 %lookupTable, ptr align 16 @C.0.1248, i64 512, i1 false) - %tmp3 = shl i32 %hash, 2 ; [#uses=1] - %tmp5 = and i32 %tmp3, 124 ; [#uses=4] - %tmp753 = getelementptr [128 x float], ptr %lookupTable, i32 0, i32 %tmp5 ; [#uses=1] - %tmp9 = load float, ptr %tmp753 ; [#uses=1] - %tmp11 = fmul float %tmp9, %x ; [#uses=1] - %tmp13 = fadd float %tmp11, 0.000000e+00 ; [#uses=1] - %tmp17.sum52 = or i32 %tmp5, 1 ; [#uses=1] - %tmp1851 = getelementptr [128 x float], ptr %lookupTable, i32 0, i32 %tmp17.sum52 ; [#uses=1] - %tmp19 = load float, ptr %tmp1851 ; [#uses=1] - %tmp21 = fmul float %tmp19, %y ; [#uses=1] - %tmp23 = fadd float %tmp21, %tmp13 ; [#uses=1] - %tmp27.sum50 = or i32 %tmp5, 2 ; [#uses=1] - %tmp2849 = getelementptr [128 x float], ptr %lookupTable, i32 0, i32 %tmp27.sum50 ; [#uses=1] - %tmp29 = load float, ptr %tmp2849 ; [#uses=1] - %tmp31 = fmul float %tmp29, %z ; [#uses=1] - %tmp33 = fadd float %tmp31, %tmp23 ; [#uses=1] - %tmp37.sum48 = or i32 %tmp5, 3 ; [#uses=1] - %tmp3847 = getelementptr [128 x float], ptr %lookupTable, i32 0, i32 %tmp37.sum48 ; [#uses=1] - %tmp39 = load float, ptr %tmp3847 ; [#uses=1] - %tmp41 = fmul float %tmp39, %w ; [#uses=1] - %tmp43 = fadd float %tmp41, %tmp33 ; [#uses=1] - ret float %tmp43 + %t3 = shl i32 %hash, 2 + %t5 = and i32 %t3, 124 + %t753 = getelementptr [128 x float], ptr %lookupTable, i32 0, i32 %t5 + %t9 = load float, ptr %t753 + %t11 = fmul float %t9, %x + %t13 = fadd float %t11, 0.000000e+00 + %t17.sum52 = or i32 %t5, 1 + %t1851 = getelementptr [128 x float], ptr %lookupTable, i32 0, i32 %t17.sum52 + %t19 = load float, ptr %t1851 + %t21 = fmul float %t19, %y + %t23 = fadd float %t21, %t13 + %t27.sum50 = or i32 %t5, 2 + %t2849 = getelementptr [128 x float], ptr %lookupTable, i32 0, i32 %t27.sum50 + %t29 = load float, ptr %t2849 + %t31 = fmul float %t29, %z + %t33 = fadd float %t31, %t23 + %t37.sum48 = or i32 %t5, 3 + %t3847 = getelementptr [128 x float], ptr %lookupTable, i32 0, i32 %t37.sum48 + %t39 = load float, ptr %t3847 + %t41 = fmul float %t39, %w + %t43 = fadd float %t41, %t33 + ret float %t43 } declare void @llvm.memcpy.p0.p0.i64(ptr nocapture, ptr nocapture, i64, i1) nounwind diff --git a/llvm/test/Transforms/InstCombine/merging-multiple-stores-into-successor.ll b/llvm/test/Transforms/InstCombine/merging-multiple-stores-into-successor.ll index 866381ff2887f93b4fc7ce13f3488919519af865..9c5bf3cb5a41bf38c58ff59a68981a373400d6cd 100644 --- a/llvm/test/Transforms/InstCombine/merging-multiple-stores-into-successor.ll +++ b/llvm/test/Transforms/InstCombine/merging-multiple-stores-into-successor.ll @@ -105,11 +105,11 @@ define i32 @diff_types_diff_width_no_merge(i1 %cond, i32 %a, i64 %b) { ; CHECK-LABEL: @diff_types_diff_width_no_merge( ; CHECK-NEXT: entry: ; CHECK-NEXT: [[ALLOCA:%.*]] = alloca i64, align 8 -; CHECK-NEXT: br i1 [[COND:%.*]], label [[A:%.*]], label [[B:%.*]] -; CHECK: A: +; CHECK-NEXT: br i1 [[COND:%.*]], label [[IF:%.*]], label [[ELSE:%.*]] +; CHECK: if: ; CHECK-NEXT: store i32 [[A:%.*]], ptr [[ALLOCA]], align 4 ; CHECK-NEXT: br label [[SINK:%.*]] -; CHECK: B: +; CHECK: else: ; CHECK-NEXT: store i64 [[B:%.*]], ptr [[ALLOCA]], align 4 ; CHECK-NEXT: br label [[SINK]] ; CHECK: sink: @@ -118,11 +118,11 @@ define i32 @diff_types_diff_width_no_merge(i1 %cond, i32 %a, i64 %b) { ; entry: %alloca = alloca i64 - br i1 %cond, label %A, label %B -A: + br i1 %cond, label %if, label %else +if: store i32 %a, ptr %alloca br label %sink -B: + else: store i64 %b, ptr %alloca br label %sink sink: @@ -134,11 +134,11 @@ define <4 x i32> @vec_no_merge(i1 %cond, <2 x i32> %a, <4 x i32> %b) { ; CHECK-LABEL: @vec_no_merge( ; CHECK-NEXT: entry: ; CHECK-NEXT: [[ALLOCA:%.*]] = alloca i64, align 8 -; CHECK-NEXT: br i1 [[COND:%.*]], label [[A:%.*]], label [[B:%.*]] -; CHECK: A: +; CHECK-NEXT: br i1 [[COND:%.*]], label [[IF:%.*]], label [[ELSE:%.*]] +; CHECK: if: ; CHECK-NEXT: store <2 x i32> [[A:%.*]], ptr [[ALLOCA]], align 8 ; CHECK-NEXT: br label [[SINK:%.*]] -; CHECK: B: +; CHECK: else: ; CHECK-NEXT: store <4 x i32> [[B:%.*]], ptr [[ALLOCA]], align 16 ; CHECK-NEXT: br label [[SINK]] ; CHECK: sink: @@ -147,11 +147,11 @@ define <4 x i32> @vec_no_merge(i1 %cond, <2 x i32> %a, <4 x i32> %b) { ; entry: %alloca = alloca i64 - br i1 %cond, label %A, label %B -A: + br i1 %cond, label %if, label %else +if: store <2 x i32> %a, ptr %alloca br label %sink -B: +else: store <4 x i32> %b, ptr %alloca br label %sink sink: @@ -195,11 +195,11 @@ define %struct.tup @multi_elem_struct_no_merge(i1 %cond, %struct.tup %a, half %b ; CHECK-LABEL: @multi_elem_struct_no_merge( ; CHECK-NEXT: entry: ; CHECK-NEXT: [[ALLOCA:%.*]] = alloca i64, align 8 -; CHECK-NEXT: br i1 [[COND:%.*]], label [[A:%.*]], label [[B:%.*]] -; CHECK: A: +; CHECK-NEXT: br i1 [[COND:%.*]], label [[IF:%.*]], label [[ELSE:%.*]] +; CHECK: if: ; CHECK-NEXT: store [[STRUCT_TUP:%.*]] [[A:%.*]], ptr [[ALLOCA]], align 4 ; CHECK-NEXT: br label [[SINK:%.*]] -; CHECK: B: +; CHECK: else: ; CHECK-NEXT: store half [[B:%.*]], ptr [[ALLOCA]], align 2 ; CHECK-NEXT: br label [[SINK]] ; CHECK: sink: @@ -208,11 +208,11 @@ define %struct.tup @multi_elem_struct_no_merge(i1 %cond, %struct.tup %a, half %b ; entry: %alloca = alloca i64 - br i1 %cond, label %A, label %B -A: + br i1 %cond, label %if, label %else +if: store %struct.tup %a, ptr %alloca br label %sink -B: +else: store half %b, ptr %alloca br label %sink sink: diff --git a/llvm/test/Transforms/InstCombine/minmax-fold.ll b/llvm/test/Transforms/InstCombine/minmax-fold.ll index 8b47dc7a28079ec95e9dc1f2b9d7d9a0fc39cca6..3e870c695cf1a5ffa14d35c9d6a3772757d12353 100644 --- a/llvm/test/Transforms/InstCombine/minmax-fold.ll +++ b/llvm/test/Transforms/InstCombine/minmax-fold.ll @@ -1524,7 +1524,7 @@ define i32 @test_smin_umin4(i32 %x) { define i32 @test_umax_nonminmax(i32 %x) { ; CHECK-LABEL: @test_umax_nonminmax( -; CHECK-NEXT: [[Y:%.*]] = call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0:![0-9]+]] +; CHECK-NEXT: [[Y:%.*]] = call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: [[UMAX:%.*]] = call i32 @llvm.umax.i32(i32 [[Y]], i32 1) ; CHECK-NEXT: ret i32 [[UMAX]] ; diff --git a/llvm/test/Transforms/InstCombine/mul.ll b/llvm/test/Transforms/InstCombine/mul.ll index 227ca4a6d5cfadffb9800e81cf7dc88d2ff6e7fe..4c1ce10171dd712a5bd3529df4149f7aa7d89124 100644 --- a/llvm/test/Transforms/InstCombine/mul.ll +++ b/llvm/test/Transforms/InstCombine/mul.ll @@ -2061,8 +2061,8 @@ define i32 @mul_sext_icmp_with_zero(i32 %x) { define i32 @test_mul_sext_bool(i1 %x, i32 %y) { ; CHECK-LABEL: @test_mul_sext_bool( -; CHECK-NEXT: [[Y_NEG:%.*]] = sub i32 0, [[Y:%.*]] -; CHECK-NEXT: [[MUL:%.*]] = select i1 [[X:%.*]], i32 [[Y_NEG]], i32 0 +; CHECK-NEXT: [[TMP1:%.*]] = sub i32 0, [[Y:%.*]] +; CHECK-NEXT: [[MUL:%.*]] = select i1 [[X:%.*]], i32 [[TMP1]], i32 0 ; CHECK-NEXT: ret i32 [[MUL]] ; %sext = sext i1 %x to i32 @@ -2072,8 +2072,8 @@ define i32 @test_mul_sext_bool(i1 %x, i32 %y) { define i32 @test_mul_sext_bool_nuw(i1 %x, i32 %y) { ; CHECK-LABEL: @test_mul_sext_bool_nuw( -; CHECK-NEXT: [[Y_NEG:%.*]] = sub i32 0, [[Y:%.*]] -; CHECK-NEXT: [[MUL:%.*]] = select i1 [[X:%.*]], i32 [[Y_NEG]], i32 0 +; CHECK-NEXT: [[TMP1:%.*]] = sub i32 0, [[Y:%.*]] +; CHECK-NEXT: [[MUL:%.*]] = select i1 [[X:%.*]], i32 [[TMP1]], i32 0 ; CHECK-NEXT: ret i32 [[MUL]] ; %sext = sext i1 %x to i32 @@ -2083,8 +2083,8 @@ define i32 @test_mul_sext_bool_nuw(i1 %x, i32 %y) { define i32 @test_mul_sext_bool_nsw(i1 %x, i32 %y) { ; CHECK-LABEL: @test_mul_sext_bool_nsw( -; CHECK-NEXT: [[Y_NEG:%.*]] = sub nsw i32 0, [[Y:%.*]] -; CHECK-NEXT: [[MUL:%.*]] = select i1 [[X:%.*]], i32 [[Y_NEG]], i32 0 +; CHECK-NEXT: [[TMP1:%.*]] = sub nsw i32 0, [[Y:%.*]] +; CHECK-NEXT: [[MUL:%.*]] = select i1 [[X:%.*]], i32 [[TMP1]], i32 0 ; CHECK-NEXT: ret i32 [[MUL]] ; %sext = sext i1 %x to i32 @@ -2094,8 +2094,8 @@ define i32 @test_mul_sext_bool_nsw(i1 %x, i32 %y) { define i32 @test_mul_sext_bool_nuw_nsw(i1 %x, i32 %y) { ; CHECK-LABEL: @test_mul_sext_bool_nuw_nsw( -; CHECK-NEXT: [[Y_NEG:%.*]] = sub nsw i32 0, [[Y:%.*]] -; CHECK-NEXT: [[MUL:%.*]] = select i1 [[X:%.*]], i32 [[Y_NEG]], i32 0 +; CHECK-NEXT: [[TMP1:%.*]] = sub nsw i32 0, [[Y:%.*]] +; CHECK-NEXT: [[MUL:%.*]] = select i1 [[X:%.*]], i32 [[TMP1]], i32 0 ; CHECK-NEXT: ret i32 [[MUL]] ; %sext = sext i1 %x to i32 @@ -2106,8 +2106,8 @@ define i32 @test_mul_sext_bool_nuw_nsw(i1 %x, i32 %y) { define i32 @test_mul_sext_bool_commuted(i1 %x, i32 %y) { ; CHECK-LABEL: @test_mul_sext_bool_commuted( ; CHECK-NEXT: [[TMP1:%.*]] = xor i32 [[Y:%.*]], -2 -; CHECK-NEXT: [[YY_NEG1:%.*]] = add i32 [[TMP1]], 1 -; CHECK-NEXT: [[MUL:%.*]] = select i1 [[X:%.*]], i32 [[YY_NEG1]], i32 0 +; CHECK-NEXT: [[YY_NEG:%.*]] = add i32 [[TMP1]], 1 +; CHECK-NEXT: [[MUL:%.*]] = select i1 [[X:%.*]], i32 [[YY_NEG]], i32 0 ; CHECK-NEXT: ret i32 [[MUL]] ; %yy = xor i32 %y, 1 @@ -2139,3 +2139,63 @@ define i32 @test_mul_sext_multiuse(i1 %x, i32 %y) { %mul = mul i32 %sext, %y ret i32 %mul } + +define i8 @mul_nsw_nonneg(i8 %x, i8 %y) { +; CHECK-LABEL: @mul_nsw_nonneg( +; CHECK-NEXT: [[X_NNEG:%.*]] = icmp sgt i8 [[X:%.*]], -1 +; CHECK-NEXT: call void @llvm.assume(i1 [[X_NNEG]]) +; CHECK-NEXT: [[Y_NNEG:%.*]] = icmp sgt i8 [[Y:%.*]], -1 +; CHECK-NEXT: call void @llvm.assume(i1 [[Y_NNEG]]) +; CHECK-NEXT: [[MUL:%.*]] = mul nsw i8 [[X]], [[Y]] +; CHECK-NEXT: ret i8 [[MUL]] +; + %x.nneg = icmp sge i8 %x, 0 + call void @llvm.assume(i1 %x.nneg) + %y.nneg = icmp sge i8 %y, 0 + call void @llvm.assume(i1 %y.nneg) + %mul = mul nsw i8 %x, %y + ret i8 %mul +} + +define i8 @mul_nsw_not_nonneg1(i8 %x, i8 %y) { +; CHECK-LABEL: @mul_nsw_not_nonneg1( +; CHECK-NEXT: [[Y_NNEG:%.*]] = icmp sgt i8 [[Y:%.*]], -1 +; CHECK-NEXT: call void @llvm.assume(i1 [[Y_NNEG]]) +; CHECK-NEXT: [[MUL:%.*]] = mul nsw i8 [[X:%.*]], [[Y]] +; CHECK-NEXT: ret i8 [[MUL]] +; + %y.nneg = icmp sge i8 %y, 0 + call void @llvm.assume(i1 %y.nneg) + %mul = mul nsw i8 %x, %y + ret i8 %mul +} + +define i8 @mul_nsw_not_nonneg2(i8 %x, i8 %y) { +; CHECK-LABEL: @mul_nsw_not_nonneg2( +; CHECK-NEXT: [[X_NNEG:%.*]] = icmp sgt i8 [[X:%.*]], -1 +; CHECK-NEXT: call void @llvm.assume(i1 [[X_NNEG]]) +; CHECK-NEXT: [[MUL:%.*]] = mul nsw i8 [[X]], [[Y:%.*]] +; CHECK-NEXT: ret i8 [[MUL]] +; + %x.nneg = icmp sge i8 %x, 0 + call void @llvm.assume(i1 %x.nneg) + %mul = mul nsw i8 %x, %y + ret i8 %mul +} + +define i8 @mul_not_nsw_nonneg(i8 %x, i8 %y) { +; CHECK-LABEL: @mul_not_nsw_nonneg( +; CHECK-NEXT: [[X_NNEG:%.*]] = icmp sgt i8 [[X:%.*]], -1 +; CHECK-NEXT: call void @llvm.assume(i1 [[X_NNEG]]) +; CHECK-NEXT: [[Y_NNEG:%.*]] = icmp sgt i8 [[Y:%.*]], -1 +; CHECK-NEXT: call void @llvm.assume(i1 [[Y_NNEG]]) +; CHECK-NEXT: [[MUL:%.*]] = mul i8 [[X]], [[Y]] +; CHECK-NEXT: ret i8 [[MUL]] +; + %x.nneg = icmp sge i8 %x, 0 + call void @llvm.assume(i1 %x.nneg) + %y.nneg = icmp sge i8 %y, 0 + call void @llvm.assume(i1 %y.nneg) + %mul = mul i8 %x, %y + ret i8 %mul +} diff --git a/llvm/test/Transforms/InstCombine/reduction-add-sext-zext-i1.ll b/llvm/test/Transforms/InstCombine/reduction-add-sext-zext-i1.ll index b94be990199bf547845899efdadae9787788b9bf..ca586a71b42c8cd0bd9fb965365d40824f03e04c 100644 --- a/llvm/test/Transforms/InstCombine/reduction-add-sext-zext-i1.ll +++ b/llvm/test/Transforms/InstCombine/reduction-add-sext-zext-i1.ll @@ -4,7 +4,7 @@ define i1 @reduce_add_self(<8 x i1> %x) { ; CHECK-LABEL: @reduce_add_self( ; CHECK-NEXT: [[TMP1:%.*]] = bitcast <8 x i1> [[X:%.*]] to i8 -; CHECK-NEXT: [[TMP2:%.*]] = call i8 @llvm.ctpop.i8(i8 [[TMP1]]), !range [[RNG0:![0-9]+]] +; CHECK-NEXT: [[TMP2:%.*]] = call range(i8 0, 9) i8 @llvm.ctpop.i8(i8 [[TMP1]]) ; CHECK-NEXT: [[RES:%.*]] = trunc i8 [[TMP2]] to i1 ; CHECK-NEXT: ret i1 [[RES]] ; @@ -15,7 +15,7 @@ define i1 @reduce_add_self(<8 x i1> %x) { define i32 @reduce_add_sext(<4 x i1> %x) { ; CHECK-LABEL: @reduce_add_sext( ; CHECK-NEXT: [[TMP1:%.*]] = bitcast <4 x i1> [[X:%.*]] to i4 -; CHECK-NEXT: [[TMP2:%.*]] = call i4 @llvm.ctpop.i4(i4 [[TMP1]]), !range [[RNG1:![0-9]+]] +; CHECK-NEXT: [[TMP2:%.*]] = call range(i4 0, 5) i4 @llvm.ctpop.i4(i4 [[TMP1]]) ; CHECK-NEXT: [[TMP3:%.*]] = zext nneg i4 [[TMP2]] to i32 ; CHECK-NEXT: [[RES:%.*]] = sub nsw i32 0, [[TMP3]] ; CHECK-NEXT: ret i32 [[RES]] @@ -28,7 +28,7 @@ define i32 @reduce_add_sext(<4 x i1> %x) { define i64 @reduce_add_zext(<8 x i1> %x) { ; CHECK-LABEL: @reduce_add_zext( ; CHECK-NEXT: [[TMP1:%.*]] = bitcast <8 x i1> [[X:%.*]] to i8 -; CHECK-NEXT: [[TMP2:%.*]] = call i8 @llvm.ctpop.i8(i8 [[TMP1]]), !range [[RNG0]] +; CHECK-NEXT: [[TMP2:%.*]] = call range(i8 0, 9) i8 @llvm.ctpop.i8(i8 [[TMP1]]) ; CHECK-NEXT: [[RES:%.*]] = zext nneg i8 [[TMP2]] to i64 ; CHECK-NEXT: ret i64 [[RES]] ; @@ -40,7 +40,7 @@ define i64 @reduce_add_zext(<8 x i1> %x) { define i16 @reduce_add_sext_same(<16 x i1> %x) { ; CHECK-LABEL: @reduce_add_sext_same( ; CHECK-NEXT: [[TMP1:%.*]] = bitcast <16 x i1> [[X:%.*]] to i16 -; CHECK-NEXT: [[TMP2:%.*]] = call i16 @llvm.ctpop.i16(i16 [[TMP1]]), !range [[RNG2:![0-9]+]] +; CHECK-NEXT: [[TMP2:%.*]] = call range(i16 0, 17) i16 @llvm.ctpop.i16(i16 [[TMP1]]) ; CHECK-NEXT: [[RES:%.*]] = sub nsw i16 0, [[TMP2]] ; CHECK-NEXT: ret i16 [[RES]] ; @@ -52,7 +52,7 @@ define i16 @reduce_add_sext_same(<16 x i1> %x) { define i8 @reduce_add_zext_long(<128 x i1> %x) { ; CHECK-LABEL: @reduce_add_zext_long( ; CHECK-NEXT: [[TMP1:%.*]] = bitcast <128 x i1> [[X:%.*]] to i128 -; CHECK-NEXT: [[TMP2:%.*]] = call i128 @llvm.ctpop.i128(i128 [[TMP1]]), !range [[RNG3:![0-9]+]] +; CHECK-NEXT: [[TMP2:%.*]] = call range(i128 0, 129) i128 @llvm.ctpop.i128(i128 [[TMP1]]) ; CHECK-NEXT: [[TMP3:%.*]] = trunc nuw i128 [[TMP2]] to i8 ; CHECK-NEXT: [[RES:%.*]] = sub i8 0, [[TMP3]] ; CHECK-NEXT: ret i8 [[RES]] @@ -66,7 +66,7 @@ define i8 @reduce_add_zext_long(<128 x i1> %x) { define i8 @reduce_add_zext_long_external_use(<128 x i1> %x) { ; CHECK-LABEL: @reduce_add_zext_long_external_use( ; CHECK-NEXT: [[TMP1:%.*]] = bitcast <128 x i1> [[X:%.*]] to i128 -; CHECK-NEXT: [[TMP2:%.*]] = call i128 @llvm.ctpop.i128(i128 [[TMP1]]), !range [[RNG3]] +; CHECK-NEXT: [[TMP2:%.*]] = call range(i128 0, 129) i128 @llvm.ctpop.i128(i128 [[TMP1]]) ; CHECK-NEXT: [[TMP3:%.*]] = trunc nuw i128 [[TMP2]] to i8 ; CHECK-NEXT: [[RES:%.*]] = sub i8 0, [[TMP3]] ; CHECK-NEXT: [[TMP4:%.*]] = extractelement <128 x i1> [[X]], i64 0 @@ -85,7 +85,7 @@ define i8 @reduce_add_zext_long_external_use(<128 x i1> %x) { define i64 @reduce_add_zext_external_use(<8 x i1> %x) { ; CHECK-LABEL: @reduce_add_zext_external_use( ; CHECK-NEXT: [[TMP1:%.*]] = bitcast <8 x i1> [[X:%.*]] to i8 -; CHECK-NEXT: [[TMP2:%.*]] = call i8 @llvm.ctpop.i8(i8 [[TMP1]]), !range [[RNG0]] +; CHECK-NEXT: [[TMP2:%.*]] = call range(i8 0, 9) i8 @llvm.ctpop.i8(i8 [[TMP1]]) ; CHECK-NEXT: [[RES:%.*]] = zext nneg i8 [[TMP2]] to i64 ; CHECK-NEXT: [[TMP3:%.*]] = extractelement <8 x i1> [[X]], i64 0 ; CHECK-NEXT: [[EXT:%.*]] = zext i1 [[TMP3]] to i64 diff --git a/llvm/test/Transforms/InstCombine/reduction-xor-sext-zext-i1.ll b/llvm/test/Transforms/InstCombine/reduction-xor-sext-zext-i1.ll index 84ac9369b5ff066c0211ef34cf5dc7535bf258c9..b5baf8ec71a4893e75329547b41c017c21b23751 100644 --- a/llvm/test/Transforms/InstCombine/reduction-xor-sext-zext-i1.ll +++ b/llvm/test/Transforms/InstCombine/reduction-xor-sext-zext-i1.ll @@ -4,7 +4,7 @@ define i1 @reduce_xor_self(<8 x i1> %x) { ; CHECK-LABEL: @reduce_xor_self( ; CHECK-NEXT: [[TMP1:%.*]] = bitcast <8 x i1> [[X:%.*]] to i8 -; CHECK-NEXT: [[TMP2:%.*]] = call i8 @llvm.ctpop.i8(i8 [[TMP1]]), !range [[RNG0:![0-9]+]] +; CHECK-NEXT: [[TMP2:%.*]] = call range(i8 0, 9) i8 @llvm.ctpop.i8(i8 [[TMP1]]) ; CHECK-NEXT: [[RES:%.*]] = trunc i8 [[TMP2]] to i1 ; CHECK-NEXT: ret i1 [[RES]] ; @@ -15,7 +15,7 @@ define i1 @reduce_xor_self(<8 x i1> %x) { define i32 @reduce_xor_sext(<4 x i1> %x) { ; CHECK-LABEL: @reduce_xor_sext( ; CHECK-NEXT: [[TMP1:%.*]] = bitcast <4 x i1> [[X:%.*]] to i4 -; CHECK-NEXT: [[TMP2:%.*]] = call i4 @llvm.ctpop.i4(i4 [[TMP1]]), !range [[RNG1:![0-9]+]] +; CHECK-NEXT: [[TMP2:%.*]] = call range(i4 0, 5) i4 @llvm.ctpop.i4(i4 [[TMP1]]) ; CHECK-NEXT: [[TMP3:%.*]] = trunc i4 [[TMP2]] to i1 ; CHECK-NEXT: [[RES:%.*]] = sext i1 [[TMP3]] to i32 ; CHECK-NEXT: ret i32 [[RES]] @@ -28,7 +28,7 @@ define i32 @reduce_xor_sext(<4 x i1> %x) { define i64 @reduce_xor_zext(<8 x i1> %x) { ; CHECK-LABEL: @reduce_xor_zext( ; CHECK-NEXT: [[TMP1:%.*]] = bitcast <8 x i1> [[X:%.*]] to i8 -; CHECK-NEXT: [[TMP2:%.*]] = call i8 @llvm.ctpop.i8(i8 [[TMP1]]), !range [[RNG0]] +; CHECK-NEXT: [[TMP2:%.*]] = call range(i8 0, 9) i8 @llvm.ctpop.i8(i8 [[TMP1]]) ; CHECK-NEXT: [[TMP3:%.*]] = and i8 [[TMP2]], 1 ; CHECK-NEXT: [[RES:%.*]] = zext nneg i8 [[TMP3]] to i64 ; CHECK-NEXT: ret i64 [[RES]] @@ -41,7 +41,7 @@ define i64 @reduce_xor_zext(<8 x i1> %x) { define i16 @reduce_xor_sext_same(<16 x i1> %x) { ; CHECK-LABEL: @reduce_xor_sext_same( ; CHECK-NEXT: [[TMP1:%.*]] = bitcast <16 x i1> [[X:%.*]] to i16 -; CHECK-NEXT: [[TMP2:%.*]] = call i16 @llvm.ctpop.i16(i16 [[TMP1]]), !range [[RNG2:![0-9]+]] +; CHECK-NEXT: [[TMP2:%.*]] = call range(i16 0, 17) i16 @llvm.ctpop.i16(i16 [[TMP1]]) ; CHECK-NEXT: [[TMP3:%.*]] = and i16 [[TMP2]], 1 ; CHECK-NEXT: [[SEXT:%.*]] = sub nsw i16 0, [[TMP3]] ; CHECK-NEXT: ret i16 [[SEXT]] @@ -54,7 +54,7 @@ define i16 @reduce_xor_sext_same(<16 x i1> %x) { define i8 @reduce_xor_zext_long(<128 x i1> %x) { ; CHECK-LABEL: @reduce_xor_zext_long( ; CHECK-NEXT: [[TMP1:%.*]] = bitcast <128 x i1> [[X:%.*]] to i128 -; CHECK-NEXT: [[TMP2:%.*]] = call i128 @llvm.ctpop.i128(i128 [[TMP1]]), !range [[RNG3:![0-9]+]] +; CHECK-NEXT: [[TMP2:%.*]] = call range(i128 0, 129) i128 @llvm.ctpop.i128(i128 [[TMP1]]) ; CHECK-NEXT: [[TMP3:%.*]] = trunc i128 [[TMP2]] to i1 ; CHECK-NEXT: [[RES:%.*]] = sext i1 [[TMP3]] to i8 ; CHECK-NEXT: ret i8 [[RES]] @@ -68,7 +68,7 @@ define i8 @reduce_xor_zext_long(<128 x i1> %x) { define i8 @reduce_xor_zext_long_external_use(<128 x i1> %x) { ; CHECK-LABEL: @reduce_xor_zext_long_external_use( ; CHECK-NEXT: [[TMP1:%.*]] = bitcast <128 x i1> [[X:%.*]] to i128 -; CHECK-NEXT: [[TMP2:%.*]] = call i128 @llvm.ctpop.i128(i128 [[TMP1]]), !range [[RNG3]] +; CHECK-NEXT: [[TMP2:%.*]] = call range(i128 0, 129) i128 @llvm.ctpop.i128(i128 [[TMP1]]) ; CHECK-NEXT: [[TMP3:%.*]] = trunc i128 [[TMP2]] to i1 ; CHECK-NEXT: [[RES:%.*]] = sext i1 [[TMP3]] to i8 ; CHECK-NEXT: [[TMP5:%.*]] = extractelement <128 x i1> [[X]], i64 0 @@ -87,7 +87,7 @@ define i8 @reduce_xor_zext_long_external_use(<128 x i1> %x) { define i64 @reduce_xor_zext_external_use(<8 x i1> %x) { ; CHECK-LABEL: @reduce_xor_zext_external_use( ; CHECK-NEXT: [[TMP1:%.*]] = bitcast <8 x i1> [[X:%.*]] to i8 -; CHECK-NEXT: [[TMP2:%.*]] = call i8 @llvm.ctpop.i8(i8 [[TMP1]]), !range [[RNG0]] +; CHECK-NEXT: [[TMP2:%.*]] = call range(i8 0, 9) i8 @llvm.ctpop.i8(i8 [[TMP1]]) ; CHECK-NEXT: [[TMP3:%.*]] = and i8 [[TMP2]], 1 ; CHECK-NEXT: [[RES:%.*]] = zext nneg i8 [[TMP3]] to i64 ; CHECK-NEXT: [[TMP4:%.*]] = extractelement <8 x i1> [[X]], i64 0 diff --git a/llvm/test/Transforms/InstCombine/select-cmp-cttz-ctlz.ll b/llvm/test/Transforms/InstCombine/select-cmp-cttz-ctlz.ll index 69896f855f5f1615c009e44e7bb739dc8912e502..3d5f2c209edf3b540b81532ff8ef8f77a6f2f64a 100644 --- a/llvm/test/Transforms/InstCombine/select-cmp-cttz-ctlz.ll +++ b/llvm/test/Transforms/InstCombine/select-cmp-cttz-ctlz.ll @@ -7,7 +7,7 @@ define i16 @test1(i16 %x) { ; CHECK-LABEL: @test1( -; CHECK-NEXT: [[CT:%.*]] = tail call i16 @llvm.ctlz.i16(i16 [[X:%.*]], i1 false), !range [[RNG0:![0-9]+]] +; CHECK-NEXT: [[CT:%.*]] = tail call range(i16 0, 17) i16 @llvm.ctlz.i16(i16 [[X:%.*]], i1 false) ; CHECK-NEXT: ret i16 [[CT]] ; %ct = tail call i16 @llvm.ctlz.i16(i16 %x, i1 true) @@ -18,7 +18,7 @@ define i16 @test1(i16 %x) { define i32 @test2(i32 %x) { ; CHECK-LABEL: @test2( -; CHECK-NEXT: [[CT:%.*]] = tail call i32 @llvm.ctlz.i32(i32 [[X:%.*]], i1 false), !range [[RNG1:![0-9]+]] +; CHECK-NEXT: [[CT:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[X:%.*]], i1 false) ; CHECK-NEXT: ret i32 [[CT]] ; %ct = tail call i32 @llvm.ctlz.i32(i32 %x, i1 true) @@ -29,7 +29,7 @@ define i32 @test2(i32 %x) { define i64 @test3(i64 %x) { ; CHECK-LABEL: @test3( -; CHECK-NEXT: [[CT:%.*]] = tail call i64 @llvm.ctlz.i64(i64 [[X:%.*]], i1 false), !range [[RNG2:![0-9]+]] +; CHECK-NEXT: [[CT:%.*]] = tail call range(i64 0, 65) i64 @llvm.ctlz.i64(i64 [[X:%.*]], i1 false) ; CHECK-NEXT: ret i64 [[CT]] ; %ct = tail call i64 @llvm.ctlz.i64(i64 %x, i1 true) @@ -40,7 +40,7 @@ define i64 @test3(i64 %x) { define i16 @test4(i16 %x) { ; CHECK-LABEL: @test4( -; CHECK-NEXT: [[CT:%.*]] = tail call i16 @llvm.ctlz.i16(i16 [[X:%.*]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[CT:%.*]] = tail call range(i16 0, 17) i16 @llvm.ctlz.i16(i16 [[X:%.*]], i1 false) ; CHECK-NEXT: ret i16 [[CT]] ; %ct = tail call i16 @llvm.ctlz.i16(i16 %x, i1 true) @@ -51,7 +51,7 @@ define i16 @test4(i16 %x) { define i32 @test5(i32 %x) { ; CHECK-LABEL: @test5( -; CHECK-NEXT: [[CT:%.*]] = tail call i32 @llvm.ctlz.i32(i32 [[X:%.*]], i1 false), !range [[RNG1]] +; CHECK-NEXT: [[CT:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[X:%.*]], i1 false) ; CHECK-NEXT: ret i32 [[CT]] ; %ct = tail call i32 @llvm.ctlz.i32(i32 %x, i1 true) @@ -62,7 +62,7 @@ define i32 @test5(i32 %x) { define i64 @test6(i64 %x) { ; CHECK-LABEL: @test6( -; CHECK-NEXT: [[CT:%.*]] = tail call i64 @llvm.ctlz.i64(i64 [[X:%.*]], i1 false), !range [[RNG2]] +; CHECK-NEXT: [[CT:%.*]] = tail call range(i64 0, 65) i64 @llvm.ctlz.i64(i64 [[X:%.*]], i1 false) ; CHECK-NEXT: ret i64 [[CT]] ; %ct = tail call i64 @llvm.ctlz.i64(i64 %x, i1 true) @@ -73,7 +73,7 @@ define i64 @test6(i64 %x) { define i16 @test1b(i16 %x) { ; CHECK-LABEL: @test1b( -; CHECK-NEXT: [[CT:%.*]] = tail call i16 @llvm.cttz.i16(i16 [[X:%.*]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[CT:%.*]] = tail call range(i16 0, 17) i16 @llvm.cttz.i16(i16 [[X:%.*]], i1 false) ; CHECK-NEXT: ret i16 [[CT]] ; %ct = tail call i16 @llvm.cttz.i16(i16 %x, i1 true) @@ -84,7 +84,7 @@ define i16 @test1b(i16 %x) { define i32 @test2b(i32 %x) { ; CHECK-LABEL: @test2b( -; CHECK-NEXT: [[CT:%.*]] = tail call i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 false), !range [[RNG1]] +; CHECK-NEXT: [[CT:%.*]] = tail call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 false) ; CHECK-NEXT: ret i32 [[CT]] ; %ct = tail call i32 @llvm.cttz.i32(i32 %x, i1 true) @@ -95,7 +95,7 @@ define i32 @test2b(i32 %x) { define i64 @test3b(i64 %x) { ; CHECK-LABEL: @test3b( -; CHECK-NEXT: [[CT:%.*]] = tail call i64 @llvm.cttz.i64(i64 [[X:%.*]], i1 false), !range [[RNG2]] +; CHECK-NEXT: [[CT:%.*]] = tail call range(i64 0, 65) i64 @llvm.cttz.i64(i64 [[X:%.*]], i1 false) ; CHECK-NEXT: ret i64 [[CT]] ; %ct = tail call i64 @llvm.cttz.i64(i64 %x, i1 true) @@ -106,7 +106,7 @@ define i64 @test3b(i64 %x) { define i16 @test4b(i16 %x) { ; CHECK-LABEL: @test4b( -; CHECK-NEXT: [[CT:%.*]] = tail call i16 @llvm.cttz.i16(i16 [[X:%.*]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[CT:%.*]] = tail call range(i16 0, 17) i16 @llvm.cttz.i16(i16 [[X:%.*]], i1 false) ; CHECK-NEXT: ret i16 [[CT]] ; %ct = tail call i16 @llvm.cttz.i16(i16 %x, i1 true) @@ -118,7 +118,7 @@ define i16 @test4b(i16 %x) { define i32 @test5b(i32 %x) { ; CHECK-LABEL: @test5b( ; CHECK-NEXT: entry: -; CHECK-NEXT: [[CT:%.*]] = tail call i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 false), !range [[RNG1]] +; CHECK-NEXT: [[CT:%.*]] = tail call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 false) ; CHECK-NEXT: ret i32 [[CT]] ; entry: @@ -130,7 +130,7 @@ entry: define i64 @test6b(i64 %x) { ; CHECK-LABEL: @test6b( -; CHECK-NEXT: [[CT:%.*]] = tail call i64 @llvm.cttz.i64(i64 [[X:%.*]], i1 false), !range [[RNG2]] +; CHECK-NEXT: [[CT:%.*]] = tail call range(i64 0, 65) i64 @llvm.cttz.i64(i64 [[X:%.*]], i1 false) ; CHECK-NEXT: ret i64 [[CT]] ; %ct = tail call i64 @llvm.cttz.i64(i64 %x, i1 true) @@ -141,7 +141,7 @@ define i64 @test6b(i64 %x) { define i32 @test1c(i16 %x) { ; CHECK-LABEL: @test1c( -; CHECK-NEXT: [[CT:%.*]] = tail call i16 @llvm.cttz.i16(i16 [[X:%.*]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[CT:%.*]] = tail call range(i16 0, 17) i16 @llvm.cttz.i16(i16 [[X:%.*]], i1 false) ; CHECK-NEXT: [[CAST2:%.*]] = zext nneg i16 [[CT]] to i32 ; CHECK-NEXT: ret i32 [[CAST2]] ; @@ -154,7 +154,7 @@ define i32 @test1c(i16 %x) { define i64 @test2c(i16 %x) { ; CHECK-LABEL: @test2c( -; CHECK-NEXT: [[CT:%.*]] = tail call i16 @llvm.cttz.i16(i16 [[X:%.*]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[CT:%.*]] = tail call range(i16 0, 17) i16 @llvm.cttz.i16(i16 [[X:%.*]], i1 false) ; CHECK-NEXT: [[CONV:%.*]] = zext nneg i16 [[CT]] to i64 ; CHECK-NEXT: ret i64 [[CONV]] ; @@ -167,7 +167,7 @@ define i64 @test2c(i16 %x) { define i64 @test3c(i32 %x) { ; CHECK-LABEL: @test3c( -; CHECK-NEXT: [[CT:%.*]] = tail call i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 false), !range [[RNG1]] +; CHECK-NEXT: [[CT:%.*]] = tail call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 false) ; CHECK-NEXT: [[CONV:%.*]] = zext nneg i32 [[CT]] to i64 ; CHECK-NEXT: ret i64 [[CONV]] ; @@ -180,7 +180,7 @@ define i64 @test3c(i32 %x) { define i32 @test4c(i16 %x) { ; CHECK-LABEL: @test4c( -; CHECK-NEXT: [[CT:%.*]] = tail call i16 @llvm.ctlz.i16(i16 [[X:%.*]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[CT:%.*]] = tail call range(i16 0, 17) i16 @llvm.ctlz.i16(i16 [[X:%.*]], i1 false) ; CHECK-NEXT: [[CAST:%.*]] = zext nneg i16 [[CT]] to i32 ; CHECK-NEXT: ret i32 [[CAST]] ; @@ -193,7 +193,7 @@ define i32 @test4c(i16 %x) { define i64 @test5c(i16 %x) { ; CHECK-LABEL: @test5c( -; CHECK-NEXT: [[CT:%.*]] = tail call i16 @llvm.ctlz.i16(i16 [[X:%.*]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[CT:%.*]] = tail call range(i16 0, 17) i16 @llvm.ctlz.i16(i16 [[X:%.*]], i1 false) ; CHECK-NEXT: [[CAST:%.*]] = zext nneg i16 [[CT]] to i64 ; CHECK-NEXT: ret i64 [[CAST]] ; @@ -206,7 +206,7 @@ define i64 @test5c(i16 %x) { define i64 @test6c(i32 %x) { ; CHECK-LABEL: @test6c( -; CHECK-NEXT: [[CT:%.*]] = tail call i32 @llvm.ctlz.i32(i32 [[X:%.*]], i1 false), !range [[RNG1]] +; CHECK-NEXT: [[CT:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[X:%.*]], i1 false) ; CHECK-NEXT: [[CAST:%.*]] = zext nneg i32 [[CT]] to i64 ; CHECK-NEXT: ret i64 [[CAST]] ; @@ -219,7 +219,7 @@ define i64 @test6c(i32 %x) { define i16 @test1d(i64 %x) { ; CHECK-LABEL: @test1d( -; CHECK-NEXT: [[CT:%.*]] = tail call i64 @llvm.cttz.i64(i64 [[X:%.*]], i1 false), !range [[RNG2]] +; CHECK-NEXT: [[CT:%.*]] = tail call range(i64 0, 65) i64 @llvm.cttz.i64(i64 [[X:%.*]], i1 false) ; CHECK-NEXT: [[CONV:%.*]] = trunc nuw nsw i64 [[CT]] to i16 ; CHECK-NEXT: ret i16 [[CONV]] ; @@ -232,7 +232,7 @@ define i16 @test1d(i64 %x) { define i32 @test2d(i64 %x) { ; CHECK-LABEL: @test2d( -; CHECK-NEXT: [[CT:%.*]] = tail call i64 @llvm.cttz.i64(i64 [[X:%.*]], i1 false), !range [[RNG2]] +; CHECK-NEXT: [[CT:%.*]] = tail call range(i64 0, 65) i64 @llvm.cttz.i64(i64 [[X:%.*]], i1 false) ; CHECK-NEXT: [[CAST:%.*]] = trunc nuw nsw i64 [[CT]] to i32 ; CHECK-NEXT: ret i32 [[CAST]] ; @@ -245,7 +245,7 @@ define i32 @test2d(i64 %x) { define i16 @test3d(i32 %x) { ; CHECK-LABEL: @test3d( -; CHECK-NEXT: [[CT:%.*]] = tail call i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 false), !range [[RNG1]] +; CHECK-NEXT: [[CT:%.*]] = tail call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 false) ; CHECK-NEXT: [[CAST:%.*]] = trunc nuw nsw i32 [[CT]] to i16 ; CHECK-NEXT: ret i16 [[CAST]] ; @@ -258,7 +258,7 @@ define i16 @test3d(i32 %x) { define i16 @test4d(i64 %x) { ; CHECK-LABEL: @test4d( -; CHECK-NEXT: [[CT:%.*]] = tail call i64 @llvm.ctlz.i64(i64 [[X:%.*]], i1 false), !range [[RNG2]] +; CHECK-NEXT: [[CT:%.*]] = tail call range(i64 0, 65) i64 @llvm.ctlz.i64(i64 [[X:%.*]], i1 false) ; CHECK-NEXT: [[CAST:%.*]] = trunc nuw nsw i64 [[CT]] to i16 ; CHECK-NEXT: ret i16 [[CAST]] ; @@ -271,7 +271,7 @@ define i16 @test4d(i64 %x) { define i32 @test5d(i64 %x) { ; CHECK-LABEL: @test5d( -; CHECK-NEXT: [[CT:%.*]] = tail call i64 @llvm.ctlz.i64(i64 [[X:%.*]], i1 false), !range [[RNG2]] +; CHECK-NEXT: [[CT:%.*]] = tail call range(i64 0, 65) i64 @llvm.ctlz.i64(i64 [[X:%.*]], i1 false) ; CHECK-NEXT: [[CAST:%.*]] = trunc nuw nsw i64 [[CT]] to i32 ; CHECK-NEXT: ret i32 [[CAST]] ; @@ -287,7 +287,7 @@ define i32 @test5d(i64 %x) { define i32 @not_op_ctlz(i64 %x) { ; CHECK-LABEL: @not_op_ctlz( ; CHECK-NEXT: [[N:%.*]] = xor i64 [[X:%.*]], -1 -; CHECK-NEXT: [[CT:%.*]] = tail call i64 @llvm.ctlz.i64(i64 [[N]], i1 false), !range [[RNG2]] +; CHECK-NEXT: [[CT:%.*]] = tail call range(i64 0, 65) i64 @llvm.ctlz.i64(i64 [[N]], i1 false) ; CHECK-NEXT: [[CAST:%.*]] = trunc nuw nsw i64 [[CT]] to i32 ; CHECK-NEXT: ret i32 [[CAST]] ; @@ -302,7 +302,7 @@ define i32 @not_op_ctlz(i64 %x) { define i32 @not_op_cttz(i64 %x) { ; CHECK-LABEL: @not_op_cttz( ; CHECK-NEXT: [[N:%.*]] = xor i64 [[X:%.*]], -1 -; CHECK-NEXT: [[CT:%.*]] = tail call i64 @llvm.cttz.i64(i64 [[N]], i1 false), !range [[RNG2]] +; CHECK-NEXT: [[CT:%.*]] = tail call range(i64 0, 65) i64 @llvm.cttz.i64(i64 [[N]], i1 false) ; CHECK-NEXT: [[CAST:%.*]] = trunc nuw nsw i64 [[CT]] to i32 ; CHECK-NEXT: ret i32 [[CAST]] ; @@ -319,7 +319,7 @@ define i32 @not_op_cttz(i64 %x) { define i32 @not_op_ctlz_wrong_xor_op1(i64 %x) { ; CHECK-LABEL: @not_op_ctlz_wrong_xor_op1( ; CHECK-NEXT: [[N:%.*]] = xor i64 [[X:%.*]], -2 -; CHECK-NEXT: [[CT:%.*]] = tail call i64 @llvm.ctlz.i64(i64 [[N]], i1 true), !range [[RNG2]] +; CHECK-NEXT: [[CT:%.*]] = tail call range(i64 0, 65) i64 @llvm.ctlz.i64(i64 [[N]], i1 true) ; CHECK-NEXT: [[CAST:%.*]] = trunc nuw nsw i64 [[CT]] to i32 ; CHECK-NEXT: [[TOBOOL:%.*]] = icmp eq i64 [[X]], -1 ; CHECK-NEXT: [[R:%.*]] = select i1 [[TOBOOL]], i32 64, i32 [[CAST]] @@ -338,7 +338,7 @@ define i32 @not_op_ctlz_wrong_xor_op1(i64 %x) { define i32 @not_op_ctlz_wrong_xor_op0(i64 %x, i64 %y) { ; CHECK-LABEL: @not_op_ctlz_wrong_xor_op0( ; CHECK-NEXT: [[N:%.*]] = xor i64 [[Y:%.*]], -1 -; CHECK-NEXT: [[CT:%.*]] = tail call i64 @llvm.ctlz.i64(i64 [[N]], i1 true), !range [[RNG2]] +; CHECK-NEXT: [[CT:%.*]] = tail call range(i64 0, 65) i64 @llvm.ctlz.i64(i64 [[N]], i1 true) ; CHECK-NEXT: [[CAST:%.*]] = trunc nuw nsw i64 [[CT]] to i32 ; CHECK-NEXT: [[TOBOOL:%.*]] = icmp eq i64 [[X:%.*]], -1 ; CHECK-NEXT: [[R:%.*]] = select i1 [[TOBOOL]], i32 64, i32 [[CAST]] @@ -357,7 +357,7 @@ define i32 @not_op_ctlz_wrong_xor_op0(i64 %x, i64 %y) { define i32 @not_op_cttz_wrong_cmp(i64 %x) { ; CHECK-LABEL: @not_op_cttz_wrong_cmp( ; CHECK-NEXT: [[N:%.*]] = xor i64 [[X:%.*]], -1 -; CHECK-NEXT: [[CT:%.*]] = tail call i64 @llvm.cttz.i64(i64 [[N]], i1 true), !range [[RNG2]] +; CHECK-NEXT: [[CT:%.*]] = tail call range(i64 0, 65) i64 @llvm.cttz.i64(i64 [[N]], i1 true) ; CHECK-NEXT: [[CAST:%.*]] = trunc nuw nsw i64 [[CT]] to i32 ; CHECK-NEXT: [[TOBOOL:%.*]] = icmp eq i64 [[X]], 0 ; CHECK-NEXT: [[R:%.*]] = select i1 [[TOBOOL]], i32 64, i32 [[CAST]] @@ -373,7 +373,7 @@ define i32 @not_op_cttz_wrong_cmp(i64 %x) { define i16 @test6d(i32 %x) { ; CHECK-LABEL: @test6d( -; CHECK-NEXT: [[CT:%.*]] = tail call i32 @llvm.ctlz.i32(i32 [[X:%.*]], i1 false), !range [[RNG1]] +; CHECK-NEXT: [[CT:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[X:%.*]], i1 false) ; CHECK-NEXT: [[CAST:%.*]] = trunc nuw nsw i32 [[CT]] to i16 ; CHECK-NEXT: ret i16 [[CAST]] ; @@ -386,7 +386,7 @@ define i16 @test6d(i32 %x) { define i64 @select_bug1(i32 %x) { ; CHECK-LABEL: @select_bug1( -; CHECK-NEXT: [[CT:%.*]] = tail call i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 false), !range [[RNG1]] +; CHECK-NEXT: [[CT:%.*]] = tail call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 false) ; CHECK-NEXT: [[CONV:%.*]] = zext nneg i32 [[CT]] to i64 ; CHECK-NEXT: ret i64 [[CONV]] ; @@ -399,7 +399,7 @@ define i64 @select_bug1(i32 %x) { define i16 @select_bug2(i32 %x) { ; CHECK-LABEL: @select_bug2( -; CHECK-NEXT: [[CT:%.*]] = tail call i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 false), !range [[RNG1]] +; CHECK-NEXT: [[CT:%.*]] = tail call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 false) ; CHECK-NEXT: [[CONV:%.*]] = trunc nuw nsw i32 [[CT]] to i16 ; CHECK-NEXT: ret i16 [[CONV]] ; @@ -412,7 +412,7 @@ define i16 @select_bug2(i32 %x) { define i128 @test7(i128 %x) { ; CHECK-LABEL: @test7( -; CHECK-NEXT: [[CT:%.*]] = tail call i128 @llvm.ctlz.i128(i128 [[X:%.*]], i1 false), !range [[RNG3:![0-9]+]] +; CHECK-NEXT: [[CT:%.*]] = tail call range(i128 0, 129) i128 @llvm.ctlz.i128(i128 [[X:%.*]], i1 false) ; CHECK-NEXT: ret i128 [[CT]] ; %ct = tail call i128 @llvm.ctlz.i128(i128 %x, i1 true) @@ -423,7 +423,7 @@ define i128 @test7(i128 %x) { define i128 @test8(i128 %x) { ; CHECK-LABEL: @test8( -; CHECK-NEXT: [[CT:%.*]] = tail call i128 @llvm.cttz.i128(i128 [[X:%.*]], i1 false), !range [[RNG3]] +; CHECK-NEXT: [[CT:%.*]] = tail call range(i128 0, 129) i128 @llvm.cttz.i128(i128 [[X:%.*]], i1 false) ; CHECK-NEXT: ret i128 [[CT]] ; %ct = tail call i128 @llvm.cttz.i128(i128 %x, i1 true) @@ -434,7 +434,7 @@ define i128 @test8(i128 %x) { define i32 @test_ctlz_not_bw(i32 %x) { ; CHECK-LABEL: @test_ctlz_not_bw( -; CHECK-NEXT: [[CT:%.*]] = tail call i32 @llvm.ctlz.i32(i32 [[X:%.*]], i1 true), !range [[RNG1]] +; CHECK-NEXT: [[CT:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[X:%.*]], i1 true) ; CHECK-NEXT: [[CMP_NOT:%.*]] = icmp eq i32 [[X]], 0 ; CHECK-NEXT: [[RES:%.*]] = select i1 [[CMP_NOT]], i32 123, i32 [[CT]] ; CHECK-NEXT: ret i32 [[RES]] @@ -447,7 +447,7 @@ define i32 @test_ctlz_not_bw(i32 %x) { define i32 @test_ctlz_not_bw_multiuse(i32 %x) { ; CHECK-LABEL: @test_ctlz_not_bw_multiuse( -; CHECK-NEXT: [[CT:%.*]] = tail call i32 @llvm.ctlz.i32(i32 [[X:%.*]], i1 false), !range [[RNG1]] +; CHECK-NEXT: [[CT:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[X:%.*]], i1 false) ; CHECK-NEXT: [[CMP_NOT:%.*]] = icmp eq i32 [[X]], 0 ; CHECK-NEXT: [[SEL:%.*]] = select i1 [[CMP_NOT]], i32 123, i32 [[CT]] ; CHECK-NEXT: [[RES:%.*]] = or i32 [[SEL]], [[CT]] @@ -462,7 +462,7 @@ define i32 @test_ctlz_not_bw_multiuse(i32 %x) { define i32 @test_cttz_not_bw(i32 %x) { ; CHECK-LABEL: @test_cttz_not_bw( -; CHECK-NEXT: [[CT:%.*]] = tail call i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 true), !range [[RNG1]] +; CHECK-NEXT: [[CT:%.*]] = tail call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 true) ; CHECK-NEXT: [[CMP_NOT:%.*]] = icmp eq i32 [[X]], 0 ; CHECK-NEXT: [[RES:%.*]] = select i1 [[CMP_NOT]], i32 123, i32 [[CT]] ; CHECK-NEXT: ret i32 [[RES]] @@ -475,7 +475,7 @@ define i32 @test_cttz_not_bw(i32 %x) { define i32 @test_cttz_not_bw_multiuse(i32 %x) { ; CHECK-LABEL: @test_cttz_not_bw_multiuse( -; CHECK-NEXT: [[CT:%.*]] = tail call i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 false), !range [[RNG1]] +; CHECK-NEXT: [[CT:%.*]] = tail call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 false) ; CHECK-NEXT: [[CMP_NOT:%.*]] = icmp eq i32 [[X]], 0 ; CHECK-NEXT: [[SEL:%.*]] = select i1 [[CMP_NOT]], i32 123, i32 [[CT]] ; CHECK-NEXT: [[RES:%.*]] = or i32 [[SEL]], [[CT]] @@ -490,7 +490,7 @@ define i32 @test_cttz_not_bw_multiuse(i32 %x) { define <2 x i32> @test_ctlz_bw_vec(<2 x i32> %x) { ; CHECK-LABEL: @test_ctlz_bw_vec( -; CHECK-NEXT: [[CT:%.*]] = tail call <2 x i32> @llvm.ctlz.v2i32(<2 x i32> [[X:%.*]], i1 false), !range [[RNG1]] +; CHECK-NEXT: [[CT:%.*]] = tail call range(i32 0, 33) <2 x i32> @llvm.ctlz.v2i32(<2 x i32> [[X:%.*]], i1 false) ; CHECK-NEXT: ret <2 x i32> [[CT]] ; %ct = tail call <2 x i32> @llvm.ctlz.v2i32(<2 x i32> %x, i1 true) @@ -501,7 +501,7 @@ define <2 x i32> @test_ctlz_bw_vec(<2 x i32> %x) { define <2 x i32> @test_ctlz_not_bw_vec(<2 x i32> %x) { ; CHECK-LABEL: @test_ctlz_not_bw_vec( -; CHECK-NEXT: [[CT:%.*]] = tail call <2 x i32> @llvm.ctlz.v2i32(<2 x i32> [[X:%.*]], i1 true), !range [[RNG1]] +; CHECK-NEXT: [[CT:%.*]] = tail call range(i32 0, 33) <2 x i32> @llvm.ctlz.v2i32(<2 x i32> [[X:%.*]], i1 true) ; CHECK-NEXT: [[CMP_NOT:%.*]] = icmp eq <2 x i32> [[X]], zeroinitializer ; CHECK-NEXT: [[RES:%.*]] = select <2 x i1> [[CMP_NOT]], <2 x i32> zeroinitializer, <2 x i32> [[CT]] ; CHECK-NEXT: ret <2 x i32> [[RES]] @@ -514,7 +514,7 @@ define <2 x i32> @test_ctlz_not_bw_vec(<2 x i32> %x) { define <2 x i32> @test_cttz_bw_vec(<2 x i32> %x) { ; CHECK-LABEL: @test_cttz_bw_vec( -; CHECK-NEXT: [[CT:%.*]] = tail call <2 x i32> @llvm.cttz.v2i32(<2 x i32> [[X:%.*]], i1 false), !range [[RNG1]] +; CHECK-NEXT: [[CT:%.*]] = tail call range(i32 0, 33) <2 x i32> @llvm.cttz.v2i32(<2 x i32> [[X:%.*]], i1 false) ; CHECK-NEXT: ret <2 x i32> [[CT]] ; %ct = tail call <2 x i32> @llvm.cttz.v2i32(<2 x i32> %x, i1 true) @@ -525,7 +525,7 @@ define <2 x i32> @test_cttz_bw_vec(<2 x i32> %x) { define <2 x i32> @test_cttz_not_bw_vec(<2 x i32> %x) { ; CHECK-LABEL: @test_cttz_not_bw_vec( -; CHECK-NEXT: [[CT:%.*]] = tail call <2 x i32> @llvm.cttz.v2i32(<2 x i32> [[X:%.*]], i1 true), !range [[RNG1]] +; CHECK-NEXT: [[CT:%.*]] = tail call range(i32 0, 33) <2 x i32> @llvm.cttz.v2i32(<2 x i32> [[X:%.*]], i1 true) ; CHECK-NEXT: [[CMP_NOT:%.*]] = icmp eq <2 x i32> [[X]], zeroinitializer ; CHECK-NEXT: [[RES:%.*]] = select <2 x i1> [[CMP_NOT]], <2 x i32> zeroinitializer, <2 x i32> [[CT]] ; CHECK-NEXT: ret <2 x i32> [[RES]] @@ -538,7 +538,7 @@ define <2 x i32> @test_cttz_not_bw_vec(<2 x i32> %x) { define i32 @test_multiuse_def(i32 %x, ptr %p) { ; CHECK-LABEL: @test_multiuse_def( -; CHECK-NEXT: [[CT:%.*]] = tail call i32 @llvm.ctlz.i32(i32 [[X:%.*]], i1 false), !range [[RNG1]] +; CHECK-NEXT: [[CT:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[X:%.*]], i1 false) ; CHECK-NEXT: store i32 [[CT]], ptr [[P:%.*]], align 4 ; CHECK-NEXT: ret i32 [[CT]] ; @@ -551,7 +551,7 @@ define i32 @test_multiuse_def(i32 %x, ptr %p) { define i32 @test_multiuse_undef(i32 %x, ptr %p) { ; CHECK-LABEL: @test_multiuse_undef( -; CHECK-NEXT: [[CT:%.*]] = tail call i32 @llvm.ctlz.i32(i32 [[X:%.*]], i1 false), !range [[RNG1]] +; CHECK-NEXT: [[CT:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[X:%.*]], i1 false) ; CHECK-NEXT: store i32 [[CT]], ptr [[P:%.*]], align 4 ; CHECK-NEXT: ret i32 [[CT]] ; @@ -564,7 +564,7 @@ define i32 @test_multiuse_undef(i32 %x, ptr %p) { define i64 @test_multiuse_zext_def(i32 %x, ptr %p) { ; CHECK-LABEL: @test_multiuse_zext_def( -; CHECK-NEXT: [[CT:%.*]] = tail call i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 false), !range [[RNG1]] +; CHECK-NEXT: [[CT:%.*]] = tail call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 false) ; CHECK-NEXT: [[CONV:%.*]] = zext nneg i32 [[CT]] to i64 ; CHECK-NEXT: store i64 [[CONV]], ptr [[P:%.*]], align 4 ; CHECK-NEXT: ret i64 [[CONV]] @@ -579,7 +579,7 @@ define i64 @test_multiuse_zext_def(i32 %x, ptr %p) { define i64 @test_multiuse_zext_undef(i32 %x, ptr %p) { ; CHECK-LABEL: @test_multiuse_zext_undef( -; CHECK-NEXT: [[CT:%.*]] = tail call i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 false), !range [[RNG1]] +; CHECK-NEXT: [[CT:%.*]] = tail call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 false) ; CHECK-NEXT: [[CONV:%.*]] = zext nneg i32 [[CT]] to i64 ; CHECK-NEXT: store i64 [[CONV]], ptr [[P:%.*]], align 4 ; CHECK-NEXT: ret i64 [[CONV]] @@ -594,7 +594,7 @@ define i64 @test_multiuse_zext_undef(i32 %x, ptr %p) { define i16 @test_multiuse_trunc_def(i64 %x, ptr %p) { ; CHECK-LABEL: @test_multiuse_trunc_def( -; CHECK-NEXT: [[CT:%.*]] = tail call i64 @llvm.cttz.i64(i64 [[X:%.*]], i1 false), !range [[RNG2]] +; CHECK-NEXT: [[CT:%.*]] = tail call range(i64 0, 65) i64 @llvm.cttz.i64(i64 [[X:%.*]], i1 false) ; CHECK-NEXT: [[CONV:%.*]] = trunc nuw nsw i64 [[CT]] to i16 ; CHECK-NEXT: store i16 [[CONV]], ptr [[P:%.*]], align 2 ; CHECK-NEXT: ret i16 [[CONV]] @@ -609,7 +609,7 @@ define i16 @test_multiuse_trunc_def(i64 %x, ptr %p) { define i16 @test_multiuse_trunc_undef(i64 %x, ptr %p) { ; CHECK-LABEL: @test_multiuse_trunc_undef( -; CHECK-NEXT: [[CT:%.*]] = tail call i64 @llvm.cttz.i64(i64 [[X:%.*]], i1 false), !range [[RNG2]] +; CHECK-NEXT: [[CT:%.*]] = tail call range(i64 0, 65) i64 @llvm.cttz.i64(i64 [[X:%.*]], i1 false) ; CHECK-NEXT: [[CONV:%.*]] = trunc nuw nsw i64 [[CT]] to i16 ; CHECK-NEXT: store i16 [[CONV]], ptr [[P:%.*]], align 2 ; CHECK-NEXT: ret i16 [[CONV]] diff --git a/llvm/test/Transforms/InstCombine/select-ctlz-to-cttz.ll b/llvm/test/Transforms/InstCombine/select-ctlz-to-cttz.ll index fa8443d4c9578ecf368c2e6b5764da76a8af52d8..59d33ee3b39df5f584361ad76244ee250b7ccad2 100644 --- a/llvm/test/Transforms/InstCombine/select-ctlz-to-cttz.ll +++ b/llvm/test/Transforms/InstCombine/select-ctlz-to-cttz.ll @@ -16,7 +16,7 @@ declare void @use2(i1) define i32 @select_clz_to_ctz(i32 %a) { ; CHECK-LABEL: @select_clz_to_ctz( -; CHECK-NEXT: [[SUB1:%.*]] = call i32 @llvm.cttz.i32(i32 [[A:%.*]], i1 true), !range [[RNG0:![0-9]+]] +; CHECK-NEXT: [[SUB1:%.*]] = call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[A:%.*]], i1 true) ; CHECK-NEXT: ret i32 [[SUB1]] ; %sub = sub i32 0, %a @@ -30,7 +30,7 @@ define i32 @select_clz_to_ctz(i32 %a) { define i32 @select_clz_to_ctz_preserve_flag(i32 %a) { ; CHECK-LABEL: @select_clz_to_ctz_preserve_flag( -; CHECK-NEXT: [[COND:%.*]] = call i32 @llvm.cttz.i32(i32 [[A:%.*]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[COND:%.*]] = call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[A:%.*]], i1 false) ; CHECK-NEXT: ret i32 [[COND]] ; %sub = sub i32 0, %a @@ -44,7 +44,7 @@ define i32 @select_clz_to_ctz_preserve_flag(i32 %a) { define i32 @select_clz_to_ctz_constant_for_zero(i32 %a) { ; CHECK-LABEL: @select_clz_to_ctz_constant_for_zero( -; CHECK-NEXT: [[COND:%.*]] = call i32 @llvm.cttz.i32(i32 [[A:%.*]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[COND:%.*]] = call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[A:%.*]], i1 false) ; CHECK-NEXT: ret i32 [[COND]] ; %sub = sub i32 0, %a @@ -58,7 +58,7 @@ define i32 @select_clz_to_ctz_constant_for_zero(i32 %a) { define <2 x i32> @select_clz_to_ctz_vec(<2 x i32> %a) { ; CHECK-LABEL: @select_clz_to_ctz_vec( -; CHECK-NEXT: [[COND:%.*]] = call <2 x i32> @llvm.cttz.v2i32(<2 x i32> [[A:%.*]], i1 true), !range [[RNG0]] +; CHECK-NEXT: [[COND:%.*]] = call range(i32 0, 33) <2 x i32> @llvm.cttz.v2i32(<2 x i32> [[A:%.*]], i1 true) ; CHECK-NEXT: ret <2 x i32> [[COND]] ; %sub = sub <2 x i32> zeroinitializer, %a @@ -72,7 +72,7 @@ define <2 x i32> @select_clz_to_ctz_vec(<2 x i32> %a) { define i32 @select_clz_to_ctz_extra_use(i32 %a) { ; CHECK-LABEL: @select_clz_to_ctz_extra_use( -; CHECK-NEXT: [[SUB1:%.*]] = call i32 @llvm.cttz.i32(i32 [[A:%.*]], i1 true), !range [[RNG0]] +; CHECK-NEXT: [[SUB1:%.*]] = call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[A:%.*]], i1 true) ; CHECK-NEXT: call void @use(i32 [[SUB1]]) ; CHECK-NEXT: ret i32 [[SUB1]] ; @@ -88,7 +88,7 @@ define i32 @select_clz_to_ctz_extra_use(i32 %a) { define i32 @select_clz_to_ctz_and_commuted(i32 %a) { ; CHECK-LABEL: @select_clz_to_ctz_and_commuted( -; CHECK-NEXT: [[SUB1:%.*]] = call i32 @llvm.cttz.i32(i32 [[A:%.*]], i1 true), !range [[RNG0]] +; CHECK-NEXT: [[SUB1:%.*]] = call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[A:%.*]], i1 true) ; CHECK-NEXT: ret i32 [[SUB1]] ; %sub = sub i32 0, %a @@ -104,7 +104,7 @@ define i32 @select_clz_to_ctz_icmp_ne(i32 %a) { ; CHECK-LABEL: @select_clz_to_ctz_icmp_ne( ; CHECK-NEXT: [[TOBOOL:%.*]] = icmp ne i32 [[A:%.*]], 0 ; CHECK-NEXT: call void @use2(i1 [[TOBOOL]]) -; CHECK-NEXT: [[SUB1:%.*]] = call i32 @llvm.cttz.i32(i32 [[A]], i1 true), !range [[RNG0]] +; CHECK-NEXT: [[SUB1:%.*]] = call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[A]], i1 true) ; CHECK-NEXT: ret i32 [[SUB1]] ; %sub = sub i32 0, %a @@ -119,7 +119,7 @@ define i32 @select_clz_to_ctz_icmp_ne(i32 %a) { define i64 @select_clz_to_ctz_i64(i64 %a) { ; CHECK-LABEL: @select_clz_to_ctz_i64( -; CHECK-NEXT: [[SUB1:%.*]] = call i64 @llvm.cttz.i64(i64 [[A:%.*]], i1 true), !range [[RNG1:![0-9]+]] +; CHECK-NEXT: [[SUB1:%.*]] = call range(i64 0, 65) i64 @llvm.cttz.i64(i64 [[A:%.*]], i1 true) ; CHECK-NEXT: ret i64 [[SUB1]] ; %sub = sub i64 0, %a @@ -137,7 +137,7 @@ define i32 @select_clz_to_ctz_wrong_sub(i32 %a) { ; CHECK-LABEL: @select_clz_to_ctz_wrong_sub( ; CHECK-NEXT: [[SUB:%.*]] = sub i32 1, [[A:%.*]] ; CHECK-NEXT: [[AND:%.*]] = and i32 [[SUB]], [[A]] -; CHECK-NEXT: [[LZ:%.*]] = tail call i32 @llvm.ctlz.i32(i32 [[AND]], i1 true), !range [[RNG0]] +; CHECK-NEXT: [[LZ:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[AND]], i1 true) ; CHECK-NEXT: [[SUB1:%.*]] = xor i32 [[LZ]], 31 ; CHECK-NEXT: ret i32 [[SUB1]] ; @@ -155,7 +155,7 @@ define i64 @select_clz_to_ctz_i64_wrong_xor(i64 %a) { ; CHECK-LABEL: @select_clz_to_ctz_i64_wrong_xor( ; CHECK-NEXT: [[SUB:%.*]] = sub i64 0, [[A:%.*]] ; CHECK-NEXT: [[AND:%.*]] = and i64 [[SUB]], [[A]] -; CHECK-NEXT: [[LZ:%.*]] = tail call i64 @llvm.ctlz.i64(i64 [[AND]], i1 true), !range [[RNG1]] +; CHECK-NEXT: [[LZ:%.*]] = tail call range(i64 0, 65) i64 @llvm.ctlz.i64(i64 [[AND]], i1 true) ; CHECK-NEXT: [[SUB11:%.*]] = or disjoint i64 [[LZ]], 64 ; CHECK-NEXT: ret i64 [[SUB11]] ; @@ -171,7 +171,7 @@ define i64 @select_clz_to_ctz_i64_wrong_xor(i64 %a) { define i64 @select_clz_to_ctz_i64_wrong_icmp_cst(i64 %a) { ; CHECK-LABEL: @select_clz_to_ctz_i64_wrong_icmp_cst( ; CHECK-NEXT: [[TOBOOL:%.*]] = icmp eq i64 [[A:%.*]], 1 -; CHECK-NEXT: [[SUB1:%.*]] = call i64 @llvm.cttz.i64(i64 [[A]], i1 true), !range [[RNG1]] +; CHECK-NEXT: [[SUB1:%.*]] = call range(i64 0, 65) i64 @llvm.cttz.i64(i64 [[A]], i1 true) ; CHECK-NEXT: [[COND:%.*]] = select i1 [[TOBOOL]], i64 63, i64 [[SUB1]] ; CHECK-NEXT: ret i64 [[COND]] ; @@ -188,7 +188,7 @@ define i64 @select_clz_to_ctz_i64_wrong_icmp_pred(i64 %a) { ; CHECK-LABEL: @select_clz_to_ctz_i64_wrong_icmp_pred( ; CHECK-NEXT: [[SUB:%.*]] = sub i64 0, [[A:%.*]] ; CHECK-NEXT: [[AND:%.*]] = and i64 [[SUB]], [[A]] -; CHECK-NEXT: [[LZ:%.*]] = tail call i64 @llvm.ctlz.i64(i64 [[AND]], i1 true), !range [[RNG1]] +; CHECK-NEXT: [[LZ:%.*]] = tail call range(i64 0, 65) i64 @llvm.ctlz.i64(i64 [[AND]], i1 true) ; CHECK-NEXT: [[TOBOOL:%.*]] = icmp slt i64 [[A]], 0 ; CHECK-NEXT: [[SUB1:%.*]] = xor i64 [[LZ]], 63 ; CHECK-NEXT: [[COND:%.*]] = select i1 [[TOBOOL]], i64 [[LZ]], i64 [[SUB1]] @@ -207,7 +207,7 @@ define <2 x i32> @select_clz_to_ctz_vec_with_undef(<2 x i32> %a) { ; CHECK-LABEL: @select_clz_to_ctz_vec_with_undef( ; CHECK-NEXT: [[SUB:%.*]] = sub <2 x i32> zeroinitializer, [[A:%.*]] ; CHECK-NEXT: [[AND:%.*]] = and <2 x i32> [[SUB]], [[A]] -; CHECK-NEXT: [[LZ:%.*]] = tail call <2 x i32> @llvm.ctlz.v2i32(<2 x i32> [[AND]], i1 true), !range [[RNG0]] +; CHECK-NEXT: [[LZ:%.*]] = tail call range(i32 0, 33) <2 x i32> @llvm.ctlz.v2i32(<2 x i32> [[AND]], i1 true) ; CHECK-NEXT: [[TOBOOL:%.*]] = icmp eq <2 x i32> [[A]], zeroinitializer ; CHECK-NEXT: [[SUB1:%.*]] = xor <2 x i32> [[LZ]], ; CHECK-NEXT: [[COND:%.*]] = select <2 x i1> [[TOBOOL]], <2 x i32> [[LZ]], <2 x i32> [[SUB1]] @@ -226,7 +226,7 @@ define i32 @select_clz_to_ctz_wrong_constant_for_zero(i32 %a) { ; CHECK-LABEL: @select_clz_to_ctz_wrong_constant_for_zero( ; CHECK-NEXT: [[SUB:%.*]] = sub i32 0, [[A:%.*]] ; CHECK-NEXT: [[AND:%.*]] = and i32 [[SUB]], [[A]] -; CHECK-NEXT: [[LZ:%.*]] = tail call i32 @llvm.ctlz.i32(i32 [[AND]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[LZ:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[AND]], i1 false) ; CHECK-NEXT: [[TOBOOL:%.*]] = icmp eq i32 [[A]], 0 ; CHECK-NEXT: [[SUB1:%.*]] = xor i32 [[LZ]], 31 ; CHECK-NEXT: [[COND:%.*]] = select i1 [[TOBOOL]], i32 31, i32 [[SUB1]] @@ -243,7 +243,7 @@ define i32 @select_clz_to_ctz_wrong_constant_for_zero(i32 %a) { define i4 @PR45762(i3 %x4) { ; CHECK-LABEL: @PR45762( -; CHECK-NEXT: [[T4:%.*]] = call i3 @llvm.cttz.i3(i3 [[X4:%.*]], i1 false), !range [[RNG2:![0-9]+]] +; CHECK-NEXT: [[T4:%.*]] = call range(i3 0, -4) i3 @llvm.cttz.i3(i3 [[X4:%.*]], i1 false) ; CHECK-NEXT: [[T7:%.*]] = zext nneg i3 [[T4]] to i4 ; CHECK-NEXT: [[ONE_HOT_16:%.*]] = shl nuw i4 1, [[T7]] ; CHECK-NEXT: [[OR_69_NOT:%.*]] = icmp eq i3 [[X4]], 0 @@ -272,7 +272,7 @@ define i4 @PR45762(i3 %x4) { define i4 @PR45762_logical(i3 %x4) { ; CHECK-LABEL: @PR45762_logical( -; CHECK-NEXT: [[T4:%.*]] = call i3 @llvm.cttz.i3(i3 [[X4:%.*]], i1 false), !range [[RNG2]] +; CHECK-NEXT: [[T4:%.*]] = call range(i3 0, -4) i3 @llvm.cttz.i3(i3 [[X4:%.*]], i1 false) ; CHECK-NEXT: [[T7:%.*]] = zext nneg i3 [[T4]] to i4 ; CHECK-NEXT: [[ONE_HOT_16:%.*]] = shl nuw i4 1, [[T7]] ; CHECK-NEXT: [[OR_69_NOT:%.*]] = icmp eq i3 [[X4]], 0 diff --git a/llvm/test/Transforms/InstCombine/select.ll b/llvm/test/Transforms/InstCombine/select.ll index 2ec092a745c52c7a043ff7ea66c26c2a26d8b7b9..2efe2742ca4916427b3873247622cb75b84d5d62 100644 --- a/llvm/test/Transforms/InstCombine/select.ll +++ b/llvm/test/Transforms/InstCombine/select.ll @@ -2736,7 +2736,7 @@ define void @select_freeze_icmp_multuses(i32 %x, i32 %y) { define i32 @pr47322_more_poisonous_replacement(i32 %arg) { ; CHECK-LABEL: @pr47322_more_poisonous_replacement( ; CHECK-NEXT: [[CMP:%.*]] = icmp eq i32 [[ARG:%.*]], 0 -; CHECK-NEXT: [[TRAILING:%.*]] = call i32 @llvm.cttz.i32(i32 [[ARG]], i1 immarg true), !range [[RNG0:![0-9]+]] +; CHECK-NEXT: [[TRAILING:%.*]] = call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[ARG]], i1 immarg true) ; CHECK-NEXT: [[SHIFTED:%.*]] = lshr i32 [[ARG]], [[TRAILING]] ; CHECK-NEXT: [[R1_SROA_0_1:%.*]] = select i1 [[CMP]], i32 0, i32 [[SHIFTED]] ; CHECK-NEXT: ret i32 [[R1_SROA_0_1]] @@ -3830,14 +3830,17 @@ entry: ret i32 %cond } -; FIXME: This is a miscompile. define <2 x i32> @src_and_eq_C_xor_OrAndNotC_vec_poison(<2 x i32> %0, <2 x i32> %1, <2 x i32> %2) { ; CHECK-LABEL: @src_and_eq_C_xor_OrAndNotC_vec_poison( ; CHECK-NEXT: entry: -; CHECK-NEXT: [[OR:%.*]] = or <2 x i32> [[TMP1:%.*]], [[TMP0:%.*]] -; CHECK-NEXT: [[NOT:%.*]] = xor <2 x i32> [[TMP2:%.*]], +; CHECK-NEXT: [[AND:%.*]] = and <2 x i32> [[TMP1:%.*]], [[TMP0:%.*]] +; CHECK-NEXT: [[CMP:%.*]] = icmp eq <2 x i32> [[AND]], [[TMP2:%.*]] +; CHECK-NEXT: [[XOR:%.*]] = xor <2 x i32> [[TMP1]], [[TMP0]] +; CHECK-NEXT: [[OR:%.*]] = or <2 x i32> [[TMP1]], [[TMP0]] +; CHECK-NEXT: [[NOT:%.*]] = xor <2 x i32> [[TMP2]], ; CHECK-NEXT: [[AND1:%.*]] = and <2 x i32> [[OR]], [[NOT]] -; CHECK-NEXT: ret <2 x i32> [[AND1]] +; CHECK-NEXT: [[COND:%.*]] = select <2 x i1> [[CMP]], <2 x i32> [[XOR]], <2 x i32> [[AND1]] +; CHECK-NEXT: ret <2 x i32> [[COND]] ; entry: %and = and <2 x i32> %1, %0 diff --git a/llvm/test/Transforms/InstCombine/sext.ll b/llvm/test/Transforms/InstCombine/sext.ll index 6d263cfcda057797347f1086eb48c58973c98fa3..a554f2b28d6f29905cf5bf1170754abf40c626fe 100644 --- a/llvm/test/Transforms/InstCombine/sext.ll +++ b/llvm/test/Transforms/InstCombine/sext.ll @@ -11,7 +11,7 @@ declare void @use_vec(<2 x i5>) define i64 @test1(i32 %x) { ; CHECK-LABEL: @test1( -; CHECK-NEXT: [[T:%.*]] = call i32 @llvm.ctpop.i32(i32 [[X:%.*]]), !range [[RNG0:![0-9]+]] +; CHECK-NEXT: [[T:%.*]] = call range(i32 0, 33) i32 @llvm.ctpop.i32(i32 [[X:%.*]]) ; CHECK-NEXT: [[S:%.*]] = zext nneg i32 [[T]] to i64 ; CHECK-NEXT: ret i64 [[S]] ; @@ -22,7 +22,7 @@ define i64 @test1(i32 %x) { define i64 @test2(i32 %x) { ; CHECK-LABEL: @test2( -; CHECK-NEXT: [[T:%.*]] = call i32 @llvm.ctlz.i32(i32 [[X:%.*]], i1 true), !range [[RNG0]] +; CHECK-NEXT: [[T:%.*]] = call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[X:%.*]], i1 true) ; CHECK-NEXT: [[S:%.*]] = zext nneg i32 [[T]] to i64 ; CHECK-NEXT: ret i64 [[S]] ; @@ -33,7 +33,7 @@ define i64 @test2(i32 %x) { define i64 @test3(i32 %x) { ; CHECK-LABEL: @test3( -; CHECK-NEXT: [[T:%.*]] = call i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 true), !range [[RNG0]] +; CHECK-NEXT: [[T:%.*]] = call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 true) ; CHECK-NEXT: [[S:%.*]] = zext nneg i32 [[T]] to i64 ; CHECK-NEXT: ret i64 [[S]] ; diff --git a/llvm/test/Transforms/InstCombine/shift-cttz-ctlz.ll b/llvm/test/Transforms/InstCombine/shift-cttz-ctlz.ll index 2b2f820c9a095608edb1addadd9481857fba0fb2..1c381d0839071598a1fd1a018835a511e70fb2e0 100644 --- a/llvm/test/Transforms/InstCombine/shift-cttz-ctlz.ll +++ b/llvm/test/Transforms/InstCombine/shift-cttz-ctlz.ll @@ -5,7 +5,7 @@ define i32 @shl_cttz_false(i32 %x, i32 %y) { ; CHECK-LABEL: define i32 @shl_cttz_false( ; CHECK-SAME: i32 [[X:%.*]], i32 [[Y:%.*]]) { ; CHECK-NEXT: entry: -; CHECK-NEXT: [[CTTZ:%.*]] = call i32 @llvm.cttz.i32(i32 [[Y]], i1 true), !range [[RNG0:![0-9]+]] +; CHECK-NEXT: [[CTTZ:%.*]] = call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[Y]], i1 true) ; CHECK-NEXT: [[RES:%.*]] = shl i32 [[X]], [[CTTZ]] ; CHECK-NEXT: ret i32 [[RES]] ; @@ -19,7 +19,7 @@ define i32 @shl_ctlz_false(i32 %x, i32 %y) { ; CHECK-LABEL: define i32 @shl_ctlz_false( ; CHECK-SAME: i32 [[X:%.*]], i32 [[Y:%.*]]) { ; CHECK-NEXT: entry: -; CHECK-NEXT: [[CTTZ:%.*]] = call i32 @llvm.ctlz.i32(i32 [[Y]], i1 true), !range [[RNG0]] +; CHECK-NEXT: [[CTTZ:%.*]] = call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[Y]], i1 true) ; CHECK-NEXT: [[RES:%.*]] = shl i32 [[X]], [[CTTZ]] ; CHECK-NEXT: ret i32 [[RES]] ; @@ -33,7 +33,7 @@ define i32 @lshr_cttz_false(i32 %x, i32 %y) { ; CHECK-LABEL: define i32 @lshr_cttz_false( ; CHECK-SAME: i32 [[X:%.*]], i32 [[Y:%.*]]) { ; CHECK-NEXT: entry: -; CHECK-NEXT: [[CTTZ:%.*]] = call i32 @llvm.cttz.i32(i32 [[Y]], i1 true), !range [[RNG0]] +; CHECK-NEXT: [[CTTZ:%.*]] = call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[Y]], i1 true) ; CHECK-NEXT: [[RES:%.*]] = lshr i32 [[X]], [[CTTZ]] ; CHECK-NEXT: ret i32 [[RES]] ; @@ -47,7 +47,7 @@ define i32 @ashr_cttz_false(i32 %x, i32 %y) { ; CHECK-LABEL: define i32 @ashr_cttz_false( ; CHECK-SAME: i32 [[X:%.*]], i32 [[Y:%.*]]) { ; CHECK-NEXT: entry: -; CHECK-NEXT: [[CTTZ:%.*]] = call i32 @llvm.cttz.i32(i32 [[Y]], i1 true), !range [[RNG0]] +; CHECK-NEXT: [[CTTZ:%.*]] = call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[Y]], i1 true) ; CHECK-NEXT: [[RES:%.*]] = ashr i32 [[X]], [[CTTZ]] ; CHECK-NEXT: ret i32 [[RES]] ; @@ -61,7 +61,7 @@ define i32 @shl_cttz_false_multiuse(i32 %x, i32 %y) { ; CHECK-LABEL: define i32 @shl_cttz_false_multiuse( ; CHECK-SAME: i32 [[X:%.*]], i32 [[Y:%.*]]) { ; CHECK-NEXT: entry: -; CHECK-NEXT: [[CTTZ:%.*]] = call i32 @llvm.cttz.i32(i32 [[Y]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[CTTZ:%.*]] = call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[Y]], i1 false) ; CHECK-NEXT: call void @use(i32 [[CTTZ]]) ; CHECK-NEXT: [[RES:%.*]] = shl i32 [[X]], [[CTTZ]] ; CHECK-NEXT: ret i32 [[RES]] @@ -77,7 +77,7 @@ define i32 @shl_cttz_as_lhs(i32 %x, i32 %y) { ; CHECK-LABEL: define i32 @shl_cttz_as_lhs( ; CHECK-SAME: i32 [[X:%.*]], i32 [[Y:%.*]]) { ; CHECK-NEXT: entry: -; CHECK-NEXT: [[CTTZ:%.*]] = call i32 @llvm.cttz.i32(i32 [[Y]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[CTTZ:%.*]] = call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[Y]], i1 false) ; CHECK-NEXT: [[RES:%.*]] = shl i32 [[CTTZ]], [[X]] ; CHECK-NEXT: ret i32 [[RES]] ; @@ -88,6 +88,3 @@ entry: } declare void @use(i32) -;. -; CHECK: [[RNG0]] = !{i32 0, i32 33} -;. diff --git a/llvm/test/Transforms/InstCombine/shift.ll b/llvm/test/Transforms/InstCombine/shift.ll index bb8661919c89f5e4d33997062816d33dba791f3b..8da52e074637363f6047e129877257e82c831b16 100644 --- a/llvm/test/Transforms/InstCombine/shift.ll +++ b/llvm/test/Transforms/InstCombine/shift.ll @@ -366,7 +366,7 @@ define i32 @test26(i32 %A) { ret i32 %D } -define i1 @test27(i32 %x) nounwind { +define i1 @test27(i32 %x) { ; CHECK-LABEL: @test27( ; CHECK-NEXT: [[TMP1:%.*]] = and i32 [[X:%.*]], 8 ; CHECK-NEXT: [[Z:%.*]] = icmp ne i32 [[TMP1]], 0 @@ -605,7 +605,7 @@ define <2 x i32> @shl_nuw_nsw_splat_vec(<2 x i8> %x) { ret <2 x i32> %t3 } -define i32 @test38(i32 %x) nounwind readnone { +define i32 @test38(i32 %x) { ; CHECK-LABEL: @test38( ; CHECK-NEXT: [[REM1:%.*]] = and i32 [[X:%.*]], 31 ; CHECK-NEXT: [[SHL:%.*]] = shl nuw i32 1, [[REM1]] @@ -616,7 +616,7 @@ define i32 @test38(i32 %x) nounwind readnone { ret i32 %shl } -define <2 x i32> @test38_uniform(<2 x i32> %x) nounwind readnone { +define <2 x i32> @test38_uniform(<2 x i32> %x) { ; CHECK-LABEL: @test38_uniform( ; CHECK-NEXT: [[REM1:%.*]] = and <2 x i32> [[X:%.*]], ; CHECK-NEXT: [[SHL:%.*]] = shl nuw <2 x i32> , [[REM1]] @@ -627,7 +627,7 @@ define <2 x i32> @test38_uniform(<2 x i32> %x) nounwind readnone { ret <2 x i32> %shl } -define <3 x i32> @test38_nonuniform(<3 x i32> %x) nounwind readnone { +define <3 x i32> @test38_nonuniform(<3 x i32> %x) { ; CHECK-LABEL: @test38_nonuniform( ; CHECK-NEXT: [[REM1:%.*]] = and <3 x i32> [[X:%.*]], ; CHECK-NEXT: [[SHL:%.*]] = shl nuw <3 x i32> , [[REM1]] @@ -638,7 +638,7 @@ define <3 x i32> @test38_nonuniform(<3 x i32> %x) nounwind readnone { ret <3 x i32> %shl } -define <2 x i32> @test38_poison(<2 x i32> %x) nounwind readnone { +define <2 x i32> @test38_poison(<2 x i32> %x) { ; CHECK-LABEL: @test38_poison( ; CHECK-NEXT: ret <2 x i32> poison ; @@ -658,8 +658,8 @@ define i8 @test39(i32 %a0) { ; CHECK-NEXT: [[I51:%.*]] = xor i8 [[I50]], [[I5]] ; CHECK-NEXT: [[TMP0:%.*]] = lshr exact i8 [[I5]], 3 ; CHECK-NEXT: [[I54:%.*]] = and i8 [[TMP0]], 16 -; CHECK-NEXT: [[I551:%.*]] = or disjoint i8 [[I54]], [[I51]] -; CHECK-NEXT: ret i8 [[I551]] +; CHECK-NEXT: [[I55:%.*]] = or disjoint i8 [[I54]], [[I51]] +; CHECK-NEXT: ret i8 [[I55]] ; entry: %i4 = trunc i32 %a0 to i8 @@ -675,7 +675,7 @@ entry: ret i8 %i55 } -define i32 @test42(i32 %a, i32 %b) nounwind { +define i32 @test42(i32 %a, i32 %b) { ; CHECK-LABEL: @test42( ; CHECK-NEXT: [[DIV:%.*]] = lshr exact i32 4096, [[B:%.*]] ; CHECK-NEXT: [[DIV2:%.*]] = udiv i32 [[A:%.*]], [[DIV]] @@ -697,7 +697,7 @@ define <2 x i32> @test42vec(<2 x i32> %a, <2 x i32> %b) { ret <2 x i32> %div2 } -define i32 @test43(i32 %a, i32 %b) nounwind { +define i32 @test43(i32 %a, i32 %b) { ; CHECK-LABEL: @test43( ; CHECK-NEXT: [[TMP1:%.*]] = add i32 [[B:%.*]], 12 ; CHECK-NEXT: [[DIV21:%.*]] = lshr i32 [[A:%.*]], [[TMP1]] @@ -708,7 +708,7 @@ define i32 @test43(i32 %a, i32 %b) nounwind { ret i32 %div2 } -define i32 @test44(i32 %a) nounwind { +define i32 @test44(i32 %a) { ; CHECK-LABEL: @test44( ; CHECK-NEXT: [[Y:%.*]] = shl i32 [[A:%.*]], 5 ; CHECK-NEXT: ret i32 [[Y]] @@ -718,7 +718,20 @@ define i32 @test44(i32 %a) nounwind { ret i32 %z } -define i32 @test45(i32 %a) nounwind { +define i32 @test44_multiuse(i32 %a) { +; CHECK-LABEL: @test44_multiuse( +; CHECK-NEXT: [[Y:%.*]] = shl nuw i32 [[A:%.*]], 1 +; CHECK-NEXT: call void @use_i32(i32 [[Y]]) +; CHECK-NEXT: [[Z:%.*]] = shl i32 [[A]], 5 +; CHECK-NEXT: ret i32 [[Z]] +; + %y = shl nuw i32 %a, 1 + call void @use_i32(i32 %y) + %z = shl i32 %y, 4 + ret i32 %z +} + +define i32 @test45(i32 %a) { ; CHECK-LABEL: @test45( ; CHECK-NEXT: [[Y:%.*]] = lshr i32 [[A:%.*]], 5 ; CHECK-NEXT: ret i32 [[Y]] @@ -728,6 +741,19 @@ define i32 @test45(i32 %a) nounwind { ret i32 %z } +define i32 @test45_multiuse(i32 %a) { +; CHECK-LABEL: @test45_multiuse( +; CHECK-NEXT: [[Y:%.*]] = lshr exact i32 [[A:%.*]], 1 +; CHECK-NEXT: call void @use_i32(i32 [[Y]]) +; CHECK-NEXT: [[Z:%.*]] = lshr i32 [[A]], 5 +; CHECK-NEXT: ret i32 [[Z]] +; + %y = lshr exact i32 %a, 1 + call void @use_i32(i32 %y) + %z = lshr i32 %y, 4 + ret i32 %z +} + ; (X >>?exact C1) << C2 --> X >>?exact (C1-C2) define i32 @test46(i32 %a) { @@ -1751,14 +1777,14 @@ define void @ashr_out_of_range_1(ptr %A) { ; CHECK-NEXT: [[L:%.*]] = load i177, ptr [[A:%.*]], align 4 ; CHECK-NEXT: [[L_FROZEN:%.*]] = freeze i177 [[L]] ; CHECK-NEXT: [[TMP1:%.*]] = icmp eq i177 [[L_FROZEN]], -1 -; CHECK-NEXT: [[TMP6:%.*]] = trunc i177 [[L_FROZEN]] to i64 -; CHECK-NEXT: [[TMP2:%.*]] = select i1 [[TMP1]], i64 0, i64 [[TMP6]] -; CHECK-NEXT: [[TMP3:%.*]] = getelementptr i177, ptr [[A]], i64 [[TMP2]] -; CHECK-NEXT: [[G11:%.*]] = getelementptr i8, ptr [[TMP3]], i64 -24 -; CHECK-NEXT: [[TMP4:%.*]] = sext i1 [[TMP1]] to i64 -; CHECK-NEXT: [[G62:%.*]] = getelementptr i177, ptr [[G11]], i64 [[TMP4]] -; CHECK-NEXT: [[TMP5:%.*]] = icmp eq i177 [[L_FROZEN]], -1 -; CHECK-NEXT: [[B28:%.*]] = select i1 [[TMP5]], i177 0, i177 [[L_FROZEN]] +; CHECK-NEXT: [[TMP2:%.*]] = trunc i177 [[L_FROZEN]] to i64 +; CHECK-NEXT: [[TMP3:%.*]] = select i1 [[TMP1]], i64 0, i64 [[TMP2]] +; CHECK-NEXT: [[TMP4:%.*]] = getelementptr i177, ptr [[A]], i64 [[TMP3]] +; CHECK-NEXT: [[G11:%.*]] = getelementptr i8, ptr [[TMP4]], i64 -24 +; CHECK-NEXT: [[TMP5:%.*]] = sext i1 [[TMP1]] to i64 +; CHECK-NEXT: [[G62:%.*]] = getelementptr i177, ptr [[G11]], i64 [[TMP5]] +; CHECK-NEXT: [[TMP6:%.*]] = icmp eq i177 [[L_FROZEN]], -1 +; CHECK-NEXT: [[B28:%.*]] = select i1 [[TMP6]], i177 0, i177 [[L_FROZEN]] ; CHECK-NEXT: store i177 [[B28]], ptr [[G62]], align 4 ; CHECK-NEXT: ret void ; @@ -2055,7 +2081,7 @@ define <2 x i8> @shl1_cttz_vec_poison(<2 x i8> %x) { define i32 @shl1_cttz_extra_use(i32 %x) { ; CHECK-LABEL: @shl1_cttz_extra_use( -; CHECK-NEXT: [[TZ:%.*]] = call i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 false), !range [[RNG0:![0-9]+]] +; CHECK-NEXT: [[TZ:%.*]] = call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 false) ; CHECK-NEXT: call void @use_i32(i32 [[TZ]]) ; CHECK-NEXT: [[SHL:%.*]] = shl nuw i32 1, [[TZ]] ; CHECK-NEXT: ret i32 [[SHL]] @@ -2070,7 +2096,7 @@ define i32 @shl1_cttz_extra_use(i32 %x) { define i32 @shl2_cttz(i32 %x) { ; CHECK-LABEL: @shl2_cttz( -; CHECK-NEXT: [[TZ:%.*]] = call i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 true), !range [[RNG0]] +; CHECK-NEXT: [[TZ:%.*]] = call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 true) ; CHECK-NEXT: [[SHL:%.*]] = shl i32 2, [[TZ]] ; CHECK-NEXT: ret i32 [[SHL]] ; diff --git a/llvm/test/Transforms/InstCombine/simplify-demanded-fpclass.ll b/llvm/test/Transforms/InstCombine/simplify-demanded-fpclass.ll index a7d01b4f824db06fc5d36a5d77f7f412d1323997..e4fb7764ba9e539211474b3bfe635c61ece0dc88 100644 --- a/llvm/test/Transforms/InstCombine/simplify-demanded-fpclass.ll +++ b/llvm/test/Transforms/InstCombine/simplify-demanded-fpclass.ll @@ -364,8 +364,8 @@ define nofpclass(inf) float @ret_nofpclass_inf__select_chain_inf_nan_1(i1 %cond, define nofpclass(inf) float @ret_nofpclass_inf__fabs_select_ninf_rhs(i1 %cond, float %x) { ; CHECK-LABEL: define nofpclass(inf) float @ret_nofpclass_inf__fabs_select_ninf_rhs ; CHECK-SAME: (i1 [[COND:%.*]], float [[X:%.*]]) { -; CHECK-NEXT: [[FABS:%.*]] = call float @llvm.fabs.f32(float [[X]]) -; CHECK-NEXT: ret float [[FABS]] +; CHECK-NEXT: [[TMP1:%.*]] = call float @llvm.fabs.f32(float [[X]]) +; CHECK-NEXT: ret float [[TMP1]] ; %select = select i1 %cond, float %x, float 0xFFF0000000000000 %fabs = call float @llvm.fabs.f32(float %select) @@ -376,8 +376,8 @@ define nofpclass(inf) float @ret_nofpclass_inf__fabs_select_ninf_rhs(i1 %cond, f define nofpclass(inf) float @ret_nofpclass_inf__fabs_select_pinf_rhs(i1 %cond, float %x) { ; CHECK-LABEL: define nofpclass(inf) float @ret_nofpclass_inf__fabs_select_pinf_rhs ; CHECK-SAME: (i1 [[COND:%.*]], float [[X:%.*]]) { -; CHECK-NEXT: [[FABS:%.*]] = call float @llvm.fabs.f32(float [[X]]) -; CHECK-NEXT: ret float [[FABS]] +; CHECK-NEXT: [[TMP1:%.*]] = call float @llvm.fabs.f32(float [[X]]) +; CHECK-NEXT: ret float [[TMP1]] ; %select = select i1 %cond, float %x, float 0x7FF0000000000000 %fabs = call float @llvm.fabs.f32(float %select) @@ -400,8 +400,8 @@ define nofpclass(ninf nnorm nsub nzero) float @ret_nofpclass_no_negatives__fabs_ define nofpclass(pinf pnorm psub pzero) float @ret_nofpclass_no_positives__fabs_select_pinf_rhs(i1 %cond, float %x) { ; CHECK-LABEL: define nofpclass(pinf pzero psub pnorm) float @ret_nofpclass_no_positives__fabs_select_pinf_rhs ; CHECK-SAME: (i1 [[COND:%.*]], float [[X:%.*]]) { -; CHECK-NEXT: [[FABS:%.*]] = call float @llvm.fabs.f32(float [[X]]) -; CHECK-NEXT: ret float [[FABS]] +; CHECK-NEXT: [[TMP1:%.*]] = call float @llvm.fabs.f32(float [[X]]) +; CHECK-NEXT: ret float [[TMP1]] ; %select = select i1 %cond, float %x, float 0x7FF0000000000000 %fabs = call float @llvm.fabs.f32(float %select) @@ -435,8 +435,8 @@ define nofpclass(nan pinf pnorm psub pzero) float @ret_nofpclass_no_positives_na define nofpclass(inf) float @ret_nofpclass_inf__fneg_select_ninf_rhs(i1 %cond, float %x) { ; CHECK-LABEL: define nofpclass(inf) float @ret_nofpclass_inf__fneg_select_ninf_rhs ; CHECK-SAME: (i1 [[COND:%.*]], float [[X:%.*]]) { -; CHECK-NEXT: [[FNEG:%.*]] = fneg float [[X]] -; CHECK-NEXT: ret float [[FNEG]] +; CHECK-NEXT: [[X_NEG:%.*]] = fneg float [[X]] +; CHECK-NEXT: ret float [[X_NEG]] ; %select = select i1 %cond, float %x, float 0xFFF0000000000000 %fneg = fneg float %select @@ -447,8 +447,8 @@ define nofpclass(inf) float @ret_nofpclass_inf__fneg_select_ninf_rhs(i1 %cond, f define nofpclass(inf nnorm nsub nzero) float @ret_nofpclass_nonegatives_noinf___fneg_select_pinf_rhs(i1 %cond, float %x) { ; CHECK-LABEL: define nofpclass(inf nzero nsub nnorm) float @ret_nofpclass_nonegatives_noinf___fneg_select_pinf_rhs ; CHECK-SAME: (i1 [[COND:%.*]], float [[X:%.*]]) { -; CHECK-NEXT: [[FNEG:%.*]] = fneg float [[X]] -; CHECK-NEXT: ret float [[FNEG]] +; CHECK-NEXT: [[X_NEG:%.*]] = fneg float [[X]] +; CHECK-NEXT: ret float [[X_NEG]] ; %select = select i1 %cond, float %x, float 0x7FF0000000000000 %fneg = fneg float %select @@ -459,8 +459,8 @@ define nofpclass(inf nnorm nsub nzero) float @ret_nofpclass_nonegatives_noinf___ define nofpclass(inf nnorm nsub nzero) float @ret_nofpclass_nonegatives_noinf___fneg_select_ninf_lhs(i1 %cond, float %x) { ; CHECK-LABEL: define nofpclass(inf nzero nsub nnorm) float @ret_nofpclass_nonegatives_noinf___fneg_select_ninf_lhs ; CHECK-SAME: (i1 [[COND:%.*]], float [[X:%.*]]) { -; CHECK-NEXT: [[FNEG:%.*]] = fneg float [[X]] -; CHECK-NEXT: ret float [[FNEG]] +; CHECK-NEXT: [[X_NEG:%.*]] = fneg float [[X]] +; CHECK-NEXT: ret float [[X_NEG]] ; %select = select i1 %cond, float 0xFFF0000000000000, float %x %fneg = fneg float %select @@ -470,8 +470,8 @@ define nofpclass(inf nnorm nsub nzero) float @ret_nofpclass_nonegatives_noinf___ define nofpclass(pzero psub pnorm pinf) float @ret_nofpclass_nopositives___fneg_select_pinf_rhs(i1 %cond, float %x) { ; CHECK-LABEL: define nofpclass(pinf pzero psub pnorm) float @ret_nofpclass_nopositives___fneg_select_pinf_rhs ; CHECK-SAME: (i1 [[COND:%.*]], float [[X:%.*]]) { -; CHECK-NEXT: [[SELECT:%.*]] = select i1 [[COND]], float [[X]], float 0x7FF0000000000000 -; CHECK-NEXT: [[FNEG:%.*]] = fneg float [[SELECT]] +; CHECK-NEXT: [[X_NEG:%.*]] = fneg float [[X]] +; CHECK-NEXT: [[FNEG:%.*]] = select i1 [[COND]], float [[X_NEG]], float 0xFFF0000000000000 ; CHECK-NEXT: ret float [[FNEG]] ; %select = select i1 %cond, float %x, float 0x7FF0000000000000 @@ -483,9 +483,9 @@ define nofpclass(pzero psub pnorm pinf) float @ret_nofpclass_nopositives___fneg_ define nofpclass(inf) float @ret_nofpclass_inf__fneg_fabs_select_pinf_rhs(i1 %cond, float %x) { ; CHECK-LABEL: define nofpclass(inf) float @ret_nofpclass_inf__fneg_fabs_select_pinf_rhs ; CHECK-SAME: (i1 [[COND:%.*]], float [[X:%.*]]) { -; CHECK-NEXT: [[FABS:%.*]] = call float @llvm.fabs.f32(float [[X]]) -; CHECK-NEXT: [[FNEG:%.*]] = fneg float [[FABS]] -; CHECK-NEXT: ret float [[FNEG]] +; CHECK-NEXT: [[TMP1:%.*]] = call float @llvm.fabs.f32(float [[X]]) +; CHECK-NEXT: [[DOTNEG:%.*]] = fneg float [[TMP1]] +; CHECK-NEXT: ret float [[DOTNEG]] ; %select = select i1 %cond, float %x, float 0x7FF0000000000000 %fabs = call float @llvm.fabs.f32(float %select) @@ -497,9 +497,9 @@ define nofpclass(inf) float @ret_nofpclass_inf__fneg_fabs_select_pinf_rhs(i1 %co define nofpclass(ninf nnorm nsub nzero) float @ret_nofpclass_nonegatives__fneg_fabs_select_pinf_rhs(i1 %cond, float %x) { ; CHECK-LABEL: define nofpclass(ninf nzero nsub nnorm) float @ret_nofpclass_nonegatives__fneg_fabs_select_pinf_rhs ; CHECK-SAME: (i1 [[COND:%.*]], float [[X:%.*]]) { -; CHECK-NEXT: [[FABS:%.*]] = call float @llvm.fabs.f32(float [[X]]) -; CHECK-NEXT: [[FNEG:%.*]] = fneg float [[FABS]] -; CHECK-NEXT: ret float [[FNEG]] +; CHECK-NEXT: [[TMP1:%.*]] = call float @llvm.fabs.f32(float [[X]]) +; CHECK-NEXT: [[DOTNEG:%.*]] = fneg float [[TMP1]] +; CHECK-NEXT: ret float [[DOTNEG]] ; %select = select i1 %cond, float %x, float 0x7FF0000000000000 %fabs = call float @llvm.fabs.f32(float %select) @@ -535,8 +535,8 @@ define nofpclass(inf) float @ret_nofpclass_inf__copysign_unknown_select_pinf_rhs define nofpclass(inf) float @ret_nofpclass_inf__copysign_positive_select_pinf_rhs(i1 %cond, float %x) { ; CHECK-LABEL: define nofpclass(inf) float @ret_nofpclass_inf__copysign_positive_select_pinf_rhs ; CHECK-SAME: (i1 [[COND:%.*]], float [[X:%.*]]) { -; CHECK-NEXT: [[COPYSIGN:%.*]] = call float @llvm.fabs.f32(float [[X]]) -; CHECK-NEXT: ret float [[COPYSIGN]] +; CHECK-NEXT: [[TMP1:%.*]] = call float @llvm.fabs.f32(float [[X]]) +; CHECK-NEXT: ret float [[TMP1]] ; %select = select i1 %cond, float %x, float 0x7FF0000000000000 %copysign = call float @llvm.copysign.f32(float %select, float 1.0) @@ -547,8 +547,8 @@ define nofpclass(inf) float @ret_nofpclass_inf__copysign_negative_select_pinf_rh ; CHECK-LABEL: define nofpclass(inf) float @ret_nofpclass_inf__copysign_negative_select_pinf_rhs ; CHECK-SAME: (i1 [[COND:%.*]], float [[X:%.*]]) { ; CHECK-NEXT: [[TMP1:%.*]] = call float @llvm.fabs.f32(float [[X]]) -; CHECK-NEXT: [[COPYSIGN:%.*]] = fneg float [[TMP1]] -; CHECK-NEXT: ret float [[COPYSIGN]] +; CHECK-NEXT: [[DOTNEG:%.*]] = fneg float [[TMP1]] +; CHECK-NEXT: ret float [[DOTNEG]] ; %select = select i1 %cond, float %x, float 0x7FF0000000000000 %copysign = call float @llvm.copysign.f32(float %select, float -1.0) @@ -627,8 +627,8 @@ define nofpclass(nan ninf nnorm nsub nzero) float @ret_nofpclass_nonegatives_non define nofpclass(pinf pnorm psub pzero) float @ret_nofpclass_nopositives__copysign_fabs_select_pinf_rhs(i1 %cond, float %x, float %sign) { ; CHECK-LABEL: define nofpclass(pinf pzero psub pnorm) float @ret_nofpclass_nopositives__copysign_fabs_select_pinf_rhs ; CHECK-SAME: (i1 [[COND:%.*]], float [[X:%.*]], float [[SIGN:%.*]]) { -; CHECK-NEXT: [[COPYSIGN:%.*]] = call float @llvm.fabs.f32(float [[X]]) -; CHECK-NEXT: ret float [[COPYSIGN]] +; CHECK-NEXT: [[TMP1:%.*]] = call float @llvm.fabs.f32(float [[X]]) +; CHECK-NEXT: ret float [[TMP1]] ; %select = select i1 %cond, float %x, float 0x7FF0000000000000 %fabs.sign = call float @llvm.fabs.f32(float %sign) @@ -678,9 +678,9 @@ define nofpclass(ninf nnorm nsub nzero) float @ret_nofpclass_no_negatives__copys define nofpclass(pinf pnorm psub pzero) float @ret_nofpclass_no_positives__copysign_unknown_select_pinf_rhs(i1 %cond, float %x, float %unknown.sign) { ; CHECK-LABEL: define nofpclass(pinf pzero psub pnorm) float @ret_nofpclass_no_positives__copysign_unknown_select_pinf_rhs ; CHECK-SAME: (i1 [[COND:%.*]], float [[X:%.*]], float [[UNKNOWN_SIGN:%.*]]) { -; CHECK-NEXT: [[TMP2:%.*]] = call float @llvm.fabs.f32(float [[X]]) -; CHECK-NEXT: [[TMP1:%.*]] = select i1 [[COND]], float [[TMP2]], float 0x7FF0000000000000 -; CHECK-NEXT: [[COPYSIGN:%.*]] = fneg float [[TMP1]] +; CHECK-NEXT: [[TMP1:%.*]] = call float @llvm.fabs.f32(float [[X]]) +; CHECK-NEXT: [[DOTNEG:%.*]] = fneg float [[TMP1]] +; CHECK-NEXT: [[COPYSIGN:%.*]] = select i1 [[COND]], float [[DOTNEG]], float 0xFFF0000000000000 ; CHECK-NEXT: ret float [[COPYSIGN]] ; %select = select i1 %cond, float %x, float 0x7FF0000000000000 @@ -705,9 +705,9 @@ define nofpclass(nan ninf nnorm nsub nzero) float @ret_nofpclass_no_negatives_no define nofpclass(nan pinf pnorm psub pzero) float @ret_nofpclass_no_positives_nonan__copysign_unknown_select_pinf_rhs(i1 %cond, float %x, float %unknown.sign) { ; CHECK-LABEL: define nofpclass(nan pinf pzero psub pnorm) float @ret_nofpclass_no_positives_nonan__copysign_unknown_select_pinf_rhs ; CHECK-SAME: (i1 [[COND:%.*]], float [[X:%.*]], float [[UNKNOWN_SIGN:%.*]]) { -; CHECK-NEXT: [[TMP2:%.*]] = call float @llvm.fabs.f32(float [[X]]) -; CHECK-NEXT: [[TMP1:%.*]] = select i1 [[COND]], float [[TMP2]], float 0x7FF0000000000000 -; CHECK-NEXT: [[COPYSIGN:%.*]] = fneg float [[TMP1]] +; CHECK-NEXT: [[TMP1:%.*]] = call float @llvm.fabs.f32(float [[X]]) +; CHECK-NEXT: [[DOTNEG:%.*]] = fneg float [[TMP1]] +; CHECK-NEXT: [[COPYSIGN:%.*]] = select i1 [[COND]], float [[DOTNEG]], float 0xFFF0000000000000 ; CHECK-NEXT: ret float [[COPYSIGN]] ; %select = select i1 %cond, float %x, float 0x7FF0000000000000 diff --git a/llvm/test/Transforms/InstCombine/sub-of-negatible.ll b/llvm/test/Transforms/InstCombine/sub-of-negatible.ll index 72fd7f7be2b04cb203c29de8f8639de75d07dfc5..b2e14ceaca1b084ce1b01bea67bcb76877162aea 100644 --- a/llvm/test/Transforms/InstCombine/sub-of-negatible.ll +++ b/llvm/test/Transforms/InstCombine/sub-of-negatible.ll @@ -1385,12 +1385,12 @@ define i8 @dont_negate_ordinary_select(i8 %x, i8 %y, i8 %z, i1 %c) { ret i8 %t1 } -; FIXME: This is a miscompile. define <2 x i32> @negate_select_of_negation_poison(<2 x i1> %c, <2 x i32> %x) { ; CHECK-LABEL: @negate_select_of_negation_poison( ; CHECK-NEXT: [[NEG:%.*]] = sub <2 x i32> , [[X:%.*]] -; CHECK-NEXT: [[TMP1:%.*]] = select <2 x i1> [[C:%.*]], <2 x i32> [[X]], <2 x i32> [[NEG]] -; CHECK-NEXT: ret <2 x i32> [[TMP1]] +; CHECK-NEXT: [[SEL:%.*]] = select <2 x i1> [[C:%.*]], <2 x i32> [[NEG]], <2 x i32> [[X]] +; CHECK-NEXT: [[NEG2:%.*]] = sub <2 x i32> zeroinitializer, [[SEL]] +; CHECK-NEXT: ret <2 x i32> [[NEG2]] ; %neg = sub <2 x i32> , %x %sel = select <2 x i1> %c, <2 x i32> %neg, <2 x i32> %x diff --git a/llvm/test/Transforms/InstCombine/sub-xor.ll b/llvm/test/Transforms/InstCombine/sub-xor.ll index 2976598e043fee5c5e03c363cc34395cc999cd6d..b4add9698b160915d6c9713e8868b9046f57f600 100644 --- a/llvm/test/Transforms/InstCombine/sub-xor.ll +++ b/llvm/test/Transforms/InstCombine/sub-xor.ll @@ -97,7 +97,7 @@ declare i32 @llvm.ctlz.i32(i32, i1) define i32 @range_masked_sub(i32 %x) { ; CHECK-LABEL: @range_masked_sub( -; CHECK-NEXT: [[COUNT:%.*]] = tail call i32 @llvm.ctlz.i32(i32 [[X:%.*]], i1 true) #[[ATTR1:[0-9]+]], !range [[RNG0:![0-9]+]] +; CHECK-NEXT: [[COUNT:%.*]] = tail call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[X:%.*]], i1 true) #[[ATTR1:[0-9]+]] ; CHECK-NEXT: [[SUB:%.*]] = xor i32 [[COUNT]], 31 ; CHECK-NEXT: ret i32 [[SUB]] ; diff --git a/llvm/test/Transforms/InstCombine/sub.ll b/llvm/test/Transforms/InstCombine/sub.ll index a84e389f13c3b8439e43e0047f5b9779487cd6db..32ed4a787e9262ef4b64ed572067aa6f8a64445a 100644 --- a/llvm/test/Transforms/InstCombine/sub.ll +++ b/llvm/test/Transforms/InstCombine/sub.ll @@ -1123,7 +1123,8 @@ define i64 @test58(ptr %foo, i64 %i, i64 %j) { define i64 @test59(ptr %foo, i64 %i) { ; CHECK-LABEL: @test59( -; CHECK-NEXT: [[GEP1:%.*]] = getelementptr inbounds [100 x [100 x i8]], ptr [[FOO:%.*]], i64 0, i64 42, i64 [[I:%.*]] +; CHECK-NEXT: [[TMP1:%.*]] = getelementptr i8, ptr [[FOO:%.*]], i64 [[I:%.*]] +; CHECK-NEXT: [[GEP1:%.*]] = getelementptr i8, ptr [[TMP1]], i64 4200 ; CHECK-NEXT: [[GEP2:%.*]] = getelementptr inbounds i8, ptr [[FOO]], i64 4200 ; CHECK-NEXT: store ptr [[GEP1]], ptr @dummy_global1, align 8 ; CHECK-NEXT: store ptr [[GEP2]], ptr @dummy_global2, align 8 @@ -1142,13 +1143,12 @@ define i64 @test59(ptr %foo, i64 %i) { define i64 @test60(ptr %foo, i64 %i, i64 %j) { ; CHECK-LABEL: @test60( -; CHECK-NEXT: [[GEP1:%.*]] = getelementptr inbounds [100 x [100 x i8]], ptr [[FOO:%.*]], i64 0, i64 [[J:%.*]], i64 [[I:%.*]] -; CHECK-NEXT: [[GEP2:%.*]] = getelementptr inbounds i8, ptr [[FOO]], i64 4200 -; CHECK-NEXT: [[CAST1:%.*]] = ptrtoint ptr [[GEP1]] to i64 -; CHECK-NEXT: [[CAST2:%.*]] = ptrtoint ptr [[GEP2]] to i64 -; CHECK-NEXT: [[SUB:%.*]] = sub i64 [[CAST1]], [[CAST2]] +; CHECK-NEXT: [[GEP1_IDX:%.*]] = mul nsw i64 [[J:%.*]], 100 +; CHECK-NEXT: [[GEP1_OFFS:%.*]] = add nsw i64 [[GEP1_IDX]], [[I:%.*]] +; CHECK-NEXT: [[GEP1:%.*]] = getelementptr inbounds i8, ptr [[FOO:%.*]], i64 [[GEP1_OFFS]] +; CHECK-NEXT: [[GEPDIFF:%.*]] = add nsw i64 [[GEP1_OFFS]], -4200 ; CHECK-NEXT: store ptr [[GEP1]], ptr @dummy_global1, align 8 -; CHECK-NEXT: ret i64 [[SUB]] +; CHECK-NEXT: ret i64 [[GEPDIFF]] ; ; gep1 has a non-constant index and more than one uses. Shouldn't duplicate the arithmetic. %gep1 = getelementptr inbounds [100 x [100 x i8]], ptr %foo, i64 0, i64 %j, i64 %i @@ -1162,13 +1162,12 @@ define i64 @test60(ptr %foo, i64 %i, i64 %j) { define i64 @test61(ptr %foo, i64 %i, i64 %j) { ; CHECK-LABEL: @test61( -; CHECK-NEXT: [[GEP1:%.*]] = getelementptr inbounds i8, ptr [[FOO:%.*]], i64 4200 -; CHECK-NEXT: [[GEP2:%.*]] = getelementptr inbounds [100 x [100 x i8]], ptr [[FOO]], i64 0, i64 [[J:%.*]], i64 [[I:%.*]] -; CHECK-NEXT: [[CAST1:%.*]] = ptrtoint ptr [[GEP1]] to i64 -; CHECK-NEXT: [[CAST2:%.*]] = ptrtoint ptr [[GEP2]] to i64 -; CHECK-NEXT: [[SUB:%.*]] = sub i64 [[CAST1]], [[CAST2]] +; CHECK-NEXT: [[GEP2_IDX:%.*]] = mul nsw i64 [[J:%.*]], 100 +; CHECK-NEXT: [[GEP2_OFFS:%.*]] = add nsw i64 [[GEP2_IDX]], [[I:%.*]] +; CHECK-NEXT: [[GEP2:%.*]] = getelementptr inbounds i8, ptr [[FOO:%.*]], i64 [[GEP2_OFFS]] +; CHECK-NEXT: [[GEPDIFF:%.*]] = sub nsw i64 4200, [[GEP2_OFFS]] ; CHECK-NEXT: store ptr [[GEP2]], ptr @dummy_global2, align 8 -; CHECK-NEXT: ret i64 [[SUB]] +; CHECK-NEXT: ret i64 [[GEPDIFF]] ; ; gep2 has a non-constant index and more than one uses. Shouldn't duplicate the arithmetic. %gep1 = getelementptr inbounds [100 x [100 x i8]], ptr %foo, i64 0, i64 42, i64 0 @@ -1180,6 +1179,24 @@ define i64 @test61(ptr %foo, i64 %i, i64 %j) { ret i64 %sub } +declare void @use.ptr(ptr) + +define i64 @test_sub_ptradd_multiuse(ptr %p, i64 %idx1, i64 %idx2) { +; CHECK-LABEL: @test_sub_ptradd_multiuse( +; CHECK-NEXT: [[P1:%.*]] = getelementptr inbounds i8, ptr [[P:%.*]], i64 [[IDX1:%.*]] +; CHECK-NEXT: call void @use.ptr(ptr [[P1]]) +; CHECK-NEXT: [[GEPDIFF:%.*]] = sub nsw i64 [[IDX1]], [[IDX2:%.*]] +; CHECK-NEXT: ret i64 [[GEPDIFF]] +; + %p1 = getelementptr inbounds i8, ptr %p, i64 %idx1 + call void @use.ptr(ptr %p1) + %p2 = getelementptr inbounds i8, ptr %p, i64 %idx2 + %p1.int = ptrtoint ptr %p1 to i64 + %p2.int = ptrtoint ptr %p2 to i64 + %sub = sub i64 %p1.int, %p2.int + ret i64 %sub +} + define i32 @test62(i32 %A) { ; CHECK-LABEL: @test62( ; CHECK-NEXT: [[TMP1:%.*]] = shl i32 [[A:%.*]], 1 diff --git a/llvm/test/Transforms/InstCombine/xor.ll b/llvm/test/Transforms/InstCombine/xor.ll index ba9e992a9443c9dd4b5c3167b4181a2e5ed64f2c..9a59db40ef8b1e5e756d0dc2d3b1989b1c31176c 100644 --- a/llvm/test/Transforms/InstCombine/xor.ll +++ b/llvm/test/Transforms/InstCombine/xor.ll @@ -1336,7 +1336,7 @@ define i32 @xor_orn_2use(i32 %a, i32 %b, ptr %s1, ptr %s2) { define i32 @ctlz_pow2(i32 %x) { ; CHECK-LABEL: @ctlz_pow2( -; CHECK-NEXT: [[R:%.*]] = call i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 true), !range [[RNG0:![0-9]+]] +; CHECK-NEXT: [[R:%.*]] = call range(i32 0, 33) i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 true) ; CHECK-NEXT: ret i32 [[R]] ; %n = sub i32 0, %x @@ -1352,7 +1352,7 @@ define <2 x i8> @cttz_pow2(<2 x i8> %x, <2 x i8> %y) { ; CHECK-LABEL: @cttz_pow2( ; CHECK-NEXT: [[S:%.*]] = shl nuw <2 x i8> , [[X:%.*]] ; CHECK-NEXT: [[D:%.*]] = udiv exact <2 x i8> [[S]], [[Y:%.*]] -; CHECK-NEXT: [[R:%.*]] = call <2 x i8> @llvm.ctlz.v2i8(<2 x i8> [[D]], i1 true), !range [[RNG1:![0-9]+]] +; CHECK-NEXT: [[R:%.*]] = call range(i8 0, 9) <2 x i8> @llvm.ctlz.v2i8(<2 x i8> [[D]], i1 true) ; CHECK-NEXT: ret <2 x i8> [[R]] ; %s = shl <2 x i8> , %x @@ -1368,7 +1368,7 @@ define i32 @ctlz_pow2_or_zero(i32 %x) { ; CHECK-LABEL: @ctlz_pow2_or_zero( ; CHECK-NEXT: [[N:%.*]] = sub i32 0, [[X:%.*]] ; CHECK-NEXT: [[A:%.*]] = and i32 [[N]], [[X]] -; CHECK-NEXT: [[Z:%.*]] = call i32 @llvm.ctlz.i32(i32 [[A]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[Z:%.*]] = call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[A]], i1 false) ; CHECK-NEXT: [[R:%.*]] = xor i32 [[Z]], 31 ; CHECK-NEXT: ret i32 [[R]] ; @@ -1385,7 +1385,7 @@ define i32 @ctlz_pow2_wrong_const(i32 %x) { ; CHECK-LABEL: @ctlz_pow2_wrong_const( ; CHECK-NEXT: [[N:%.*]] = sub i32 0, [[X:%.*]] ; CHECK-NEXT: [[A:%.*]] = and i32 [[N]], [[X]] -; CHECK-NEXT: [[Z:%.*]] = call i32 @llvm.ctlz.i32(i32 [[A]], i1 true), !range [[RNG0]] +; CHECK-NEXT: [[Z:%.*]] = call range(i32 0, 33) i32 @llvm.ctlz.i32(i32 [[A]], i1 true) ; CHECK-NEXT: [[R:%.*]] = xor i32 [[Z]], 30 ; CHECK-NEXT: ret i32 [[R]] ; diff --git a/llvm/test/Transforms/InstCombine/zext-ctlz-trunc-to-ctlz-add.ll b/llvm/test/Transforms/InstCombine/zext-ctlz-trunc-to-ctlz-add.ll index c8eb513a8440b493b8c41f12bdb4fb8bac637c34..384ff8d2b7a3a3f9e1a597bb8135ebbc8ef455eb 100644 --- a/llvm/test/Transforms/InstCombine/zext-ctlz-trunc-to-ctlz-add.ll +++ b/llvm/test/Transforms/InstCombine/zext-ctlz-trunc-to-ctlz-add.ll @@ -13,7 +13,7 @@ declare void @use1() define i16 @trunc_ctlz_zext_i16_i32(i16 %x) { ; CHECK-LABEL: @trunc_ctlz_zext_i16_i32( -; CHECK-NEXT: [[TMP1:%.*]] = call i16 @llvm.ctlz.i16(i16 [[X:%.*]], i1 false), !range [[RNG0:![0-9]+]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i16 0, 17) i16 @llvm.ctlz.i16(i16 [[X:%.*]], i1 false) ; CHECK-NEXT: [[ZZ:%.*]] = add nuw nsw i16 [[TMP1]], 16 ; CHECK-NEXT: ret i16 [[ZZ]] ; @@ -27,7 +27,7 @@ define i16 @trunc_ctlz_zext_i16_i32(i16 %x) { define <2 x i8> @trunc_ctlz_zext_v2i8_v2i33(<2 x i8> %x) { ; CHECK-LABEL: @trunc_ctlz_zext_v2i8_v2i33( -; CHECK-NEXT: [[TMP1:%.*]] = call <2 x i8> @llvm.ctlz.v2i8(<2 x i8> [[X:%.*]], i1 true), !range [[RNG1:![0-9]+]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i8 0, 9) <2 x i8> @llvm.ctlz.v2i8(<2 x i8> [[X:%.*]], i1 true) ; CHECK-NEXT: [[ZZ:%.*]] = add nuw nsw <2 x i8> [[TMP1]], ; CHECK-NEXT: ret <2 x i8> [[ZZ]] ; @@ -41,7 +41,7 @@ define <2 x i8> @trunc_ctlz_zext_v2i8_v2i33(<2 x i8> %x) { define @trunc_ctlz_zext_nxv2i16_nxv2i64( %x) { ; CHECK-LABEL: @trunc_ctlz_zext_nxv2i16_nxv2i64( -; CHECK-NEXT: [[TMP1:%.*]] = call @llvm.ctlz.nxv2i16( [[X:%.*]], i1 false), !range [[RNG0]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i16 0, 17) @llvm.ctlz.nxv2i16( [[X:%.*]], i1 false) ; CHECK-NEXT: [[ZZ:%.*]] = add nuw nsw [[TMP1]], shufflevector ( insertelement ( poison, i16 48, i64 0), poison, zeroinitializer) ; CHECK-NEXT: ret [[ZZ]] ; @@ -56,7 +56,7 @@ define @trunc_ctlz_zext_nxv2i16_nxv2i64( %x define <2 x i17> @trunc_ctlz_zext_v2i17_v2i32_multiple_uses(<2 x i17> %x) { ; CHECK-LABEL: @trunc_ctlz_zext_v2i17_v2i32_multiple_uses( ; CHECK-NEXT: [[Z:%.*]] = zext <2 x i17> [[X:%.*]] to <2 x i32> -; CHECK-NEXT: [[P:%.*]] = call <2 x i32> @llvm.ctlz.v2i32(<2 x i32> [[Z]], i1 false), !range [[RNG2:![0-9]+]] +; CHECK-NEXT: [[P:%.*]] = call range(i32 15, 33) <2 x i32> @llvm.ctlz.v2i32(<2 x i32> [[Z]], i1 false) ; CHECK-NEXT: [[ZZ:%.*]] = trunc nuw nsw <2 x i32> [[P]] to <2 x i17> ; CHECK-NEXT: call void @use(<2 x i32> [[P]]) ; CHECK-NEXT: ret <2 x i17> [[ZZ]] @@ -73,7 +73,7 @@ define <2 x i17> @trunc_ctlz_zext_v2i17_v2i32_multiple_uses(<2 x i17> %x) { define @trunc_ctlz_zext_nxv2i16_nxv2i63_multiple_uses( %x) { ; CHECK-LABEL: @trunc_ctlz_zext_nxv2i16_nxv2i63_multiple_uses( ; CHECK-NEXT: [[Z:%.*]] = zext [[X:%.*]] to -; CHECK-NEXT: [[TMP1:%.*]] = call @llvm.ctlz.nxv2i16( [[X]], i1 true), !range [[RNG0]] +; CHECK-NEXT: [[TMP1:%.*]] = call range(i16 0, 17) @llvm.ctlz.nxv2i16( [[X]], i1 true) ; CHECK-NEXT: [[ZZ:%.*]] = add nuw nsw [[TMP1]], shufflevector ( insertelement ( poison, i16 47, i64 0), poison, zeroinitializer) ; CHECK-NEXT: call void @use1( [[Z]]) ; CHECK-NEXT: ret [[ZZ]] @@ -90,7 +90,7 @@ define @trunc_ctlz_zext_nxv2i16_nxv2i63_multiple_uses( [[TMP19]], ; CHECK-NEXT: [[TMP47:%.*]] = select <4 x i1> [[TMP46]], <4 x i1> , <4 x i1> [[TMP44]] ; CHECK-NEXT: [[TMP48:%.*]] = bitcast <4 x i1> [[TMP47]] to i4 -; CHECK-NEXT: [[TMP49:%.*]] = call i4 @llvm.ctpop.i4(i4 [[TMP48]]), !range [[RNG42:![0-9]+]] +; CHECK-NEXT: [[TMP49:%.*]] = call range(i4 0, 5) i4 @llvm.ctpop.i4(i4 [[TMP48]]) ; CHECK-NEXT: [[TMP50:%.*]] = zext nneg i4 [[TMP49]] to i32 ; CHECK-NEXT: [[TMP51]] = add i32 [[VEC_PHI]], [[TMP50]] ; CHECK-NEXT: [[INDEX_NEXT]] = add nuw i32 [[INDEX]], 4 ; CHECK-NEXT: [[TMP52:%.*]] = icmp eq i32 [[INDEX_NEXT]], 1000 -; CHECK-NEXT: br i1 [[TMP52]], label [[MIDDLE_BLOCK:%.*]], label [[VECTOR_BODY]], !llvm.loop [[LOOP43:![0-9]+]] +; CHECK-NEXT: br i1 [[TMP52]], label [[MIDDLE_BLOCK:%.*]], label [[VECTOR_BODY]], !llvm.loop [[LOOP42:![0-9]+]] ; CHECK: middle.block: ; CHECK-NEXT: br i1 true, label [[FOR_COND_CLEANUP:%.*]], label [[SCALAR_PH]] ; CHECK: scalar.ph: @@ -1377,7 +1377,7 @@ define i32 @predicated_or_dominates_reduction(ptr %b) { ; CHECK: if.then: ; CHECK-NEXT: br label [[FOR_INC]] ; CHECK: for.inc: -; CHECK-NEXT: br i1 poison, label [[FOR_COND_CLEANUP]], label [[FOR_BODY]], !llvm.loop [[LOOP44:![0-9]+]] +; CHECK-NEXT: br i1 poison, label [[FOR_COND_CLEANUP]], label [[FOR_BODY]], !llvm.loop [[LOOP43:![0-9]+]] ; entry: br label %for.body diff --git a/llvm/test/Transforms/LoopVectorize/vplan-infer-not-or-type.ll b/llvm/test/Transforms/LoopVectorize/vplan-infer-not-or-type.ll new file mode 100644 index 0000000000000000000000000000000000000000..102ef699cb379df7ce983e837cd7aa67d1bb2232 --- /dev/null +++ b/llvm/test/Transforms/LoopVectorize/vplan-infer-not-or-type.ll @@ -0,0 +1,64 @@ +; NOTE: Assertions have been autogenerated by utils/update_test_checks.py UTC_ARGS: --version 4 +; RUN: opt < %s -passes=loop-vectorize -S | FileCheck %s + +; This test used to crash due to missing Or/Not cases in +; inferScalarTypeForRecipe. + +define void @foo(i8 %arg.0, i8 %arg.1) { +; CHECK-LABEL: define void @foo( +; CHECK-SAME: i8 [[ARG_0:%.*]], i8 [[ARG_1:%.*]]) { +; CHECK-NEXT: entry: +; CHECK-NEXT: br i1 false, label [[SCALAR_PH:%.*]], label [[VECTOR_PH:%.*]] +; CHECK: vector.ph: +; CHECK-NEXT: br label [[VECTOR_BODY:%.*]] +; CHECK: vector.body: +; CHECK-NEXT: [[INDEX:%.*]] = phi i32 [ 0, [[VECTOR_PH]] ], [ [[INDEX_NEXT:%.*]], [[VECTOR_BODY]] ] +; CHECK-NEXT: [[INDEX_NEXT]] = add nuw i32 [[INDEX]], 2 +; CHECK-NEXT: br i1 true, label [[MIDDLE_BLOCK:%.*]], label [[VECTOR_BODY]], !llvm.loop [[LOOP0:![0-9]+]] +; CHECK: middle.block: +; CHECK-NEXT: br i1 true, label [[LOOPEXIT:%.*]], label [[SCALAR_PH]] +; CHECK: scalar.ph: +; CHECK-NEXT: [[BC_RESUME_VAL:%.*]] = phi i8 [ 2, [[MIDDLE_BLOCK]] ], [ 0, [[ENTRY:%.*]] ] +; CHECK-NEXT: br label [[LOOP_HEADER:%.*]] +; CHECK: loop.header: +; CHECK-NEXT: [[INCREMENTOR:%.*]] = phi i8 [ [[ADD:%.*]], [[LATCH:%.*]] ], [ [[BC_RESUME_VAL]], [[SCALAR_PH]] ] +; CHECK-NEXT: [[AND:%.*]] = and i8 [[ARG_0]], [[ARG_1]] +; CHECK-NEXT: [[EXTRACT_T:%.*]] = trunc i8 [[AND]] to i1 +; CHECK-NEXT: br i1 [[EXTRACT_T]], label [[LATCH]], label [[INDIRECT_LATCH:%.*]] +; CHECK: indirect.latch: +; CHECK-NEXT: br label [[LATCH]] +; CHECK: latch: +; CHECK-NEXT: [[ADD]] = add i8 [[INCREMENTOR]], 1 +; CHECK-NEXT: [[CONV:%.*]] = zext i8 [[INCREMENTOR]] to i32 +; CHECK-NEXT: [[CMP:%.*]] = icmp ult i32 [[CONV]], 1 +; CHECK-NEXT: br i1 [[CMP]], label [[LOOP_HEADER]], label [[LOOPEXIT]], !llvm.loop [[LOOP3:![0-9]+]] +; CHECK: loop.exit: +; CHECK-NEXT: ret void +; +entry: + br label %loop.header + +loop.header: ; preds = %latch, %entry + %incrementor = phi i8 [ %add, %latch ], [ 0, %entry ] + %and = and i8 %arg.0, %arg.1 + %extract.t = trunc i8 %and to i1 + br i1 %extract.t, label %latch, label %indirect.latch + +indirect.latch: ; preds = %loop.header + br label %latch + +latch: ; preds = %loop.header16, %loop.header + %add = add i8 %incrementor, 1 + %conv = zext i8 %incrementor to i32 + %cmp = icmp ult i32 %conv, 1 + br i1 %cmp, label %loop.header, label %loop.exit + +loop.exit: + ret void +} +;. +; CHECK: [[LOOP0]] = distinct !{[[LOOP0]], [[META1:![0-9]+]], [[META2:![0-9]+]]} +; CHECK: [[META1]] = !{!"llvm.loop.isvectorized", i32 1} +; CHECK: [[META2]] = !{!"llvm.loop.unroll.runtime.disable"} +; CHECK: [[LOOP3]] = distinct !{[[LOOP3]], [[META2]], [[META1]]} +;. diff --git a/llvm/test/Transforms/LowerTypeTests/cfi-nounwind-direct-call.ll b/llvm/test/Transforms/LowerTypeTests/cfi-nounwind-direct-call.ll index 4c88f4acc12f164f7b2f805d724b65ee59e0c924..2795333effd76ba5febc25467ca8908067a6d694 100644 --- a/llvm/test/Transforms/LowerTypeTests/cfi-nounwind-direct-call.ll +++ b/llvm/test/Transforms/LowerTypeTests/cfi-nounwind-direct-call.ll @@ -109,8 +109,8 @@ attributes #6 = { noreturn nounwind } !11 = !{} !12 = !{!"branch_weights", i32 1048575, i32 1} ; CHECK: Function Attrs: minsize mustprogress nofree norecurse nosync nounwind optsize willreturn memory(none) -; CHECK-LABEL: define dso_local noundef i32 @_Z9nothrow_ei -; CHECK-SAME: (i32 noundef [[NUM:%.*]]) #[[ATTR0:[0-9]+]] !type !4 !type !5 !type !6 { +; CHECK-LABEL: define dso_local noundef range(i32 0, 2) i32 @_Z9nothrow_ei +; CHECK-SAME: (i32 noundef [[NUM:%.*]]) #[[ATTR0:[0-9]+]] !type [[META4:![0-9]+]] !type [[META5:![0-9]+]] !type [[META6:![0-9]+]] { ; CHECK-NEXT: entry: ; CHECK-NEXT: [[TOBOOL_NOT:%.*]] = icmp ne i32 [[NUM]], 0 ; CHECK-NEXT: [[DOT:%.*]] = zext i1 [[TOBOOL_NOT]] to i32 @@ -118,8 +118,8 @@ attributes #6 = { noreturn nounwind } ; ; ; CHECK: Function Attrs: minsize mustprogress nofree norecurse nosync nounwind optsize willreturn memory(write, argmem: none, inaccessiblemem: none) -; CHECK-LABEL: define dso_local noundef i32 @_Z10call_catchi -; CHECK-SAME: (i32 noundef [[NUM:%.*]]) local_unnamed_addr #[[ATTR1:[0-9]+]] !type !4 !type !5 !type !6 { +; CHECK-LABEL: define dso_local noundef range(i32 0, 2) i32 @_Z10call_catchi +; CHECK-SAME: (i32 noundef [[NUM:%.*]]) local_unnamed_addr #[[ATTR1:[0-9]+]] !type [[META4]] !type [[META5]] !type [[META6]] { ; CHECK-NEXT: entry: ; CHECK-NEXT: store ptr @_Z9nothrow_ei.cfi_jt, ptr @catch_ptr, align 8, !tbaa [[TBAA7:![0-9]+]] ; CHECK-NEXT: [[TOBOOL_NOT_I:%.*]] = icmp ne i32 [[NUM]], 0 @@ -131,17 +131,17 @@ attributes #6 = { noreturn nounwind } ; CHECK-LABEL: define weak_odr hidden void @__cfi_check_fail ; CHECK-SAME: (ptr noundef [[TMP0:%.*]], ptr noundef [[TMP1:%.*]]) #[[ATTR2:[0-9]+]] { ; CHECK-NEXT: entry: -; CHECK-NEXT: [[DOTNOT:%.*]] = icmp eq ptr [[TMP0]], null, !nosanitize !11 -; CHECK-NEXT: br i1 [[DOTNOT]], label [[TRAP:%.*]], label [[CONT:%.*]], !nosanitize !11 +; CHECK-NEXT: [[DOTNOT:%.*]] = icmp eq ptr [[TMP0]], null, !nosanitize [[META11:![0-9]+]] +; CHECK-NEXT: br i1 [[DOTNOT]], label [[TRAP:%.*]], label [[CONT:%.*]], !nosanitize [[META11]] ; CHECK: trap: -; CHECK-NEXT: tail call void @llvm.ubsantrap(i8 2) #[[ATTR5:[0-9]+]], !nosanitize !11 -; CHECK-NEXT: unreachable, !nosanitize !11 +; CHECK-NEXT: tail call void @llvm.ubsantrap(i8 2) #[[ATTR6:[0-9]+]], !nosanitize [[META11]] +; CHECK-NEXT: unreachable, !nosanitize [[META11]] ; CHECK: cont: -; CHECK-NEXT: [[TMP2:%.*]] = load i8, ptr [[TMP0]], align 4, !nosanitize !11 +; CHECK-NEXT: [[TMP2:%.*]] = load i8, ptr [[TMP0]], align 4, !nosanitize [[META11]] ; CHECK-NEXT: [[SWITCH:%.*]] = icmp ult i8 [[TMP2]], 5 ; CHECK-NEXT: br i1 [[SWITCH]], label [[TRAP]], label [[CONT6:%.*]] ; CHECK: cont6: -; CHECK-NEXT: ret void, !nosanitize !11 +; CHECK-NEXT: ret void, !nosanitize [[META11]] ; ; ; CHECK-LABEL: define weak void @__cfi_check @@ -153,8 +153,8 @@ attributes #6 = { noreturn nounwind } ; ; CHECK: Function Attrs: naked nocf_check noinline nounwind ; CHECK-LABEL: define internal void @_Z9nothrow_ei.cfi_jt -; CHECK-SAME: () #[[ATTR4:[0-9]+]] align 8 { +; CHECK-SAME: () #[[ATTR5:[0-9]+]] align 8 { ; CHECK-NEXT: entry: -; CHECK-NEXT: tail call void asm sideeffect "jmp ${0:c}@plt\0Aint3\0Aint3\0Aint3\0A", "s"(ptr nonnull @_Z9nothrow_ei) #[[ATTR6:[0-9]+]] +; CHECK-NEXT: tail call void asm sideeffect "jmp ${0:c}@plt\0Aint3\0Aint3\0Aint3\0A", "s"(ptr nonnull @_Z9nothrow_ei) #[[ATTR7:[0-9]+]] ; CHECK-NEXT: unreachable ; diff --git a/llvm/test/Transforms/OpenMP/add_attributes.ll b/llvm/test/Transforms/OpenMP/add_attributes.ll index 47ff5cad4e7eb4c0b9eb4cc78880b05c369a45ec..ebcca3067f045a173798d6d6c272cd5cfbc2f58c 100644 --- a/llvm/test/Transforms/OpenMP/add_attributes.ll +++ b/llvm/test/Transforms/OpenMP/add_attributes.ll @@ -641,8 +641,6 @@ declare i32 @__tgt_target_teams_mapper(ptr, i64, ptr, i32, ptr, ptr, ptr, ptr, p declare i32 @__tgt_target_teams_nowait_mapper(ptr, i64, ptr, i32, ptr, ptr, ptr, ptr, ptr, ptr, i32, i32, i32, ptr, i32, ptr) -declare void @__tgt_register_requires(i64) - declare void @__tgt_target_data_begin_mapper(ptr, i64, i32, ptr, ptr, ptr, ptr, ptr, ptr) declare void @__tgt_target_data_begin_nowait_mapper(ptr, i64, i32, ptr, ptr, ptr, ptr, ptr, ptr) @@ -1248,9 +1246,6 @@ declare i32 @__tgt_target_kernel_nowait(ptr, i64, i32, i32, ptr, ptr, i32, ptr, ; CHECK: ; Function Attrs: nounwind ; CHECK-NEXT: declare i32 @__tgt_target_teams_nowait_mapper(ptr, i64, ptr, i32, ptr, ptr, ptr, ptr, ptr, ptr, i32, i32, i32, ptr, i32, ptr) -; CHECK: ; Function Attrs: nounwind -; CHECK-NEXT: declare void @__tgt_register_requires(i64) - ; CHECK: ; Function Attrs: nounwind ; CHECK-NEXT: declare void @__tgt_target_data_begin_mapper(ptr, i64, i32, ptr, ptr, ptr, ptr, ptr, ptr) @@ -1893,9 +1888,6 @@ declare i32 @__tgt_target_kernel_nowait(ptr, i64, i32, i32, ptr, ptr, i32, ptr, ; OPTIMISTIC: ; Function Attrs: nounwind ; OPTIMISTIC-NEXT: declare i32 @__tgt_target_teams_nowait_mapper(ptr, i64, ptr, i32, ptr, ptr, ptr, ptr, ptr, ptr, i32, i32, i32, ptr, i32, ptr) -; OPTIMISTIC: ; Function Attrs: nounwind -; OPTIMISTIC-NEXT: declare void @__tgt_register_requires(i64) - ; OPTIMISTIC: ; Function Attrs: nounwind ; OPTIMISTIC-NEXT: declare void @__tgt_target_data_begin_mapper(ptr, i64, i32, ptr, ptr, ptr, ptr, ptr, ptr) @@ -2551,9 +2543,6 @@ declare i32 @__tgt_target_kernel_nowait(ptr, i64, i32, i32, ptr, ptr, i32, ptr, ; EXT: ; Function Attrs: nounwind ; EXT-NEXT: declare signext i32 @__tgt_target_teams_nowait_mapper(ptr, i64, ptr, i32 signext, ptr, ptr, ptr, ptr, ptr, ptr, i32 signext, i32 signext, i32 signext, ptr, i32 signext, ptr) -; EXT: ; Function Attrs: nounwind -; EXT-NEXT: declare void @__tgt_register_requires(i64) - ; EXT: ; Function Attrs: nounwind ; EXT-NEXT: declare void @__tgt_target_data_begin_mapper(ptr, i64, i32 signext, ptr, ptr, ptr, ptr, ptr, ptr) diff --git a/llvm/test/Transforms/PhaseOrdering/AArch64/extra-unroll-simplifications.ll b/llvm/test/Transforms/PhaseOrdering/AArch64/extra-unroll-simplifications.ll index 6132c35c96ca32e4cbcb537028ef0969d00a478a..b32f4e2a258cd7528039cb1f014e7cc1d9747283 100644 --- a/llvm/test/Transforms/PhaseOrdering/AArch64/extra-unroll-simplifications.ll +++ b/llvm/test/Transforms/PhaseOrdering/AArch64/extra-unroll-simplifications.ll @@ -72,6 +72,86 @@ exit: ret void } +define void @cse_matching_load_from_previous_unrolled_iteration(i32 %N, ptr %src, ptr noalias %dst) { +; CHECK-LABEL: define void @cse_matching_load_from_previous_unrolled_iteration( +; CHECK-SAME: i32 [[N:%.*]], ptr nocapture readonly [[SRC:%.*]], ptr noalias nocapture writeonly [[DST:%.*]]) local_unnamed_addr #[[ATTR0]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[SRC_4:%.*]] = getelementptr i8, ptr [[SRC]], i64 4 +; CHECK-NEXT: [[SRC_12:%.*]] = getelementptr i8, ptr [[SRC]], i64 12 +; CHECK-NEXT: [[CMP141:%.*]] = icmp sgt i32 [[N]], 0 +; CHECK-NEXT: br i1 [[CMP141]], label [[LOOP_LATCH_PREHEADER:%.*]], label [[EXIT:%.*]] +; CHECK: loop.latch.preheader: +; CHECK-NEXT: [[WIDE_TRIP_COUNT:%.*]] = zext nneg i32 [[N]] to i64 +; CHECK-NEXT: [[XTRAITER:%.*]] = and i64 [[WIDE_TRIP_COUNT]], 1 +; CHECK-NEXT: [[TMP0:%.*]] = icmp eq i32 [[N]], 1 +; CHECK-NEXT: br i1 [[TMP0]], label [[EXIT_LOOPEXIT_UNR_LCSSA:%.*]], label [[LOOP_LATCH_PREHEADER_NEW:%.*]] +; CHECK: loop.latch.preheader.new: +; CHECK-NEXT: [[UNROLL_ITER:%.*]] = and i64 [[WIDE_TRIP_COUNT]], 2147483646 +; CHECK-NEXT: br label [[LOOP_LATCH:%.*]] +; CHECK: loop.latch: +; CHECK-NEXT: [[INDVARS_IV:%.*]] = phi i64 [ 0, [[LOOP_LATCH_PREHEADER_NEW]] ], [ [[INDVARS_IV_NEXT_1:%.*]], [[LOOP_LATCH]] ] +; CHECK-NEXT: [[NITER:%.*]] = phi i64 [ 0, [[LOOP_LATCH_PREHEADER_NEW]] ], [ [[NITER_NEXT_1:%.*]], [[LOOP_LATCH]] ] +; CHECK-NEXT: [[GEP_SRC_12:%.*]] = getelementptr <2 x i32>, ptr [[SRC_12]], i64 [[INDVARS_IV]] +; CHECK-NEXT: [[L_12:%.*]] = load <2 x i32>, ptr [[GEP_SRC_12]], align 8 +; CHECK-NEXT: [[GEP_SRC_4:%.*]] = getelementptr <2 x i32>, ptr [[SRC_4]], i64 [[INDVARS_IV]] +; CHECK-NEXT: [[L_4:%.*]] = load <2 x i32>, ptr [[GEP_SRC_4]], align 8 +; CHECK-NEXT: [[MUL:%.*]] = mul <2 x i32> [[L_4]], [[L_12]] +; CHECK-NEXT: [[GEP_DST:%.*]] = getelementptr <2 x i32>, ptr [[DST]], i64 [[INDVARS_IV]] +; CHECK-NEXT: store <2 x i32> [[MUL]], ptr [[GEP_DST]], align 8 +; CHECK-NEXT: [[INDVARS_IV_NEXT:%.*]] = or disjoint i64 [[INDVARS_IV]], 1 +; CHECK-NEXT: [[GEP_SRC_12_1:%.*]] = getelementptr <2 x i32>, ptr [[SRC_12]], i64 [[INDVARS_IV_NEXT]] +; CHECK-NEXT: [[L_12_1:%.*]] = load <2 x i32>, ptr [[GEP_SRC_12_1]], align 8 +; CHECK-NEXT: [[GEP_SRC_4_1:%.*]] = getelementptr <2 x i32>, ptr [[SRC_4]], i64 [[INDVARS_IV_NEXT]] +; CHECK-NEXT: [[L_4_1:%.*]] = load <2 x i32>, ptr [[GEP_SRC_4_1]], align 8 +; CHECK-NEXT: [[MUL_1:%.*]] = mul <2 x i32> [[L_4_1]], [[L_12_1]] +; CHECK-NEXT: [[GEP_DST_1:%.*]] = getelementptr <2 x i32>, ptr [[DST]], i64 [[INDVARS_IV_NEXT]] +; CHECK-NEXT: store <2 x i32> [[MUL_1]], ptr [[GEP_DST_1]], align 8 +; CHECK-NEXT: [[INDVARS_IV_NEXT_1]] = add nuw nsw i64 [[INDVARS_IV]], 2 +; CHECK-NEXT: [[NITER_NEXT_1]] = add i64 [[NITER]], 2 +; CHECK-NEXT: [[NITER_NCMP_1:%.*]] = icmp eq i64 [[NITER_NEXT_1]], [[UNROLL_ITER]] +; CHECK-NEXT: br i1 [[NITER_NCMP_1]], label [[EXIT_LOOPEXIT_UNR_LCSSA]], label [[LOOP_LATCH]], !llvm.loop [[LOOP3:![0-9]+]] +; CHECK: exit.loopexit.unr-lcssa: +; CHECK-NEXT: [[INDVARS_IV_UNR:%.*]] = phi i64 [ 0, [[LOOP_LATCH_PREHEADER]] ], [ [[INDVARS_IV_NEXT_1]], [[LOOP_LATCH]] ] +; CHECK-NEXT: [[LCMP_MOD_NOT:%.*]] = icmp eq i64 [[XTRAITER]], 0 +; CHECK-NEXT: br i1 [[LCMP_MOD_NOT]], label [[EXIT]], label [[LOOP_LATCH_EPIL:%.*]] +; CHECK: loop.latch.epil: +; CHECK-NEXT: [[GEP_SRC_12_EPIL:%.*]] = getelementptr <2 x i32>, ptr [[SRC_12]], i64 [[INDVARS_IV_UNR]] +; CHECK-NEXT: [[L_12_EPIL:%.*]] = load <2 x i32>, ptr [[GEP_SRC_12_EPIL]], align 8 +; CHECK-NEXT: [[GEP_SRC_4_EPIL:%.*]] = getelementptr <2 x i32>, ptr [[SRC_4]], i64 [[INDVARS_IV_UNR]] +; CHECK-NEXT: [[L_4_EPIL:%.*]] = load <2 x i32>, ptr [[GEP_SRC_4_EPIL]], align 8 +; CHECK-NEXT: [[MUL_EPIL:%.*]] = mul <2 x i32> [[L_4_EPIL]], [[L_12_EPIL]] +; CHECK-NEXT: [[GEP_DST_EPIL:%.*]] = getelementptr <2 x i32>, ptr [[DST]], i64 [[INDVARS_IV_UNR]] +; CHECK-NEXT: store <2 x i32> [[MUL_EPIL]], ptr [[GEP_DST_EPIL]], align 8 +; CHECK-NEXT: br label [[EXIT]] +; CHECK: exit: +; CHECK-NEXT: ret void +; +entry: + %src.4 = getelementptr i8, ptr %src, i64 4 + %src.12 = getelementptr i8, ptr %src, i64 12 + br label %loop.header + +loop.header: + %iv = phi i32 [ 0, %entry ], [ %iv.next, %loop.latch ] + %cmp14 = icmp slt i32 %iv, %N + br i1 %cmp14, label %loop.latch, label %exit + +loop.latch: + %iv.ext = zext i32 %iv to i64 + %gep.src.12 = getelementptr <2 x i32>, ptr %src.12, i64 %iv.ext + %l.12 = load <2 x i32>, ptr %gep.src.12, align 8 + %gep.src.4 = getelementptr <2 x i32>, ptr %src.4, i64 %iv.ext + %l.4 = load <2 x i32>, ptr %gep.src.4, align 8 + %mul = mul <2 x i32> %l.12, %l.4 + %gep.dst = getelementptr <2 x i32>, ptr %dst, i64 %iv.ext + store <2 x i32> %mul, ptr %gep.dst + %iv.next = add nuw nsw i32 %iv, 1 + br label %loop.header, !llvm.loop !0 + +exit: + ret void +} + !0 = distinct !{!0, !1, !2} !1 = !{!"llvm.loop.mustprogress"} !2 = !{!"llvm.loop.unroll.count", i32 2} @@ -79,4 +159,5 @@ exit: ; CHECK: [[LOOP0]] = distinct !{[[LOOP0]], [[META1:![0-9]+]], [[META2:![0-9]+]]} ; CHECK: [[META1]] = !{!"llvm.loop.mustprogress"} ; CHECK: [[META2]] = !{!"llvm.loop.unroll.disable"} +; CHECK: [[LOOP3]] = distinct !{[[LOOP3]], [[META1]], [[META2]]} ;. diff --git a/llvm/test/Transforms/PhaseOrdering/AArch64/quant_4x4.ll b/llvm/test/Transforms/PhaseOrdering/AArch64/quant_4x4.ll index 9206893cb2341e5a2037e0955407c55f62350f59..c133852f66937d4013cf5111ea204477c5928a9d 100644 --- a/llvm/test/Transforms/PhaseOrdering/AArch64/quant_4x4.ll +++ b/llvm/test/Transforms/PhaseOrdering/AArch64/quant_4x4.ll @@ -7,7 +7,7 @@ target triple = "aarch64" ; Check that the function gets vectorized. define i32 @quant_4x4(ptr noundef %dct, ptr noundef %mf, ptr noundef %bias) { -; CHECK-LABEL: define i32 @quant_4x4 +; CHECK-LABEL: define range(i32 0, 2) i32 @quant_4x4 ; CHECK-SAME: (ptr nocapture noundef [[DCT:%.*]], ptr nocapture noundef readonly [[MF:%.*]], ptr nocapture noundef readonly [[BIAS:%.*]]) local_unnamed_addr #[[ATTR0:[0-9]+]] { ; CHECK-NEXT: entry: ; CHECK-NEXT: [[SCEVGEP:%.*]] = getelementptr i8, ptr [[DCT]], i64 32 diff --git a/llvm/test/Transforms/PhaseOrdering/X86/loop-idiom-vs-indvars.ll b/llvm/test/Transforms/PhaseOrdering/X86/loop-idiom-vs-indvars.ll index 4b5f3107466c8bbb9c509910d9b1428a3a36dd67..7382c3c80d427300dc0f420bb8b9f52f9bd72836 100644 --- a/llvm/test/Transforms/PhaseOrdering/X86/loop-idiom-vs-indvars.ll +++ b/llvm/test/Transforms/PhaseOrdering/X86/loop-idiom-vs-indvars.ll @@ -12,7 +12,7 @@ define i32 @cttz(i32 %n, ptr %p1) { ; ALL-LABEL: @cttz( ; ALL-NEXT: entry: ; ALL-NEXT: [[TMP0:%.*]] = shl i32 [[N:%.*]], 1 -; ALL-NEXT: [[TMP1:%.*]] = tail call i32 @llvm.cttz.i32(i32 [[TMP0]], i1 false), !range [[RNG0:![0-9]+]] +; ALL-NEXT: [[TMP1:%.*]] = tail call range(i32 1, 33) i32 @llvm.cttz.i32(i32 [[TMP0]], i1 false) ; ALL-NEXT: [[TMP2:%.*]] = sub nuw nsw i32 32, [[TMP1]] ; ALL-NEXT: [[TMP3:%.*]] = sub nuw nsw i32 75, [[TMP1]] ; ALL-NEXT: store i32 [[TMP3]], ptr [[P1:%.*]], align 4 diff --git a/llvm/test/Transforms/PhaseOrdering/icmp-ashr-breaking-select-idiom.ll b/llvm/test/Transforms/PhaseOrdering/icmp-ashr-breaking-select-idiom.ll index 67d721b23d6f008efcdb5f280496987912438e0e..35d5ceeb91950fdfeee67af3afe1bdbdada0b1d2 100644 --- a/llvm/test/Transforms/PhaseOrdering/icmp-ashr-breaking-select-idiom.ll +++ b/llvm/test/Transforms/PhaseOrdering/icmp-ashr-breaking-select-idiom.ll @@ -2,7 +2,7 @@ ; RUN: opt -O1 -S < %s | FileCheck %s define i32 @testa(i32 %mul) { -; CHECK-LABEL: define i32 @testa( +; CHECK-LABEL: define range(i32 -65536, 65536) i32 @testa( ; CHECK-SAME: i32 [[MUL:%.*]]) local_unnamed_addr #[[ATTR0:[0-9]+]] { ; CHECK-NEXT: [[SHR:%.*]] = ashr i32 [[MUL]], 15 ; CHECK-NEXT: [[SPEC_SELECT_I:%.*]] = tail call i32 @llvm.smin.i32(i32 [[SHR]], i32 32767) @@ -16,7 +16,7 @@ define i32 @testa(i32 %mul) { } define i32 @testb(i32 %mul) { -; CHECK-LABEL: define i32 @testb( +; CHECK-LABEL: define range(i32 -16777216, 16777216) i32 @testb( ; CHECK-SAME: i32 [[MUL:%.*]]) local_unnamed_addr #[[ATTR0]] { ; CHECK-NEXT: [[SHR102:%.*]] = ashr i32 [[MUL]], 7 ; CHECK-NEXT: [[TMP1:%.*]] = tail call i32 @llvm.smax.i32(i32 [[SHR102]], i32 -128) diff --git a/llvm/test/Transforms/PhaseOrdering/lower-table-based-cttz.ll b/llvm/test/Transforms/PhaseOrdering/lower-table-based-cttz.ll index 284873a9737624a6bd8562301ffef35d93bb63fa..19fbc1f1ae64e38d27cc8f17bacf5c05030d32dc 100644 --- a/llvm/test/Transforms/PhaseOrdering/lower-table-based-cttz.ll +++ b/llvm/test/Transforms/PhaseOrdering/lower-table-based-cttz.ll @@ -15,7 +15,7 @@ ; RUN: opt -O3 -S < %s | FileCheck %s -; CHECK: call i32 @llvm.cttz.i32 +; CHECK: call range(i32 0, 33) i32 @llvm.cttz.i32 @ctz1.table = internal constant [32 x i8] c"\00\01\1C\02\1D\0E\18\03\1E\16\14\0F\19\11\04\08\1F\1B\0D\17\15\13\10\07\1A\0C\12\06\0B\05\0A\09", align 16 diff --git a/llvm/test/Transforms/PhaseOrdering/min_max_loop.ll b/llvm/test/Transforms/PhaseOrdering/min_max_loop.ll index fb338a6507eba8658add62edc71a076466be26ff..63cfef6f3d09ae1338ac7782bbaff318980703a6 100644 --- a/llvm/test/Transforms/PhaseOrdering/min_max_loop.ll +++ b/llvm/test/Transforms/PhaseOrdering/min_max_loop.ll @@ -19,7 +19,7 @@ ;; } define i16 @vecreduce_smin_v2i16(i32 %n, ptr %v) { -; CHECK-LABEL: define i16 @vecreduce_smin_v2i16( +; CHECK-LABEL: define range(i16 -32768, 1) i16 @vecreduce_smin_v2i16( ; CHECK: @llvm.smin.v2i16 entry: @@ -65,7 +65,7 @@ for.end: ; preds = %for.cond } define i16 @vecreduce_smax_v2i16(i32 %n, ptr %v) { -; CHECK-LABEL: define i16 @vecreduce_smax_v2i16( +; CHECK-LABEL: define range(i16 0, -32768) i16 @vecreduce_smax_v2i16( ; CHECK: @llvm.smax.v2i16 entry: diff --git a/llvm/test/Transforms/SCCP/and-add-shl.ll b/llvm/test/Transforms/SCCP/and-add-shl.ll index 7c037ffa6bf640a24e76ffb096a3be68fa9903d6..7af563f13a18abcf35ecd579e3a6ef0945c81fdb 100644 --- a/llvm/test/Transforms/SCCP/and-add-shl.ll +++ b/llvm/test/Transforms/SCCP/and-add-shl.ll @@ -59,7 +59,7 @@ define i8 @and_not_shl_1(i8 %x) { ; Negative test: https://alive2.llvm.org/ce/z/Zv4Pyu define i8 @and_add_shl_overlap(i8 %x) { -; CHECK-LABEL: define i8 @and_add_shl_overlap +; CHECK-LABEL: define range(i8 0, 33) i8 @and_add_shl_overlap ; CHECK-SAME: (i8 [[X:%.*]]) { ; CHECK-NEXT: [[OP1_P2:%.*]] = icmp ule i8 [[X]], 6 ; CHECK-NEXT: call void @llvm.assume(i1 [[OP1_P2]]) @@ -77,7 +77,7 @@ define i8 @and_add_shl_overlap(i8 %x) { } define i8 @and_not_shl_overlap(i8 %x) { -; CHECK-LABEL: define i8 @and_not_shl_overlap +; CHECK-LABEL: define range(i8 0, 5) i8 @and_not_shl_overlap ; CHECK-SAME: (i8 [[X:%.*]]) { ; CHECK-NEXT: [[OP1_P2:%.*]] = icmp ule i8 [[X]], 3 ; CHECK-NEXT: call void @llvm.assume(i1 [[OP1_P2]]) diff --git a/llvm/test/Transforms/SCCP/ip-add-range-to-call.ll b/llvm/test/Transforms/SCCP/ip-add-range-to-call.ll index 64c1b9020a054f31f5963b14db181c990920bd38..c24c554102ddf80c478131bb2f7af98883dae94b 100644 --- a/llvm/test/Transforms/SCCP/ip-add-range-to-call.ll +++ b/llvm/test/Transforms/SCCP/ip-add-range-to-call.ll @@ -1,20 +1,21 @@ -; NOTE: Assertions have been autogenerated by utils/update_test_checks.py +; NOTE: Assertions have been autogenerated by utils/update_test_checks.py UTC_ARGS: --version 4 ; RUN: opt -passes=ipsccp -S %s | FileCheck %s ; Test 1. ; Both arguments and return value of @callee can be tracked. The inferred range ; can be added to call sites. define internal i32 @callee(i32 %x) { -; CHECK-LABEL: @callee( -; CHECK-NEXT: ret i32 [[X:%.*]] +; CHECK-LABEL: define internal range(i32 0, 21) i32 @callee( +; CHECK-SAME: i32 [[X:%.*]]) { +; CHECK-NEXT: ret i32 [[X]] ; ret i32 %x } define i32 @caller1() { -; CHECK-LABEL: @caller1( -; CHECK-NEXT: [[C1:%.*]] = call i32 @callee(i32 10), !range [[RNG0:![0-9]+]] -; CHECK-NEXT: [[C2:%.*]] = call i32 @callee(i32 20), !range [[RNG0]] +; CHECK-LABEL: define range(i32 0, 41) i32 @caller1() { +; CHECK-NEXT: [[C1:%.*]] = call i32 @callee(i32 10) +; CHECK-NEXT: [[C2:%.*]] = call i32 @callee(i32 20) ; CHECK-NEXT: [[A:%.*]] = add nuw nsw i32 [[C1]], [[C2]] ; CHECK-NEXT: ret i32 [[A]] ; @@ -25,9 +26,10 @@ define i32 @caller1() { } define i32 @caller2(i32 %x) { -; CHECK-LABEL: @caller2( -; CHECK-NEXT: [[X_15:%.*]] = and i32 [[X:%.*]], 15 -; CHECK-NEXT: [[C:%.*]] = call i32 @callee(i32 [[X_15]]), !range [[RNG0]] +; CHECK-LABEL: define range(i32 0, 21) i32 @caller2( +; CHECK-SAME: i32 [[X:%.*]]) { +; CHECK-NEXT: [[X_15:%.*]] = and i32 [[X]], 15 +; CHECK-NEXT: [[C:%.*]] = call i32 @callee(i32 [[X_15]]) ; CHECK-NEXT: ret i32 [[C]] ; %x.15 = and i32 %x, 15 @@ -43,14 +45,15 @@ define i32 @caller2(i32 %x) { declare void @use_cb1(ptr) define internal i32 @callee2(i32 %x) { -; CHECK-LABEL: @callee2( -; CHECK-NEXT: ret i32 [[X:%.*]] +; CHECK-LABEL: define internal i32 @callee2( +; CHECK-SAME: i32 [[X:%.*]]) { +; CHECK-NEXT: ret i32 [[X]] ; ret i32 %x } define void @caller_cb1() { -; CHECK-LABEL: @caller_cb1( +; CHECK-LABEL: define void @caller_cb1() { ; CHECK-NEXT: [[C1:%.*]] = call i32 @callee2(i32 9) ; CHECK-NEXT: [[C2:%.*]] = call i32 @callee2(i32 10) ; CHECK-NEXT: call void @use_cb1(ptr @callee2) @@ -70,8 +73,9 @@ define void @caller_cb1() { declare void @use_cb2(ptr) define internal i32 @callee3(i32 %x) { -; CHECK-LABEL: @callee3( -; CHECK-NEXT: [[C:%.*]] = icmp eq i32 [[X:%.*]], 10 +; CHECK-LABEL: define internal range(i32 500, 601) i32 @callee3( +; CHECK-SAME: i32 [[X:%.*]]) { +; CHECK-NEXT: [[C:%.*]] = icmp eq i32 [[X]], 10 ; CHECK-NEXT: [[S:%.*]] = select i1 [[C]], i32 500, i32 600 ; CHECK-NEXT: ret i32 [[S]] ; @@ -81,9 +85,9 @@ define internal i32 @callee3(i32 %x) { } define void @caller_cb2() { -; CHECK-LABEL: @caller_cb2( -; CHECK-NEXT: [[C1:%.*]] = call i32 @callee3(i32 9), !range [[RNG1:![0-9]+]] -; CHECK-NEXT: [[C2:%.*]] = call i32 @callee3(i32 10), !range [[RNG1]] +; CHECK-LABEL: define void @caller_cb2() { +; CHECK-NEXT: [[C1:%.*]] = call i32 @callee3(i32 9) +; CHECK-NEXT: [[C2:%.*]] = call i32 @callee3(i32 10) ; CHECK-NEXT: call void @use_cb2(ptr @callee3) ; CHECK-NEXT: ret void ; @@ -100,9 +104,10 @@ define void @caller_cb2() { declare void @use_cb3(ptr) define internal i32 @callee4(i32 %x, i32 %y) { -; CHECK-LABEL: @callee4( -; CHECK-NEXT: [[C:%.*]] = icmp eq i32 [[X:%.*]], 10 -; CHECK-NEXT: [[S:%.*]] = select i1 [[C]], i32 500, i32 [[Y:%.*]] +; CHECK-LABEL: define internal i32 @callee4( +; CHECK-SAME: i32 [[X:%.*]], i32 [[Y:%.*]]) { +; CHECK-NEXT: [[C:%.*]] = icmp eq i32 [[X]], 10 +; CHECK-NEXT: [[S:%.*]] = select i1 [[C]], i32 500, i32 [[Y]] ; CHECK-NEXT: ret i32 [[S]] ; %c = icmp eq i32 %x, 10 @@ -111,11 +116,9 @@ define internal i32 @callee4(i32 %x, i32 %y) { } define void @caller_cb3() { -; CHECK-LABEL: @caller_cb3( +; CHECK-LABEL: define void @caller_cb3() { ; CHECK-NEXT: [[C1:%.*]] = call i32 @callee4(i32 11, i32 30) -; CHECK-NOT: !range ; CHECK-NEXT: [[C2:%.*]] = call i32 @callee4(i32 12, i32 40) -; CHECK-NOT: !range ; CHECK-NEXT: call void @use_cb3(ptr @callee4) ; CHECK-NEXT: ret void ; @@ -129,15 +132,16 @@ define void @caller_cb3() { ; Range for the return value of callee5 includes undef. No range metadata ; should be added at call sites. define internal i32 @callee5(i32 %x, i32 %y) { -; CHECK-LABEL: @callee5( -; CHECK-NEXT: [[C:%.*]] = icmp slt i32 [[X:%.*]], 15 +; CHECK-LABEL: define internal i32 @callee5( +; CHECK-SAME: i32 [[X:%.*]], i32 [[Y:%.*]]) { +; CHECK-NEXT: [[C:%.*]] = icmp slt i32 [[X]], 15 ; CHECK-NEXT: br i1 [[C]], label [[BB1:%.*]], label [[BB2:%.*]] ; CHECK: bb1: ; CHECK-NEXT: br label [[EXIT:%.*]] ; CHECK: bb2: ; CHECK-NEXT: br label [[EXIT]] ; CHECK: exit: -; CHECK-NEXT: [[RES:%.*]] = phi i32 [ [[Y:%.*]], [[BB1]] ], [ undef, [[BB2]] ] +; CHECK-NEXT: [[RES:%.*]] = phi i32 [ [[Y]], [[BB1]] ], [ undef, [[BB2]] ] ; CHECK-NEXT: ret i32 [[RES]] ; %c = icmp slt i32 %x, 15 @@ -155,11 +159,9 @@ exit: } define i32 @caller5() { -; CHECK-LABEL: @caller5( +; CHECK-LABEL: define range(i32 200, 401) i32 @caller5() { ; CHECK-NEXT: [[C1:%.*]] = call i32 @callee5(i32 10, i32 100) -; CHECK-NOT: !range ; CHECK-NEXT: [[C2:%.*]] = call i32 @callee5(i32 20, i32 200) -; CHECK-NOT: !range ; CHECK-NEXT: [[A:%.*]] = add i32 [[C1]], [[C2]] ; CHECK-NEXT: ret i32 [[A]] ; @@ -170,8 +172,9 @@ define i32 @caller5() { } define internal <2 x i64> @ctlz(<2 x i64> %arg) { -; CHECK-LABEL: @ctlz( -; CHECK-NEXT: [[RES:%.*]] = call <2 x i64> @llvm.ctlz.v2i64(<2 x i64> [[ARG:%.*]], i1 false) +; CHECK-LABEL: define internal range(i64 0, 65) <2 x i64> @ctlz( +; CHECK-SAME: <2 x i64> [[ARG:%.*]]) { +; CHECK-NEXT: [[RES:%.*]] = call <2 x i64> @llvm.ctlz.v2i64(<2 x i64> [[ARG]], i1 false) ; CHECK-NEXT: ret <2 x i64> [[RES]] ; %res = call <2 x i64> @llvm.ctlz.v2i64(<2 x i64> %arg, i1 false) @@ -179,8 +182,9 @@ define internal <2 x i64> @ctlz(<2 x i64> %arg) { } define <2 x i64> @ctlz_caller(<2 x i64> %arg) { -; CHECK-LABEL: @ctlz_caller( -; CHECK-NEXT: [[RES:%.*]] = call <2 x i64> @ctlz(<2 x i64> [[ARG:%.*]]), !range [[RNG2:![0-9]+]] +; CHECK-LABEL: define range(i64 0, 65) <2 x i64> @ctlz_caller( +; CHECK-SAME: <2 x i64> [[ARG:%.*]]) { +; CHECK-NEXT: [[RES:%.*]] = call <2 x i64> @ctlz(<2 x i64> [[ARG]]) ; CHECK-NEXT: ret <2 x i64> [[RES]] ; %res = call <2 x i64> @ctlz(<2 x i64> %arg) @@ -189,6 +193,3 @@ define <2 x i64> @ctlz_caller(<2 x i64> %arg) { declare <2 x i64> @llvm.ctlz.v2i64(<2 x i64>, i1) -; CHECK: [[RNG0]] = !{i32 0, i32 21} -; CHECK: [[RNG1]] = !{i32 500, i32 601} -; CHECK: [[RNG2]] = !{i64 0, i64 65} diff --git a/llvm/test/Transforms/SCCP/ip-ranges-casts.ll b/llvm/test/Transforms/SCCP/ip-ranges-casts.ll index 80d90922c2fbdb4a9e8f0944613efc823cf398ba..05fa04a9fbe06ff114a7af50523118fadc149b7d 100644 --- a/llvm/test/Transforms/SCCP/ip-ranges-casts.ll +++ b/llvm/test/Transforms/SCCP/ip-ranges-casts.ll @@ -1,10 +1,11 @@ -; NOTE: Assertions have been autogenerated by utils/update_test_checks.py +; NOTE: Assertions have been autogenerated by utils/update_test_checks.py UTC_ARGS: --version 4 ; RUN: opt < %s -passes=ipsccp -S | FileCheck %s ; x = [100, 301) define internal i1 @f.trunc(i32 %x) { -; CHECK-LABEL: @f.trunc( -; CHECK-NEXT: [[T_1:%.*]] = trunc nuw nsw i32 [[X:%.*]] to i16 +; CHECK-LABEL: define internal i1 @f.trunc( +; CHECK-SAME: i32 [[X:%.*]]) { +; CHECK-NEXT: [[T_1:%.*]] = trunc nuw nsw i32 [[X]] to i16 ; CHECK-NEXT: [[C_2:%.*]] = icmp sgt i16 [[T_1]], 299 ; CHECK-NEXT: [[C_4:%.*]] = icmp slt i16 [[T_1]], 101 ; CHECK-NEXT: [[RES_1:%.*]] = add nuw nsw i1 false, [[C_2]] @@ -43,7 +44,7 @@ define internal i1 @f.trunc(i32 %x) { } define i1 @caller1() { -; CHECK-LABEL: @caller1( +; CHECK-LABEL: define i1 @caller1() { ; CHECK-NEXT: [[CALL_1:%.*]] = tail call i1 @f.trunc(i32 100) ; CHECK-NEXT: [[CALL_2:%.*]] = tail call i1 @f.trunc(i32 300) ; CHECK-NEXT: [[RES:%.*]] = and i1 [[CALL_1]], [[CALL_2]] @@ -58,14 +59,15 @@ define i1 @caller1() { ; x = [100, 301) define internal i1 @f.zext(i32 %x, i32 %y) { -; CHECK-LABEL: @f.zext( -; CHECK-NEXT: [[T_1:%.*]] = zext nneg i32 [[X:%.*]] to i64 +; CHECK-LABEL: define internal i1 @f.zext( +; CHECK-SAME: i32 [[X:%.*]], i32 [[Y:%.*]]) { +; CHECK-NEXT: [[T_1:%.*]] = zext nneg i32 [[X]] to i64 ; CHECK-NEXT: [[C_2:%.*]] = icmp sgt i64 [[T_1]], 299 ; CHECK-NEXT: [[C_4:%.*]] = icmp slt i64 [[T_1]], 101 ; CHECK-NEXT: [[RES_1:%.*]] = add nuw nsw i1 false, [[C_2]] ; CHECK-NEXT: [[RES_2:%.*]] = add nuw nsw i1 [[RES_1]], false ; CHECK-NEXT: [[RES_3:%.*]] = add i1 [[RES_2]], [[C_4]] -; CHECK-NEXT: [[T_2:%.*]] = zext i32 [[Y:%.*]] to i64 +; CHECK-NEXT: [[T_2:%.*]] = zext i32 [[Y]] to i64 ; CHECK-NEXT: [[C_5:%.*]] = icmp sgt i64 [[T_2]], 300 ; CHECK-NEXT: [[C_6:%.*]] = icmp sgt i64 [[T_2]], 299 ; CHECK-NEXT: [[C_8:%.*]] = icmp slt i64 [[T_2]], 1 @@ -97,7 +99,7 @@ define internal i1 @f.zext(i32 %x, i32 %y) { } define i1 @caller.zext() { -; CHECK-LABEL: @caller.zext( +; CHECK-LABEL: define i1 @caller.zext() { ; CHECK-NEXT: [[CALL_1:%.*]] = tail call i1 @f.zext(i32 100, i32 -120) ; CHECK-NEXT: [[CALL_2:%.*]] = tail call i1 @f.zext(i32 300, i32 900) ; CHECK-NEXT: [[RES:%.*]] = and i1 [[CALL_1]], [[CALL_2]] @@ -111,14 +113,15 @@ define i1 @caller.zext() { ; x = [100, 301) define internal i1 @f.sext(i32 %x, i32 %y) { -; CHECK-LABEL: @f.sext( -; CHECK-NEXT: [[T_1:%.*]] = zext nneg i32 [[X:%.*]] to i64 +; CHECK-LABEL: define internal i1 @f.sext( +; CHECK-SAME: i32 [[X:%.*]], i32 [[Y:%.*]]) { +; CHECK-NEXT: [[T_1:%.*]] = zext nneg i32 [[X]] to i64 ; CHECK-NEXT: [[C_2:%.*]] = icmp sgt i64 [[T_1]], 299 ; CHECK-NEXT: [[C_4:%.*]] = icmp slt i64 [[T_1]], 101 ; CHECK-NEXT: [[RES_1:%.*]] = add nuw nsw i1 false, [[C_2]] ; CHECK-NEXT: [[RES_2:%.*]] = add nuw nsw i1 [[RES_1]], false ; CHECK-NEXT: [[RES_3:%.*]] = add i1 [[RES_2]], [[C_4]] -; CHECK-NEXT: [[T_2:%.*]] = sext i32 [[Y:%.*]] to i64 +; CHECK-NEXT: [[T_2:%.*]] = sext i32 [[Y]] to i64 ; CHECK-NEXT: [[C_6:%.*]] = icmp sgt i64 [[T_2]], 899 ; CHECK-NEXT: [[C_8:%.*]] = icmp slt i64 [[T_2]], -119 ; CHECK-NEXT: [[RES_4:%.*]] = add nuw nsw i1 [[RES_3]], false @@ -148,7 +151,7 @@ define internal i1 @f.sext(i32 %x, i32 %y) { } define i1 @caller.sext() { -; CHECK-LABEL: @caller.sext( +; CHECK-LABEL: define i1 @caller.sext() { ; CHECK-NEXT: [[CALL_1:%.*]] = tail call i1 @f.sext(i32 100, i32 -120) ; CHECK-NEXT: [[CALL_2:%.*]] = tail call i1 @f.sext(i32 300, i32 900) ; CHECK-NEXT: [[RES:%.*]] = and i1 [[CALL_1]], [[CALL_2]] @@ -162,8 +165,9 @@ define i1 @caller.sext() { ; There's nothing we can do besides going to the full range or overdefined. define internal i1 @f.fptosi(i32 %x) { -; CHECK-LABEL: @f.fptosi( -; CHECK-NEXT: [[TO_DOUBLE:%.*]] = sitofp i32 [[X:%.*]] to double +; CHECK-LABEL: define internal i1 @f.fptosi( +; CHECK-SAME: i32 [[X:%.*]]) { +; CHECK-NEXT: [[TO_DOUBLE:%.*]] = sitofp i32 [[X]] to double ; CHECK-NEXT: [[ADD:%.*]] = fadd double 0.000000e+00, [[TO_DOUBLE]] ; CHECK-NEXT: [[TO_I32:%.*]] = fptosi double [[ADD]] to i32 ; CHECK-NEXT: [[C_1:%.*]] = icmp sgt i32 [[TO_I32]], 300 @@ -189,7 +193,7 @@ define internal i1 @f.fptosi(i32 %x) { } define i1 @caller.fptosi() { -; CHECK-LABEL: @caller.fptosi( +; CHECK-LABEL: define i1 @caller.fptosi() { ; CHECK-NEXT: [[CALL_1:%.*]] = tail call i1 @f.fptosi(i32 100) ; CHECK-NEXT: [[CALL_2:%.*]] = tail call i1 @f.fptosi(i32 300) ; CHECK-NEXT: [[RES:%.*]] = and i1 [[CALL_1]], [[CALL_2]] @@ -203,8 +207,9 @@ define i1 @caller.fptosi() { ; There's nothing we can do besides going to the full range or overdefined. define internal i1 @f.fpext(i16 %x) { -; CHECK-LABEL: @f.fpext( -; CHECK-NEXT: [[TO_FLOAT:%.*]] = sitofp i16 [[X:%.*]] to float +; CHECK-LABEL: define internal i1 @f.fpext( +; CHECK-SAME: i16 [[X:%.*]]) { +; CHECK-NEXT: [[TO_FLOAT:%.*]] = sitofp i16 [[X]] to float ; CHECK-NEXT: [[TO_DOUBLE:%.*]] = fpext float [[TO_FLOAT]] to double ; CHECK-NEXT: [[TO_I64:%.*]] = fptoui float [[TO_FLOAT]] to i64 ; CHECK-NEXT: [[C_1:%.*]] = icmp sgt i64 [[TO_I64]], 300 @@ -231,7 +236,7 @@ define internal i1 @f.fpext(i16 %x) { ; There's nothing we can do besides going to the full range or overdefined. define i1 @caller.fpext() { -; CHECK-LABEL: @caller.fpext( +; CHECK-LABEL: define i1 @caller.fpext() { ; CHECK-NEXT: [[CALL_1:%.*]] = tail call i1 @f.fpext(i16 100) ; CHECK-NEXT: [[CALL_2:%.*]] = tail call i1 @f.fpext(i16 300) ; CHECK-NEXT: [[RES:%.*]] = and i1 [[CALL_1]], [[CALL_2]] @@ -245,8 +250,9 @@ define i1 @caller.fpext() { ; There's nothing we can do besides going to the full range or overdefined. define internal i1 @f.inttoptr.ptrtoint(i64 %x) { -; CHECK-LABEL: @f.inttoptr.ptrtoint( -; CHECK-NEXT: [[TO_PTR:%.*]] = inttoptr i64 [[X:%.*]] to ptr +; CHECK-LABEL: define internal i1 @f.inttoptr.ptrtoint( +; CHECK-SAME: i64 [[X:%.*]]) { +; CHECK-NEXT: [[TO_PTR:%.*]] = inttoptr i64 [[X]] to ptr ; CHECK-NEXT: [[TO_I64:%.*]] = ptrtoint ptr [[TO_PTR]] to i64 ; CHECK-NEXT: [[C_1:%.*]] = icmp sgt i64 [[TO_I64]], 300 ; CHECK-NEXT: [[C_2:%.*]] = icmp sgt i64 [[TO_I64]], 299 @@ -270,7 +276,7 @@ define internal i1 @f.inttoptr.ptrtoint(i64 %x) { } define i1 @caller.inttoptr.ptrtoint() { -; CHECK-LABEL: @caller.inttoptr.ptrtoint( +; CHECK-LABEL: define i1 @caller.inttoptr.ptrtoint() { ; CHECK-NEXT: [[CALL_1:%.*]] = tail call i1 @f.inttoptr.ptrtoint(i64 100) ; CHECK-NEXT: [[CALL_2:%.*]] = tail call i1 @f.inttoptr.ptrtoint(i64 300) ; CHECK-NEXT: [[RES:%.*]] = and i1 [[CALL_1]], [[CALL_2]] @@ -284,8 +290,9 @@ define i1 @caller.inttoptr.ptrtoint() { ; Make sure we do not create constant ranges for int to fp casts. define i1 @int_range_to_double_cast(i32 %a) { -; CHECK-LABEL: @int_range_to_double_cast( -; CHECK-NEXT: [[R:%.*]] = and i32 [[A:%.*]], 255 +; CHECK-LABEL: define i1 @int_range_to_double_cast( +; CHECK-SAME: i32 [[A:%.*]]) { +; CHECK-NEXT: [[R:%.*]] = and i32 [[A]], 255 ; CHECK-NEXT: [[T4:%.*]] = sitofp i32 [[R]] to double ; CHECK-NEXT: [[T10:%.*]] = fadd double 0.000000e+00, [[T4]] ; CHECK-NEXT: [[T11:%.*]] = fcmp olt double [[T4]], [[T10]] @@ -300,7 +307,7 @@ define i1 @int_range_to_double_cast(i32 %a) { ; Make sure we do not use ranges to propagate info from vectors. define i16 @vector_binop_and_cast() { -; CHECK-LABEL: @vector_binop_and_cast( +; CHECK-LABEL: define i16 @vector_binop_and_cast() { ; CHECK-NEXT: entry: ; CHECK-NEXT: [[VECINIT7:%.*]] = insertelement <8 x i16> , i16 undef, i32 0 ; CHECK-NEXT: [[REM:%.*]] = srem <8 x i16> , [[VECINIT7]] @@ -317,8 +324,9 @@ entry: } define internal i64 @f.sext_to_zext(i32 %t) { -; CHECK-LABEL: @f.sext_to_zext( -; CHECK-NEXT: [[A:%.*]] = zext nneg i32 [[T:%.*]] to i64 +; CHECK-LABEL: define internal range(i64 0, 2) i64 @f.sext_to_zext( +; CHECK-SAME: i32 [[T:%.*]]) { +; CHECK-NEXT: [[A:%.*]] = zext nneg i32 [[T]] to i64 ; CHECK-NEXT: ret i64 [[A]] ; %a = sext i32 %t to i64 @@ -326,10 +334,11 @@ define internal i64 @f.sext_to_zext(i32 %t) { } define i64 @caller.sext_to_zext(i32 %i) { -; CHECK-LABEL: @caller.sext_to_zext( -; CHECK-NEXT: [[CMP:%.*]] = icmp sle i32 [[I:%.*]], 9 +; CHECK-LABEL: define range(i64 0, 2) i64 @caller.sext_to_zext( +; CHECK-SAME: i32 [[I:%.*]]) { +; CHECK-NEXT: [[CMP:%.*]] = icmp sle i32 [[I]], 9 ; CHECK-NEXT: [[CONV:%.*]] = zext i1 [[CMP]] to i32 -; CHECK-NEXT: [[T:%.*]] = call i64 @f.sext_to_zext(i32 [[CONV]]), !range [[RNG0:![0-9]+]] +; CHECK-NEXT: [[T:%.*]] = call i64 @f.sext_to_zext(i32 [[CONV]]) ; CHECK-NEXT: ret i64 [[T]] ; %cmp = icmp sle i32 %i, 9 diff --git a/llvm/test/Transforms/SCCP/ipsccp-basic.ll b/llvm/test/Transforms/SCCP/ipsccp-basic.ll index 71c042b9b294671b9a958de9a2f1b8bff91e6def..6a7ab8ac2864cdcac807b7a34e86a6d42b5df135 100644 --- a/llvm/test/Transforms/SCCP/ipsccp-basic.ll +++ b/llvm/test/Transforms/SCCP/ipsccp-basic.ll @@ -71,7 +71,7 @@ define void @test3a() { } define i32 @test3b() { -; CHECK-LABEL: define i32 @test3b() { +; CHECK-LABEL: define range(i32 0, 18) i32 @test3b() { ; CHECK-NEXT: [[V:%.*]] = load i32, ptr @G, align 4 ; CHECK-NEXT: [[C:%.*]] = icmp eq i32 [[V]], 17 ; CHECK-NEXT: br i1 [[C]], label [[T:%.*]], label [[F:%.*]] @@ -105,7 +105,7 @@ define internal {i64,i64} @test4a() { } define i64 @test4b() personality ptr @__gxx_personality_v0 { -; CHECK-LABEL: define i64 @test4b() personality ptr @__gxx_personality_v0 { +; CHECK-LABEL: define range(i64 0, 6) i64 @test4b() personality ptr @__gxx_personality_v0 { ; CHECK-NEXT: [[A:%.*]] = invoke { i64, i64 } @test4a() ; CHECK-NEXT: to label [[A:%.*]] unwind label [[B:%.*]] ; CHECK: A: @@ -149,7 +149,7 @@ define internal {i64,i64} @test5a() { } define i64 @test5b() personality ptr @__gxx_personality_v0 { -; CHECK-LABEL: define i64 @test5b() personality ptr @__gxx_personality_v0 { +; CHECK-LABEL: define range(i64 0, 6) i64 @test5b() personality ptr @__gxx_personality_v0 { ; CHECK-NEXT: [[A:%.*]] = invoke { i64, i64 } @test5a() ; CHECK-NEXT: to label [[A:%.*]] unwind label [[B:%.*]] ; CHECK: A: diff --git a/llvm/test/Transforms/SCCP/switch.ll b/llvm/test/Transforms/SCCP/switch.ll index 306f0eebf2b4084244b997e4c44138ba137a9b7b..5208213de210c1eb2e16b5056fcad2f406fddf1a 100644 --- a/llvm/test/Transforms/SCCP/switch.ll +++ b/llvm/test/Transforms/SCCP/switch.ll @@ -1,4 +1,4 @@ -; NOTE: Assertions have been autogenerated by utils/update_test_checks.py +; NOTE: Assertions have been autogenerated by utils/update_test_checks.py UTC_ARGS: --version 4 ; RUN: opt -S -passes=ipsccp < %s | FileCheck %s ; Make sure we always consider the default edge executable for a switch @@ -7,7 +7,7 @@ declare void @foo() declare i32 @g(i32) define void @test1() { -; CHECK-LABEL: @test1( +; CHECK-LABEL: define void @test1() { ; CHECK-NEXT: switch i32 undef, label [[D:%.*]] [ ; CHECK-NEXT: ] ; CHECK: d: @@ -21,15 +21,16 @@ d: } define i32 @test_duplicate_successors_phi(i1 %c, i32 %x) { -; CHECK-LABEL: @test_duplicate_successors_phi( +; CHECK-LABEL: define i32 @test_duplicate_successors_phi( +; CHECK-SAME: i1 [[C:%.*]], i32 [[X:%.*]]) { ; CHECK-NEXT: entry: -; CHECK-NEXT: br i1 [[C:%.*]], label [[SWITCH:%.*]], label [[END:%.*]] +; CHECK-NEXT: br i1 [[C]], label [[SWITCH:%.*]], label [[END:%.*]] ; CHECK: switch: ; CHECK-NEXT: br label [[SWITCH_DEFAULT:%.*]] ; CHECK: switch.default: ; CHECK-NEXT: ret i32 -1 ; CHECK: end: -; CHECK-NEXT: ret i32 [[X:%.*]] +; CHECK-NEXT: ret i32 [[X]] ; entry: br i1 %c, label %switch, label %end @@ -49,13 +50,14 @@ end: } define i32 @test_duplicate_successors_phi_2(i1 %c, i32 %x) { -; CHECK-LABEL: @test_duplicate_successors_phi_2( +; CHECK-LABEL: define i32 @test_duplicate_successors_phi_2( +; CHECK-SAME: i1 [[C:%.*]], i32 [[X:%.*]]) { ; CHECK-NEXT: entry: -; CHECK-NEXT: br i1 [[C:%.*]], label [[SWITCH:%.*]], label [[END:%.*]] +; CHECK-NEXT: br i1 [[C]], label [[SWITCH:%.*]], label [[END:%.*]] ; CHECK: switch: ; CHECK-NEXT: br label [[END]] ; CHECK: end: -; CHECK-NEXT: [[PHI:%.*]] = phi i32 [ [[X:%.*]], [[ENTRY:%.*]] ], [ 1, [[SWITCH]] ] +; CHECK-NEXT: [[PHI:%.*]] = phi i32 [ [[X]], [[ENTRY:%.*]] ], [ 1, [[SWITCH]] ] ; CHECK-NEXT: ret i32 [[PHI]] ; entry: @@ -76,22 +78,23 @@ end: } define i32 @test_duplicate_successors_phi_3(i1 %c1, ptr %p, i32 %y) { -; CHECK-LABEL: @test_duplicate_successors_phi_3( +; CHECK-LABEL: define i32 @test_duplicate_successors_phi_3( +; CHECK-SAME: i1 [[C1:%.*]], ptr [[P:%.*]], i32 [[Y:%.*]]) { ; CHECK-NEXT: entry: -; CHECK-NEXT: br i1 [[C1:%.*]], label [[SWITCH:%.*]], label [[SWITCH_1:%.*]] +; CHECK-NEXT: br i1 [[C1]], label [[SWITCH:%.*]], label [[SWITCH_1:%.*]] ; CHECK: switch: -; CHECK-NEXT: [[X:%.*]] = load i32, ptr [[P:%.*]], align 4, !range [[RNG0:![0-9]+]] +; CHECK-NEXT: [[X:%.*]] = load i32, ptr [[P]], align 4, !range [[RNG0:![0-9]+]] ; CHECK-NEXT: switch i32 [[X]], label [[SWITCH_DEFAULT:%.*]] [ -; CHECK-NEXT: i32 0, label [[SWITCH_DEFAULT]] -; CHECK-NEXT: i32 1, label [[SWITCH_0:%.*]] -; CHECK-NEXT: i32 2, label [[SWITCH_0]] +; CHECK-NEXT: i32 0, label [[SWITCH_DEFAULT]] +; CHECK-NEXT: i32 1, label [[SWITCH_0:%.*]] +; CHECK-NEXT: i32 2, label [[SWITCH_0]] ; CHECK-NEXT: ] ; CHECK: switch.default: ; CHECK-NEXT: ret i32 -1 ; CHECK: switch.0: ; CHECK-NEXT: ret i32 0 ; CHECK: switch.1: -; CHECK-NEXT: ret i32 [[Y:%.*]] +; CHECK-NEXT: ret i32 [[Y]] ; entry: br i1 %c1, label %switch, label %switch.1 @@ -118,12 +121,13 @@ switch.1: } define i32 @test_local_range(ptr %p) { -; CHECK-LABEL: @test_local_range( -; CHECK-NEXT: [[X:%.*]] = load i32, ptr [[P:%.*]], align 4, !range [[RNG0]] +; CHECK-LABEL: define range(i32 0, 3) i32 @test_local_range( +; CHECK-SAME: ptr [[P:%.*]]) { +; CHECK-NEXT: [[X:%.*]] = load i32, ptr [[P]], align 4, !range [[RNG0]] ; CHECK-NEXT: switch i32 [[X]], label [[DEFAULT_UNREACHABLE:%.*]] [ -; CHECK-NEXT: i32 0, label [[SWITCH_0:%.*]] -; CHECK-NEXT: i32 1, label [[SWITCH_1:%.*]] -; CHECK-NEXT: i32 2, label [[SWITCH_2:%.*]] +; CHECK-NEXT: i32 0, label [[SWITCH_0:%.*]] +; CHECK-NEXT: i32 1, label [[SWITCH_1:%.*]] +; CHECK-NEXT: i32 2, label [[SWITCH_2:%.*]] ; CHECK-NEXT: ] ; CHECK: default.unreachable: ; CHECK-NEXT: unreachable @@ -160,13 +164,14 @@ switch.3: ; TODO: Determine that case i3 is dead, even though the edge is shared? define i32 @test_duplicate_successors(ptr %p) { -; CHECK-LABEL: @test_duplicate_successors( -; CHECK-NEXT: [[X:%.*]] = load i32, ptr [[P:%.*]], align 4, !range [[RNG0]] +; CHECK-LABEL: define range(i32 0, 2) i32 @test_duplicate_successors( +; CHECK-SAME: ptr [[P:%.*]]) { +; CHECK-NEXT: [[X:%.*]] = load i32, ptr [[P]], align 4, !range [[RNG0]] ; CHECK-NEXT: switch i32 [[X]], label [[DEFAULT_UNREACHABLE:%.*]] [ -; CHECK-NEXT: i32 0, label [[SWITCH_0:%.*]] -; CHECK-NEXT: i32 1, label [[SWITCH_0]] -; CHECK-NEXT: i32 2, label [[SWITCH_1:%.*]] -; CHECK-NEXT: i32 3, label [[SWITCH_1]] +; CHECK-NEXT: i32 0, label [[SWITCH_0:%.*]] +; CHECK-NEXT: i32 1, label [[SWITCH_0]] +; CHECK-NEXT: i32 2, label [[SWITCH_1:%.*]] +; CHECK-NEXT: i32 3, label [[SWITCH_1]] ; CHECK-NEXT: ] ; CHECK: default.unreachable: ; CHECK-NEXT: unreachable @@ -201,11 +206,12 @@ switch.2: ; Case i32 2 is dead as well, but this cannot be determined based on ; range information. define internal i32 @test_ip_range(i32 %x) { -; CHECK-LABEL: @test_ip_range( -; CHECK-NEXT: switch i32 [[X:%.*]], label [[DEFAULT_UNREACHABLE:%.*]] [ -; CHECK-NEXT: i32 3, label [[SWITCH_3:%.*]] -; CHECK-NEXT: i32 1, label [[SWITCH_1:%.*]] -; CHECK-NEXT: i32 2, label [[SWITCH_2:%.*]] +; CHECK-LABEL: define internal range(i32 1, 4) i32 @test_ip_range( +; CHECK-SAME: i32 [[X:%.*]]) { +; CHECK-NEXT: switch i32 [[X]], label [[DEFAULT_UNREACHABLE:%.*]] [ +; CHECK-NEXT: i32 3, label [[SWITCH_3:%.*]] +; CHECK-NEXT: i32 1, label [[SWITCH_1:%.*]] +; CHECK-NEXT: i32 2, label [[SWITCH_2:%.*]] ; CHECK-NEXT: ], !prof [[PROF1:![0-9]+]] ; CHECK: default.unreachable: ; CHECK-NEXT: unreachable @@ -240,9 +246,9 @@ switch.3: } define void @call_test_ip_range() { -; CHECK-LABEL: @call_test_ip_range( -; CHECK-NEXT: [[TMP1:%.*]] = call i32 @test_ip_range(i32 1), !range [[RNG2:![0-9]+]] -; CHECK-NEXT: [[TMP2:%.*]] = call i32 @test_ip_range(i32 3), !range [[RNG2]] +; CHECK-LABEL: define void @call_test_ip_range() { +; CHECK-NEXT: [[TMP1:%.*]] = call i32 @test_ip_range(i32 1) +; CHECK-NEXT: [[TMP2:%.*]] = call i32 @test_ip_range(i32 3) ; CHECK-NEXT: ret void ; call i32 @test_ip_range(i32 1) @@ -251,11 +257,12 @@ define void @call_test_ip_range() { } define i32 @test_switch_range_may_include_undef(i1 %c.1, i1 %c.2, i32 %x) { -; CHECK-LABEL: @test_switch_range_may_include_undef( +; CHECK-LABEL: define range(i32 -1, 21) i32 @test_switch_range_may_include_undef( +; CHECK-SAME: i1 [[C_1:%.*]], i1 [[C_2:%.*]], i32 [[X:%.*]]) { ; CHECK-NEXT: entry: -; CHECK-NEXT: br i1 [[C_1:%.*]], label [[THEN_1:%.*]], label [[ELSE_1:%.*]] +; CHECK-NEXT: br i1 [[C_1]], label [[THEN_1:%.*]], label [[ELSE_1:%.*]] ; CHECK: then.1: -; CHECK-NEXT: br i1 [[C_2:%.*]], label [[SWITCH:%.*]], label [[ELSE_2:%.*]] +; CHECK-NEXT: br i1 [[C_2]], label [[SWITCH:%.*]], label [[ELSE_2:%.*]] ; CHECK: else.1: ; CHECK-NEXT: br label [[SWITCH]] ; CHECK: else.2: @@ -263,8 +270,8 @@ define i32 @test_switch_range_may_include_undef(i1 %c.1, i1 %c.2, i32 %x) { ; CHECK: switch: ; CHECK-NEXT: [[P:%.*]] = phi i32 [ 0, [[THEN_1]] ], [ 2, [[ELSE_1]] ], [ undef, [[ELSE_2]] ] ; CHECK-NEXT: switch i32 [[P]], label [[SWITCH_DEFAULT:%.*]] [ -; CHECK-NEXT: i32 0, label [[END_1:%.*]] -; CHECK-NEXT: i32 3, label [[END_2:%.*]] +; CHECK-NEXT: i32 0, label [[END_1:%.*]] +; CHECK-NEXT: i32 3, label [[END_2:%.*]] ; CHECK-NEXT: ] ; CHECK: switch.default: ; CHECK-NEXT: ret i32 -1 @@ -303,9 +310,10 @@ end.2: } define i32 @test_default_unreachable_by_dom_cond(i32 %x) { -; CHECK-LABEL: @test_default_unreachable_by_dom_cond( +; CHECK-LABEL: define i32 @test_default_unreachable_by_dom_cond( +; CHECK-SAME: i32 [[X:%.*]]) { ; CHECK-NEXT: entry: -; CHECK-NEXT: [[OR_COND:%.*]] = icmp ult i32 [[X:%.*]], 4 +; CHECK-NEXT: [[OR_COND:%.*]] = icmp ult i32 [[X]], 4 ; CHECK-NEXT: br i1 [[OR_COND]], label [[IF_THEN:%.*]], label [[RETURN:%.*]] ; CHECK: if.then: ; CHECK-NEXT: switch i32 [[X]], label [[DEFAULT_UNREACHABLE:%.*]] [ @@ -371,4 +379,7 @@ return: declare void @llvm.assume(i1) -; CHECK: !1 = !{!"branch_weights", i32 1, i32 5, i32 3, i32 4} +;. +; CHECK: [[RNG0]] = !{i32 0, i32 3} +; CHECK: [[PROF1]] = !{!"branch_weights", i32 1, i32 5, i32 3, i32 4} +;. diff --git a/llvm/test/Transforms/SCCP/trunc-nuw-nsw-flags.ll b/llvm/test/Transforms/SCCP/trunc-nuw-nsw-flags.ll index fc3e56011d46cd4acc9ec3c28dbbf65de338e56b..d3bac0d68a979f5dbae56d9f19268dfa839fdeeb 100644 --- a/llvm/test/Transforms/SCCP/trunc-nuw-nsw-flags.ll +++ b/llvm/test/Transforms/SCCP/trunc-nuw-nsw-flags.ll @@ -16,7 +16,7 @@ entry: } define i8 @range_from_or_nsw(i16 %a) { -; CHECK-LABEL: define i8 @range_from_or_nsw( +; CHECK-LABEL: define range(i8 -128, 0) i8 @range_from_or_nsw( ; CHECK-SAME: i16 [[A:%.*]]) { ; CHECK-NEXT: entry: ; CHECK-NEXT: [[AND1:%.*]] = or i16 [[A]], -128 @@ -30,7 +30,7 @@ entry: } define i16 @range_from_and_nuw_nsw(i32 %a) { -; CHECK-LABEL: define i16 @range_from_and_nuw_nsw( +; CHECK-LABEL: define range(i16 0, -32768) i16 @range_from_and_nuw_nsw( ; CHECK-SAME: i32 [[A:%.*]]) { ; CHECK-NEXT: entry: ; CHECK-NEXT: [[AND1:%.*]] = and i32 [[A]], 32767 diff --git a/llvm/test/Transforms/SLPVectorizer/AArch64/vec3-reorder-reshuffle.ll b/llvm/test/Transforms/SLPVectorizer/AArch64/vec3-reorder-reshuffle.ll index 47d918eabdfe2b3efaf430be34f3499f65ea099c..9bbd314a27cb952b55e72a36863ccd91fec10263 100644 --- a/llvm/test/Transforms/SLPVectorizer/AArch64/vec3-reorder-reshuffle.ll +++ b/llvm/test/Transforms/SLPVectorizer/AArch64/vec3-reorder-reshuffle.ll @@ -537,24 +537,18 @@ entry: } define void @vec3_extract(<3 x i16> %pixel.sroa.0.4.vec.insert606, ptr %call3.i536) { -; NON-POW2-LABEL: define void @vec3_extract( -; NON-POW2-SAME: <3 x i16> [[PIXEL_SROA_0_4_VEC_INSERT606:%.*]], ptr [[CALL3_I536:%.*]]) { -; NON-POW2-NEXT: entry: -; NON-POW2-NEXT: store <3 x i16> [[PIXEL_SROA_0_4_VEC_INSERT606]], ptr [[CALL3_I536]], align 2 -; NON-POW2-NEXT: ret void -; -; POW2-ONLY-LABEL: define void @vec3_extract( -; POW2-ONLY-SAME: <3 x i16> [[PIXEL_SROA_0_4_VEC_INSERT606:%.*]], ptr [[CALL3_I536:%.*]]) { -; POW2-ONLY-NEXT: entry: -; POW2-ONLY-NEXT: [[PIXEL_SROA_0_4_VEC_EXTRACT:%.*]] = extractelement <3 x i16> [[PIXEL_SROA_0_4_VEC_INSERT606]], i64 2 -; POW2-ONLY-NEXT: [[RED668:%.*]] = getelementptr i16, ptr [[CALL3_I536]], i64 2 -; POW2-ONLY-NEXT: store i16 [[PIXEL_SROA_0_4_VEC_EXTRACT]], ptr [[RED668]], align 2 -; POW2-ONLY-NEXT: [[PIXEL_SROA_0_2_VEC_EXTRACT:%.*]] = extractelement <3 x i16> [[PIXEL_SROA_0_4_VEC_INSERT606]], i64 1 -; POW2-ONLY-NEXT: [[GREEN670:%.*]] = getelementptr i16, ptr [[CALL3_I536]], i64 1 -; POW2-ONLY-NEXT: store i16 [[PIXEL_SROA_0_2_VEC_EXTRACT]], ptr [[GREEN670]], align 2 -; POW2-ONLY-NEXT: [[PIXEL_SROA_0_0_VEC_EXTRACT:%.*]] = extractelement <3 x i16> [[PIXEL_SROA_0_4_VEC_INSERT606]], i64 0 -; POW2-ONLY-NEXT: store i16 [[PIXEL_SROA_0_0_VEC_EXTRACT]], ptr [[CALL3_I536]], align 2 -; POW2-ONLY-NEXT: ret void +; CHECK-LABEL: define void @vec3_extract( +; CHECK-SAME: <3 x i16> [[PIXEL_SROA_0_4_VEC_INSERT606:%.*]], ptr [[CALL3_I536:%.*]]) { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[PIXEL_SROA_0_4_VEC_EXTRACT:%.*]] = extractelement <3 x i16> [[PIXEL_SROA_0_4_VEC_INSERT606]], i64 2 +; CHECK-NEXT: [[RED668:%.*]] = getelementptr i16, ptr [[CALL3_I536]], i64 2 +; CHECK-NEXT: store i16 [[PIXEL_SROA_0_4_VEC_EXTRACT]], ptr [[RED668]], align 2 +; CHECK-NEXT: [[PIXEL_SROA_0_2_VEC_EXTRACT:%.*]] = extractelement <3 x i16> [[PIXEL_SROA_0_4_VEC_INSERT606]], i64 1 +; CHECK-NEXT: [[GREEN670:%.*]] = getelementptr i16, ptr [[CALL3_I536]], i64 1 +; CHECK-NEXT: store i16 [[PIXEL_SROA_0_2_VEC_EXTRACT]], ptr [[GREEN670]], align 2 +; CHECK-NEXT: [[PIXEL_SROA_0_0_VEC_EXTRACT:%.*]] = extractelement <3 x i16> [[PIXEL_SROA_0_4_VEC_INSERT606]], i64 0 +; CHECK-NEXT: store i16 [[PIXEL_SROA_0_0_VEC_EXTRACT]], ptr [[CALL3_I536]], align 2 +; CHECK-NEXT: ret void ; entry: %pixel.sroa.0.4.vec.extract = extractelement <3 x i16> %pixel.sroa.0.4.vec.insert606, i64 2 diff --git a/llvm/test/Transforms/SLPVectorizer/RISCV/unsigned-icmp-signed-op.ll b/llvm/test/Transforms/SLPVectorizer/RISCV/unsigned-icmp-signed-op.ll new file mode 100644 index 0000000000000000000000000000000000000000..5ec6b4f1040d81722b22d4d0724070ffc51f0692 --- /dev/null +++ b/llvm/test/Transforms/SLPVectorizer/RISCV/unsigned-icmp-signed-op.ll @@ -0,0 +1,43 @@ +; NOTE: Assertions have been autogenerated by utils/update_test_checks.py UTC_ARGS: --version 4 +; RUN: opt -S --passes=slp-vectorizer -mtriple=riscv64-unknown-linux-gnu -mattr=+v < %s | FileCheck %s + +define i32 @test(ptr %f, i16 %0) { +; CHECK-LABEL: define i32 @test( +; CHECK-SAME: ptr [[F:%.*]], i16 [[TMP0:%.*]]) #[[ATTR0:[0-9]+]] { +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP1:%.*]] = load i16, ptr [[F]], align 2 +; CHECK-NEXT: [[TMP2:%.*]] = insertelement <4 x i16> , i16 [[TMP0]], i32 1 +; CHECK-NEXT: [[TMP3:%.*]] = insertelement <4 x i16> , i16 [[TMP1]], i32 1 +; CHECK-NEXT: [[TMP6:%.*]] = zext <4 x i16> [[TMP3]] to <4 x i32> +; CHECK-NEXT: [[TMP7:%.*]] = sext <4 x i16> [[TMP2]] to <4 x i32> +; CHECK-NEXT: [[TMP4:%.*]] = icmp ule <4 x i32> [[TMP6]], [[TMP7]] +; CHECK-NEXT: [[TMP5:%.*]] = call i1 @llvm.vector.reduce.and.v4i1(<4 x i1> [[TMP4]]) +; CHECK-NEXT: [[ZEXT_4:%.*]] = zext i1 [[TMP5]] to i32 +; CHECK-NEXT: ret i32 [[ZEXT_4]] +; +entry: + %1 = load i16, ptr %f, align 2 + + %zext.0 = zext i16 %1 to i32 + %sext.0 = sext i16 %0 to i32 + + %zext.1 = zext i16 0 to i32 + %sext.1 = sext i16 0 to i32 + %zext.2 = zext i16 0 to i32 + %sext.2 = sext i16 0 to i32 + %zext.3 = zext i16 0 to i32 + %sext.3 = sext i16 0 to i32 + + %cmp.0 = icmp ule i32 %zext.0, %sext.0 + %cmp.1 = icmp ule i32 %zext.1, %sext.1 + %cmp.2 = icmp ule i32 %zext.2, %sext.2 + %cmp.3 = icmp ule i32 %zext.3, %sext.3 + + %and.0 = and i1 %cmp.0, %cmp.1 + %and.1 = and i1 %and.0, %cmp.2 + %and.2 = and i1 %and.1, %cmp.3 + + %zext.4 = zext i1 %and.2 to i32 + + ret i32 %zext.4 +} diff --git a/llvm/test/Transforms/SLPVectorizer/X86/pr46983.ll b/llvm/test/Transforms/SLPVectorizer/X86/pr46983.ll index 75505f632a43f37c5735863a98dc8b6308aa8ce4..29021150ccd2e3957d27a8b5ec87b30b3ff62a37 100644 --- a/llvm/test/Transforms/SLPVectorizer/X86/pr46983.ll +++ b/llvm/test/Transforms/SLPVectorizer/X86/pr46983.ll @@ -1,9 +1,9 @@ ; NOTE: Assertions have been autogenerated by utils/update_test_checks.py -; RUN: opt < %s -passes=slp-vectorizer,instcombine -S -mtriple=x86_64-unknown-linux-gnu -mattr=+sse2 | FileCheck %s --check-prefixes=CHECK,SSE -; RUN: opt < %s -passes=slp-vectorizer,instcombine -S -mtriple=x86_64-unknown-linux-gnu -mattr=+sse4.2 | FileCheck %s --check-prefixes=CHECK,SSE -; RUN: opt < %s -passes=slp-vectorizer,instcombine -S -mtriple=x86_64-unknown-linux-gnu -mattr=+avx | FileCheck %s --check-prefixes=CHECK,AVX -; RUN: opt < %s -passes=slp-vectorizer,instcombine -S -mtriple=x86_64-unknown-linux-gnu -mattr=+avx2 | FileCheck %s --check-prefixes=CHECK,AVX -; RUN: opt < %s -passes=slp-vectorizer,instcombine -S -mtriple=x86_64-unknown-linux-gnu -mattr=+avx512bw,+avx512vl | FileCheck %s --check-prefixes=CHECK,AVX +; RUN: opt < %s -passes=slp-vectorizer,instcombine -S -mtriple=x86_64-unknown-linux-gnu -mattr=+sse2 -slp-threshold=-1 | FileCheck %s +; RUN: opt < %s -passes=slp-vectorizer,instcombine -S -mtriple=x86_64-unknown-linux-gnu -mattr=+sse4.2 | FileCheck %s +; RUN: opt < %s -passes=slp-vectorizer,instcombine -S -mtriple=x86_64-unknown-linux-gnu -mattr=+avx | FileCheck %s +; RUN: opt < %s -passes=slp-vectorizer,instcombine -S -mtriple=x86_64-unknown-linux-gnu -mattr=+avx2 | FileCheck %s +; RUN: opt < %s -passes=slp-vectorizer,instcombine -S -mtriple=x86_64-unknown-linux-gnu -mattr=+avx512bw,+avx512vl | FileCheck %s define void @store_i32(ptr nocapture %0, i32 %1, i32 %2) { ; CHECK-LABEL: @store_i32( @@ -98,58 +98,19 @@ define void @store_i8(ptr nocapture %0, i32 %1, i32 %2) { } define void @store_i64(ptr nocapture %0, i32 %1, i32 %2) { -; SSE-LABEL: @store_i64( -; SSE-NEXT: [[TMP4:%.*]] = zext i32 [[TMP1:%.*]] to i64 -; SSE-NEXT: [[TMP5:%.*]] = load i64, ptr [[TMP0:%.*]], align 8, !tbaa [[TBAA5:![0-9]+]] -; SSE-NEXT: [[TMP6:%.*]] = mul i64 [[TMP5]], [[TMP4]] -; SSE-NEXT: [[TMP7:%.*]] = lshr i64 [[TMP6]], 15 -; SSE-NEXT: [[TMP8:%.*]] = trunc i64 [[TMP7]] to i32 -; SSE-NEXT: [[TMP9:%.*]] = icmp ult i32 [[TMP8]], 255 -; SSE-NEXT: [[TMP10:%.*]] = and i64 [[TMP7]], 4294967295 -; SSE-NEXT: [[TMP11:%.*]] = select i1 [[TMP9]], i64 [[TMP10]], i64 255 -; SSE-NEXT: store i64 [[TMP11]], ptr [[TMP0]], align 8, !tbaa [[TBAA5]] -; SSE-NEXT: [[TMP12:%.*]] = getelementptr inbounds i8, ptr [[TMP0]], i64 8 -; SSE-NEXT: [[TMP13:%.*]] = load i64, ptr [[TMP12]], align 8, !tbaa [[TBAA5]] -; SSE-NEXT: [[TMP14:%.*]] = mul i64 [[TMP13]], [[TMP4]] -; SSE-NEXT: [[TMP15:%.*]] = lshr i64 [[TMP14]], 15 -; SSE-NEXT: [[TMP16:%.*]] = trunc i64 [[TMP15]] to i32 -; SSE-NEXT: [[TMP17:%.*]] = icmp ult i32 [[TMP16]], 255 -; SSE-NEXT: [[TMP18:%.*]] = and i64 [[TMP15]], 4294967295 -; SSE-NEXT: [[TMP19:%.*]] = select i1 [[TMP17]], i64 [[TMP18]], i64 255 -; SSE-NEXT: store i64 [[TMP19]], ptr [[TMP12]], align 8, !tbaa [[TBAA5]] -; SSE-NEXT: [[TMP20:%.*]] = getelementptr inbounds i8, ptr [[TMP0]], i64 16 -; SSE-NEXT: [[TMP21:%.*]] = load i64, ptr [[TMP20]], align 8, !tbaa [[TBAA5]] -; SSE-NEXT: [[TMP22:%.*]] = mul i64 [[TMP21]], [[TMP4]] -; SSE-NEXT: [[TMP23:%.*]] = lshr i64 [[TMP22]], 15 -; SSE-NEXT: [[TMP24:%.*]] = trunc i64 [[TMP23]] to i32 -; SSE-NEXT: [[TMP25:%.*]] = icmp ult i32 [[TMP24]], 255 -; SSE-NEXT: [[TMP26:%.*]] = and i64 [[TMP23]], 4294967295 -; SSE-NEXT: [[TMP27:%.*]] = select i1 [[TMP25]], i64 [[TMP26]], i64 255 -; SSE-NEXT: store i64 [[TMP27]], ptr [[TMP20]], align 8, !tbaa [[TBAA5]] -; SSE-NEXT: [[TMP28:%.*]] = getelementptr inbounds i8, ptr [[TMP0]], i64 24 -; SSE-NEXT: [[TMP29:%.*]] = load i64, ptr [[TMP28]], align 8, !tbaa [[TBAA5]] -; SSE-NEXT: [[TMP30:%.*]] = mul i64 [[TMP29]], [[TMP4]] -; SSE-NEXT: [[TMP31:%.*]] = lshr i64 [[TMP30]], 15 -; SSE-NEXT: [[TMP32:%.*]] = trunc i64 [[TMP31]] to i32 -; SSE-NEXT: [[TMP33:%.*]] = icmp ult i32 [[TMP32]], 255 -; SSE-NEXT: [[TMP34:%.*]] = and i64 [[TMP31]], 4294967295 -; SSE-NEXT: [[TMP35:%.*]] = select i1 [[TMP33]], i64 [[TMP34]], i64 255 -; SSE-NEXT: store i64 [[TMP35]], ptr [[TMP28]], align 8, !tbaa [[TBAA5]] -; SSE-NEXT: ret void -; -; AVX-LABEL: @store_i64( -; AVX-NEXT: [[TMP4:%.*]] = zext i32 [[TMP1:%.*]] to i64 -; AVX-NEXT: [[TMP5:%.*]] = load <4 x i64>, ptr [[TMP0:%.*]], align 8, !tbaa [[TBAA5:![0-9]+]] -; AVX-NEXT: [[TMP6:%.*]] = insertelement <4 x i64> poison, i64 [[TMP4]], i64 0 -; AVX-NEXT: [[TMP7:%.*]] = shufflevector <4 x i64> [[TMP6]], <4 x i64> poison, <4 x i32> zeroinitializer -; AVX-NEXT: [[TMP8:%.*]] = mul <4 x i64> [[TMP5]], [[TMP7]] -; AVX-NEXT: [[TMP9:%.*]] = lshr <4 x i64> [[TMP8]], -; AVX-NEXT: [[TMP10:%.*]] = trunc <4 x i64> [[TMP9]] to <4 x i32> -; AVX-NEXT: [[TMP11:%.*]] = icmp ult <4 x i32> [[TMP10]], -; AVX-NEXT: [[TMP12:%.*]] = and <4 x i64> [[TMP9]], -; AVX-NEXT: [[TMP13:%.*]] = select <4 x i1> [[TMP11]], <4 x i64> [[TMP12]], <4 x i64> -; AVX-NEXT: store <4 x i64> [[TMP13]], ptr [[TMP0]], align 8, !tbaa [[TBAA5]] -; AVX-NEXT: ret void +; CHECK-LABEL: @store_i64( +; CHECK-NEXT: [[TMP4:%.*]] = zext i32 [[TMP1:%.*]] to i64 +; CHECK-NEXT: [[TMP5:%.*]] = load <4 x i64>, ptr [[TMP0:%.*]], align 8, !tbaa [[TBAA5:![0-9]+]] +; CHECK-NEXT: [[TMP6:%.*]] = insertelement <4 x i64> poison, i64 [[TMP4]], i64 0 +; CHECK-NEXT: [[TMP7:%.*]] = shufflevector <4 x i64> [[TMP6]], <4 x i64> poison, <4 x i32> zeroinitializer +; CHECK-NEXT: [[TMP8:%.*]] = mul <4 x i64> [[TMP5]], [[TMP7]] +; CHECK-NEXT: [[TMP9:%.*]] = lshr <4 x i64> [[TMP8]], +; CHECK-NEXT: [[TMP10:%.*]] = trunc <4 x i64> [[TMP9]] to <4 x i32> +; CHECK-NEXT: [[TMP11:%.*]] = icmp ult <4 x i32> [[TMP10]], +; CHECK-NEXT: [[TMP12:%.*]] = and <4 x i64> [[TMP9]], +; CHECK-NEXT: [[TMP13:%.*]] = select <4 x i1> [[TMP11]], <4 x i64> [[TMP12]], <4 x i64> +; CHECK-NEXT: store <4 x i64> [[TMP13]], ptr [[TMP0]], align 8, !tbaa [[TBAA5]] +; CHECK-NEXT: ret void ; %4 = zext i32 %1 to i64 %5 = load i64, ptr %0, align 8, !tbaa !7 diff --git a/llvm/test/Transforms/SimplifyCFG/UnreachableEliminate.ll b/llvm/test/Transforms/SimplifyCFG/UnreachableEliminate.ll index 757340527ec030379d81f281a7a149d490d6889f..ef2d3219cca9b6fd6c466740a818b93bce2351d1 100644 --- a/llvm/test/Transforms/SimplifyCFG/UnreachableEliminate.ll +++ b/llvm/test/Transforms/SimplifyCFG/UnreachableEliminate.ll @@ -627,7 +627,233 @@ else: ret void } +define i32 @test_assume_false(i32 %cond) { +; CHECK-LABEL: @test_assume_false( +; CHECK-NEXT: entry: +; CHECK-NEXT: switch i32 [[COND:%.*]], label [[DEFAULT:%.*]] [ +; CHECK-NEXT: i32 0, label [[EXIT:%.*]] +; CHECK-NEXT: i32 1, label [[CASE1:%.*]] +; CHECK-NEXT: i32 2, label [[CASE2:%.*]] +; CHECK-NEXT: ] +; CHECK: case1: +; CHECK-NEXT: br label [[EXIT]] +; CHECK: case2: +; CHECK-NEXT: br label [[EXIT]] +; CHECK: default: +; CHECK-NEXT: unreachable +; CHECK: exit: +; CHECK-NEXT: [[RES:%.*]] = phi i32 [ 2, [[CASE1]] ], [ 3, [[CASE2]] ], [ 1, [[ENTRY:%.*]] ] +; CHECK-NEXT: call void @llvm.assume(i1 true) +; CHECK-NEXT: ret i32 [[RES]] +; +entry: + switch i32 %cond, label %default [ + i32 0, label %case0 + i32 1, label %case1 + i32 2, label %case2 + ] + +case0: + br label %exit + +case1: + br label %exit + +case2: + br label %exit + +default: + br label %exit + +exit: + %bool = phi i1 [ false, %default ], [ true, %case0 ], [ true, %case1 ], [ true, %case2 ] + %res = phi i32 [ 0, %default ], [ 1, %case0 ], [ 2, %case1 ], [ 3, %case2 ] + call void @llvm.assume(i1 %bool) + ret i32 %res +} + +define i32 @test_assume_undef(i32 %cond) { +; CHECK-LABEL: @test_assume_undef( +; CHECK-NEXT: entry: +; CHECK-NEXT: switch i32 [[COND:%.*]], label [[DEFAULT:%.*]] [ +; CHECK-NEXT: i32 0, label [[EXIT:%.*]] +; CHECK-NEXT: i32 1, label [[CASE1:%.*]] +; CHECK-NEXT: i32 2, label [[CASE2:%.*]] +; CHECK-NEXT: ] +; CHECK: case1: +; CHECK-NEXT: br label [[EXIT]] +; CHECK: case2: +; CHECK-NEXT: br label [[EXIT]] +; CHECK: default: +; CHECK-NEXT: unreachable +; CHECK: exit: +; CHECK-NEXT: [[RES:%.*]] = phi i32 [ 2, [[CASE1]] ], [ 3, [[CASE2]] ], [ 1, [[ENTRY:%.*]] ] +; CHECK-NEXT: call void @llvm.assume(i1 true) +; CHECK-NEXT: ret i32 [[RES]] +; +entry: + switch i32 %cond, label %default [ + i32 0, label %case0 + i32 1, label %case1 + i32 2, label %case2 + ] + +case0: + br label %exit + +case1: + br label %exit + +case2: + br label %exit + +default: + br label %exit + +exit: + %bool = phi i1 [ undef, %default ], [ true, %case0 ], [ true, %case1 ], [ true, %case2 ] + %res = phi i32 [ 0, %default ], [ 1, %case0 ], [ 2, %case1 ], [ 3, %case2 ] + call void @llvm.assume(i1 %bool) + ret i32 %res +} + +define i32 @test_assume_var(i32 %cond, i1 %var) { +; CHECK-LABEL: @test_assume_var( +; CHECK-NEXT: entry: +; CHECK-NEXT: switch i32 [[COND:%.*]], label [[DEFAULT:%.*]] [ +; CHECK-NEXT: i32 0, label [[EXIT:%.*]] +; CHECK-NEXT: i32 1, label [[CASE1:%.*]] +; CHECK-NEXT: i32 2, label [[CASE2:%.*]] +; CHECK-NEXT: ] +; CHECK: case1: +; CHECK-NEXT: br label [[EXIT]] +; CHECK: case2: +; CHECK-NEXT: br label [[EXIT]] +; CHECK: default: +; CHECK-NEXT: br label [[EXIT]] +; CHECK: exit: +; CHECK-NEXT: [[BOOL:%.*]] = phi i1 [ [[VAR:%.*]], [[DEFAULT]] ], [ true, [[CASE1]] ], [ true, [[CASE2]] ], [ true, [[ENTRY:%.*]] ] +; CHECK-NEXT: [[RES:%.*]] = phi i32 [ 0, [[DEFAULT]] ], [ 2, [[CASE1]] ], [ 3, [[CASE2]] ], [ 1, [[ENTRY]] ] +; CHECK-NEXT: call void @llvm.assume(i1 [[BOOL]]) +; CHECK-NEXT: ret i32 [[RES]] +; +entry: + switch i32 %cond, label %default [ + i32 0, label %case0 + i32 1, label %case1 + i32 2, label %case2 + ] + +case0: + br label %exit +case1: + br label %exit + +case2: + br label %exit + +default: + br label %exit + +exit: + %bool = phi i1 [ %var, %default ], [ true, %case0 ], [ true, %case1 ], [ true, %case2 ] + %res = phi i32 [ 0, %default ], [ 1, %case0 ], [ 2, %case1 ], [ 3, %case2 ] + call void @llvm.assume(i1 %bool) + ret i32 %res +} + +define i32 @test_assume_bundle_nonnull(i32 %cond, ptr nonnull %p) { +; CHECK-LABEL: @test_assume_bundle_nonnull( +; CHECK-NEXT: entry: +; CHECK-NEXT: switch i32 [[COND:%.*]], label [[DEFAULT:%.*]] [ +; CHECK-NEXT: i32 0, label [[EXIT:%.*]] +; CHECK-NEXT: i32 1, label [[CASE1:%.*]] +; CHECK-NEXT: i32 2, label [[CASE2:%.*]] +; CHECK-NEXT: ] +; CHECK: case1: +; CHECK-NEXT: br label [[EXIT]] +; CHECK: case2: +; CHECK-NEXT: br label [[EXIT]] +; CHECK: default: +; CHECK-NEXT: br label [[EXIT]] +; CHECK: exit: +; CHECK-NEXT: [[PTR:%.*]] = phi ptr [ null, [[DEFAULT]] ], [ [[P:%.*]], [[CASE1]] ], [ [[P]], [[CASE2]] ], [ [[P]], [[ENTRY:%.*]] ] +; CHECK-NEXT: [[RES:%.*]] = phi i32 [ 0, [[DEFAULT]] ], [ 2, [[CASE1]] ], [ 3, [[CASE2]] ], [ 1, [[ENTRY]] ] +; CHECK-NEXT: call void @llvm.assume(i1 true) [ "nonnull"(ptr [[PTR]]) ] +; CHECK-NEXT: ret i32 [[RES]] +; +entry: + switch i32 %cond, label %default [ + i32 0, label %case0 + i32 1, label %case1 + i32 2, label %case2 + ] + +case0: + br label %exit + +case1: + br label %exit + +case2: + br label %exit + +default: + br label %exit + +exit: + %ptr = phi ptr [ null, %default ], [ %p, %case0 ], [ %p, %case1 ], [ %p, %case2 ] + %res = phi i32 [ 0, %default ], [ 1, %case0 ], [ 2, %case1 ], [ 3, %case2 ] + call void @llvm.assume(i1 true) [ "nonnull"(ptr %ptr) ] + ret i32 %res +} + +define i32 @test_assume_bundle_align(i32 %cond, ptr nonnull %p) { +; CHECK-LABEL: @test_assume_bundle_align( +; CHECK-NEXT: entry: +; CHECK-NEXT: switch i32 [[COND:%.*]], label [[DEFAULT:%.*]] [ +; CHECK-NEXT: i32 0, label [[EXIT:%.*]] +; CHECK-NEXT: i32 1, label [[CASE1:%.*]] +; CHECK-NEXT: i32 2, label [[CASE2:%.*]] +; CHECK-NEXT: ] +; CHECK: case1: +; CHECK-NEXT: br label [[EXIT]] +; CHECK: case2: +; CHECK-NEXT: br label [[EXIT]] +; CHECK: default: +; CHECK-NEXT: br label [[EXIT]] +; CHECK: exit: +; CHECK-NEXT: [[PTR:%.*]] = phi ptr [ null, [[DEFAULT]] ], [ [[P:%.*]], [[CASE1]] ], [ [[P]], [[CASE2]] ], [ [[P]], [[ENTRY:%.*]] ] +; CHECK-NEXT: [[RES:%.*]] = phi i32 [ 0, [[DEFAULT]] ], [ 2, [[CASE1]] ], [ 3, [[CASE2]] ], [ 1, [[ENTRY]] ] +; CHECK-NEXT: call void @llvm.assume(i1 true) [ "align"(ptr [[PTR]], i32 8) ] +; CHECK-NEXT: ret i32 [[RES]] +; +entry: + switch i32 %cond, label %default [ + i32 0, label %case0 + i32 1, label %case1 + i32 2, label %case2 + ] + +case0: + br label %exit + +case1: + br label %exit + +case2: + br label %exit + +default: + br label %exit + +exit: + %ptr = phi ptr [ null, %default ], [ %p, %case0 ], [ %p, %case1 ], [ %p, %case2 ] + %res = phi i32 [ 0, %default ], [ 1, %case0 ], [ 2, %case1 ], [ 3, %case2 ] + call void @llvm.assume(i1 true) [ "align"(ptr %ptr, i32 8) ] + ret i32 %res +} attributes #0 = { null_pointer_is_valid } ;. diff --git a/llvm/test/Transforms/SimplifyCFG/hoist-dbgvalue-inlined.ll b/llvm/test/Transforms/SimplifyCFG/hoist-dbgvalue-inlined.ll index e00d1daf71de58c7ec8472bd84d4f142bafd8e27..5af73e789f11ce83fb89195ba1dd141f510defba 100644 --- a/llvm/test/Transforms/SimplifyCFG/hoist-dbgvalue-inlined.ll +++ b/llvm/test/Transforms/SimplifyCFG/hoist-dbgvalue-inlined.ll @@ -9,7 +9,6 @@ init: ; CHECK: %vala = load i64, ptr %ptr ; CHECK-NEXT: call void @llvm.dbg.value(metadata i64 %vala, metadata [[MD:![0-9]*]] -; CHECK-NEXT: call void @llvm.dbg.value(metadata i64 %vala, metadata [[MD]] ; CHECK-NEXT: %valbmasked = and i64 %vala, 1 a: ; preds = %init diff --git a/llvm/test/Transforms/SimplifyCFG/hoist-dbgvalue.ll b/llvm/test/Transforms/SimplifyCFG/hoist-dbgvalue.ll index af7da45ec089cccb6d610ad020e5923c2b77b397..c5d723c4e3dd6173cfe8eb5f9bbf905651428b7d 100644 --- a/llvm/test/Transforms/SimplifyCFG/hoist-dbgvalue.ll +++ b/llvm/test/Transforms/SimplifyCFG/hoist-dbgvalue.ll @@ -47,7 +47,6 @@ define i1 @hoist_with_debug2(i32 %x) !dbg !22 { ; CHECK-NEXT: entry: ; CHECK-NEXT: [[TOBOOL_NOT:%.*]] = icmp ugt i32 [[X:%.*]], 2 ; CHECK-NEXT: call void @llvm.dbg.value(metadata i32 [[X]], metadata [[META21:![0-9]+]], metadata !DIExpression()), !dbg [[DBG23:![0-9]+]] -; CHECK-NEXT: call void @llvm.dbg.value(metadata i32 [[X]], metadata [[META21]], metadata !DIExpression()), !dbg [[DBG23]] ; CHECK-NEXT: [[DOT:%.*]] = select i1 [[TOBOOL_NOT]], i1 false, i1 true ; CHECK-NEXT: ret i1 [[DOT]] ; diff --git a/llvm/test/Transforms/SimplifyCFG/mmra.ll b/llvm/test/Transforms/SimplifyCFG/mmra.ll new file mode 100644 index 0000000000000000000000000000000000000000..6670657471376bdbb494a355f551341f0f7a37f5 --- /dev/null +++ b/llvm/test/Transforms/SimplifyCFG/mmra.ll @@ -0,0 +1,150 @@ +; NOTE: Assertions have been autogenerated by utils/update_test_checks.py UTC_ARGS: --version 4 +; RUN: opt -passes=simplifycfg -simplifycfg-require-and-preserve-domtree=1 -S %s | FileCheck %s + +; RUN: opt -passes='simplifycfg,verify' -S %s | FileCheck %s + +declare void @clobber1() +declare void @clobber2() + +define void @sink(ptr %arg, i1 %c) { +; CHECK-LABEL: define void @sink( +; CHECK-SAME: ptr [[ARG:%.*]], i1 [[C:%.*]]) { +; CHECK-NEXT: bb: +; CHECK-NEXT: br i1 [[C]], label [[THEN:%.*]], label [[ELSE:%.*]] +; CHECK: then: +; CHECK-NEXT: call void @clobber1() +; CHECK-NEXT: store ptr null, ptr [[ARG]], align 8 +; CHECK-NEXT: br label [[EXIT:%.*]] +; CHECK: else: +; CHECK-NEXT: call void @clobber2() +; CHECK-NEXT: store ptr null, ptr [[ARG]], align 8, !mmra [[META0:![0-9]+]] +; CHECK-NEXT: br label [[EXIT]] +; CHECK: exit: +; CHECK-NEXT: ret void +; +bb: + br i1 %c, label %then, label %else + +then: + call void @clobber1() + store ptr null, ptr %arg, align 8 + br label %exit + +else: + call void @clobber2() + store ptr null, ptr %arg, align 8, !mmra !0 + br label %exit + +exit: + ret void +} + +define void @hoist_store(ptr %arg, i1 %c) { +; CHECK-LABEL: define void @hoist_store( +; CHECK-SAME: ptr [[ARG:%.*]], i1 [[C:%.*]]) { +; CHECK-NEXT: bb: +; CHECK-NEXT: br i1 [[C]], label [[THEN:%.*]], label [[ELSE:%.*]] +; CHECK: then: +; CHECK-NEXT: store ptr null, ptr [[ARG]], align 8 +; CHECK-NEXT: call void @clobber1() +; CHECK-NEXT: br label [[EXIT:%.*]] +; CHECK: else: +; CHECK-NEXT: store ptr null, ptr [[ARG]], align 8, !mmra [[META0]] +; CHECK-NEXT: call void @clobber2() +; CHECK-NEXT: br label [[EXIT]] +; CHECK: exit: +; CHECK-NEXT: ret void +; +bb: + br i1 %c, label %then, label %else + +then: + store ptr null, ptr %arg, align 8 + call void @clobber1() + br label %exit + +else: + store ptr null, ptr %arg, align 8, !mmra !0 + call void @clobber2() + br label %exit + +exit: + ret void +} + +define ptr @sink_load(ptr %arg, i1 %c) { +; CHECK-LABEL: define ptr @sink_load( +; CHECK-SAME: ptr [[ARG:%.*]], i1 [[C:%.*]]) { +; CHECK-NEXT: bb: +; CHECK-NEXT: br i1 [[C]], label [[THEN:%.*]], label [[ELSE:%.*]] +; CHECK: then: +; CHECK-NEXT: call void @clobber1() +; CHECK-NEXT: [[L1:%.*]] = load ptr, ptr [[ARG]], align 8 +; CHECK-NEXT: br label [[EXIT:%.*]] +; CHECK: else: +; CHECK-NEXT: call void @clobber2() +; CHECK-NEXT: [[L2:%.*]] = load ptr, ptr [[ARG]], align 8, !mmra [[META0]] +; CHECK-NEXT: br label [[EXIT]] +; CHECK: exit: +; CHECK-NEXT: [[P:%.*]] = phi ptr [ [[L1]], [[THEN]] ], [ [[L2]], [[ELSE]] ] +; CHECK-NEXT: ret ptr [[P]] +; +bb: + br i1 %c, label %then, label %else + +then: + call void @clobber1() + %l1 = load ptr, ptr %arg, align 8 + br label %exit + +else: + call void @clobber2() + %l2 = load ptr, ptr %arg, align 8, !mmra !0 + br label %exit + +exit: + %p = phi ptr [ %l1, %then ], [ %l2, %else ] + ret ptr %p +} + +define ptr @hoist_load(ptr %arg, i1 %c) { +; CHECK-LABEL: define ptr @hoist_load( +; CHECK-SAME: ptr [[ARG:%.*]], i1 [[C:%.*]]) { +; CHECK-NEXT: bb: +; CHECK-NEXT: br i1 [[C]], label [[THEN:%.*]], label [[ELSE:%.*]] +; CHECK: then: +; CHECK-NEXT: [[L1:%.*]] = load ptr, ptr [[ARG]], align 8 +; CHECK-NEXT: call void @clobber1() +; CHECK-NEXT: br label [[EXIT:%.*]] +; CHECK: else: +; CHECK-NEXT: [[L2:%.*]] = load ptr, ptr [[ARG]], align 8, !mmra [[META0]] +; CHECK-NEXT: call void @clobber2() +; CHECK-NEXT: br label [[EXIT]] +; CHECK: exit: +; CHECK-NEXT: [[P:%.*]] = phi ptr [ [[L1]], [[THEN]] ], [ [[L2]], [[ELSE]] ] +; CHECK-NEXT: ret ptr [[P]] +; +bb: + br i1 %c, label %then, label %else + +then: + %l1 = load ptr, ptr %arg, align 8 + call void @clobber1() + br label %exit + +else: + %l2 = load ptr, ptr %arg, align 8, !mmra !0 + call void @clobber2() + br label %exit + +exit: + %p = phi ptr [ %l1, %then ], [ %l2, %else ] + ret ptr %p +} + + +!0 = !{!"foo", !"bar"} + +;. +; CHECK: [[META0]] = !{!"foo", !"bar"} +;. diff --git a/llvm/test/Transforms/VectorCombine/AArch64/shuffletoidentity.ll b/llvm/test/Transforms/VectorCombine/AArch64/shuffletoidentity.ll index 4cc7d5f253289ba1c312074c2ad87e2bee1d4474..6a81964b917edf0af6638dc79984eb4a75288129 100644 --- a/llvm/test/Transforms/VectorCombine/AArch64/shuffletoidentity.ll +++ b/llvm/test/Transforms/VectorCombine/AArch64/shuffletoidentity.ll @@ -5,7 +5,7 @@ target triple = "aarch64" define <8 x i8> @trivial(<8 x i8> %a) { ; CHECK-LABEL: @trivial( -; CHECK-NEXT: ret <8 x i8> [[R:%.*]] +; CHECK-NEXT: ret <8 x i8> [[A:%.*]] ; %ab = shufflevector <8 x i8> %a, <8 x i8> poison, <4 x i32> %at = shufflevector <8 x i8> %a, <8 x i8> poison, <4 x i32> diff --git a/llvm/test/Transforms/VectorCombine/X86/shuffle-of-binops.ll b/llvm/test/Transforms/VectorCombine/X86/shuffle-of-binops.ll index 5c4ad4f1fcc4e5ca3f2d418e3b422f470e7c4d2f..c423053a9a4839adaa7b2def3e405e65e2f3856a 100644 --- a/llvm/test/Transforms/VectorCombine/X86/shuffle-of-binops.ll +++ b/llvm/test/Transforms/VectorCombine/X86/shuffle-of-binops.ll @@ -25,9 +25,9 @@ define <4 x float> @shuf_fdiv_v4f32_yy(<4 x float> %x, <4 x float> %y, <4 x floa define <4 x i32> @shuf_add_v4i32_xx(<4 x i32> %x, <4 x i32> %y, <4 x i32> %z) { ; CHECK-LABEL: define <4 x i32> @shuf_add_v4i32_xx( ; CHECK-SAME: <4 x i32> [[X:%.*]], <4 x i32> [[Y:%.*]], <4 x i32> [[Z:%.*]]) #[[ATTR0]] { -; CHECK-NEXT: [[TMP1:%.*]] = shufflevector <4 x i32> [[X]], <4 x i32> poison, <4 x i32> -; CHECK-NEXT: [[R1:%.*]] = shufflevector <4 x i32> [[Y]], <4 x i32> [[Z]], <4 x i32> -; CHECK-NEXT: [[R2:%.*]] = add <4 x i32> [[TMP1]], [[R1]] +; CHECK-NEXT: [[B0:%.*]] = add <4 x i32> [[X]], [[Y]] +; CHECK-NEXT: [[B1:%.*]] = add <4 x i32> [[X]], [[Z]] +; CHECK-NEXT: [[R2:%.*]] = shufflevector <4 x i32> [[B0]], <4 x i32> [[B1]], <4 x i32> ; CHECK-NEXT: ret <4 x i32> [[R2]] ; %b0 = add <4 x i32> %x, %y @@ -36,15 +36,22 @@ define <4 x i32> @shuf_add_v4i32_xx(<4 x i32> %x, <4 x i32> %y, <4 x i32> %z) { ret <4 x i32> %r } -; For commutative instructions, common operand may be swapped. +; For commutative instructions, common operand may be swapped (SSE - expensive fmul vs AVX - cheap fmul) define <4 x float> @shuf_fmul_v4f32_xx_swap(<4 x float> %x, <4 x float> %y, <4 x float> %z) { -; CHECK-LABEL: define <4 x float> @shuf_fmul_v4f32_xx_swap( -; CHECK-SAME: <4 x float> [[X:%.*]], <4 x float> [[Y:%.*]], <4 x float> [[Z:%.*]]) #[[ATTR0]] { -; CHECK-NEXT: [[TMP1:%.*]] = shufflevector <4 x float> [[Y]], <4 x float> [[Z]], <4 x i32> -; CHECK-NEXT: [[TMP2:%.*]] = shufflevector <4 x float> [[X]], <4 x float> poison, <4 x i32> -; CHECK-NEXT: [[R:%.*]] = fmul <4 x float> [[TMP1]], [[TMP2]] -; CHECK-NEXT: ret <4 x float> [[R]] +; SSE-LABEL: define <4 x float> @shuf_fmul_v4f32_xx_swap( +; SSE-SAME: <4 x float> [[X:%.*]], <4 x float> [[Y:%.*]], <4 x float> [[Z:%.*]]) #[[ATTR0]] { +; SSE-NEXT: [[TMP1:%.*]] = shufflevector <4 x float> [[Y]], <4 x float> [[Z]], <4 x i32> +; SSE-NEXT: [[TMP2:%.*]] = shufflevector <4 x float> [[X]], <4 x float> poison, <4 x i32> +; SSE-NEXT: [[R:%.*]] = fmul <4 x float> [[TMP1]], [[TMP2]] +; SSE-NEXT: ret <4 x float> [[R]] +; +; AVX-LABEL: define <4 x float> @shuf_fmul_v4f32_xx_swap( +; AVX-SAME: <4 x float> [[X:%.*]], <4 x float> [[Y:%.*]], <4 x float> [[Z:%.*]]) #[[ATTR0]] { +; AVX-NEXT: [[B0:%.*]] = fmul <4 x float> [[X]], [[Y]] +; AVX-NEXT: [[B1:%.*]] = fmul <4 x float> [[Z]], [[X]] +; AVX-NEXT: [[R:%.*]] = shufflevector <4 x float> [[B0]], <4 x float> [[B1]], <4 x i32> +; AVX-NEXT: ret <4 x float> [[R]] ; %b0 = fmul <4 x float> %x, %y %b1 = fmul <4 x float> %z, %x @@ -57,9 +64,9 @@ define <4 x float> @shuf_fmul_v4f32_xx_swap(<4 x float> %x, <4 x float> %y, <4 x define <2 x i64> @shuf_and_v2i64_yy_swap(<2 x i64> %x, <2 x i64> %y, <2 x i64> %z) { ; CHECK-LABEL: define <2 x i64> @shuf_and_v2i64_yy_swap( ; CHECK-SAME: <2 x i64> [[X:%.*]], <2 x i64> [[Y:%.*]], <2 x i64> [[Z:%.*]]) #[[ATTR0]] { -; CHECK-NEXT: [[TMP1:%.*]] = shufflevector <2 x i64> [[Y]], <2 x i64> poison, <2 x i32> -; CHECK-NEXT: [[TMP2:%.*]] = shufflevector <2 x i64> [[X]], <2 x i64> [[Z]], <2 x i32> -; CHECK-NEXT: [[R:%.*]] = and <2 x i64> [[TMP1]], [[TMP2]] +; CHECK-NEXT: [[B0:%.*]] = and <2 x i64> [[X]], [[Y]] +; CHECK-NEXT: [[B1:%.*]] = and <2 x i64> [[Y]], [[Z]] +; CHECK-NEXT: [[R:%.*]] = shufflevector <2 x i64> [[B0]], <2 x i64> [[B1]], <2 x i32> ; CHECK-NEXT: ret <2 x i64> [[R]] ; %b0 = and <2 x i64> %x, %y @@ -84,15 +91,22 @@ define <4 x i32> @shuf_shl_v4i32_xx(<4 x i32> %x, <4 x i32> %y, <4 x i32> %z) { ret <4 x i32> %r } -; negative test - common operand, but not commutable +; common operand, but not commutable (SSE - expensive vector shift vs AVX2 - cheap vector shift) define <4 x i32> @shuf_shl_v4i32_xx_swap(<4 x i32> %x, <4 x i32> %y, <4 x i32> %z) { -; CHECK-LABEL: define <4 x i32> @shuf_shl_v4i32_xx_swap( -; CHECK-SAME: <4 x i32> [[X:%.*]], <4 x i32> [[Y:%.*]], <4 x i32> [[Z:%.*]]) #[[ATTR0]] { -; CHECK-NEXT: [[B0:%.*]] = shl <4 x i32> [[X]], [[Y]] -; CHECK-NEXT: [[B1:%.*]] = shl <4 x i32> [[Z]], [[X]] -; CHECK-NEXT: [[R1:%.*]] = shufflevector <4 x i32> [[B0]], <4 x i32> [[B1]], <4 x i32> -; CHECK-NEXT: ret <4 x i32> [[R1]] +; SSE-LABEL: define <4 x i32> @shuf_shl_v4i32_xx_swap( +; SSE-SAME: <4 x i32> [[X:%.*]], <4 x i32> [[Y:%.*]], <4 x i32> [[Z:%.*]]) #[[ATTR0]] { +; SSE-NEXT: [[TMP1:%.*]] = shufflevector <4 x i32> [[X]], <4 x i32> [[Z]], <4 x i32> +; SSE-NEXT: [[TMP2:%.*]] = shufflevector <4 x i32> [[Y]], <4 x i32> [[X]], <4 x i32> +; SSE-NEXT: [[R:%.*]] = shl <4 x i32> [[TMP1]], [[TMP2]] +; SSE-NEXT: ret <4 x i32> [[R]] +; +; AVX-LABEL: define <4 x i32> @shuf_shl_v4i32_xx_swap( +; AVX-SAME: <4 x i32> [[X:%.*]], <4 x i32> [[Y:%.*]], <4 x i32> [[Z:%.*]]) #[[ATTR0]] { +; AVX-NEXT: [[B0:%.*]] = shl <4 x i32> [[X]], [[Y]] +; AVX-NEXT: [[B1:%.*]] = shl <4 x i32> [[Z]], [[X]] +; AVX-NEXT: [[R:%.*]] = shufflevector <4 x i32> [[B0]], <4 x i32> [[B1]], <4 x i32> +; AVX-NEXT: ret <4 x i32> [[R]] ; %b0 = shl <4 x i32> %x, %y %b1 = shl <4 x i32> %z, %x @@ -116,7 +130,7 @@ define <2 x i64> @shuf_sub_add_v2i64_yy(<2 x i64> %x, <2 x i64> %y, <2 x i64> %z ret <2 x i64> %r } -; negative test - type change via shuffle +; type change via shuffle define <8 x float> @shuf_fmul_v4f32_xx_type(<4 x float> %x, <4 x float> %y, <4 x float> %z) { ; CHECK-LABEL: define <8 x float> @shuf_fmul_v4f32_xx_type( @@ -168,18 +182,18 @@ define <4 x i32> @shuf_mul_v4i32_yy_use2(<4 x i32> %x, <4 x i32> %y, <4 x i32> % ret <4 x i32> %r } -; negative test - must have matching operand +; non-matching operands (not commutable) -define <4 x float> @shuf_fadd_v4f32_no_common_op(<4 x float> %x, <4 x float> %y, <4 x float> %z, <4 x float> %w) { -; CHECK-LABEL: define <4 x float> @shuf_fadd_v4f32_no_common_op( +define <4 x float> @shuf_fdiv_v4f32_no_common_op(<4 x float> %x, <4 x float> %y, <4 x float> %z, <4 x float> %w) { +; CHECK-LABEL: define <4 x float> @shuf_fdiv_v4f32_no_common_op( ; CHECK-SAME: <4 x float> [[X:%.*]], <4 x float> [[Y:%.*]], <4 x float> [[Z:%.*]], <4 x float> [[W:%.*]]) #[[ATTR0]] { -; CHECK-NEXT: [[B0:%.*]] = fadd <4 x float> [[X]], [[Y]] -; CHECK-NEXT: [[B1:%.*]] = fadd <4 x float> [[Z]], [[W]] -; CHECK-NEXT: [[R:%.*]] = shufflevector <4 x float> [[B0]], <4 x float> [[B1]], <4 x i32> +; CHECK-NEXT: [[TMP1:%.*]] = shufflevector <4 x float> [[X]], <4 x float> [[Z]], <4 x i32> +; CHECK-NEXT: [[TMP2:%.*]] = shufflevector <4 x float> [[Y]], <4 x float> [[W]], <4 x i32> +; CHECK-NEXT: [[R:%.*]] = fdiv <4 x float> [[TMP1]], [[TMP2]] ; CHECK-NEXT: ret <4 x float> [[R]] ; - %b0 = fadd <4 x float> %x, %y - %b1 = fadd <4 x float> %z, %w + %b0 = fdiv <4 x float> %x, %y + %b1 = fdiv <4 x float> %z, %w %r = shufflevector <4 x float> %b0, <4 x float> %b1, <4 x i32> ret <4 x float> %r } @@ -216,6 +230,3 @@ define <4 x i32> @shuf_srem_v4i32_poison(<4 x i32> %a0, <4 x i32> %a1) { ret <4 x i32> %r } -;; NOTE: These prefixes are unused and the list is autogenerated. Do not add tests below this line: -; AVX: {{.*}} -; SSE: {{.*}} diff --git a/llvm/test/Verifier/mmra-allowed.ll b/llvm/test/Verifier/mmra-allowed.ll new file mode 100644 index 0000000000000000000000000000000000000000..76dff3f207cdf3cd848046c57ea58999a43df08b --- /dev/null +++ b/llvm/test/Verifier/mmra-allowed.ll @@ -0,0 +1,31 @@ +; RUN: opt -S -passes=verify < %s + +; This file contains MMRA metadata that is okay and should pass the verifier. + +define void @test(ptr %ptr) { + %ld = load i8, ptr %ptr, !mmra !0 + store i8 1, ptr %ptr, !mmra !1 + call void @writesMem(), !mmra !2 + call void @readsMem(), !mmra !2 + fence release, !mmra !0 + %rmw.1 = atomicrmw add ptr %ptr, i8 0 release, !mmra !0 + %rmw.2 = atomicrmw add ptr %ptr, i8 0 acquire, !mmra !0 + %pair = cmpxchg ptr %ptr, i8 0, i8 1 acquire acquire, !mmra !1 + %ld.atomic = load atomic i8, ptr %ptr acquire, align 4, !mmra !1 + store atomic i8 1, ptr %ptr release, align 4, !mmra !2 + %mld = call <2 x i64> @llvm.vp.load.v2i64.p0(ptr undef, <2 x i1> undef, i32 undef), !mmra !2 + ; TODO: barrier + ret void +} + +declare <2 x i64> @llvm.vp.load.v2i64.p0(ptr, <2 x i1>, i32) + +declare void @readsMem(ptr) #0 +declare void @writesMem(ptr) #1 + +attributes #0 = { memory(read) } +attributes #1 = { memory(write) } + +!0 = !{!"scope", !"workgroup"} +!1 = !{!"as", !"private"} +!2 = !{!0, !1} diff --git a/llvm/test/Verifier/mmra.ll b/llvm/test/Verifier/mmra.ll new file mode 100644 index 0000000000000000000000000000000000000000..b506d593a1c433f4e5b2151a3762049660c7f245 --- /dev/null +++ b/llvm/test/Verifier/mmra.ll @@ -0,0 +1,43 @@ +; RUN: not opt -S -passes=verify < %s 2>&1 | FileCheck %s + +define void @foo(ptr %ptr, i32 %x) { + + ; CHECK: !mmra metadata attached to unexpected instruction kind + ; CHECK-NEXT: %bad.add + %bad.add = add i32 %x, 42, !mmra !{} + + ; CHECK: !mmra metadata attached to unexpected instruction kind + ; CHECK-NEXT: %bad.sub + %bad.sub = sub i32 %x, 42, !mmra !{} + + ; CHECK: !mmra metadata attached to unexpected instruction kind + ; CHECK-NEXT: %bad.sqrt + %bad.sqrt = call float @llvm.sqrt.f32(float undef), !mmra !{} + + ; CHECK: !mmra expected to be a metadata tuple + ; CHECK-NEXT: %bad.md0 + ; CHECK-NEXT: !DIFile + %bad.md0 = load atomic i32, ptr %ptr acquire, align 4, !mmra !0 + + ; CHECK: !mmra expected to be a metadata tuple + ; CHECK-NEXT: %bad.md1 + ; CHECK-NEXT: !DIFile + %bad.md1 = load atomic i32, ptr %ptr acquire, align 4, !mmra !0 + + ; CHECK: !mmra metadata tuple operand is not an MMRA tag + ; CHECK-NEXT: %bad.md2 + ; CHECK-NEXT: !"foo" + %bad.md2 = load atomic i32, ptr %ptr acquire, align 4, !mmra !1 + + ; CHECK: !mmra metadata tuple operand is not an MMRA tag + ; CHECK-NEXT: %bad.md3 + ; CHECK-NEXT: !"baz" + %bad.md3 = load atomic i32, ptr %ptr acquire, align 4, !mmra !2 + ret void +} + +declare float @llvm.sqrt.f32(float) + +!0 = !DIFile(filename: "test.c", directory: "") +!1 = !{!"foo", !"bar", !"bux"} +!2 = !{!"baz", !0} diff --git a/llvm/test/lit.cfg.py b/llvm/test/lit.cfg.py index 4c05317036d1a3802ad0c1160351f1f434967164..affd87b98c1410b4d08f3d0ad4250ecb8815a436 100644 --- a/llvm/test/lit.cfg.py +++ b/llvm/test/lit.cfg.py @@ -306,6 +306,9 @@ def enable_ptxas(ptxas_executable): (11, 8), (12, 0), (12, 1), + (12, 2), + (12, 3), + (12, 4), ] def version_int(ver): diff --git a/llvm/test/tools/llvm-profdata/memprof-merge-v0.test b/llvm/test/tools/llvm-profdata/memprof-merge-v0.test index 03ccbdd42efdad9acbf02aa543f4fa45074b08d6..28f65e0781bc630297ae9fc8bb02517147b4dc35 100644 --- a/llvm/test/tools/llvm-profdata/memprof-merge-v0.test +++ b/llvm/test/tools/llvm-profdata/memprof-merge-v0.test @@ -16,6 +16,9 @@ RUN: llvm-profdata show %t.prof.v1 | FileCheck %s RUN: llvm-profdata merge %t.proftext %p/Inputs/basic.memprofraw --memprof-version=2 --profiled-binary %p/Inputs/basic.memprofexe -o %t.prof.v2 RUN: llvm-profdata show %t.prof.v2 | FileCheck %s +RUN: llvm-profdata merge %t.proftext %p/Inputs/basic.memprofraw --memprof-version=2 --memprof-full-schema --profiled-binary %p/Inputs/basic.memprofexe -o %t.prof.v2 +RUN: llvm-profdata show %t.prof.v2 | FileCheck %s + For now we only check the validity of the instrumented profile since we don't have a way to display the contents of the memprof indexed format yet. diff --git a/llvm/tools/gold/gold-plugin.cpp b/llvm/tools/gold/gold-plugin.cpp index b8a33f74bd570f4d185213c275446562998780cd..5503f7343cb6725f953bba30b121ce5e1bd0cea0 100644 --- a/llvm/tools/gold/gold-plugin.cpp +++ b/llvm/tools/gold/gold-plugin.cpp @@ -434,8 +434,10 @@ ld_plugin_status onload(ld_plugin_tv *tv) { // FIXME: When binutils 2.31 (containing gold 1.16) is the minimum // required version, this should be changed to: // get_wrap_symbols = tv->tv_u.tv_get_wrap_symbols; - get_wrap_symbols = - (ld_plugin_get_wrap_symbols)tv->tv_u.tv_message; +#pragma GCC diagnostic push +#pragma GCC diagnostic ignored "-Wcast-function-type" + get_wrap_symbols = (ld_plugin_get_wrap_symbols)tv->tv_u.tv_message; +#pragma GCC diagnostic pop break; default: break; diff --git a/llvm/tools/llvm-exegesis/lib/BenchmarkRunner.cpp b/llvm/tools/llvm-exegesis/lib/BenchmarkRunner.cpp index 498308e2edbe1fd541c27221dcff61c7164c2129..ed53f8fabb1751c2bad1c1b59af82ac425ab686b 100644 --- a/llvm/tools/llvm-exegesis/lib/BenchmarkRunner.cpp +++ b/llvm/tools/llvm-exegesis/lib/BenchmarkRunner.cpp @@ -18,6 +18,7 @@ #include "PerfHelper.h" #include "SubprocessMemory.h" #include "Target.h" +#include "llvm/ADT/ScopeExit.h" #include "llvm/ADT/StringExtras.h" #include "llvm/ADT/StringRef.h" #include "llvm/ADT/Twine.h" @@ -283,6 +284,7 @@ private: SmallVectorImpl &CounterValues, ArrayRef ValidationCounters, SmallVectorImpl &ValidationCounterValues) const { + auto WriteFDClose = make_scope_exit([WriteFD]() { close(WriteFD); }); const ExegesisTarget &ET = State.getExegesisTarget(); auto CounterOrError = ET.createCounter(CounterName, State, ValidationCounters, ChildPID); diff --git a/llvm/tools/llvm-exegesis/lib/SubprocessMemory.cpp b/llvm/tools/llvm-exegesis/lib/SubprocessMemory.cpp index 1d44e09ad61e1d5fd44c053328b08ce3d03b50aa..cda0440505020160a1b9267f69040b194900ad6b 100644 --- a/llvm/tools/llvm-exegesis/lib/SubprocessMemory.cpp +++ b/llvm/tools/llvm-exegesis/lib/SubprocessMemory.cpp @@ -8,6 +8,7 @@ #include "SubprocessMemory.h" #include "Error.h" +#include "llvm/ADT/ScopeExit.h" #include "llvm/Support/Error.h" #include "llvm/Support/FormatVariadic.h" #include @@ -56,6 +57,8 @@ Error SubprocessMemory::initializeSubprocessMemory(pid_t ProcessID) { return make_error( "Failed to create shared memory object for auxiliary memory: " + Twine(strerror(errno))); + auto AuxiliaryMemoryFDClose = + make_scope_exit([AuxiliaryMemoryFD]() { close(AuxiliaryMemoryFD); }); if (ftruncate(AuxiliaryMemoryFD, AuxiliaryMemorySize) != 0) { return make_error("Truncating the auxiliary memory failed: " + Twine(strerror(errno))); @@ -78,6 +81,8 @@ Error SubprocessMemory::addMemoryDefinition( return make_error( "Failed to create shared memory object for memory definition: " + Twine(strerror(errno))); + auto SharedMemoryFDClose = + make_scope_exit([SharedMemoryFD]() { close(SharedMemoryFD); }); if (ftruncate(SharedMemoryFD, MemVal.SizeBytes) != 0) { return make_error("Truncating a memory definiton failed: " + Twine(strerror(errno))); diff --git a/llvm/tools/llvm-jitlink/llvm-jitlink.cpp b/llvm/tools/llvm-jitlink/llvm-jitlink.cpp index 09b2a5900eb0b7f272747c0cf76c91ce037c8762..bff05b9ca4bebc90d93d8168b75c8fc962185f9c 100644 --- a/llvm/tools/llvm-jitlink/llvm-jitlink.cpp +++ b/llvm/tools/llvm-jitlink/llvm-jitlink.cpp @@ -807,8 +807,8 @@ static Expected> launchExecutor() { S.CreateMemoryManager = createSharedMemoryManager; return SimpleRemoteEPC::Create( - std::make_unique(), std::move(S), - FromExecutor[ReadEnd], ToExecutor[WriteEnd]); + std::make_unique(std::nullopt), + std::move(S), FromExecutor[ReadEnd], ToExecutor[WriteEnd]); #endif } @@ -897,7 +897,7 @@ static Expected> connectToExecutor() { S.CreateMemoryManager = createSharedMemoryManager; return SimpleRemoteEPC::Create( - std::make_unique(), + std::make_unique(std::nullopt), std::move(S), *SockFD, *SockFD); #endif } diff --git a/llvm/tools/llvm-profdata/llvm-profdata.cpp b/llvm/tools/llvm-profdata/llvm-profdata.cpp index 78daf9f7dc109a2429a38bf7fb34d0ca97f86750..ec046ebfab130b783fb37dab8417e5c6bd9786f3 100644 --- a/llvm/tools/llvm-profdata/llvm-profdata.cpp +++ b/llvm/tools/llvm-profdata/llvm-profdata.cpp @@ -308,6 +308,10 @@ cl::opt MemProfVersionRequested( clEnumValN(memprof::Version1, "1", "version 1"), clEnumValN(memprof::Version2, "2", "version 2"))); +cl::opt MemProfFullSchema( + "memprof-full-schema", cl::Hidden, cl::sub(MergeSubcommand), + cl::desc("Use the full schema for serialization"), cl::init(false)); + // Options specific to overlap subcommand. cl::opt BaseFilename(cl::Positional, cl::Required, cl::desc(""), @@ -600,7 +604,7 @@ struct WriterContext { SmallSet &WriterErrorCodes, uint64_t ReservoirSize = 0, uint64_t MaxTraceLength = 0) : Writer(IsSparse, ReservoirSize, MaxTraceLength, DoWritePrevVersion, - MemProfVersionRequested), + MemProfVersionRequested, MemProfFullSchema), ErrLock(ErrLock), WriterErrorCodes(WriterErrorCodes) {} }; diff --git a/llvm/tools/llvm-readtapi/llvm-readtapi.cpp b/llvm/tools/llvm-readtapi/llvm-readtapi.cpp index 80064ed9848517886600befbc4f0aef505c52c3e..1f183975d9481fdb13de926a8918bccaebc4e303 100644 --- a/llvm/tools/llvm-readtapi/llvm-readtapi.cpp +++ b/llvm/tools/llvm-readtapi/llvm-readtapi.cpp @@ -133,9 +133,7 @@ getInterfaceFile(const StringRef Filename, bool ResetBanner = true) { std::unique_ptr IF; switch (identify_magic(Buffer->getBuffer())) { case file_magic::macho_dynamically_linked_shared_lib: - LLVM_FALLTHROUGH; case file_magic::macho_dynamically_linked_shared_lib_stub: - LLVM_FALLTHROUGH; case file_magic::macho_universal_binary: IF = ExitOnErr(DylibReader::get(Buffer->getMemBufferRef())); break; diff --git a/llvm/unittests/Analysis/LoadsTest.cpp b/llvm/unittests/Analysis/LoadsTest.cpp index 0111cfeefa41aecf5a6920cd79d0d865e217e82e..5da3feaf762f37c945bce821cec313233d78a371 100644 --- a/llvm/unittests/Analysis/LoadsTest.cpp +++ b/llvm/unittests/Analysis/LoadsTest.cpp @@ -68,35 +68,49 @@ TEST(LoadsTest, CanReplacePointersIfEqual) { R"IR( @y = common global [1 x i32] zeroinitializer, align 4 @x = common global [1 x i32] zeroinitializer, align 4 - declare void @use(i32*) -define void @f(i32* %p) { +define void @f(i32* %p1, i32* %p2, i64 %i) { call void @use(i32* getelementptr inbounds ([1 x i32], [1 x i32]* @y, i64 0, i64 0)) - call void @use(i32* getelementptr inbounds (i32, i32* getelementptr inbounds ([1 x i32], [1 x i32]* @x, i64 0, i64 0), i64 1)) + + %p1_idx = getelementptr inbounds i32, i32* %p1, i64 %i + call void @use(i32* %p1_idx) + + %icmp = icmp eq i32* %p1, getelementptr inbounds ([1 x i32], [1 x i32]* @y, i64 0, i64 0) + %ptrInt = ptrtoint i32* %p1 to i64 ret void } )IR"); - const auto &DL = M->getDataLayout(); + const DataLayout &DL = M->getDataLayout(); auto *GV = M->getNamedValue("f"); ASSERT_TRUE(GV); auto *F = dyn_cast(GV); ASSERT_TRUE(F); - // NOTE: the implementation of canReplacePointersIfEqual is incomplete. - // Currently the only the cases it returns false for are really sound and - // returning true means unknown. - Value *P = &*F->arg_begin(); + Value *P1 = &*F->arg_begin(); + Value *P2 = F->getArg(1); + Value *NullPtr = Constant::getNullValue(P1->getType()); auto InstIter = F->front().begin(); - Value *ConstDerefPtr = *cast(&*InstIter)->arg_begin(); - // ConstDerefPtr is a constant pointer that is provably de-referenceable. We - // can replace an arbitrary pointer with it. - EXPECT_TRUE(canReplacePointersIfEqual(P, ConstDerefPtr, DL, nullptr)); + CallInst *UserOfY = cast(&*InstIter); + Value *ConstDerefPtr = UserOfY->getArgOperand(0); + // We cannot replace two pointers in arbitrary instructions unless we are + // replacing with null, a constant dereferencable pointer or they have the + // same underlying object. + EXPECT_FALSE(canReplacePointersIfEqual(ConstDerefPtr, P1, DL)); + EXPECT_FALSE(canReplacePointersIfEqual(P1, P2, DL)); + EXPECT_TRUE(canReplacePointersIfEqual(P1, ConstDerefPtr, DL)); + EXPECT_TRUE(canReplacePointersIfEqual(P1, NullPtr, DL)); + + GetElementPtrInst *BasedOnP1 = cast(&*++InstIter); + EXPECT_TRUE(canReplacePointersIfEqual(BasedOnP1, P1, DL)); + EXPECT_FALSE(canReplacePointersIfEqual(BasedOnP1, P2, DL)); - ++InstIter; - Value *ConstUnDerefPtr = *cast(&*InstIter)->arg_begin(); - // ConstUndDerefPtr is a constant pointer that is provably not - // de-referenceable. We cannot replace an arbitrary pointer with it. - EXPECT_FALSE( - canReplacePointersIfEqual(ConstDerefPtr, ConstUnDerefPtr, DL, nullptr)); + // We can replace two arbitrary pointers in icmp and ptrtoint instructions. + auto P1UseIter = P1->use_begin(); + const Use &PtrToIntUse = *P1UseIter; + const Use &IcmpUse = *++P1UseIter; + const Use &GEPUse = *++P1UseIter; + EXPECT_FALSE(canReplacePointersInUseIfEqual(GEPUse, P2, DL)); + EXPECT_TRUE(canReplacePointersInUseIfEqual(PtrToIntUse, P2, DL)); + EXPECT_TRUE(canReplacePointersInUseIfEqual(IcmpUse, P2, DL)); } diff --git a/llvm/unittests/CodeGen/MachineInstrTest.cpp b/llvm/unittests/CodeGen/MachineInstrTest.cpp index 49da0c38eefdca505a0f84b89103cb5e22bf2b19..8ea12a6ec6453cf6dc5a2361fe5359a00539bb56 100644 --- a/llvm/unittests/CodeGen/MachineInstrTest.cpp +++ b/llvm/unittests/CodeGen/MachineInstrTest.cpp @@ -18,6 +18,7 @@ #include "llvm/CodeGen/TargetSubtargetInfo.h" #include "llvm/IR/DebugInfoMetadata.h" #include "llvm/IR/IRBuilder.h" +#include "llvm/IR/MemoryModelRelaxationAnnotations.h" #include "llvm/IR/ModuleSlotTracker.h" #include "llvm/MC/MCAsmInfo.h" #include "llvm/MC/MCSymbol.h" @@ -277,12 +278,14 @@ TEST(MachineInstrExtraInfo, AddExtraInfo) { MCSymbol *Sym2 = MC->createTempSymbol("post_label", false); MDNode *HAM = MDNode::getDistinct(Ctx, std::nullopt); MDNode *PCS = MDNode::getDistinct(Ctx, std::nullopt); + MDNode *MMRA = MMRAMetadata::getTagMD(Ctx, "foo", "bar"); ASSERT_TRUE(MI->memoperands_empty()); ASSERT_FALSE(MI->getPreInstrSymbol()); ASSERT_FALSE(MI->getPostInstrSymbol()); ASSERT_FALSE(MI->getHeapAllocMarker()); ASSERT_FALSE(MI->getPCSections()); + ASSERT_FALSE(MI->getMMRAMetadata()); MI->setMemRefs(*MF, MMOs); ASSERT_TRUE(MI->memoperands().size() == 1); @@ -290,6 +293,7 @@ TEST(MachineInstrExtraInfo, AddExtraInfo) { ASSERT_FALSE(MI->getPostInstrSymbol()); ASSERT_FALSE(MI->getHeapAllocMarker()); ASSERT_FALSE(MI->getPCSections()); + ASSERT_FALSE(MI->getMMRAMetadata()); MI->setPreInstrSymbol(*MF, Sym1); ASSERT_TRUE(MI->memoperands().size() == 1); @@ -297,6 +301,7 @@ TEST(MachineInstrExtraInfo, AddExtraInfo) { ASSERT_FALSE(MI->getPostInstrSymbol()); ASSERT_FALSE(MI->getHeapAllocMarker()); ASSERT_FALSE(MI->getPCSections()); + ASSERT_FALSE(MI->getMMRAMetadata()); MI->setPostInstrSymbol(*MF, Sym2); ASSERT_TRUE(MI->memoperands().size() == 1); @@ -304,6 +309,7 @@ TEST(MachineInstrExtraInfo, AddExtraInfo) { ASSERT_TRUE(MI->getPostInstrSymbol() == Sym2); ASSERT_FALSE(MI->getHeapAllocMarker()); ASSERT_FALSE(MI->getPCSections()); + ASSERT_FALSE(MI->getMMRAMetadata()); MI->setHeapAllocMarker(*MF, HAM); ASSERT_TRUE(MI->memoperands().size() == 1); @@ -311,6 +317,7 @@ TEST(MachineInstrExtraInfo, AddExtraInfo) { ASSERT_TRUE(MI->getPostInstrSymbol() == Sym2); ASSERT_TRUE(MI->getHeapAllocMarker() == HAM); ASSERT_FALSE(MI->getPCSections()); + ASSERT_FALSE(MI->getMMRAMetadata()); MI->setPCSections(*MF, PCS); ASSERT_TRUE(MI->memoperands().size() == 1); @@ -318,6 +325,21 @@ TEST(MachineInstrExtraInfo, AddExtraInfo) { ASSERT_TRUE(MI->getPostInstrSymbol() == Sym2); ASSERT_TRUE(MI->getHeapAllocMarker() == HAM); ASSERT_TRUE(MI->getPCSections() == PCS); + ASSERT_FALSE(MI->getMMRAMetadata()); + + MI->setMMRAMetadata(*MF, MMRA); + ASSERT_TRUE(MI->memoperands().size() == 1); + ASSERT_TRUE(MI->getPreInstrSymbol() == Sym1); + ASSERT_TRUE(MI->getPostInstrSymbol() == Sym2); + ASSERT_TRUE(MI->getHeapAllocMarker() == HAM); + ASSERT_TRUE(MI->getPCSections() == PCS); + ASSERT_TRUE(MI->getMMRAMetadata() == MMRA); + + // Check with nothing but MMRAs. + MachineInstr *MMRAMI = MF->CreateMachineInstr(MCID, DebugLoc()); + ASSERT_FALSE(MMRAMI->getMMRAMetadata()); + MMRAMI->setMMRAMetadata(*MF, MMRA); + ASSERT_TRUE(MMRAMI->getMMRAMetadata() == MMRA); } TEST(MachineInstrExtraInfo, ChangeExtraInfo) { @@ -338,11 +360,15 @@ TEST(MachineInstrExtraInfo, ChangeExtraInfo) { MDNode *HAM = MDNode::getDistinct(Ctx, std::nullopt); MDNode *PCS = MDNode::getDistinct(Ctx, std::nullopt); + MDNode *MMRA1 = MMRAMetadata::getTagMD(Ctx, "foo", "bar"); + MDNode *MMRA2 = MMRAMetadata::getTagMD(Ctx, "bar", "bux"); + MI->setMemRefs(*MF, MMOs); MI->setPreInstrSymbol(*MF, Sym1); MI->setPostInstrSymbol(*MF, Sym2); MI->setHeapAllocMarker(*MF, HAM); MI->setPCSections(*MF, PCS); + MI->setMMRAMetadata(*MF, MMRA1); MMOs.push_back(MMO); @@ -352,6 +378,7 @@ TEST(MachineInstrExtraInfo, ChangeExtraInfo) { ASSERT_TRUE(MI->getPostInstrSymbol() == Sym2); ASSERT_TRUE(MI->getHeapAllocMarker() == HAM); ASSERT_TRUE(MI->getPCSections() == PCS); + ASSERT_TRUE(MI->getMMRAMetadata() == MMRA1); MI->setPostInstrSymbol(*MF, Sym1); ASSERT_TRUE(MI->memoperands().size() == 2); @@ -359,6 +386,15 @@ TEST(MachineInstrExtraInfo, ChangeExtraInfo) { ASSERT_TRUE(MI->getPostInstrSymbol() == Sym1); ASSERT_TRUE(MI->getHeapAllocMarker() == HAM); ASSERT_TRUE(MI->getPCSections() == PCS); + ASSERT_TRUE(MI->getMMRAMetadata() == MMRA1); + + MI->setMMRAMetadata(*MF, MMRA2); + ASSERT_TRUE(MI->memoperands().size() == 2); + ASSERT_TRUE(MI->getPreInstrSymbol() == Sym1); + ASSERT_TRUE(MI->getPostInstrSymbol() == Sym1); + ASSERT_TRUE(MI->getHeapAllocMarker() == HAM); + ASSERT_TRUE(MI->getPCSections() == PCS); + ASSERT_TRUE(MI->getMMRAMetadata() == MMRA2); } TEST(MachineInstrExtraInfo, RemoveExtraInfo) { @@ -380,11 +416,14 @@ TEST(MachineInstrExtraInfo, RemoveExtraInfo) { MDNode *HAM = MDNode::getDistinct(Ctx, std::nullopt); MDNode *PCS = MDNode::getDistinct(Ctx, std::nullopt); + MDNode *MMRA = MDTuple::get(Ctx, {}); + MI->setMemRefs(*MF, MMOs); MI->setPreInstrSymbol(*MF, Sym1); MI->setPostInstrSymbol(*MF, Sym2); MI->setHeapAllocMarker(*MF, HAM); MI->setPCSections(*MF, PCS); + MI->setMMRAMetadata(*MF, MMRA); MI->setPostInstrSymbol(*MF, nullptr); ASSERT_TRUE(MI->memoperands().size() == 2); @@ -392,6 +431,7 @@ TEST(MachineInstrExtraInfo, RemoveExtraInfo) { ASSERT_FALSE(MI->getPostInstrSymbol()); ASSERT_TRUE(MI->getHeapAllocMarker() == HAM); ASSERT_TRUE(MI->getPCSections() == PCS); + ASSERT_TRUE(MI->getMMRAMetadata() == MMRA); MI->setHeapAllocMarker(*MF, nullptr); ASSERT_TRUE(MI->memoperands().size() == 2); @@ -399,6 +439,7 @@ TEST(MachineInstrExtraInfo, RemoveExtraInfo) { ASSERT_FALSE(MI->getPostInstrSymbol()); ASSERT_FALSE(MI->getHeapAllocMarker()); ASSERT_TRUE(MI->getPCSections() == PCS); + ASSERT_TRUE(MI->getMMRAMetadata() == MMRA); MI->setPCSections(*MF, nullptr); ASSERT_TRUE(MI->memoperands().size() == 2); @@ -406,6 +447,7 @@ TEST(MachineInstrExtraInfo, RemoveExtraInfo) { ASSERT_FALSE(MI->getPostInstrSymbol()); ASSERT_FALSE(MI->getHeapAllocMarker()); ASSERT_FALSE(MI->getPCSections()); + ASSERT_TRUE(MI->getMMRAMetadata() == MMRA); MI->setPreInstrSymbol(*MF, nullptr); ASSERT_TRUE(MI->memoperands().size() == 2); @@ -413,6 +455,7 @@ TEST(MachineInstrExtraInfo, RemoveExtraInfo) { ASSERT_FALSE(MI->getPostInstrSymbol()); ASSERT_FALSE(MI->getHeapAllocMarker()); ASSERT_FALSE(MI->getPCSections()); + ASSERT_TRUE(MI->getMMRAMetadata() == MMRA); MI->setMemRefs(*MF, {}); ASSERT_TRUE(MI->memoperands_empty()); @@ -420,6 +463,15 @@ TEST(MachineInstrExtraInfo, RemoveExtraInfo) { ASSERT_FALSE(MI->getPostInstrSymbol()); ASSERT_FALSE(MI->getHeapAllocMarker()); ASSERT_FALSE(MI->getPCSections()); + ASSERT_TRUE(MI->getMMRAMetadata() == MMRA); + + MI->setMMRAMetadata(*MF, nullptr); + ASSERT_TRUE(MI->memoperands_empty()); + ASSERT_FALSE(MI->getPreInstrSymbol()); + ASSERT_FALSE(MI->getPostInstrSymbol()); + ASSERT_FALSE(MI->getHeapAllocMarker()); + ASSERT_FALSE(MI->getPCSections()); + ASSERT_FALSE(MI->getMMRAMetadata()); } TEST(MachineInstrDebugValue, AddDebugValueOperand) { diff --git a/llvm/unittests/ExecutionEngine/Orc/CoreAPIsTest.cpp b/llvm/unittests/ExecutionEngine/Orc/CoreAPIsTest.cpp index 5e2b5f35bcf47178ee132f33597b0978d6f6643e..3b24e29e1ed38606529f001a53b512899db890de 100644 --- a/llvm/unittests/ExecutionEngine/Orc/CoreAPIsTest.cpp +++ b/llvm/unittests/ExecutionEngine/Orc/CoreAPIsTest.cpp @@ -1005,11 +1005,11 @@ TEST_F(CoreAPIsStandardTest, RedefineBoundWeakSymbol) { TEST_F(CoreAPIsStandardTest, DefineMaterializingSymbol) { bool ExpectNoMoreMaterialization = false; - ES.setDispatchTask([&](std::unique_ptr T) { + DispatchOverride = [&](std::unique_ptr T) { if (ExpectNoMoreMaterialization && isa(*T)) ADD_FAILURE() << "Unexpected materialization"; T->run(); - }); + }; auto MU = std::make_unique( SymbolFlagsMap({{Foo, FooSym.getFlags()}}), @@ -1403,7 +1403,7 @@ TEST_F(CoreAPIsStandardTest, TestLookupWithThreadedMaterialization) { std::mutex WorkThreadsMutex; std::vector WorkThreads; - ES.setDispatchTask([&](std::unique_ptr T) { + DispatchOverride = [&](std::unique_ptr T) { std::promise WaitP; std::lock_guard Lock(WorkThreadsMutex); WorkThreads.push_back( @@ -1412,7 +1412,7 @@ TEST_F(CoreAPIsStandardTest, TestLookupWithThreadedMaterialization) { T->run(); })); WaitP.set_value(); - }); + }; cantFail(JD.define(absoluteSymbols({{Foo, FooSym}}))); diff --git a/llvm/unittests/ExecutionEngine/Orc/OrcTestCommon.cpp b/llvm/unittests/ExecutionEngine/Orc/OrcTestCommon.cpp index bc87df1fe8c6a911785279f24082752a63e0a66a..307f14dfe24d034ede6953cbb676e68e13c46087 100644 --- a/llvm/unittests/ExecutionEngine/Orc/OrcTestCommon.cpp +++ b/llvm/unittests/ExecutionEngine/Orc/OrcTestCommon.cpp @@ -22,3 +22,18 @@ ModuleBuilder::ModuleBuilder(LLVMContext &Context, StringRef Triple, if (Triple != "") M->setTargetTriple(Triple); } + +void llvm::orc::CoreAPIsBasedStandardTest::OverridableDispatcher::dispatch( + std::unique_ptr T) { + if (Parent.DispatchOverride) + Parent.DispatchOverride(std::move(T)); + else + InPlaceTaskDispatcher::dispatch(std::move(T)); +} + +std::unique_ptr +llvm::orc::CoreAPIsBasedStandardTest::makeEPC( + std::shared_ptr SSP) { + return std::make_unique( + std::move(SSP), std::make_unique(*this)); +} diff --git a/llvm/unittests/ExecutionEngine/Orc/OrcTestCommon.h b/llvm/unittests/ExecutionEngine/Orc/OrcTestCommon.h index ce7da76c9653a32aba24a57e64c672833c57b022..0981f4b8132bd0aebb389fa813f89ea074c00877 100644 --- a/llvm/unittests/ExecutionEngine/Orc/OrcTestCommon.h +++ b/llvm/unittests/ExecutionEngine/Orc/OrcTestCommon.h @@ -52,8 +52,20 @@ public: } protected: + class OverridableDispatcher : public InPlaceTaskDispatcher { + public: + OverridableDispatcher(CoreAPIsBasedStandardTest &Parent) : Parent(Parent) {} + void dispatch(std::unique_ptr T) override; + + private: + CoreAPIsBasedStandardTest &Parent; + }; + + std::unique_ptr + makeEPC(std::shared_ptr SSP); + std::shared_ptr SSP = std::make_shared(); - ExecutionSession ES{std::make_unique(SSP)}; + ExecutionSession ES{makeEPC(SSP)}; JITDylib &JD = ES.createBareJITDylib("JD"); SymbolStringPtr Foo = ES.intern("foo"); SymbolStringPtr Bar = ES.intern("bar"); @@ -67,6 +79,7 @@ protected: ExecutorSymbolDef BarSym{BarAddr, JITSymbolFlags::Exported}; ExecutorSymbolDef BazSym{BazAddr, JITSymbolFlags::Exported}; ExecutorSymbolDef QuxSym{QuxAddr, JITSymbolFlags::Exported}; + unique_function)> DispatchOverride; }; } // end namespace orc diff --git a/llvm/unittests/ExecutionEngine/Orc/TaskDispatchTest.cpp b/llvm/unittests/ExecutionEngine/Orc/TaskDispatchTest.cpp index 83d386c631dddb2ce41fd922bc5ac8d3b9ca76a9..6af0d60cf8ae6a00b56c0d21380942fcae35fb15 100644 --- a/llvm/unittests/ExecutionEngine/Orc/TaskDispatchTest.cpp +++ b/llvm/unittests/ExecutionEngine/Orc/TaskDispatchTest.cpp @@ -24,7 +24,7 @@ TEST(InPlaceTaskDispatchTest, GenericNamedTask) { #if LLVM_ENABLE_THREADS TEST(DynamicThreadPoolDispatchTest, GenericNamedTask) { - auto D = std::make_unique(); + auto D = std::make_unique(std::nullopt); std::promise P; auto F = P.get_future(); D->dispatch(makeGenericNamedTask( diff --git a/llvm/unittests/Frontend/OpenMPCompositionTest.cpp b/llvm/unittests/Frontend/OpenMPCompositionTest.cpp index 8a5117226d5a894de73b62bacece4f366153c2ac..920b445427e7e8adcc56eae79dfdc0a5605f396c 100644 --- a/llvm/unittests/Frontend/OpenMPCompositionTest.cpp +++ b/llvm/unittests/Frontend/OpenMPCompositionTest.cpp @@ -7,6 +7,7 @@ //===----------------------------------------------------------------------===// #include "llvm/ADT/ArrayRef.h" +#include "llvm/ADT/SmallVector.h" #include "llvm/Frontend/OpenMP/OMP.h" #include "gtest/gtest.h" @@ -40,6 +41,37 @@ TEST(Composition, GetCompoundConstruct) { ASSERT_EQ(C7, OMPD_do_simd); // Make sure it's not OMPD_end_do_simd } +TEST(Composition, GetLeafOrCompositeConstructs) { + SmallVector Out1; + auto Ret1 = getLeafOrCompositeConstructs( + OMPD_target_teams_distribute_parallel_for, Out1); + ASSERT_EQ(Ret1, ArrayRef(Out1)); + ASSERT_EQ((ArrayRef(Out1)), + (ArrayRef{OMPD_target, OMPD_teams, + OMPD_distribute_parallel_for})); + + SmallVector Out2; + auto Ret2 = + getLeafOrCompositeConstructs(OMPD_parallel_masked_taskloop_simd, Out2); + ASSERT_EQ(Ret2, ArrayRef(Out2)); + ASSERT_EQ( + (ArrayRef(Out2)), + (ArrayRef{OMPD_parallel, OMPD_masked, OMPD_taskloop_simd})); + + SmallVector Out3; + auto Ret3 = + getLeafOrCompositeConstructs(OMPD_distribute_parallel_do_simd, Out3); + ASSERT_EQ(Ret3, ArrayRef(Out3)); + ASSERT_EQ((ArrayRef(Out3)), + (ArrayRef{OMPD_distribute_parallel_do_simd})); + + SmallVector Out4; + auto Ret4 = getLeafOrCompositeConstructs(OMPD_target_parallel_loop, Out4); + ASSERT_EQ(Ret4, ArrayRef(Out4)); + ASSERT_EQ((ArrayRef(Out4)), + (ArrayRef{OMPD_target, OMPD_parallel, OMPD_loop})); +} + TEST(Composition, IsLeafConstruct) { ASSERT_TRUE(isLeafConstruct(OMPD_loop)); ASSERT_TRUE(isLeafConstruct(OMPD_teams)); diff --git a/llvm/unittests/IR/CMakeLists.txt b/llvm/unittests/IR/CMakeLists.txt index 803164b8f1eac635fe224a725558b390c24570ba..a03b0711ba33f018a5640893f1de17332994796b 100644 --- a/llvm/unittests/IR/CMakeLists.txt +++ b/llvm/unittests/IR/CMakeLists.txt @@ -31,6 +31,7 @@ add_llvm_unittest(IRTests IntrinsicsTest.cpp LegacyPassManagerTest.cpp MDBuilderTest.cpp + MemoryModelRelaxationAnnotationsTest.cpp ManglerTest.cpp MetadataTest.cpp ModuleTest.cpp diff --git a/llvm/unittests/IR/IntrinsicsTest.cpp b/llvm/unittests/IR/IntrinsicsTest.cpp index a500346b66a5e40d895a8fc7191ddb42850e7975..dddd2f73d4446b942276628315c87737472deefd 100644 --- a/llvm/unittests/IR/IntrinsicsTest.cpp +++ b/llvm/unittests/IR/IntrinsicsTest.cpp @@ -6,7 +6,12 @@ // //===----------------------------------------------------------------------===// +#include "llvm/IR/Intrinsics.h" +#include "llvm/ADT/SmallVector.h" +#include "llvm/IR/Constant.h" +#include "llvm/IR/IRBuilder.h" #include "llvm/IR/IntrinsicInst.h" +#include "llvm/IR/Module.h" #include "gtest/gtest.h" using namespace llvm; @@ -14,14 +19,41 @@ using namespace llvm; namespace { static const char *const NameTable1[] = { - "llvm.foo", - "llvm.foo.a", - "llvm.foo.b", - "llvm.foo.b.a", - "llvm.foo.c", + "llvm.foo", "llvm.foo.a", "llvm.foo.b", "llvm.foo.b.a", "llvm.foo.c", }; -TEST(IntrinNameLookup, Basic) { +class IntrinsicsTest : public ::testing::Test { + LLVMContext Context; + std::unique_ptr M; + BasicBlock *BB = nullptr; + + void TearDown() override { M.reset(); } + + void SetUp() override { + M = std::make_unique("Test", Context); + auto F = M->getOrInsertFunction( + "test", FunctionType::get(Type::getVoidTy(Context), false)); + BB = BasicBlock::Create(Context, "", cast(F.getCallee())); + EXPECT_NE(BB, nullptr); + } + +public: + Instruction *makeIntrinsic(Intrinsic::ID ID) const { + IRBuilder<> Builder(BB); + SmallVector ProcessedArgs; + auto *Decl = Intrinsic::getDeclaration(M.get(), ID); + for (auto *Ty : Decl->getFunctionType()->params()) { + auto *Val = Constant::getNullValue(Ty); + ProcessedArgs.push_back(Val); + } + return Builder.CreateCall(Decl, ProcessedArgs); + } + template void checkIsa(const Instruction &I) { + EXPECT_TRUE(isa(I)); + } +}; + +TEST(IntrinsicNameLookup, Basic) { int I = Intrinsic::lookupLLVMIntrinsicByName(NameTable1, "llvm.foo"); EXPECT_EQ(0, I); I = Intrinsic::lookupLLVMIntrinsicByName(NameTable1, "llvm.foo.f64"); @@ -36,4 +68,45 @@ TEST(IntrinNameLookup, Basic) { EXPECT_EQ(4, I); } +TEST_F(IntrinsicsTest, InstrProfInheritance) { + auto isInstrProfInstBase = [](const Instruction &I) { + return isa(I); + }; +#define __ISA(TYPE, PARENT) \ + auto is##TYPE = [&](const Instruction &I) -> bool { \ + return isa(I) && is##PARENT(I); \ + } + __ISA(InstrProfCntrInstBase, InstrProfInstBase); + __ISA(InstrProfMCDCCondBitmapUpdate, InstrProfInstBase); + __ISA(InstrProfCoverInst, InstrProfCntrInstBase); + __ISA(InstrProfIncrementInst, InstrProfCntrInstBase); + __ISA(InstrProfIncrementInstStep, InstrProfIncrementInst); + __ISA(InstrProfCallsite, InstrProfCntrInstBase); + __ISA(InstrProfTimestampInst, InstrProfCntrInstBase); + __ISA(InstrProfValueProfileInst, InstrProfCntrInstBase); + __ISA(InstrProfMCDCBitmapInstBase, InstrProfInstBase); + __ISA(InstrProfMCDCBitmapParameters, InstrProfMCDCBitmapInstBase); + __ISA(InstrProfMCDCTVBitmapUpdate, InstrProfMCDCBitmapInstBase); +#undef __ISA + + std::vector< + std::pair>> + LeafIDs = { + {Intrinsic::instrprof_cover, isInstrProfCoverInst}, + {Intrinsic::instrprof_increment, isInstrProfIncrementInst}, + {Intrinsic::instrprof_increment_step, isInstrProfIncrementInstStep}, + {Intrinsic::instrprof_callsite, isInstrProfCallsite}, + {Intrinsic::instrprof_mcdc_condbitmap_update, + isInstrProfMCDCCondBitmapUpdate}, + {Intrinsic::instrprof_mcdc_parameters, + isInstrProfMCDCBitmapParameters}, + {Intrinsic::instrprof_mcdc_tvbitmap_update, + isInstrProfMCDCTVBitmapUpdate}, + {Intrinsic::instrprof_timestamp, isInstrProfTimestampInst}, + {Intrinsic::instrprof_value_profile, isInstrProfValueProfileInst}}; + for (const auto &[ID, Checker] : LeafIDs) { + auto *Intr = makeIntrinsic(ID); + EXPECT_TRUE(Checker(*Intr)); + } +} } // end namespace diff --git a/llvm/unittests/IR/MemoryModelRelaxationAnnotationsTest.cpp b/llvm/unittests/IR/MemoryModelRelaxationAnnotationsTest.cpp new file mode 100644 index 0000000000000000000000000000000000000000..8feeb8af65a76e5730aebbd3cb103dd15e7609a2 --- /dev/null +++ b/llvm/unittests/IR/MemoryModelRelaxationAnnotationsTest.cpp @@ -0,0 +1,212 @@ +//===- llvm/unittests/IR/MemoryModelRelaxationAnnotationsTest.cpp ---------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#include "llvm/IR/MemoryModelRelaxationAnnotations.h" +#include "llvm/ADT/STLExtras.h" +#include "llvm/IR/Metadata.h" +#include "llvm/IR/Module.h" +#include "gtest/gtest.h" + +using namespace llvm; + +namespace { + +void checkMMRA(const MMRAMetadata &MMRA, + ArrayRef Expected) { + EXPECT_EQ(MMRA.size(), Expected.size()); + for (const auto &E : Expected) + EXPECT_TRUE(MMRA.hasTag(E.first, E.second)); +} + +MMRAMetadata createFromMD(LLVMContext &Ctx, + ArrayRef Expected) { + SmallVector MD; + for (const auto &Tag : Expected) + MD.push_back(MMRAMetadata::getTagMD(Ctx, Tag)); + return MDTuple::get(Ctx, MD); +} + +TEST(MMRATest, MDParse) { + LLVMContext Ctx; + + // No nesting: + // !{!"foo", "!bar"} + MDNode *FooBar = + MDTuple::get(Ctx, {MDString::get(Ctx, "foo"), MDString::get(Ctx, "bar")}); + MMRAMetadata FooBarMMRA(FooBar); + + checkMMRA(FooBarMMRA, {{"foo", "bar"}}); + + // Nested: + // !{!{!"foo", "!bar"}, !{!"bux", !"qux"}} + MDNode *BuxQux = + MDTuple::get(Ctx, {MDString::get(Ctx, "bux"), MDString::get(Ctx, "qux")}); + MDNode *Nested = MDTuple::get(Ctx, {FooBar, BuxQux}); + MMRAMetadata NestedMMRA(Nested); + + checkMMRA(NestedMMRA, {{"foo", "bar"}, {"bux", "qux"}}); +} + +TEST(MMRATest, GetMD) { + LLVMContext Ctx; + + EXPECT_EQ(MMRAMetadata::getMD(Ctx, {}), nullptr); + + MDTuple *SingleMD = MMRAMetadata::getMD(Ctx, {{"foo", "bar"}}); + EXPECT_EQ(SingleMD->getNumOperands(), 2u); + EXPECT_EQ(cast(SingleMD->getOperand(0))->getString(), "foo"); + EXPECT_EQ(cast(SingleMD->getOperand(1))->getString(), "bar"); + + MDTuple *MultiMD = MMRAMetadata::getMD(Ctx, {{"foo", "bar"}, {"bux", "qux"}}); + EXPECT_EQ(MultiMD->getNumOperands(), 2u); + + MDTuple *FooBar = cast(MultiMD->getOperand(0)); + EXPECT_EQ(cast(FooBar->getOperand(0))->getString(), "foo"); + EXPECT_EQ(cast(FooBar->getOperand(1))->getString(), "bar"); + MDTuple *BuxQux = cast(MultiMD->getOperand(1)); + EXPECT_EQ(cast(BuxQux->getOperand(0))->getString(), "bux"); + EXPECT_EQ(cast(BuxQux->getOperand(1))->getString(), "qux"); +} + +TEST(MMRATest, Utility) { + LLVMContext Ctx; + MMRAMetadata MMRA = + createFromMD(Ctx, {{"foo", "0"}, {"foo", "1"}, {"bar", "x"}}); + + EXPECT_TRUE(MMRA.hasTagWithPrefix("foo")); + EXPECT_TRUE(MMRA.hasTagWithPrefix("bar")); + EXPECT_FALSE(MMRA.hasTagWithPrefix("x")); + + EXPECT_TRUE(MMRA.hasTag("foo", "0")); + EXPECT_TRUE(MMRA.hasTag("foo", "1")); + EXPECT_TRUE(MMRA.hasTag("bar", "x")); +} + +TEST(MMRATest, Operators) { + LLVMContext Ctx; + + MMRAMetadata A = createFromMD(Ctx, {{"foo", "0"}, {"bar", "x"}}); + MMRAMetadata B = createFromMD(Ctx, {{"foo", "0"}, {"bar", "y"}}); + + // ensure we have different objects by creating copies. + EXPECT_EQ(MMRAMetadata(A), MMRAMetadata(A)); + EXPECT_TRUE((bool)A); + + EXPECT_EQ(MMRAMetadata(B), MMRAMetadata(B)); + EXPECT_TRUE((bool)B); + + EXPECT_NE(A, B); + + EXPECT_EQ(MMRAMetadata(), MMRAMetadata()); + EXPECT_NE(A, MMRAMetadata()); + EXPECT_NE(B, MMRAMetadata()); + + MMRAMetadata Empty; + EXPECT_FALSE((bool)Empty); +} + +TEST(MMRATest, Compatibility) { + LLVMContext Ctx; + + MMRAMetadata Foo0 = createFromMD(Ctx, {{"foo", "0"}}); + MMRAMetadata Foo1 = createFromMD(Ctx, {{"foo", "1"}}); + MMRAMetadata Foo10 = createFromMD(Ctx, {{"foo", "0"}, {"foo", "1"}}); + + MMRAMetadata Bar = createFromMD(Ctx, {{"bar", "y"}}); + + MMRAMetadata Empty; + + // Other set has no tag with same prefix + EXPECT_TRUE(Foo0.isCompatibleWith(Bar)); + EXPECT_TRUE(Bar.isCompatibleWith(Foo0)); + + EXPECT_TRUE(Foo0.isCompatibleWith(Empty)); + EXPECT_TRUE(Empty.isCompatibleWith(Foo0)); + + EXPECT_TRUE(Empty.isCompatibleWith(MMRAMetadata())); + EXPECT_TRUE(MMRAMetadata().isCompatibleWith(Empty)); + + // Other set has conflicting tags. + EXPECT_FALSE(Foo1.isCompatibleWith(Foo0)); + EXPECT_FALSE(Foo0.isCompatibleWith(Foo1)); + + // Both have common tags. + EXPECT_TRUE(Foo0.isCompatibleWith(Foo0)); + EXPECT_TRUE(Foo0.isCompatibleWith(Foo10)); + EXPECT_TRUE(Foo10.isCompatibleWith(Foo0)); + + EXPECT_TRUE(Foo1.isCompatibleWith(Foo1)); + EXPECT_TRUE(Foo1.isCompatibleWith(Foo10)); + EXPECT_TRUE(Foo10.isCompatibleWith(Foo1)); + + // Try with more prefixes now: + MMRAMetadata Multiple0 = + createFromMD(Ctx, {{"foo", "y"}, {"foo", "x"}, {"bar", "z"}}); + MMRAMetadata Multiple1 = + createFromMD(Ctx, {{"foo", "z"}, {"foo", "x"}, {"bar", "y"}}); + MMRAMetadata Multiple2 = + createFromMD(Ctx, {{"foo", "z"}, {"foo", "x"}, {"bux", "y"}}); + + // Multiple0 and Multiple1 are not compatible because "bar" is getting in the + // way. + EXPECT_FALSE(Multiple0.isCompatibleWith(Multiple1)); + EXPECT_FALSE(Multiple1.isCompatibleWith(Multiple0)); + + EXPECT_TRUE(Multiple0.isCompatibleWith(Empty)); + EXPECT_TRUE(Empty.isCompatibleWith(Multiple0)); + EXPECT_TRUE(Multiple1.isCompatibleWith(Empty)); + EXPECT_TRUE(Empty.isCompatibleWith(Multiple1)); + + // Multiple2 is compatible with both 1/0 because there is always "foo:x" in + // common, and the other prefixes are unique to each set. + EXPECT_TRUE(Multiple2.isCompatibleWith(Multiple0)); + EXPECT_TRUE(Multiple0.isCompatibleWith(Multiple2)); + EXPECT_TRUE(Multiple2.isCompatibleWith(Multiple1)); + EXPECT_TRUE(Multiple1.isCompatibleWith(Multiple2)); +} + +TEST(MMRATest, Combine) { + LLVMContext Ctx; + + MMRAMetadata Foo0 = createFromMD(Ctx, {{"foo", "0"}}); + MMRAMetadata Foo10 = createFromMD(Ctx, {{"foo", "0"}, {"foo", "1"}}); + MMRAMetadata Bar0 = createFromMD(Ctx, {{"bar", "0"}}); + MMRAMetadata BarFoo0 = createFromMD(Ctx, {{"bar", "0"}, {"foo", "0"}}); + + { + // foo is common to both sets + MMRAMetadata Combined = MMRAMetadata::combine(Ctx, Foo0, Foo10); + EXPECT_EQ(Combined, Foo10); + } + + { + // nothing is common + MMRAMetadata Combined = MMRAMetadata::combine(Ctx, Foo0, Bar0); + EXPECT_TRUE(Combined.empty()); + } + + { + // only foo is common. + MMRAMetadata Combined = MMRAMetadata::combine(Ctx, BarFoo0, Foo0); + EXPECT_EQ(Combined, Foo0); + } + + { + // only bar is common. + MMRAMetadata Combined = MMRAMetadata::combine(Ctx, BarFoo0, Bar0); + EXPECT_EQ(Combined, Bar0); + } + + { + // only foo is common + MMRAMetadata Combined = MMRAMetadata::combine(Ctx, BarFoo0, Foo10); + EXPECT_EQ(Combined, Foo10); + } +} + +} // namespace diff --git a/llvm/unittests/IR/PatternMatch.cpp b/llvm/unittests/IR/PatternMatch.cpp index f0377eae9989fd640fe4a8ce503fd71bc522167b..a25885faa3a44225cfe346171d6fccf0a10c39c8 100644 --- a/llvm/unittests/IR/PatternMatch.cpp +++ b/llvm/unittests/IR/PatternMatch.cpp @@ -1995,7 +1995,7 @@ TEST_F(PatternMatchTest, VScale) { EXPECT_TRUE(match(PtrToInt2, m_VScale())); } -TEST_F(PatternMatchTest, NotForbidUndef) { +TEST_F(PatternMatchTest, NotForbidPoison) { Type *ScalarTy = IRB.getInt8Ty(); Type *VectorTy = FixedVectorType::get(ScalarTy, 3); Constant *ScalarUndef = UndefValue::get(ScalarTy); @@ -2020,23 +2020,33 @@ TEST_F(PatternMatchTest, NotForbidUndef) { Value *X; EXPECT_TRUE(match(Not, m_Not(m_Value(X)))); EXPECT_TRUE(match(X, m_Zero())); + X = nullptr; + EXPECT_TRUE(match(Not, m_NotForbidPoison(m_Value(X)))); + EXPECT_TRUE(match(X, m_Zero())); Value *NotCommute = IRB.CreateXor(VectorOnes, VectorZero); Value *Y; EXPECT_TRUE(match(NotCommute, m_Not(m_Value(Y)))); EXPECT_TRUE(match(Y, m_Zero())); + Y = nullptr; + EXPECT_TRUE(match(NotCommute, m_NotForbidPoison(m_Value(Y)))); + EXPECT_TRUE(match(Y, m_Zero())); Value *NotWithUndefs = IRB.CreateXor(VectorZero, VectorMixedUndef); EXPECT_FALSE(match(NotWithUndefs, m_Not(m_Value()))); + EXPECT_FALSE(match(NotWithUndefs, m_NotForbidPoison(m_Value()))); Value *NotWithPoisons = IRB.CreateXor(VectorZero, VectorMixedPoison); EXPECT_TRUE(match(NotWithPoisons, m_Not(m_Value()))); + EXPECT_FALSE(match(NotWithPoisons, m_NotForbidPoison(m_Value()))); Value *NotWithUndefsCommute = IRB.CreateXor(VectorMixedUndef, VectorZero); EXPECT_FALSE(match(NotWithUndefsCommute, m_Not(m_Value()))); + EXPECT_FALSE(match(NotWithUndefsCommute, m_NotForbidPoison(m_Value()))); Value *NotWithPoisonsCommute = IRB.CreateXor(VectorMixedPoison, VectorZero); EXPECT_TRUE(match(NotWithPoisonsCommute, m_Not(m_Value()))); + EXPECT_FALSE(match(NotWithPoisonsCommute, m_NotForbidPoison(m_Value()))); } template struct MutableConstTest : PatternMatchTest { }; diff --git a/llvm/unittests/ProfileData/InstrProfTest.cpp b/llvm/unittests/ProfileData/InstrProfTest.cpp index 73ba0a23ea5f450e07981a9d517fe4cabd27c989..edc427dcbc454001add8b4cd435a74fbe256c2e3 100644 --- a/llvm/unittests/ProfileData/InstrProfTest.cpp +++ b/llvm/unittests/ProfileData/InstrProfTest.cpp @@ -370,12 +370,31 @@ static CallStackIdMapTy getCallStackMapping() { return Mapping; } +// Populate all of the fields of MIB. +MemInfoBlock makeFullMIB() { + MemInfoBlock MIB; +#define MIBEntryDef(NameTag, Name, Type) MIB.NameTag; +#include "llvm/ProfileData/MIBEntryDef.inc" +#undef MIBEntryDef + return MIB; +} + +// Populate those fields returned by getHotColdSchema. +MemInfoBlock makePartialMIB() { + MemInfoBlock MIB; + MIB.AllocCount = 1; + MIB.TotalSize = 5; + MIB.TotalLifetime = 10; + MIB.TotalLifetimeAccessDensity = 23; + return MIB; +} + IndexedMemProfRecord makeRecord( std::initializer_list> AllocFrames, std::initializer_list> CallSiteFrames, - const MemInfoBlock &Block = MemInfoBlock()) { + const MemInfoBlock &Block = makeFullMIB()) { llvm::memprof::IndexedMemProfRecord MR; for (const auto &Frames : AllocFrames) MR.AllocSites.emplace_back(Frames, llvm::memprof::hashCallStack(Frames), @@ -388,7 +407,7 @@ IndexedMemProfRecord makeRecord( IndexedMemProfRecord makeRecordV2(std::initializer_list<::llvm::memprof::CallStackId> AllocFrames, std::initializer_list<::llvm::memprof::CallStackId> CallSiteFrames, - const MemInfoBlock &Block = MemInfoBlock()) { + const MemInfoBlock &Block) { llvm::memprof::IndexedMemProfRecord MR; for (const auto &CSId : AllocFrames) // We don't populate IndexedAllocationInfo::CallStack because we use it only @@ -476,15 +495,56 @@ TEST_F(InstrProfTest, test_memprof_v0) { EXPECT_THAT(WantRecord, EqualsRecord(Record)); } -TEST_F(InstrProfTest, test_memprof_v2) { +struct CallStackIdConverter { + std::optional LastUnmappedFrameId; + std::optional LastUnmappedCSId; + + const FrameIdMapTy &IdToFrameMap; + const CallStackIdMapTy &CSIdToCallStackMap; + + CallStackIdConverter() = delete; + CallStackIdConverter(const FrameIdMapTy &IdToFrameMap, + const CallStackIdMapTy &CSIdToCallStackMap) + : IdToFrameMap(IdToFrameMap), CSIdToCallStackMap(CSIdToCallStackMap) {} + + llvm::SmallVector + operator()(::llvm::memprof::CallStackId CSId) { + auto IdToFrameCallback = [&](const memprof::FrameId Id) { + auto Iter = IdToFrameMap.find(Id); + if (Iter == IdToFrameMap.end()) { + LastUnmappedFrameId = Id; + return memprof::Frame(0, 0, 0, false); + } + return Iter->second; + }; + + llvm::SmallVector Frames; + auto CSIter = CSIdToCallStackMap.find(CSId); + if (CSIter == CSIdToCallStackMap.end()) { + LastUnmappedCSId = CSId; + } else { + const ::llvm::SmallVector<::llvm::memprof::FrameId> &CS = + CSIter->getSecond(); + Frames.reserve(CS.size()); + for (::llvm::memprof::FrameId Id : CS) + Frames.push_back(IdToFrameCallback(Id)); + } + return Frames; + } +}; + +TEST_F(InstrProfTest, test_memprof_v2_full_schema) { + const MemInfoBlock MIB = makeFullMIB(); + Writer.setMemProfVersionRequested(memprof::Version2); + Writer.setMemProfFullSchema(true); ASSERT_THAT_ERROR(Writer.mergeProfileKind(InstrProfKind::MemProf), Succeeded()); const IndexedMemProfRecord IndexedMR = makeRecordV2( /*AllocFrames=*/{0x111, 0x222}, - /*CallSiteFrames=*/{0x333}); + /*CallSiteFrames=*/{0x333}, MIB); const FrameIdMapTy IdToFrameMap = getFrameMapping(); const auto CSIdToCallStackMap = getCallStackMapping(); for (const auto &I : IdToFrameMap) { @@ -502,38 +562,54 @@ TEST_F(InstrProfTest, test_memprof_v2) { ASSERT_THAT_ERROR(RecordOr.takeError(), Succeeded()); const memprof::MemProfRecord &Record = RecordOr.get(); - std::optional LastUnmappedFrameId; - auto IdToFrameCallback = [&](const memprof::FrameId Id) { - auto Iter = IdToFrameMap.find(Id); - if (Iter == IdToFrameMap.end()) { - LastUnmappedFrameId = Id; - return memprof::Frame(0, 0, 0, false); - } - return Iter->second; - }; + CallStackIdConverter CSIdConv(IdToFrameMap, CSIdToCallStackMap); - std::optional<::llvm::memprof::CallStackId> LastUnmappedCSId; - auto CSIdToCallStackCallback = [&](::llvm::memprof::CallStackId CSId) { - llvm::SmallVector Frames; - auto CSIter = CSIdToCallStackMap.find(CSId); - if (CSIter == CSIdToCallStackMap.end()) { - LastUnmappedCSId = CSId; - } else { - const ::llvm::SmallVector<::llvm::memprof::FrameId> &CS = - CSIter->getSecond(); - Frames.reserve(CS.size()); - for (::llvm::memprof::FrameId Id : CS) - Frames.push_back(IdToFrameCallback(Id)); - } - return Frames; - }; + const ::llvm::memprof::MemProfRecord WantRecord = + IndexedMR.toMemProfRecord(CSIdConv); + ASSERT_EQ(CSIdConv.LastUnmappedFrameId, std::nullopt) + << "could not map frame id: " << *CSIdConv.LastUnmappedFrameId; + ASSERT_EQ(CSIdConv.LastUnmappedCSId, std::nullopt) + << "could not map call stack id: " << *CSIdConv.LastUnmappedCSId; + EXPECT_THAT(WantRecord, EqualsRecord(Record)); +} + +TEST_F(InstrProfTest, test_memprof_v2_partial_schema) { + const MemInfoBlock MIB = makePartialMIB(); + + Writer.setMemProfVersionRequested(memprof::Version2); + Writer.setMemProfFullSchema(false); + + ASSERT_THAT_ERROR(Writer.mergeProfileKind(InstrProfKind::MemProf), + Succeeded()); + + const IndexedMemProfRecord IndexedMR = makeRecordV2( + /*AllocFrames=*/{0x111, 0x222}, + /*CallSiteFrames=*/{0x333}, MIB); + const FrameIdMapTy IdToFrameMap = getFrameMapping(); + const auto CSIdToCallStackMap = getCallStackMapping(); + for (const auto &I : IdToFrameMap) { + Writer.addMemProfFrame(I.first, I.getSecond(), Err); + } + for (const auto &I : CSIdToCallStackMap) { + Writer.addMemProfCallStack(I.first, I.getSecond(), Err); + } + Writer.addMemProfRecord(/*Id=*/0x9999, IndexedMR); + + auto Profile = Writer.writeBuffer(); + readProfile(std::move(Profile)); + + auto RecordOr = Reader->getMemProfRecord(0x9999); + ASSERT_THAT_ERROR(RecordOr.takeError(), Succeeded()); + const memprof::MemProfRecord &Record = RecordOr.get(); + + CallStackIdConverter CSIdConv(IdToFrameMap, CSIdToCallStackMap); const ::llvm::memprof::MemProfRecord WantRecord = - IndexedMR.toMemProfRecord(CSIdToCallStackCallback); - ASSERT_EQ(LastUnmappedFrameId, std::nullopt) - << "could not map frame id: " << *LastUnmappedFrameId; - ASSERT_EQ(LastUnmappedCSId, std::nullopt) - << "could not map call stack id: " << *LastUnmappedCSId; + IndexedMR.toMemProfRecord(CSIdConv); + ASSERT_EQ(CSIdConv.LastUnmappedFrameId, std::nullopt) + << "could not map frame id: " << *CSIdConv.LastUnmappedFrameId; + ASSERT_EQ(CSIdConv.LastUnmappedCSId, std::nullopt) + << "could not map call stack id: " << *CSIdConv.LastUnmappedCSId; EXPECT_THAT(WantRecord, EqualsRecord(Record)); } diff --git a/llvm/unittests/ProfileData/MemProfTest.cpp b/llvm/unittests/ProfileData/MemProfTest.cpp index 7e00a80cacf93374a7277791540285420af922b1..98dacd3511e1d853628a8bd019c23368231dd672 100644 --- a/llvm/unittests/ProfileData/MemProfTest.cpp +++ b/llvm/unittests/ProfileData/MemProfTest.cpp @@ -122,14 +122,6 @@ MATCHER_P4(FrameContains, FunctionName, LineOffset, Column, Inline, "") { return false; } -MemProfSchema getFullSchema() { - MemProfSchema Schema; -#define MIBEntryDef(NameTag, Name, Type) Schema.push_back(Meta::Name); -#include "llvm/ProfileData/MIBEntryDef.inc" -#undef MIBEntryDef - return Schema; -} - TEST(MemProf, FillsValue) { std::unique_ptr Symbolizer(new MockSymbolizer()); @@ -187,7 +179,7 @@ TEST(MemProf, FillsValue) { // Check the memprof record for foo. const llvm::GlobalValue::GUID FooId = IndexedMemProfRecord::getGUID("foo"); - ASSERT_EQ(Records.count(FooId), 1U); + ASSERT_TRUE(Records.contains(FooId)); const MemProfRecord &Foo = Records[FooId]; ASSERT_THAT(Foo.AllocSites, SizeIs(1)); EXPECT_EQ(Foo.AllocSites[0].Info.getAllocCount(), 1U); @@ -203,7 +195,7 @@ TEST(MemProf, FillsValue) { // Check the memprof record for bar. const llvm::GlobalValue::GUID BarId = IndexedMemProfRecord::getGUID("bar"); - ASSERT_EQ(Records.count(BarId), 1U); + ASSERT_TRUE(Records.contains(BarId)); const MemProfRecord &Bar = Records[BarId]; ASSERT_THAT(Bar.AllocSites, SizeIs(1)); EXPECT_EQ(Bar.AllocSites[0].Info.getAllocCount(), 1U); @@ -223,7 +215,7 @@ TEST(MemProf, FillsValue) { // Check the memprof record for xyz. const llvm::GlobalValue::GUID XyzId = IndexedMemProfRecord::getGUID("xyz"); - ASSERT_EQ(Records.count(XyzId), 1U); + ASSERT_TRUE(Records.contains(XyzId)); const MemProfRecord &Xyz = Records[XyzId]; ASSERT_THAT(Xyz.CallSites, SizeIs(1)); ASSERT_THAT(Xyz.CallSites[0], SizeIs(2)); @@ -234,7 +226,7 @@ TEST(MemProf, FillsValue) { // Check the memprof record for abc. const llvm::GlobalValue::GUID AbcId = IndexedMemProfRecord::getGUID("abc"); - ASSERT_EQ(Records.count(AbcId), 1U); + ASSERT_TRUE(Records.contains(AbcId)); const MemProfRecord &Abc = Records[AbcId]; EXPECT_TRUE(Abc.AllocSites.empty()); ASSERT_THAT(Abc.CallSites, SizeIs(1)); @@ -248,7 +240,7 @@ TEST(MemProf, PortableWrapper) { /*dealloc_timestamp=*/2000, /*alloc_cpu=*/3, /*dealloc_cpu=*/4); - const auto Schema = getFullSchema(); + const auto Schema = llvm::memprof::getFullSchema(); PortableMemInfoBlock WriteBlock(Info); std::string Buffer; @@ -271,7 +263,7 @@ TEST(MemProf, PortableWrapper) { // Version0 and Version1 serialize IndexedMemProfRecord in the same format, so // we share one test. TEST(MemProf, RecordSerializationRoundTripVersion0And1) { - const MemProfSchema Schema = getFullSchema(); + const auto Schema = llvm::memprof::getFullSchema(); MemInfoBlock Info(/*size=*/16, /*access_count=*/7, /*alloc_timestamp=*/1000, /*dealloc_timestamp=*/2000, /*alloc_cpu=*/3, @@ -305,7 +297,7 @@ TEST(MemProf, RecordSerializationRoundTripVersion0And1) { } TEST(MemProf, RecordSerializationRoundTripVerion2) { - const MemProfSchema Schema = getFullSchema(); + const auto Schema = llvm::memprof::getFullSchema(); MemInfoBlock Info(/*size=*/16, /*access_count=*/7, /*alloc_timestamp=*/1000, /*dealloc_timestamp=*/2000, /*alloc_cpu=*/3, diff --git a/llvm/unittests/Support/CMakeLists.txt b/llvm/unittests/Support/CMakeLists.txt index 15a126279125c5bc8e307500248d2ad5f826aa98..2718be8450f80580d52b362169ccef660e293d7d 100644 --- a/llvm/unittests/Support/CMakeLists.txt +++ b/llvm/unittests/Support/CMakeLists.txt @@ -71,7 +71,6 @@ add_llvm_unittest(SupportTests ReverseIterationTest.cpp ReplaceFileTest.cpp RISCVAttributeParserTest.cpp - RISCVISAInfoTest.cpp ScaledNumberTest.cpp ScopedPrinterTest.cpp SHA256.cpp diff --git a/llvm/unittests/TargetParser/CMakeLists.txt b/llvm/unittests/TargetParser/CMakeLists.txt index 3bbc74f3f8d3212745cf551195e3c517c51a2bc9..086c57903716f59f5bfd20873db6b052844ef3b2 100644 --- a/llvm/unittests/TargetParser/CMakeLists.txt +++ b/llvm/unittests/TargetParser/CMakeLists.txt @@ -6,6 +6,7 @@ set(LLVM_LINK_COMPONENTS add_llvm_unittest(TargetParserTests CSKYTargetParserTest.cpp Host.cpp + RISCVISAInfoTest.cpp RISCVTargetParserTest.cpp TargetParserTest.cpp TripleTest.cpp diff --git a/llvm/unittests/Support/RISCVISAInfoTest.cpp b/llvm/unittests/TargetParser/RISCVISAInfoTest.cpp similarity index 93% rename from llvm/unittests/Support/RISCVISAInfoTest.cpp rename to llvm/unittests/TargetParser/RISCVISAInfoTest.cpp index caf7bf0a317174b56a52da48ac246f072497311c..81b7e2e527d966141aaef3a2caf453fe86a12fd4 100644 --- a/llvm/unittests/Support/RISCVISAInfoTest.cpp +++ b/llvm/unittests/TargetParser/RISCVISAInfoTest.cpp @@ -6,8 +6,8 @@ // //===----------------------------------------------------------------------===// +#include "llvm/TargetParser/RISCVISAInfo.h" #include "llvm/ADT/StringMap.h" -#include "llvm/Support/RISCVISAInfo.h" #include "llvm/Testing/Support/Error.h" #include "gtest/gtest.h" @@ -15,8 +15,8 @@ using ::testing::ElementsAre; using namespace llvm; -bool operator==(const RISCVISAInfo::ExtensionVersion &A, - const RISCVISAInfo::ExtensionVersion &B) { +bool operator==(const RISCVISAUtils::ExtensionVersion &A, + const RISCVISAUtils::ExtensionVersion &B) { return A.Major == B.Major && A.Minor == B.Minor; } @@ -51,7 +51,7 @@ TEST(ParseNormalizedArchString, AcceptsValidBaseISAsAndSetsXLen) { RISCVISAInfo &InfoRV32I = **MaybeRV32I; EXPECT_EQ(InfoRV32I.getExtensions().size(), 1UL); EXPECT_TRUE(InfoRV32I.getExtensions().at("i") == - (RISCVISAInfo::ExtensionVersion{2, 0})); + (RISCVISAUtils::ExtensionVersion{2, 0})); EXPECT_EQ(InfoRV32I.getXLen(), 32U); auto MaybeRV32E = RISCVISAInfo::parseNormalizedArchString("rv32e2p0"); @@ -59,7 +59,7 @@ TEST(ParseNormalizedArchString, AcceptsValidBaseISAsAndSetsXLen) { RISCVISAInfo &InfoRV32E = **MaybeRV32E; EXPECT_EQ(InfoRV32E.getExtensions().size(), 1UL); EXPECT_TRUE(InfoRV32E.getExtensions().at("e") == - (RISCVISAInfo::ExtensionVersion{2, 0})); + (RISCVISAUtils::ExtensionVersion{2, 0})); EXPECT_EQ(InfoRV32E.getXLen(), 32U); auto MaybeRV64I = RISCVISAInfo::parseNormalizedArchString("rv64i2p0"); @@ -67,7 +67,7 @@ TEST(ParseNormalizedArchString, AcceptsValidBaseISAsAndSetsXLen) { RISCVISAInfo &InfoRV64I = **MaybeRV64I; EXPECT_EQ(InfoRV64I.getExtensions().size(), 1UL); EXPECT_TRUE(InfoRV64I.getExtensions().at("i") == - (RISCVISAInfo::ExtensionVersion{2, 0})); + (RISCVISAUtils::ExtensionVersion{2, 0})); EXPECT_EQ(InfoRV64I.getXLen(), 64U); auto MaybeRV64E = RISCVISAInfo::parseNormalizedArchString("rv64e2p0"); @@ -75,7 +75,7 @@ TEST(ParseNormalizedArchString, AcceptsValidBaseISAsAndSetsXLen) { RISCVISAInfo &InfoRV64E = **MaybeRV64E; EXPECT_EQ(InfoRV64E.getExtensions().size(), 1UL); EXPECT_TRUE(InfoRV64E.getExtensions().at("e") == - (RISCVISAInfo::ExtensionVersion{2, 0})); + (RISCVISAUtils::ExtensionVersion{2, 0})); EXPECT_EQ(InfoRV64E.getXLen(), 64U); } @@ -86,15 +86,15 @@ TEST(ParseNormalizedArchString, AcceptsArbitraryExtensionsAndVersions) { RISCVISAInfo &Info = **MaybeISAInfo; EXPECT_EQ(Info.getExtensions().size(), 5UL); EXPECT_TRUE(Info.getExtensions().at("i") == - (RISCVISAInfo::ExtensionVersion{5, 1})); + (RISCVISAUtils::ExtensionVersion{5, 1})); EXPECT_TRUE(Info.getExtensions().at("m") == - (RISCVISAInfo::ExtensionVersion{3, 2})); + (RISCVISAUtils::ExtensionVersion{3, 2})); EXPECT_TRUE(Info.getExtensions().at("zmadeup") == - (RISCVISAInfo::ExtensionVersion{11, 12})); + (RISCVISAUtils::ExtensionVersion{11, 12})); EXPECT_TRUE(Info.getExtensions().at("sfoo") == - (RISCVISAInfo::ExtensionVersion{2, 0})); + (RISCVISAUtils::ExtensionVersion{2, 0})); EXPECT_TRUE(Info.getExtensions().at("xbar") == - (RISCVISAInfo::ExtensionVersion{3, 0})); + (RISCVISAUtils::ExtensionVersion{3, 0})); } TEST(ParseNormalizedArchString, UpdatesFLenMinVLenMaxELen) { @@ -139,7 +139,7 @@ TEST(ParseArchString, AcceptsSupportedBaseISAsAndSetsXLenAndFLen) { RISCVISAInfo &InfoRV32I = **MaybeRV32I; RISCVISAInfo::OrderedExtensionMap ExtsRV32I = InfoRV32I.getExtensions(); EXPECT_EQ(ExtsRV32I.size(), 1UL); - EXPECT_TRUE(ExtsRV32I.at("i") == (RISCVISAInfo::ExtensionVersion{2, 1})); + EXPECT_TRUE(ExtsRV32I.at("i") == (RISCVISAUtils::ExtensionVersion{2, 1})); EXPECT_EQ(InfoRV32I.getXLen(), 32U); EXPECT_EQ(InfoRV32I.getFLen(), 0U); @@ -148,7 +148,7 @@ TEST(ParseArchString, AcceptsSupportedBaseISAsAndSetsXLenAndFLen) { RISCVISAInfo &InfoRV32E = **MaybeRV32E; RISCVISAInfo::OrderedExtensionMap ExtsRV32E = InfoRV32E.getExtensions(); EXPECT_EQ(ExtsRV32E.size(), 1UL); - EXPECT_TRUE(ExtsRV32E.at("e") == (RISCVISAInfo::ExtensionVersion{2, 0})); + EXPECT_TRUE(ExtsRV32E.at("e") == (RISCVISAUtils::ExtensionVersion{2, 0})); EXPECT_EQ(InfoRV32E.getXLen(), 32U); EXPECT_EQ(InfoRV32E.getFLen(), 0U); @@ -157,14 +157,14 @@ TEST(ParseArchString, AcceptsSupportedBaseISAsAndSetsXLenAndFLen) { RISCVISAInfo &InfoRV32G = **MaybeRV32G; RISCVISAInfo::OrderedExtensionMap ExtsRV32G = InfoRV32G.getExtensions(); EXPECT_EQ(ExtsRV32G.size(), 7UL); - EXPECT_TRUE(ExtsRV32G.at("i") == (RISCVISAInfo::ExtensionVersion{2, 1})); - EXPECT_TRUE(ExtsRV32G.at("m") == (RISCVISAInfo::ExtensionVersion{2, 0})); - EXPECT_TRUE(ExtsRV32G.at("a") == (RISCVISAInfo::ExtensionVersion{2, 1})); - EXPECT_TRUE(ExtsRV32G.at("f") == (RISCVISAInfo::ExtensionVersion{2, 2})); - EXPECT_TRUE(ExtsRV32G.at("d") == (RISCVISAInfo::ExtensionVersion{2, 2})); - EXPECT_TRUE(ExtsRV32G.at("zicsr") == (RISCVISAInfo::ExtensionVersion{2, 0})); + EXPECT_TRUE(ExtsRV32G.at("i") == (RISCVISAUtils::ExtensionVersion{2, 1})); + EXPECT_TRUE(ExtsRV32G.at("m") == (RISCVISAUtils::ExtensionVersion{2, 0})); + EXPECT_TRUE(ExtsRV32G.at("a") == (RISCVISAUtils::ExtensionVersion{2, 1})); + EXPECT_TRUE(ExtsRV32G.at("f") == (RISCVISAUtils::ExtensionVersion{2, 2})); + EXPECT_TRUE(ExtsRV32G.at("d") == (RISCVISAUtils::ExtensionVersion{2, 2})); + EXPECT_TRUE(ExtsRV32G.at("zicsr") == (RISCVISAUtils::ExtensionVersion{2, 0})); EXPECT_TRUE(ExtsRV32G.at("zifencei") == - (RISCVISAInfo::ExtensionVersion{2, 0})); + (RISCVISAUtils::ExtensionVersion{2, 0})); EXPECT_EQ(InfoRV32G.getXLen(), 32U); EXPECT_EQ(InfoRV32G.getFLen(), 64U); @@ -173,7 +173,7 @@ TEST(ParseArchString, AcceptsSupportedBaseISAsAndSetsXLenAndFLen) { RISCVISAInfo &InfoRV64I = **MaybeRV64I; RISCVISAInfo::OrderedExtensionMap ExtsRV64I = InfoRV64I.getExtensions(); EXPECT_EQ(ExtsRV64I.size(), 1UL); - EXPECT_TRUE(ExtsRV64I.at("i") == (RISCVISAInfo::ExtensionVersion{2, 1})); + EXPECT_TRUE(ExtsRV64I.at("i") == (RISCVISAUtils::ExtensionVersion{2, 1})); EXPECT_EQ(InfoRV64I.getXLen(), 64U); EXPECT_EQ(InfoRV64I.getFLen(), 0U); @@ -182,7 +182,7 @@ TEST(ParseArchString, AcceptsSupportedBaseISAsAndSetsXLenAndFLen) { RISCVISAInfo &InfoRV64E = **MaybeRV64E; RISCVISAInfo::OrderedExtensionMap ExtsRV64E = InfoRV64E.getExtensions(); EXPECT_EQ(ExtsRV64E.size(), 1UL); - EXPECT_TRUE(ExtsRV64E.at("e") == (RISCVISAInfo::ExtensionVersion{2, 0})); + EXPECT_TRUE(ExtsRV64E.at("e") == (RISCVISAUtils::ExtensionVersion{2, 0})); EXPECT_EQ(InfoRV64E.getXLen(), 64U); EXPECT_EQ(InfoRV64E.getFLen(), 0U); @@ -191,14 +191,14 @@ TEST(ParseArchString, AcceptsSupportedBaseISAsAndSetsXLenAndFLen) { RISCVISAInfo &InfoRV64G = **MaybeRV64G; RISCVISAInfo::OrderedExtensionMap ExtsRV64G = InfoRV64G.getExtensions(); EXPECT_EQ(ExtsRV64G.size(), 7UL); - EXPECT_TRUE(ExtsRV64G.at("i") == (RISCVISAInfo::ExtensionVersion{2, 1})); - EXPECT_TRUE(ExtsRV64G.at("m") == (RISCVISAInfo::ExtensionVersion{2, 0})); - EXPECT_TRUE(ExtsRV64G.at("a") == (RISCVISAInfo::ExtensionVersion{2, 1})); - EXPECT_TRUE(ExtsRV64G.at("f") == (RISCVISAInfo::ExtensionVersion{2, 2})); - EXPECT_TRUE(ExtsRV64G.at("d") == (RISCVISAInfo::ExtensionVersion{2, 2})); - EXPECT_TRUE(ExtsRV64G.at("zicsr") == (RISCVISAInfo::ExtensionVersion{2, 0})); + EXPECT_TRUE(ExtsRV64G.at("i") == (RISCVISAUtils::ExtensionVersion{2, 1})); + EXPECT_TRUE(ExtsRV64G.at("m") == (RISCVISAUtils::ExtensionVersion{2, 0})); + EXPECT_TRUE(ExtsRV64G.at("a") == (RISCVISAUtils::ExtensionVersion{2, 1})); + EXPECT_TRUE(ExtsRV64G.at("f") == (RISCVISAUtils::ExtensionVersion{2, 2})); + EXPECT_TRUE(ExtsRV64G.at("d") == (RISCVISAUtils::ExtensionVersion{2, 2})); + EXPECT_TRUE(ExtsRV64G.at("zicsr") == (RISCVISAUtils::ExtensionVersion{2, 0})); EXPECT_TRUE(ExtsRV64G.at("zifencei") == - (RISCVISAInfo::ExtensionVersion{2, 0})); + (RISCVISAUtils::ExtensionVersion{2, 0})); EXPECT_EQ(InfoRV64G.getXLen(), 64U); EXPECT_EQ(InfoRV64G.getFLen(), 64U); } @@ -243,7 +243,7 @@ TEST(ParseArchString, IgnoresUnrecognizedExtensionNamesWithIgnoreUnknown) { RISCVISAInfo &Info = **MaybeISAInfo; RISCVISAInfo::OrderedExtensionMap Exts = Info.getExtensions(); EXPECT_EQ(Exts.size(), 1UL); - EXPECT_TRUE(Exts.at("i") == (RISCVISAInfo::ExtensionVersion{2, 1})); + EXPECT_TRUE(Exts.at("i") == (RISCVISAUtils::ExtensionVersion{2, 1})); } // Checks that supported extensions aren't incorrectly ignored when a @@ -252,7 +252,7 @@ TEST(ParseArchString, IgnoresUnrecognizedExtensionNamesWithIgnoreUnknown) { RISCVISAInfo::parseArchString("rv32i_zbc1p0_xmadeup", true, false, true); ASSERT_THAT_EXPECTED(MaybeISAInfo, Succeeded()); RISCVISAInfo::OrderedExtensionMap Exts = (*MaybeISAInfo)->getExtensions(); - EXPECT_TRUE(Exts.at("zbc") == (RISCVISAInfo::ExtensionVersion{1, 0})); + EXPECT_TRUE(Exts.at("zbc") == (RISCVISAUtils::ExtensionVersion{1, 0})); } TEST(ParseArchString, AcceptsVersionInLongOrShortForm) { @@ -260,13 +260,13 @@ TEST(ParseArchString, AcceptsVersionInLongOrShortForm) { auto MaybeISAInfo = RISCVISAInfo::parseArchString(Input, true); ASSERT_THAT_EXPECTED(MaybeISAInfo, Succeeded()); RISCVISAInfo::OrderedExtensionMap Exts = (*MaybeISAInfo)->getExtensions(); - EXPECT_TRUE(Exts.at("i") == (RISCVISAInfo::ExtensionVersion{2, 1})); + EXPECT_TRUE(Exts.at("i") == (RISCVISAUtils::ExtensionVersion{2, 1})); } for (StringRef Input : {"rv32i_zfinx1", "rv32i_zfinx1p0"}) { auto MaybeISAInfo = RISCVISAInfo::parseArchString(Input, true); ASSERT_THAT_EXPECTED(MaybeISAInfo, Succeeded()); RISCVISAInfo::OrderedExtensionMap Exts = (*MaybeISAInfo)->getExtensions(); - EXPECT_TRUE(Exts.at("zfinx") == (RISCVISAInfo::ExtensionVersion{1, 0})); + EXPECT_TRUE(Exts.at("zfinx") == (RISCVISAUtils::ExtensionVersion{1, 0})); } } @@ -295,14 +295,14 @@ TEST(ParseArchString, ASSERT_THAT_EXPECTED(MaybeISAInfo, Succeeded()); RISCVISAInfo::OrderedExtensionMap Exts = (*MaybeISAInfo)->getExtensions(); EXPECT_EQ(Exts.size(), 1UL); - EXPECT_TRUE(Exts.at("i") == (RISCVISAInfo::ExtensionVersion{2, 1})); + EXPECT_TRUE(Exts.at("i") == (RISCVISAUtils::ExtensionVersion{2, 1})); } for (StringRef Input : {"rv32e0p1", "rv32e99p99", "rv64e0p1", "rv64e99p99"}) { auto MaybeISAInfo = RISCVISAInfo::parseArchString(Input, true, false, true); ASSERT_THAT_EXPECTED(MaybeISAInfo, Succeeded()); RISCVISAInfo::OrderedExtensionMap Exts = (*MaybeISAInfo)->getExtensions(); EXPECT_EQ(Exts.size(), 1UL); - EXPECT_TRUE(Exts.at("e") == (RISCVISAInfo::ExtensionVersion{2, 0})); + EXPECT_TRUE(Exts.at("e") == (RISCVISAUtils::ExtensionVersion{2, 0})); } } @@ -313,7 +313,7 @@ TEST(ParseArchString, ASSERT_THAT_EXPECTED(MaybeISAInfo, Succeeded()); RISCVISAInfo::OrderedExtensionMap Exts = (*MaybeISAInfo)->getExtensions(); EXPECT_EQ(Exts.size(), 1UL); - EXPECT_TRUE(Exts.at("i") == (RISCVISAInfo::ExtensionVersion{2, 1})); + EXPECT_TRUE(Exts.at("i") == (RISCVISAUtils::ExtensionVersion{2, 1})); } } @@ -481,7 +481,7 @@ TEST(ParseArchString, ASSERT_THAT_EXPECTED(MaybeISAInfo, Succeeded()); RISCVISAInfo::OrderedExtensionMap Exts = (*MaybeISAInfo)->getExtensions(); EXPECT_EQ(Exts.size(), 2UL); - EXPECT_TRUE(Exts.at("ztso") == (RISCVISAInfo::ExtensionVersion{9, 9})); + EXPECT_TRUE(Exts.at("ztso") == (RISCVISAUtils::ExtensionVersion{9, 9})); } TEST(ParseArchString, RejectsUnrecognizedVersionForExperimentalExtension) { diff --git a/llvm/unittests/TargetParser/TargetParserTest.cpp b/llvm/unittests/TargetParser/TargetParserTest.cpp index 2c72a7229b5274bd9b9231b16f2d41a337d8797f..75e235008b4f25d080c4fb7443d06470b08080b9 100644 --- a/llvm/unittests/TargetParser/TargetParserTest.cpp +++ b/llvm/unittests/TargetParser/TargetParserTest.cpp @@ -1345,6 +1345,44 @@ INSTANTIATE_TEST_SUITE_P( AArch64::AEK_JSCVT, AArch64::AEK_FCMA, AArch64::AEK_PAUTH}), "9-A"), + ARMCPUTestParams( + "neoverse-v3", "armv9.2-a", "neon-fp-armv8", + AArch64::ExtensionBitset( + {AArch64::AEK_BF16, AArch64::AEK_I8MM, + AArch64::AEK_SVE, AArch64::AEK_SVE2, + AArch64::AEK_FP16, AArch64::AEK_DOTPROD, + AArch64::AEK_LSE, AArch64::AEK_RDM, + AArch64::AEK_SIMD, AArch64::AEK_RCPC, + AArch64::AEK_RAS, AArch64::AEK_CRC, + AArch64::AEK_FP, AArch64::AEK_PROFILE, + AArch64::AEK_MTE, AArch64::AEK_SSBS, + AArch64::AEK_SB, AArch64::AEK_PREDRES, + AArch64::AEK_LS64, AArch64::AEK_BRBE, + AArch64::AEK_PAUTH, AArch64::AEK_FLAGM, + AArch64::AEK_PERFMON, AArch64::AEK_RAND, + AArch64::AEK_SVE2BITPERM, AArch64::AEK_FP16FML, + AArch64::AEK_PROFILE, AArch64::AEK_JSCVT, + AArch64::AEK_FCMA}), + "9.2-A"), + ARMCPUTestParams( + "neoverse-v3ae", "armv9.2-a", "neon-fp-armv8", + AArch64::ExtensionBitset( + {AArch64::AEK_BF16, AArch64::AEK_I8MM, + AArch64::AEK_SVE, AArch64::AEK_SVE2, + AArch64::AEK_FP16, AArch64::AEK_DOTPROD, + AArch64::AEK_LSE, AArch64::AEK_RDM, + AArch64::AEK_SIMD, AArch64::AEK_RCPC, + AArch64::AEK_RAS, AArch64::AEK_CRC, + AArch64::AEK_FP, AArch64::AEK_PROFILE, + AArch64::AEK_MTE, AArch64::AEK_SSBS, + AArch64::AEK_SB, AArch64::AEK_PREDRES, + AArch64::AEK_LS64, AArch64::AEK_BRBE, + AArch64::AEK_PAUTH, AArch64::AEK_FLAGM, + AArch64::AEK_PERFMON, AArch64::AEK_RAND, + AArch64::AEK_SVE2BITPERM, AArch64::AEK_FP16FML, + AArch64::AEK_PROFILE, AArch64::AEK_JSCVT, + AArch64::AEK_FCMA}), + "9.2-A"), ARMCPUTestParams( "cortex-r82", "armv8-r", "crypto-neon-fp-armv8", AArch64::ExtensionBitset( @@ -1636,6 +1674,24 @@ INSTANTIATE_TEST_SUITE_P( AArch64::AEK_FCMA, AArch64::AEK_PAUTH, AArch64::AEK_FP16FML}), "9-A"), + ARMCPUTestParams( + "neoverse-n3", "armv9.2-a", "neon-fp-armv8", + AArch64::ExtensionBitset( + {AArch64::AEK_BF16, AArch64::AEK_I8MM, + AArch64::AEK_SVE, AArch64::AEK_SVE2, + AArch64::AEK_FP16, AArch64::AEK_DOTPROD, + AArch64::AEK_LSE, AArch64::AEK_RDM, + AArch64::AEK_SIMD, AArch64::AEK_RCPC, + AArch64::AEK_RAS, AArch64::AEK_CRC, + AArch64::AEK_FP, AArch64::AEK_PROFILE, + AArch64::AEK_MTE, AArch64::AEK_SSBS, + AArch64::AEK_SB, AArch64::AEK_PREDRES, + AArch64::AEK_FCMA, AArch64::AEK_PAUTH, + AArch64::AEK_FLAGM, AArch64::AEK_PERFMON, + AArch64::AEK_RAND, AArch64::AEK_SVE2BITPERM, + AArch64::AEK_FP16FML, AArch64::AEK_PROFILE, + AArch64::AEK_JSCVT}), + "9.2-A"), ARMCPUTestParams( "ampere1", "armv8.6-a", "crypto-neon-fp-armv8", AArch64::ExtensionBitset( @@ -1750,7 +1806,7 @@ INSTANTIATE_TEST_SUITE_P( ARMCPUTestParams::PrintToStringParamName); // Note: number of CPUs includes aliases. -static constexpr unsigned NumAArch64CPUArchs = 72; +static constexpr unsigned NumAArch64CPUArchs = 75; TEST(TargetParserTest, testAArch64CPUArchList) { SmallVector List; diff --git a/llvm/utils/LLVMVisualizers/llvm.natvis b/llvm/utils/LLVMVisualizers/llvm.natvis index 0fc50f79466a450dae9ab99041a89a194837ec57..d83ae8013c51e2791a09c3976f67d2be8d525f1e 100644 --- a/llvm/utils/LLVMVisualizers/llvm.natvis +++ b/llvm/utils/LLVMVisualizers/llvm.natvis @@ -92,11 +92,11 @@ For later versions of Visual Studio, no setup is required. {($T1)(*(intptr_t *)Value.Data & $T5::PointerBitMask)} - {($T3)((*(intptr_t *)Value.Data >> $T5::IntShift) & $T5::IntMask)} - {$T5::IntMask}: {($T1)(*(intptr_t *)Value.Data & $T5::PointerBitMask)} [{($T3)((*(intptr_t *)Value.Data >> $T5::IntShift) & $T5::IntMask)}] + {((*(intptr_t *)Value.Data >> $T5::IntShift) & $T5::IntMask)} + {$T5::IntMask}: {($T1)(*(intptr_t *)Value.Data & $T5::PointerBitMask)} [{((*(intptr_t *)Value.Data >> $T5::IntShift) & $T5::IntMask)}] ($T1)(*(intptr_t *)Value.Data & $T5::PointerBitMask) - ($T3)((*(intptr_t *)Value.Data >> $T5::IntShift) & $T5::IntMask) + ((*(intptr_t *)Value.Data >> $T5::IntShift) & $T5::IntMask) diff --git a/llvm/utils/TableGen/ARMTargetDefEmitter.cpp b/llvm/utils/TableGen/ARMTargetDefEmitter.cpp new file mode 100644 index 0000000000000000000000000000000000000000..db87ac3336c1842fdca09b69d69346a248e10be0 --- /dev/null +++ b/llvm/utils/TableGen/ARMTargetDefEmitter.cpp @@ -0,0 +1,63 @@ +//===- ARMTargetDefEmitter.cpp - Generate data about ARM Architectures ----===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// +// +// This tablegen backend exports information about CPUs, FPUs, architectures, +// and features into a common format that can be used by both TargetParser and +// the ARM and AArch64 backends. +// +//===----------------------------------------------------------------------===// + +#include "llvm/ADT/StringSet.h" +#include "llvm/TableGen/Record.h" +#include "llvm/TableGen/TableGenBackend.h" + +using namespace llvm; + +static void EmitARMTargetDef(RecordKeeper &RK, raw_ostream &OS) { + OS << "// Autogenerated by ARMTargetDefEmitter.cpp\n\n"; + + // Look through all SubtargetFeature defs with the given FieldName, and + // collect the set of all Values that that FieldName is set to. + auto gatherSubtargetFeatureFieldValues = [&RK](StringRef FieldName) { + llvm::StringSet<> Set; + for (const Record *Rec : RK.getAllDerivedDefinitions("SubtargetFeature")) { + if (Rec->getValueAsString("FieldName") == FieldName) { + Set.insert(Rec->getValueAsString("Value")); + } + } + return Set; + }; + + // The ARMProcFamilyEnum values are initialised by SubtargetFeature defs + // which set the ARMProcFamily field. We can generate the enum from these defs + // which look like this: + // + // def ProcA5 : SubtargetFeature<"a5", "ARMProcFamily", "CortexA5", + // "Cortex-A5 ARM processors", []>; + OS << "#ifndef ARM_PROCESSOR_FAMILY\n" + << "#define ARM_PROCESSOR_FAMILY(ENUM)\n" + << "#endif\n\n"; + const StringSet<> ARMProcFamilyVals = + gatherSubtargetFeatureFieldValues("ARMProcFamily"); + for (const StringRef &Family : ARMProcFamilyVals.keys()) + OS << "ARM_PROCESSOR_FAMILY(" << Family << ")\n"; + OS << "\n#undef ARM_PROCESSOR_FAMILY\n\n"; + + OS << "#ifndef ARM_ARCHITECTURE\n" + << "#define ARM_ARCHITECTURE(ENUM)\n" + << "#endif\n\n"; + // This should correspond to instances of the Architecture tablegen class. + const StringSet<> ARMArchVals = gatherSubtargetFeatureFieldValues("ARMArch"); + for (const StringRef &Arch : ARMArchVals.keys()) + OS << "ARM_ARCHITECTURE(" << Arch << ")\n"; + OS << "\n#undef ARM_ARCHITECTURE\n\n"; +} + +static TableGen::Emitter::Opt + X("gen-arm-target-def", EmitARMTargetDef, + "Generate the ARM or AArch64 Architecture information header."); diff --git a/llvm/utils/TableGen/CMakeLists.txt b/llvm/utils/TableGen/CMakeLists.txt index 577aeded4be72c37ab76048457d24281eb77f7f3..202f33fdf8b419dee7349245072024b4f3751367 100644 --- a/llvm/utils/TableGen/CMakeLists.txt +++ b/llvm/utils/TableGen/CMakeLists.txt @@ -13,6 +13,7 @@ set(LLVM_LINK_COMPONENTS Support) # ValueType definitions. add_tablegen(llvm-min-tblgen LLVM_HEADERS TableGen.cpp + ARMTargetDefEmitter.cpp Attributes.cpp DirectiveEmitter.cpp IntrinsicEmitter.cpp @@ -32,6 +33,7 @@ set(LLVM_LINK_COMPONENTS add_tablegen(llvm-tblgen LLVM DESTINATION "${LLVM_TOOLS_INSTALL_DIR}" EXPORT LLVM + ARMTargetDefEmitter.cpp AsmMatcherEmitter.cpp AsmWriterEmitter.cpp Attributes.cpp diff --git a/llvm/utils/TableGen/Common/CodeGenDAGPatterns.cpp b/llvm/utils/TableGen/Common/CodeGenDAGPatterns.cpp index 7a5d2be3ae95b2365526914a30fca3403b45f677..88d353e89a461429029f8a60aec7d13413ead559 100644 --- a/llvm/utils/TableGen/Common/CodeGenDAGPatterns.cpp +++ b/llvm/utils/TableGen/Common/CodeGenDAGPatterns.cpp @@ -4246,7 +4246,7 @@ static TreePatternNodePtr PromoteXForms(TreePatternNodePtr N) { void CodeGenDAGPatterns::ParseOnePattern( Record *TheDef, TreePattern &Pattern, TreePattern &Result, - const std::vector &InstImpResults) { + const std::vector &InstImpResults, bool ShouldIgnore) { // Inline pattern fragments and expand multiple alternatives. Pattern.InlinePatternFragments(); @@ -4332,7 +4332,7 @@ void CodeGenDAGPatterns::ParseOnePattern( AddPatternToMatch(&Pattern, PatternToMatch(TheDef, Preds, T, Temp.getOnlyTree(), InstImpResults, Complexity, - TheDef->getID())); + TheDef->getID(), ShouldIgnore)); } } else { // Show a message about a dropped pattern with some info to make it @@ -4378,7 +4378,8 @@ void CodeGenDAGPatterns::ParsePatterns() { FindPatternInputsAndOutputs(Pattern, Pattern.getTree(j), InstInputs, InstResults, InstImpResults); - ParseOnePattern(CurPattern, Pattern, Result, InstImpResults); + ParseOnePattern(CurPattern, Pattern, Result, InstImpResults, + CurPattern->getValueAsBit("GISelShouldIgnore")); } } @@ -4407,10 +4408,10 @@ void CodeGenDAGPatterns::ExpandHwModeBasedTypes() { return; } - PatternsToMatch.emplace_back(P.getSrcRecord(), P.getPredicates(), - std::move(NewSrc), std::move(NewDst), - P.getDstRegs(), P.getAddedComplexity(), - Record::getNewUID(Records), Check); + PatternsToMatch.emplace_back( + P.getSrcRecord(), P.getPredicates(), std::move(NewSrc), + std::move(NewDst), P.getDstRegs(), P.getAddedComplexity(), + Record::getNewUID(Records), P.getGISelShouldIgnore(), Check); }; for (PatternToMatch &P : Copy) { @@ -4781,6 +4782,7 @@ void CodeGenDAGPatterns::GenerateVariants() { Variant, PatternsToMatch[i].getDstPatternShared(), PatternsToMatch[i].getDstRegs(), PatternsToMatch[i].getAddedComplexity(), Record::getNewUID(Records), + PatternsToMatch[i].getGISelShouldIgnore(), PatternsToMatch[i].getHwModeFeatures()); } diff --git a/llvm/utils/TableGen/Common/CodeGenDAGPatterns.h b/llvm/utils/TableGen/Common/CodeGenDAGPatterns.h index 7fcd39a9e940cc8769d93b46a0155ae70dedb9d3..7f94db0b7d5d761119690a6e54837bad8f886adf 100644 --- a/llvm/utils/TableGen/Common/CodeGenDAGPatterns.h +++ b/llvm/utils/TableGen/Common/CodeGenDAGPatterns.h @@ -1057,17 +1057,19 @@ class PatternToMatch { TreePatternNodePtr DstPattern; // Resulting pattern. std::vector Dstregs; // Physical register defs being matched. std::string HwModeFeatures; - int AddedComplexity; // Add to matching pattern complexity. - unsigned ID; // Unique ID for the record. + int AddedComplexity; // Add to matching pattern complexity. + bool GISelShouldIgnore; // Should GlobalISel ignore importing this pattern. + unsigned ID; // Unique ID for the record. public: PatternToMatch(Record *srcrecord, ListInit *preds, TreePatternNodePtr src, TreePatternNodePtr dst, std::vector dstregs, - int complexity, unsigned uid, const Twine &hwmodefeatures = "") + int complexity, unsigned uid, bool ignore, + const Twine &hwmodefeatures = "") : SrcRecord(srcrecord), Predicates(preds), SrcPattern(src), DstPattern(dst), Dstregs(std::move(dstregs)), HwModeFeatures(hwmodefeatures.str()), AddedComplexity(complexity), - ID(uid) {} + GISelShouldIgnore(ignore), ID(uid) {} Record *getSrcRecord() const { return SrcRecord; } ListInit *getPredicates() const { return Predicates; } @@ -1078,6 +1080,7 @@ public: const std::vector &getDstRegs() const { return Dstregs; } StringRef getHwModeFeatures() const { return HwModeFeatures; } int getAddedComplexity() const { return AddedComplexity; } + bool getGISelShouldIgnore() const { return GISelShouldIgnore; } unsigned getID() const { return ID; } std::string getPredicateCheck() const; @@ -1240,7 +1243,8 @@ private: void ParseOnePattern(Record *TheDef, TreePattern &Pattern, TreePattern &Result, - const std::vector &InstImpResults); + const std::vector &InstImpResults, + bool ShouldIgnore = false); void AddPatternToMatch(TreePattern *Pattern, PatternToMatch &&PTM); void FindPatternInputsAndOutputs( TreePattern &I, TreePatternNodePtr Pat, diff --git a/llvm/utils/TableGen/Common/GlobalISel/GlobalISelMatchTable.cpp b/llvm/utils/TableGen/Common/GlobalISel/GlobalISelMatchTable.cpp index 19d42b7688dac8f99ff66d0c413b4cb222db52af..8af219f34e18b6add76b81cfef48b99945169de2 100644 --- a/llvm/utils/TableGen/Common/GlobalISel/GlobalISelMatchTable.cpp +++ b/llvm/utils/TableGen/Common/GlobalISel/GlobalISelMatchTable.cpp @@ -723,6 +723,29 @@ void RuleMatcher::optimize() { return std::tuple(L->getKind(), L->getInsnVarID(), L->getOpIdx()) < std::tuple(R->getKind(), R->getInsnVarID(), R->getOpIdx()); }); + + // Deduplicate EraseInst actions, and if an EraseInst erases the root, place + // it at the end to favor generation of GIR_EraseRootFromParent_Done + DenseSet AlreadySeenEraseInsts; + auto EraseRootIt = Actions.end(); + auto It = Actions.begin(); + while (It != Actions.end()) { + if (const auto *EI = dyn_cast(It->get())) { + unsigned InstID = EI->getInsnID(); + if (!AlreadySeenEraseInsts.insert(InstID).second) { + It = Actions.erase(It); + continue; + } + + if (InstID == 0) + EraseRootIt = It; + } + + ++It; + } + + if (EraseRootIt != Actions.end()) + Actions.splice(Actions.end(), Actions, EraseRootIt); } bool RuleMatcher::hasFirstCondition() const { @@ -966,66 +989,60 @@ void RuleMatcher::emit(MatchTable &Table) { // We must also check if it's safe to fold the matched instructions. if (InsnVariableIDs.size() >= 2) { - // Invert the map to create stable ordering (by var names) - SmallVector InsnIDs; - for (const auto &Pair : InsnVariableIDs) { - // Skip the root node since it isn't moving anywhere. Everything else is - // sinking to meet it. - if (Pair.first == Matchers.front().get()) - continue; - - InsnIDs.push_back(Pair.second); - } - llvm::sort(InsnIDs); - - for (const auto &InsnID : InsnIDs) { - // Reject the difficult cases until we have a more accurate check. - Table << MatchTable::Opcode("GIM_CheckIsSafeToFold") - << MatchTable::Comment("InsnID") << MatchTable::ULEB128Value(InsnID) - << MatchTable::LineBreak; - // FIXME: Emit checks to determine it's _actually_ safe to fold and/or - // account for unsafe cases. - // - // Example: - // MI1--> %0 = ... - // %1 = ... %0 - // MI0--> %2 = ... %0 - // It's not safe to erase MI1. We currently handle this by not - // erasing %0 (even when it's dead). - // - // Example: - // MI1--> %0 = load volatile @a - // %1 = load volatile @a - // MI0--> %2 = ... %0 - // It's not safe to sink %0's def past %1. We currently handle - // this by rejecting all loads. - // - // Example: - // MI1--> %0 = load @a - // %1 = store @a - // MI0--> %2 = ... %0 - // It's not safe to sink %0's def past %1. We currently handle - // this by rejecting all loads. - // - // Example: - // G_CONDBR %cond, @BB1 - // BB0: - // MI1--> %0 = load @a - // G_BR @BB1 - // BB1: - // MI0--> %2 = ... %0 - // It's not always safe to sink %0 across control flow. In this - // case it may introduce a memory fault. We currentl handle - // this by rejecting all loads. - } + // FIXME: Emit checks to determine it's _actually_ safe to fold and/or + // account for unsafe cases. + // + // Example: + // MI1--> %0 = ... + // %1 = ... %0 + // MI0--> %2 = ... %0 + // It's not safe to erase MI1. We currently handle this by not + // erasing %0 (even when it's dead). + // + // Example: + // MI1--> %0 = load volatile @a + // %1 = load volatile @a + // MI0--> %2 = ... %0 + // It's not safe to sink %0's def past %1. We currently handle + // this by rejecting all loads. + // + // Example: + // MI1--> %0 = load @a + // %1 = store @a + // MI0--> %2 = ... %0 + // It's not safe to sink %0's def past %1. We currently handle + // this by rejecting all loads. + // + // Example: + // G_CONDBR %cond, @BB1 + // BB0: + // MI1--> %0 = load @a + // G_BR @BB1 + // BB1: + // MI0--> %2 = ... %0 + // It's not always safe to sink %0 across control flow. In this + // case it may introduce a memory fault. We currentl handle + // this by rejecting all loads. + + Table << MatchTable::Opcode("GIM_CheckIsSafeToFold") + << MatchTable::Comment("NumInsns") + << MatchTable::IntValue(1, InsnVariableIDs.size() - 1) + << MatchTable::LineBreak; } for (const auto &PM : EpilogueMatchers) PM->emitPredicateOpcodes(Table, *this); - for (const auto &MA : Actions) - MA->emitActionOpcodes(Table, *this); + // Emit all actions except the last one, then emit coverage and emit the + // final action. + // + // This is because some actions, such as GIR_EraseRootFromParent_Done, also + // double as a GIR_Done and terminate execution of the rule. + if (!Actions.empty()) { + for (const auto &MA : drop_end(Actions)) + MA->emitActionOpcodes(Table, *this); + } assert((Table.isWithCoverage() ? !Table.isCombiner() : true) && "Combiner tables don't support coverage!"); @@ -1036,8 +1053,13 @@ void RuleMatcher::emit(MatchTable &Table) { Table << MatchTable::Comment(("GIR_Coverage, " + Twine(RuleID) + ",").str()) << MatchTable::LineBreak; - Table << MatchTable::Opcode("GIR_Done", -1) << MatchTable::LineBreak - << MatchTable::Label(LabelID); + if (Actions.empty() || + !Actions.back()->emitActionOpcodesAndDone(Table, *this)) { + Table << MatchTable::Opcode("GIR_Done", -1) << MatchTable::LineBreak; + } + + Table << MatchTable::Label(LabelID); + ++NumPatternEmitted; } @@ -1140,10 +1162,14 @@ bool LLTOperandMatcher::hasValue() const { void LLTOperandMatcher::emitPredicateOpcodes(MatchTable &Table, RuleMatcher &Rule) const { - Table << MatchTable::Opcode("GIM_CheckType") << MatchTable::Comment("MI") - << MatchTable::ULEB128Value(InsnVarID) << MatchTable::Comment("Op") - << MatchTable::ULEB128Value(OpIdx) << MatchTable::Comment("Type") - << getValue() << MatchTable::LineBreak; + if (InsnVarID == 0) { + Table << MatchTable::Opcode("GIM_RootCheckType"); + } else { + Table << MatchTable::Opcode("GIM_CheckType") << MatchTable::Comment("MI") + << MatchTable::ULEB128Value(InsnVarID); + } + Table << MatchTable::Comment("Op") << MatchTable::ULEB128Value(OpIdx) + << MatchTable::Comment("Type") << getValue() << MatchTable::LineBreak; } //===- PointerToAnyOperandMatcher -----------------------------------------===// @@ -1205,9 +1231,14 @@ bool RegisterBankOperandMatcher::isIdentical(const PredicateMatcher &B) const { void RegisterBankOperandMatcher::emitPredicateOpcodes(MatchTable &Table, RuleMatcher &Rule) const { - Table << MatchTable::Opcode("GIM_CheckRegBankForClass") - << MatchTable::Comment("MI") << MatchTable::ULEB128Value(InsnVarID) - << MatchTable::Comment("Op") << MatchTable::ULEB128Value(OpIdx) + if (InsnVarID == 0) { + Table << MatchTable::Opcode("GIM_RootCheckRegBankForClass"); + } else { + Table << MatchTable::Opcode("GIM_CheckRegBankForClass") + << MatchTable::Comment("MI") << MatchTable::ULEB128Value(InsnVarID); + } + + Table << MatchTable::Comment("Op") << MatchTable::ULEB128Value(OpIdx) << MatchTable::Comment("RC") << MatchTable::NamedValue(2, RC.getQualifiedIdName()) << MatchTable::LineBreak; @@ -1810,17 +1841,28 @@ OperandRenderer::~OperandRenderer() {} //===- CopyRenderer -------------------------------------------------------===// +void CopyRenderer::emitRenderOpcodes(MatchTable &Table, RuleMatcher &Rule, + unsigned NewInsnID, unsigned OldInsnID, + unsigned OpIdx, StringRef Name) { + if (NewInsnID == 0 && OldInsnID == 0) { + Table << MatchTable::Opcode("GIR_RootToRootCopy"); + } else { + Table << MatchTable::Opcode("GIR_Copy") << MatchTable::Comment("NewInsnID") + << MatchTable::ULEB128Value(NewInsnID) + << MatchTable::Comment("OldInsnID") + << MatchTable::ULEB128Value(OldInsnID); + } + + Table << MatchTable::Comment("OpIdx") << MatchTable::ULEB128Value(OpIdx) + << MatchTable::Comment(Name) << MatchTable::LineBreak; +} + void CopyRenderer::emitRenderOpcodes(MatchTable &Table, RuleMatcher &Rule) const { const OperandMatcher &Operand = Rule.getOperandMatcher(SymbolicName); unsigned OldInsnVarID = Rule.getInsnVarID(Operand.getInstructionMatcher()); - Table << MatchTable::Opcode("GIR_Copy") << MatchTable::Comment("NewInsnID") - << MatchTable::ULEB128Value(NewInsnID) - << MatchTable::Comment("OldInsnID") - << MatchTable::ULEB128Value(OldInsnVarID) - << MatchTable::Comment("OpIdx") - << MatchTable::ULEB128Value(Operand.getOpIdx()) - << MatchTable::Comment(SymbolicName) << MatchTable::LineBreak; + emitRenderOpcodes(Table, Rule, NewInsnID, OldInsnVarID, Operand.getOpIdx(), + SymbolicName); } //===- CopyPhysRegRenderer ------------------------------------------------===// @@ -1829,13 +1871,8 @@ void CopyPhysRegRenderer::emitRenderOpcodes(MatchTable &Table, RuleMatcher &Rule) const { const OperandMatcher &Operand = Rule.getPhysRegOperandMatcher(PhysReg); unsigned OldInsnVarID = Rule.getInsnVarID(Operand.getInstructionMatcher()); - Table << MatchTable::Opcode("GIR_Copy") << MatchTable::Comment("NewInsnID") - << MatchTable::ULEB128Value(NewInsnID) - << MatchTable::Comment("OldInsnID") - << MatchTable::ULEB128Value(OldInsnVarID) - << MatchTable::Comment("OpIdx") - << MatchTable::ULEB128Value(Operand.getOpIdx()) - << MatchTable::Comment(PhysReg->getName()) << MatchTable::LineBreak; + CopyRenderer::emitRenderOpcodes(Table, Rule, NewInsnID, OldInsnVarID, + Operand.getOpIdx(), PhysReg->getName()); } //===- CopyOrAddZeroRegRenderer -------------------------------------------===// @@ -2185,10 +2222,17 @@ void BuildMIAction::emitActionOpcodes(MatchTable &Table, // TODO: Simple permutation looks like it could be almost as common as // mutation due to commutative operations. - Table << MatchTable::Opcode("GIR_BuildMI") << MatchTable::Comment("InsnID") - << MatchTable::ULEB128Value(InsnID) << MatchTable::Comment("Opcode") + if (InsnID == 0) { + Table << MatchTable::Opcode("GIR_BuildRootMI"); + } else { + Table << MatchTable::Opcode("GIR_BuildMI") << MatchTable::Comment("InsnID") + << MatchTable::ULEB128Value(InsnID); + } + + Table << MatchTable::Comment("Opcode") << MatchTable::NamedValue(2, I->Namespace, I->TheDef->getName()) << MatchTable::LineBreak; + for (const auto &Renderer : OperandRenderers) Renderer->emitRenderOpcodes(Table, Rule); @@ -2244,8 +2288,8 @@ void BuildConstantAction::emitActionOpcodes(MatchTable &Table, //===- EraseInstAction ----------------------------------------------------===// -void EraseInstAction::emitActionOpcodes(MatchTable &Table, RuleMatcher &Rule, - unsigned InsnID) { +void EraseInstAction::emitActionOpcodes(MatchTable &Table, + RuleMatcher &Rule) const { // Avoid erasing the same inst twice. if (!Rule.tryEraseInsnID(InsnID)) return; @@ -2255,9 +2299,19 @@ void EraseInstAction::emitActionOpcodes(MatchTable &Table, RuleMatcher &Rule, << MatchTable::LineBreak; } -void EraseInstAction::emitActionOpcodes(MatchTable &Table, - RuleMatcher &Rule) const { - emitActionOpcodes(Table, Rule, InsnID); +bool EraseInstAction::emitActionOpcodesAndDone(MatchTable &Table, + RuleMatcher &Rule) const { + if (InsnID != 0) { + emitActionOpcodes(Table, Rule); + return false; + } + + if (!Rule.tryEraseInsnID(0)) + return false; + + Table << MatchTable::Opcode("GIR_EraseRootFromParent_Done", -1) + << MatchTable::LineBreak; + return true; } //===- ReplaceRegAction ---------------------------------------------------===// diff --git a/llvm/utils/TableGen/Common/GlobalISel/GlobalISelMatchTable.h b/llvm/utils/TableGen/Common/GlobalISel/GlobalISelMatchTable.h index 871fe04465aa9639e89b82eb9edf138c7d2d8dc1..30301c28ce6c4dab4309b6efca1e4d7df975e0c5 100644 --- a/llvm/utils/TableGen/Common/GlobalISel/GlobalISelMatchTable.h +++ b/llvm/utils/TableGen/Common/GlobalISel/GlobalISelMatchTable.h @@ -1884,6 +1884,10 @@ public: StringRef getSymbolicName() const { return SymbolicName; } + static void emitRenderOpcodes(MatchTable &Table, RuleMatcher &Rule, + unsigned NewInsnID, unsigned OldInsnID, + unsigned OpIdx, StringRef Name); + void emitRenderOpcodes(MatchTable &Table, RuleMatcher &Rule) const override; }; @@ -2226,6 +2230,15 @@ public: virtual void emitActionOpcodes(MatchTable &Table, RuleMatcher &Rule) const = 0; + /// If this opcode has an overload that can call GIR_Done directly, emit that + /// instead of the usual opcode and return "true". Return "false" if GIR_Done + /// still needs to be emitted. + virtual bool emitActionOpcodesAndDone(MatchTable &Table, + RuleMatcher &Rule) const { + emitActionOpcodes(Table, Rule); + return false; + } + private: ActionKind Kind; }; @@ -2334,13 +2347,15 @@ public: EraseInstAction(unsigned InsnID) : MatchAction(AK_EraseInst), InsnID(InsnID) {} + unsigned getInsnID() const { return InsnID; } + static bool classof(const MatchAction *A) { return A->getKind() == AK_EraseInst; } void emitActionOpcodes(MatchTable &Table, RuleMatcher &Rule) const override; - static void emitActionOpcodes(MatchTable &Table, RuleMatcher &Rule, - unsigned InsnID); + bool emitActionOpcodesAndDone(MatchTable &Table, + RuleMatcher &Rule) const override; }; class ReplaceRegAction : public MatchAction { @@ -2381,9 +2396,14 @@ public: } void emitActionOpcodes(MatchTable &Table, RuleMatcher &Rule) const override { - Table << MatchTable::Opcode("GIR_ConstrainSelectedInstOperands") - << MatchTable::Comment("InsnID") << MatchTable::ULEB128Value(InsnID) - << MatchTable::LineBreak; + if (InsnID == 0) { + Table << MatchTable::Opcode("GIR_RootConstrainSelectedInstOperands") + << MatchTable::LineBreak; + } else { + Table << MatchTable::Opcode("GIR_ConstrainSelectedInstOperands") + << MatchTable::Comment("InsnID") << MatchTable::ULEB128Value(InsnID) + << MatchTable::LineBreak; + } } }; diff --git a/llvm/utils/TableGen/DAGISelMatcherEmitter.cpp b/llvm/utils/TableGen/DAGISelMatcherEmitter.cpp index dcecac4380ce23eb9e18b5cbe057f3fdd23beb2e..ff508d6487333069f18630ee07b07b6799a05ed6 100644 --- a/llvm/utils/TableGen/DAGISelMatcherEmitter.cpp +++ b/llvm/utils/TableGen/DAGISelMatcherEmitter.cpp @@ -1352,7 +1352,7 @@ void llvm::EmitMatcherTable(Matcher *TheMatcher, const CodeGenDAGPatterns &CGP, MatcherEmitter.EmitHistogram(TheMatcher, OS); OS << " #undef TARGET_VAL\n"; - OS << " SelectCodeCommon(N, MatcherTable,sizeof(MatcherTable));\n"; + OS << " SelectCodeCommon(N, MatcherTable, sizeof(MatcherTable));\n"; OS << "}\n"; EndEmitFunction(OS); diff --git a/llvm/utils/TableGen/DXILEmitter.cpp b/llvm/utils/TableGen/DXILEmitter.cpp index f2504775d557f2fd58d4acef31bec6dfb0bf9029..0439df8067ede8e815c78ec40573f1b86f592390 100644 --- a/llvm/utils/TableGen/DXILEmitter.cpp +++ b/llvm/utils/TableGen/DXILEmitter.cpp @@ -97,7 +97,7 @@ static ParameterKind getParameterKind(const Record *R) { if (R->getValueAsInt("isHalfOrFloat") || R->getValueAsInt("isI16OrI32")) { return ParameterKind::Overload; } - LLVM_FALLTHROUGH; + [[fallthrough]]; default: llvm_unreachable("Support for specified DXIL Type not yet implemented"); } @@ -272,7 +272,7 @@ static std::string getOverloadKindStr(const Record *R) { return "OverloadKind::I16 | OverloadKind::I32"; } } - LLVM_FALLTHROUGH; + [[fallthrough]]; default: llvm_unreachable( "Support for specified parameter OverloadKind not yet implemented"); diff --git a/llvm/utils/TableGen/GlobalISelEmitter.cpp b/llvm/utils/TableGen/GlobalISelEmitter.cpp index 25e302ce1ca46f5a36a1f5cceb7fcfba81901a48..78abf80e7aecb38f6f4b5785f88d8eaef49388fb 100644 --- a/llvm/utils/TableGen/GlobalISelEmitter.cpp +++ b/llvm/utils/TableGen/GlobalISelEmitter.cpp @@ -2411,6 +2411,8 @@ void GlobalISelEmitter::run(raw_ostream &OS) { for (const PatternToMatch &Pat : CGP.ptms()) { ++NumPatternTotal; + if (Pat.getGISelShouldIgnore()) + continue; // skip without warning auto MatcherOrErr = runOnPattern(Pat); // The pattern analysis can fail, indicating an unsupported pattern. diff --git a/llvm/utils/TableGen/RISCVTargetDefEmitter.cpp b/llvm/utils/TableGen/RISCVTargetDefEmitter.cpp index 653e5c5fdb4219fa4699ec086c67794d4719d3f6..217b531dcfd394980c369205fff5f56f425d2f87 100644 --- a/llvm/utils/TableGen/RISCVTargetDefEmitter.cpp +++ b/llvm/utils/TableGen/RISCVTargetDefEmitter.cpp @@ -6,17 +6,105 @@ // //===----------------------------------------------------------------------===// // -// This tablegen backend emits the include file needed by the target -// parser to parse the RISC-V CPUs. +// This tablegen backend emits the include file needed by RISCVTargetParser.cpp +// and RISCVISAInfo.cpp to parse the RISC-V CPUs and extensions. // //===----------------------------------------------------------------------===// -#include "llvm/Support/RISCVISAInfo.h" +#include "llvm/Support/RISCVISAUtils.h" #include "llvm/TableGen/Record.h" #include "llvm/TableGen/TableGenBackend.h" using namespace llvm; +static StringRef getExtensionName(const Record *R) { + StringRef Name = R->getValueAsString("Name"); + Name.consume_front("experimental-"); + return Name; +} + +static void printExtensionTable(raw_ostream &OS, + const std::vector &Extensions, + bool Experimental) { + OS << "static const RISCVSupportedExtension Supported"; + if (Experimental) + OS << "Experimental"; + OS << "Extensions[] = {\n"; + + for (Record *R : Extensions) { + if (R->getValueAsBit("Experimental") != Experimental) + continue; + + OS << " {\"" << getExtensionName(R) << "\", {" + << R->getValueAsInt("MajorVersion") << ", " + << R->getValueAsInt("MinorVersion") << "}},\n"; + } + + OS << "};\n\n"; +} + +// Get the extension name from the Record name. This gives the canonical +// capitalization. +static StringRef getExtensionNameFromRecordName(const Record *R) { + StringRef Name = R->getName(); + if (!Name.consume_front("FeatureStdExt")) + Name.consume_front("FeatureVendor"); + + return Name; +} + +static void emitRISCVExtensions(RecordKeeper &Records, raw_ostream &OS) { + OS << "#ifdef GET_SUPPORTED_EXTENSIONS\n"; + OS << "#undef GET_SUPPORTED_EXTENSIONS\n\n"; + + std::vector Extensions = + Records.getAllDerivedDefinitions("RISCVExtension"); + llvm::sort(Extensions, [](const Record *Rec1, const Record *Rec2) { + return getExtensionName(Rec1) < getExtensionName(Rec2); + }); + + printExtensionTable(OS, Extensions, /*Experimental=*/false); + printExtensionTable(OS, Extensions, /*Experimental=*/true); + + OS << "#endif // GET_SUPPORTED_EXTENSIONS\n\n"; + + OS << "#ifdef GET_IMPLIED_EXTENSIONS\n"; + OS << "#undef GET_IMPLIED_EXTENSIONS\n\n"; + + for (Record *Ext : Extensions) { + auto ImpliesList = Ext->getValueAsListOfDefs("Implies"); + if (ImpliesList.empty()) + continue; + + OS << "static const char *ImpliedExts" + << getExtensionNameFromRecordName(Ext) << "[] = {"; + + ListSeparator LS(", "); + for (auto *ImpliedExt : ImpliesList) { + if (!ImpliedExt->isSubClassOf("RISCVExtension")) + continue; + + OS << LS << '"' << getExtensionName(ImpliedExt) << '"'; + } + + OS << "};\n"; + } + + OS << "\nstatic constexpr ImpliedExtsEntry ImpliedExts[] = {\n"; + for (Record *Ext : Extensions) { + auto ImpliesList = Ext->getValueAsListOfDefs("Implies"); + if (ImpliesList.empty()) + continue; + + OS << " { {\"" << getExtensionName(Ext) << "\"}, {ImpliedExts" + << getExtensionNameFromRecordName(Ext) << "} },\n"; + } + + OS << "};\n\n"; + + OS << "#endif // GET_IMPLIED_EXTENSIONS\n\n"; +} + // We can generate march string from target features as what has been described // in RISC-V ISA specification (version 20191213) 'Chapter 27. ISA Extension // Naming Conventions'. @@ -24,8 +112,8 @@ using namespace llvm; // This is almost the same as RISCVFeatures::parseFeatureBits, except that we // get feature name from feature records instead of feature bits. static void printMArch(raw_ostream &OS, const Record &Rec) { - std::map + std::map Extensions; unsigned XLen = 0; @@ -54,7 +142,7 @@ static void printMArch(raw_ostream &OS, const Record &Rec) { OS << LS << Ext.first << Ext.second.Major << 'p' << Ext.second.Minor; } -static void EmitRISCVTargetDef(RecordKeeper &RK, raw_ostream &OS) { +static void emitRISCVProcs(RecordKeeper &RK, raw_ostream &OS) { OS << "#ifndef PROC\n" << "#define PROC(ENUM, NAME, DEFAULT_MARCH, FAST_UNALIGNED_ACCESS)\n" << "#endif\n\n"; @@ -101,5 +189,11 @@ static void EmitRISCVTargetDef(RecordKeeper &RK, raw_ostream &OS) { OS << "\n#undef TUNE_PROC\n"; } +static void EmitRISCVTargetDef(RecordKeeper &RK, raw_ostream &OS) { + emitRISCVExtensions(RK, OS); + emitRISCVProcs(RK, OS); +} + static TableGen::Emitter::Opt X("gen-riscv-target-def", EmitRISCVTargetDef, - "Generate the list of CPU for RISCV"); + "Generate the list of CPUs and extensions for " + "RISC-V"); diff --git a/llvm/utils/gn/secondary/clang-tools-extra/clang-tidy/bugprone/BUILD.gn b/llvm/utils/gn/secondary/clang-tools-extra/clang-tidy/bugprone/BUILD.gn index cd90c7752e1642fa0ce6c790f6066747065081de..bbf2b84334d9d500249b0d838dd3b5ea64bb18a7 100644 --- a/llvm/utils/gn/secondary/clang-tools-extra/clang-tidy/bugprone/BUILD.gn +++ b/llvm/utils/gn/secondary/clang-tools-extra/clang-tidy/bugprone/BUILD.gn @@ -61,6 +61,7 @@ static_library("bugprone") { "PosixReturnCheck.cpp", "RedundantBranchConditionCheck.cpp", "ReservedIdentifierCheck.cpp", + "ReturnConstRefFromParameterCheck.cpp", "SharedPtrArrayMismatchCheck.cpp", "SignalHandlerCheck.cpp", "SignedCharMisuseCheck.cpp", diff --git a/llvm/utils/gn/secondary/clang-tools-extra/clang-tidy/modernize/BUILD.gn b/llvm/utils/gn/secondary/clang-tools-extra/clang-tidy/modernize/BUILD.gn index c9e081383fa02695e16345940cbda19fa3e7ff3f..0d27b786da1f6341fb0598093edff446a6fc3f65 100644 --- a/llvm/utils/gn/secondary/clang-tools-extra/clang-tidy/modernize/BUILD.gn +++ b/llvm/utils/gn/secondary/clang-tools-extra/clang-tidy/modernize/BUILD.gn @@ -25,6 +25,7 @@ static_library("modernize") { "MakeSharedCheck.cpp", "MakeSmartPtrCheck.cpp", "MakeUniqueCheck.cpp", + "MinMaxUseInitializerListCheck.cpp", "ModernizeTidyModule.cpp", "PassByValueCheck.cpp", "RawStringLiteralCheck.cpp", diff --git a/llvm/utils/gn/secondary/clang-tools-extra/clang-tidy/readability/BUILD.gn b/llvm/utils/gn/secondary/clang-tools-extra/clang-tidy/readability/BUILD.gn index 59dc38c8c4d8a8004df4f951d39372fb0a06beaf..815c5a93c72f752f1c107d367a06fcab757ce557 100644 --- a/llvm/utils/gn/secondary/clang-tools-extra/clang-tidy/readability/BUILD.gn +++ b/llvm/utils/gn/secondary/clang-tools-extra/clang-tidy/readability/BUILD.gn @@ -35,6 +35,7 @@ static_library("readability") { "IsolateDeclarationCheck.cpp", "MagicNumbersCheck.cpp", "MakeMemberFunctionConstCheck.cpp", + "MathMissingParenthesesCheck.cpp", "MisleadingIndentationCheck.cpp", "MisplacedArrayIndexCheck.cpp", "NamedParameterCheck.cpp", diff --git a/llvm/utils/gn/secondary/llvm/include/llvm/TargetParser/BUILD.gn b/llvm/utils/gn/secondary/llvm/include/llvm/TargetParser/BUILD.gn index aecb65ab6c728de9151be2d15596c809fbb035b8..a71dfa518b1df3b214841c879cb19e2184d45828 100644 --- a/llvm/utils/gn/secondary/llvm/include/llvm/TargetParser/BUILD.gn +++ b/llvm/utils/gn/secondary/llvm/include/llvm/TargetParser/BUILD.gn @@ -1,5 +1,19 @@ import("//llvm/utils/TableGen/tablegen.gni") +tablegen("ARMTargetParserDef") { + visibility = [ ":gen" ] + args = [ "-gen-arm-target-def" ] + td_file = "//llvm/lib/Target/ARM/ARM.td" + tblgen_target = "//llvm/utils/TableGen:llvm-min-tblgen" +} + +tablegen("AArch64TargetParserDef") { + visibility = [ ":gen" ] + args = [ "-gen-arm-target-def" ] + td_file = "//llvm/lib/Target/AArch64/AArch64.td" + tblgen_target = "//llvm/utils/TableGen:llvm-min-tblgen" +} + tablegen("RISCVTargetParserDef") { visibility = [ ":gen" ] args = [ "-gen-riscv-target-def" ] @@ -8,5 +22,9 @@ tablegen("RISCVTargetParserDef") { } group("gen") { - deps = [ ":RISCVTargetParserDef" ] + deps = [ + ":ARMTargetParserDef", + ":AArch64TargetParserDef", + ":RISCVTargetParserDef", + ] } diff --git a/llvm/utils/gn/secondary/llvm/lib/IR/BUILD.gn b/llvm/utils/gn/secondary/llvm/lib/IR/BUILD.gn index 896b031a7bd3fd4ab1c48efd481e5ab762562646..247ef480f5f1a45fc3ca93cf530b20ffe80b544f 100644 --- a/llvm/utils/gn/secondary/llvm/lib/IR/BUILD.gn +++ b/llvm/utils/gn/secondary/llvm/lib/IR/BUILD.gn @@ -31,8 +31,8 @@ static_library("IR") { "DataLayout.cpp", "DebugInfo.cpp", "DebugInfoMetadata.cpp", - "DebugProgramInstruction.cpp", "DebugLoc.cpp", + "DebugProgramInstruction.cpp", "DiagnosticHandler.cpp", "DiagnosticInfo.cpp", "DiagnosticPrinter.cpp", @@ -55,6 +55,7 @@ static_library("IR") { "LegacyPassManager.cpp", "MDBuilder.cpp", "Mangler.cpp", + "MemoryModelRelaxationAnnotations.cpp", "Metadata.cpp", "Module.cpp", "ModuleSummaryIndex.cpp", @@ -79,10 +80,10 @@ static_library("IR") { "TypedPointerType.cpp", "Use.cpp", "User.cpp", + "VFABIDemangler.cpp", "Value.cpp", "ValueSymbolTable.cpp", "VectorBuilder.cpp", "Verifier.cpp", - "VFABIDemangler.cpp", ] } diff --git a/llvm/utils/gn/secondary/llvm/lib/Support/BUILD.gn b/llvm/utils/gn/secondary/llvm/lib/Support/BUILD.gn index ba0f6d8c0f8cff88b392b58aa9765c85d27772ea..941d448b3367c16467bd5602858d4ce6bdf3163d 100644 --- a/llvm/utils/gn/secondary/llvm/lib/Support/BUILD.gn +++ b/llvm/utils/gn/secondary/llvm/lib/Support/BUILD.gn @@ -119,7 +119,7 @@ static_library("Support") { "PrettyStackTrace.cpp", "RISCVAttributeParser.cpp", "RISCVAttributes.cpp", - "RISCVISAInfo.cpp", + "RISCVISAUtils.cpp", "RWMutex.cpp", "RandomNumberGenerator.cpp", "Regex.cpp", diff --git a/llvm/utils/gn/secondary/llvm/lib/TargetParser/BUILD.gn b/llvm/utils/gn/secondary/llvm/lib/TargetParser/BUILD.gn index 1a91bb7e6fa9f5468f50395153f24a38b24a4ac0..31919badac7be3e20e99a3d4809ad429e3c2f078 100644 --- a/llvm/utils/gn/secondary/llvm/lib/TargetParser/BUILD.gn +++ b/llvm/utils/gn/secondary/llvm/lib/TargetParser/BUILD.gn @@ -13,6 +13,7 @@ static_library("TargetParser") { "CSKYTargetParser.cpp", "Host.cpp", "LoongArchTargetParser.cpp", + "RISCVISAInfo.cpp", "RISCVTargetParser.cpp", "SubtargetFeature.cpp", "TargetParser.cpp", diff --git a/llvm/utils/gn/secondary/llvm/unittests/IR/BUILD.gn b/llvm/utils/gn/secondary/llvm/unittests/IR/BUILD.gn index 4ffd6d4d182e1702dd17249acf8397dbea68be19..8f6caf2e575be68ff7c30ed6d42641010bb7433f 100644 --- a/llvm/utils/gn/secondary/llvm/unittests/IR/BUILD.gn +++ b/llvm/utils/gn/secondary/llvm/unittests/IR/BUILD.gn @@ -33,6 +33,7 @@ unittest("IRTests") { "LegacyPassManagerTest.cpp", "MDBuilderTest.cpp", "ManglerTest.cpp", + "MemoryModelRelaxationAnnotationsTest.cpp", "MetadataTest.cpp", "ModuleSummaryIndexTest.cpp", "ModuleTest.cpp", @@ -45,6 +46,7 @@ unittest("IRTests") { "TypesTest.cpp", "UseTest.cpp", "UserTest.cpp", + "VFABIDemanglerTest.cpp", "VPIntrinsicTest.cpp", "ValueHandleTest.cpp", "ValueMapTest.cpp", @@ -52,6 +54,5 @@ unittest("IRTests") { "VectorBuilderTest.cpp", "VectorTypesTest.cpp", "VerifierTest.cpp", - "VFABIDemanglerTest.cpp", ] } diff --git a/llvm/utils/gn/secondary/llvm/unittests/Support/BUILD.gn b/llvm/utils/gn/secondary/llvm/unittests/Support/BUILD.gn index 7a152fdcc0598257c14165eded0efdfacd3a6f38..c7356dd33a37b140dfd4360c3118e5a65a6217e4 100644 --- a/llvm/utils/gn/secondary/llvm/unittests/Support/BUILD.gn +++ b/llvm/utils/gn/secondary/llvm/unittests/Support/BUILD.gn @@ -71,7 +71,6 @@ unittest("SupportTests") { "ProcessTest.cpp", "ProgramTest.cpp", "RISCVAttributeParserTest.cpp", - "RISCVISAInfoTest.cpp", "RegexTest.cpp", "ReplaceFileTest.cpp", "ReverseIterationTest.cpp", diff --git a/llvm/utils/gn/secondary/llvm/unittests/TargetParser/BUILD.gn b/llvm/utils/gn/secondary/llvm/unittests/TargetParser/BUILD.gn index eebaf67767f477513df62805b378260a9a932e39..3739614c316093258dd77fc2df693930848c9312 100644 --- a/llvm/utils/gn/secondary/llvm/unittests/TargetParser/BUILD.gn +++ b/llvm/utils/gn/secondary/llvm/unittests/TargetParser/BUILD.gn @@ -10,6 +10,7 @@ unittest("TargetParserTests") { sources = [ "CSKYTargetParserTest.cpp", "Host.cpp", + "RISCVISAInfoTest.cpp", "RISCVTargetParserTest.cpp", "TargetParserTest.cpp", "TripleTest.cpp", diff --git a/llvm/utils/gn/secondary/llvm/utils/TableGen/BUILD.gn b/llvm/utils/gn/secondary/llvm/utils/TableGen/BUILD.gn index 53a9d8d01519a7f0555d5e4a008f2e5439e255cc..f3ae5b5899ac6a3bb2792907628795b66f8cd17d 100644 --- a/llvm/utils/gn/secondary/llvm/utils/TableGen/BUILD.gn +++ b/llvm/utils/gn/secondary/llvm/utils/TableGen/BUILD.gn @@ -1,5 +1,6 @@ source_set("llvm-min-tblgen-sources") { sources = [ + "ARMTargetDefEmitter.cpp", "Attributes.cpp", "DirectiveEmitter.cpp", "IntrinsicEmitter.cpp", diff --git a/mlir/CMakeLists.txt b/mlir/CMakeLists.txt index 5c4301af040b47e2dfb51c4067e78679b1295847..4c0ef8387b8dff11530647c05216b4f40053a9c2 100644 --- a/mlir/CMakeLists.txt +++ b/mlir/CMakeLists.txt @@ -185,10 +185,13 @@ include_directories( ${MLIR_INCLUDE_DIR}) add_subdirectory(tools/mlir-linalg-ods-gen) add_subdirectory(tools/mlir-pdll) add_subdirectory(tools/mlir-tblgen) +add_subdirectory(tools/mlir-src-sharder) set(MLIR_TABLEGEN_EXE "${MLIR_TABLEGEN_EXE}" CACHE INTERNAL "") set(MLIR_TABLEGEN_TARGET "${MLIR_TABLEGEN_TARGET}" CACHE INTERNAL "") set(MLIR_PDLL_TABLEGEN_EXE "${MLIR_PDLL_TABLEGEN_EXE}" CACHE INTERNAL "") set(MLIR_PDLL_TABLEGEN_TARGET "${MLIR_PDLL_TABLEGEN_TARGET}" CACHE INTERNAL "") +set(MLIR_SRC_SHARDER_TABLEGEN_EXE "${MLIR_SRC_SHARDER_TABLEGEN_EXE}" CACHE INTERNAL "") +set(MLIR_SRC_SHARDER_TABLEGEN_TARGET "${MLIR_SRC_SHARDER_TABLEGEN_TARGET}" CACHE INTERNAL "") add_subdirectory(include/mlir) add_subdirectory(lib) diff --git a/mlir/cmake/modules/AddMLIR.cmake b/mlir/cmake/modules/AddMLIR.cmake index 1d2ed748bc2f13dc555bb808a7ffd63bbfaede20..afb74fb2d0002550c2b8e584a0a7381d8f5196ae 100644 --- a/mlir/cmake/modules/AddMLIR.cmake +++ b/mlir/cmake/modules/AddMLIR.cmake @@ -5,6 +5,28 @@ function(mlir_tablegen ofn) tablegen(MLIR ${ARGV}) set(TABLEGEN_OUTPUT ${TABLEGEN_OUTPUT} ${CMAKE_CURRENT_BINARY_DIR}/${ofn} PARENT_SCOPE) + + # Get the current set of include paths for this td file. + cmake_parse_arguments(ARG "" "" "DEPENDS;EXTRA_INCLUDES" ${ARGN}) + get_directory_property(tblgen_includes INCLUDE_DIRECTORIES) + list(APPEND tblgen_includes ${ARG_EXTRA_INCLUDES}) + # Filter out any empty include items. + list(REMOVE_ITEM tblgen_includes "") + + # Build the absolute path for the current input file. + if (IS_ABSOLUTE ${LLVM_TARGET_DEFINITIONS}) + set(LLVM_TARGET_DEFINITIONS_ABSOLUTE ${LLVM_TARGET_DEFINITIONS}) + else() + set(LLVM_TARGET_DEFINITIONS_ABSOLUTE ${CMAKE_CURRENT_SOURCE_DIR}/${LLVM_TARGET_DEFINITIONS}) + endif() + + # Append the includes used for this file to the tablegen_compile_commands + # file. + file(APPEND ${CMAKE_BINARY_DIR}/tablegen_compile_commands.yml + "--- !FileInfo:\n" + " filepath: \"${LLVM_TARGET_DEFINITIONS_ABSOLUTE}\"\n" + " includes: \"${CMAKE_CURRENT_SOURCE_DIR};${tblgen_includes}\"\n" + ) endfunction() # Clear out any pre-existing compile_commands file before processing. This @@ -149,6 +171,22 @@ function(add_mlir_dialect dialect dialect_namespace) add_dependencies(mlir-headers MLIR${dialect}IncGen) endfunction() +# Declare sharded dialect operation declarations and definitions +function(add_sharded_ops ops_target shard_count) + set(LLVM_TARGET_DEFINITIONS ${ops_target}.td) + mlir_tablegen(${ops_target}.h.inc -gen-op-decls -op-shard-count=${shard_count}) + mlir_tablegen(${ops_target}.cpp.inc -gen-op-defs -op-shard-count=${shard_count}) + set(LLVM_TARGET_DEFINITIONS ${ops_target}.cpp) + foreach(index RANGE ${shard_count}) + set(SHARDED_SRC ${ops_target}.${index}.cpp) + list(APPEND SHARDED_SRCS ${SHARDED_SRC}) + tablegen(MLIR_SRC_SHARDER ${SHARDED_SRC} -op-shard-index=${index}) + set(TABLEGEN_OUTPUT ${TABLEGEN_OUTPUT} ${CMAKE_CURRENT_BINARY_DIR}/${SHARDED_SRC}) + endforeach() + add_public_tablegen_target(MLIR${ops_target}ShardGen) + set(SHARDED_SRCS ${SHARDED_SRCS} PARENT_SCOPE) +endfunction() + # Declare a dialect in the include directory function(add_mlir_interface interface) set(LLVM_TARGET_DEFINITIONS ${interface}.td) diff --git a/mlir/cmake/modules/CMakeLists.txt b/mlir/cmake/modules/CMakeLists.txt index 8d2904ef46dfe81deb96f4175fc3a970442f2337..3ac1c79b090ed6c330b17a26bf430ad8ee1bd90d 100644 --- a/mlir/cmake/modules/CMakeLists.txt +++ b/mlir/cmake/modules/CMakeLists.txt @@ -39,6 +39,7 @@ set(MLIR_CONFIG_INCLUDE_DIRS # Refer to the best host mlir-tbgen, which might be a host-optimized version set(MLIR_CONFIG_TABLEGEN_EXE "${MLIR_TABLEGEN_EXE}") set(MLIR_CONFIG_PDLL_TABLEGEN_EXE "${MLIR_PDLL_TABLEGEN_EXE}") +set(MLIR_CONFIG_SRC_SHARDER_TABLEGEN_EXE "${MLIR_SRC_SHARDER_TABLEGEN_EXE}") configure_file( ${CMAKE_CURRENT_SOURCE_DIR}/MLIRConfig.cmake.in @@ -77,6 +78,7 @@ set(MLIR_CONFIG_INCLUDE_DIRS # if we're building with a host-optimized mlir-tblgen (with LLVM_OPTIMIZED_TABLEGEN). set(MLIR_CONFIG_TABLEGEN_EXE mlir-tblgen) set(MLIR_CONFIG_PDLL_TABLEGEN_EXE mlir-pdll) +set(MLIR_CONFIG_SRC_SHARDER_TABLEGEN_EXE mlir-src-sharder) configure_file( ${CMAKE_CURRENT_SOURCE_DIR}/MLIRConfig.cmake.in diff --git a/mlir/cmake/modules/MLIRConfig.cmake.in b/mlir/cmake/modules/MLIRConfig.cmake.in index d4da3cd98cce9816e30f45b96e6b5dbf00ad33d6..7076d94a32f2bcd06525e043b6edd9a7cdc43ddc 100644 --- a/mlir/cmake/modules/MLIRConfig.cmake.in +++ b/mlir/cmake/modules/MLIRConfig.cmake.in @@ -11,6 +11,7 @@ set(MLIR_CMAKE_DIR "@MLIR_CONFIG_CMAKE_DIR@") set(MLIR_INCLUDE_DIRS "@MLIR_CONFIG_INCLUDE_DIRS@") set(MLIR_TABLEGEN_EXE "@MLIR_CONFIG_TABLEGEN_EXE@") set(MLIR_PDLL_TABLEGEN_EXE "@MLIR_CONFIG_PDLL_TABLEGEN_EXE@") +set(MLIR_SRC_SHARDER_TABLEGEN_EXE "@MLIR_CONFIG_SRC_SHARDER_TABLEGEN_EXE@") set(MLIR_INSTALL_AGGREGATE_OBJECTS "@MLIR_INSTALL_AGGREGATE_OBJECTS@") set(MLIR_ENABLE_BINDINGS_PYTHON "@MLIR_ENABLE_BINDINGS_PYTHON@") set(MLIR_ENABLE_EXECUTION_ENGINE "@MLIR_ENABLE_EXECUTION_ENGINE@") diff --git a/mlir/docs/DefiningDialects/Operations.md b/mlir/docs/DefiningDialects/Operations.md index 729393d5362673d52816d5f760e2779dafb20382..79a0cc55f1384036f1d7b8188f200a80b1c22547 100644 --- a/mlir/docs/DefiningDialects/Operations.md +++ b/mlir/docs/DefiningDialects/Operations.md @@ -1114,6 +1114,100 @@ void process(AddOp op, ArrayRef newOperands) { } ``` +#### Sharded Operation Definitions + +Large dialects with many operations may struggle with C++ compile time of +generated op definitions, due to large compilation units. `mlir-tblgen` +provides the ability to shard op definitions by splitting them up evenly +by passing `-op-shard-count` to `-gen-op-defs` and `-gen-op-decls`. The tool +will generate a single include file for the definitions broken up by +`GET_OP_DEFS_${N}` where `${N}` is the shard number. A shard can be compiled in +a single compilation unit by adding a file like this to your dialect library: + +```c++ +#include "mlir/IR/Operation.h" +// Add any other required includes. + +// Utilities shared by generated op definitions: custom directive parsers, +// printers, etc. +#include "OpUtils.h" + +#define GET_OP_DEFS_0 +#include "MyDialectOps.cpp.inc" +``` + +Note: this requires restructing shared utility functions within the dialect +library so they can be shared by multiple compilation units. I.e. instead of +defining `static` methods in the same source file, you should declare them in a +shared header and define them in their own source file. + +The op registration hooks are also sharded, because the template instantiation +can take a very long time to compile. Operations should be registered in your +dialect like: + +```c++ +void MyDialect::initialize() { + registerMyDialectOperations(this); +} +``` + +CMake and Bazel functions are included to make sharding dialects easier. +Assuming you have organized your operation utility functions into their own +header, define a file that looks like the one above, but without the `#define`: + +```c++ +// MyDialectOps.cpp +#include "mlir/IR/Operation.h" + +#include "OpUtils.h" + +#include "MyDialectOps.cpp.inc" +``` + +In CMake, remove the manual `mlir_tablegen` invocations and replace them with: + +```cmake +set(LLVM_TARGET_DEFINITIONS MyDialectOps.td) +add_sharded_ops(MyDialectOps 8) # shard the op definitions by 8 + +add_mlir_library(MyDialect + MyDialect.cpp + MyDialectOpDefs.cpp + ${SHARDED_SRCS} + + DEPENDS + MLIRTestOpsShardGen +) +``` + +This will automatically duplicate the `MyDialectOps.cpp` source file and add the +`#define` up the number of shards indicated. + +It is recommended that any out-of-line op member functions (like verifiers) be +defined in a separate source file. In this example, it is called +`MyDialectOpDefs.cpp`. + +In Bazel, remove the `-gen-op-defs` and `-gen-op-decls` invocations, and add + +```bazel +gentbl_sharded_ops( + name = "MyDialectOpSrcs", + hdr_out = "MyDialectOps.h.inc", + shard_count = 8, + sharder = "//mlir:mlir-src-sharder", + src_file = "MyDialectOps.cpp", + src_out = "MyDialectOps.cpp.inc", + tblgen = "//mlir:mlir-tblgen", + td_file = "MyDialectOps.td", + deps = [":MyDialectOpsTdFiles"], +) + +cc_library( + name = "MyDialect", + srcs = glob(["MyDialect/*.cpp"]) + [":MyDialectOpSrcs"] +) +``` + ## Constraints Constraint is a core concept in table-driven operation definition: operation diff --git a/mlir/docs/Tutorials/UnderstandingTheIRStructure.md b/mlir/docs/Tutorials/UnderstandingTheIRStructure.md index 067a11dc435abdd9653bbc7be823c11f09635a19..ed323fc42336bc482a2c4957f19c8a054751d117 100644 --- a/mlir/docs/Tutorials/UnderstandingTheIRStructure.md +++ b/mlir/docs/Tutorials/UnderstandingTheIRStructure.md @@ -40,8 +40,8 @@ the nested regions and print them individually: if (!op->getAttrs().empty()) { printIndent() << op->getAttrs().size() << " attributes:\n"; for (NamedAttribute attr : op->getAttrs()) - printIndent() << " - '" << attr.first << "' : '" << attr.second - << "'\n"; + printIndent() << " - '" << attr.getName() << "' : '" + << attr.getValue() << "'\n"; } // Recurse into each of the regions attached to the operation. diff --git a/mlir/include/mlir-c/Dialect/LLVM.h b/mlir/include/mlir-c/Dialect/LLVM.h index bd9b7dd26f5e9ea20761db0f4ecc161b91e2305a..b3e64bd68f7b1c18b0d19def0a49a915518460ca 100644 --- a/mlir/include/mlir-c/Dialect/LLVM.h +++ b/mlir/include/mlir-c/Dialect/LLVM.h @@ -23,6 +23,13 @@ MLIR_DECLARE_CAPI_DIALECT_REGISTRATION(LLVM, llvm); MLIR_CAPI_EXPORTED MlirType mlirLLVMPointerTypeGet(MlirContext ctx, unsigned addressSpace); +/// Returns `true` if the type is an LLVM dialect pointer type. +MLIR_CAPI_EXPORTED bool mlirTypeIsALLVMPointerType(MlirType type); + +/// Returns address space of llvm.ptr +MLIR_CAPI_EXPORTED unsigned +mlirLLVMPointerTypeGetAddressSpace(MlirType pointerType); + /// Creates an llmv.void type. MLIR_CAPI_EXPORTED MlirType mlirLLVMVoidTypeGet(MlirContext ctx); diff --git a/mlir/include/mlir-c/Dialect/SparseTensor.h b/mlir/include/mlir-c/Dialect/SparseTensor.h index 52ca7ba8a1618f48c64f77a7e5c8c2ecfe6af468..125469f57c5f552768fe6b05bdeb0275e044bfc6 100644 --- a/mlir/include/mlir-c/Dialect/SparseTensor.h +++ b/mlir/include/mlir-c/Dialect/SparseTensor.h @@ -53,7 +53,8 @@ mlirAttributeIsASparseTensorEncodingAttr(MlirAttribute attr); MLIR_CAPI_EXPORTED MlirAttribute mlirSparseTensorEncodingAttrGet( MlirContext ctx, intptr_t lvlRank, MlirSparseTensorLevelType const *lvlTypes, MlirAffineMap dimToLvl, - MlirAffineMap lvlTodim, int posWidth, int crdWidth); + MlirAffineMap lvlTodim, int posWidth, int crdWidth, + MlirAttribute explicitVal, MlirAttribute implicitVal); /// Returns the level-rank of the `sparse_tensor.encoding` attribute. MLIR_CAPI_EXPORTED intptr_t @@ -85,6 +86,14 @@ mlirSparseTensorEncodingAttrGetPosWidth(MlirAttribute attr); MLIR_CAPI_EXPORTED int mlirSparseTensorEncodingAttrGetCrdWidth(MlirAttribute attr); +/// Returns the explicit value of the `sparse_tensor.encoding` attribute. +MLIR_CAPI_EXPORTED MlirAttribute +mlirSparseTensorEncodingAttrGetExplicitVal(MlirAttribute attr); + +/// Returns the implicit value of the `sparse_tensor.encoding` attribute. +MLIR_CAPI_EXPORTED MlirAttribute +mlirSparseTensorEncodingAttrGetImplicitVal(MlirAttribute attr); + MLIR_CAPI_EXPORTED unsigned mlirSparseTensorEncodingAttrGetStructuredN(MlirSparseTensorLevelType lvlType); diff --git a/mlir/include/mlir/Dialect/Linalg/Transforms/RuntimeOpVerification.h b/mlir/include/mlir/Dialect/Linalg/Transforms/RuntimeOpVerification.h new file mode 100644 index 0000000000000000000000000000000000000000..6c3643f7835cbe86ec8bc3dd5f03a82b3b504810 --- /dev/null +++ b/mlir/include/mlir/Dialect/Linalg/Transforms/RuntimeOpVerification.h @@ -0,0 +1,21 @@ +//===- RuntimeOpVerification.h - Op Verification ----------------*- C++ -*-===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#ifndef MLIR_DIALECT_LINALG_RUNTIMEOPVERIFICATION_H +#define MLIR_DIALECT_LINALG_RUNTIMEOPVERIFICATION_H + +namespace mlir { +class DialectRegistry; + +namespace linalg { +void registerRuntimeVerifiableOpInterfaceExternalModels( + DialectRegistry ®istry); +} // namespace linalg +} // namespace mlir + +#endif // MLIR_DIALECT_LINALG_RUNTIMEOPVERIFICATION_H diff --git a/mlir/include/mlir/Dialect/OpenMP/OpenMPClauseOperands.h b/mlir/include/mlir/Dialect/OpenMP/OpenMPClauseOperands.h index 3c5fa23bd4a7f42168bd10073069a6b62471f15f..244cee1dd635b64e76347c8d7cf252b367a079cb 100644 --- a/mlir/include/mlir/Dialect/OpenMP/OpenMPClauseOperands.h +++ b/mlir/include/mlir/Dialect/OpenMP/OpenMPClauseOperands.h @@ -295,10 +295,9 @@ using TeamsClauseOps = PrivateClauseOps, ReductionClauseOps, ThreadLimitClauseOps>; using WsloopClauseOps = - detail::Clauses; + detail::Clauses; } // namespace omp } // namespace mlir diff --git a/mlir/include/mlir/Dialect/OpenMP/OpenMPOps.td b/mlir/include/mlir/Dialect/OpenMP/OpenMPOps.td index 10771f6e854dde07e95b999a104ac132f45864c3..8ab116ce391e29dd4246651b0ec86ef95347ed00 100644 --- a/mlir/include/mlir/Dialect/OpenMP/OpenMPOps.td +++ b/mlir/include/mlir/Dialect/OpenMP/OpenMPOps.td @@ -600,29 +600,30 @@ def LoopNestOp : OpenMP_Op<"loop_nest", [SameVariadicOperandSize, //===----------------------------------------------------------------------===// def WsloopOp : OpenMP_Op<"wsloop", [AttrSizedOperandSegments, - AllTypesMatch<["lowerBound", "upperBound", "step"]>, DeclareOpInterfaceMethods, - RecursiveMemoryEffects, ReductionClauseInterface]> { + RecursiveMemoryEffects, ReductionClauseInterface, + SingleBlockImplicitTerminator<"TerminatorOp">]> { let summary = "worksharing-loop construct"; let description = [{ The worksharing-loop construct specifies that the iterations of the loop(s) will be executed in parallel by threads in the current context. These iterations are spread across threads that already exist in the enclosing - parallel region. The lower and upper bounds specify a half-open range: the - range includes the lower bound but does not include the upper bound. If the - `inclusive` attribute is specified then the upper bound is also included. + parallel region. - The body region can contain any number of blocks. The region is terminated - by "omp.yield" instruction without operands. + The body region can only contain a single block which must contain a single + operation and a terminator. The operation must be another compatible loop + wrapper or an `omp.loop_nest`. ``` - omp.wsloop - for (%i1, %i2) : index = (%c0, %c0) to (%c10, %c10) step (%c1, %c1) { - %a = load %arrA[%i1, %i2] : memref - %b = load %arrB[%i1, %i2] : memref - %sum = arith.addf %a, %b : f32 - store %sum, %arrC[%i1, %i2] : memref - omp.yield + omp.wsloop { + omp.loop_nest (%i1, %i2) : index = (%c0, %c0) to (%c10, %c10) step (%c1, %c1) { + %a = load %arrA[%i1, %i2] : memref + %b = load %arrB[%i1, %i2] : memref + %sum = arith.addf %a, %b : f32 + store %sum, %arrC[%i1, %i2] : memref + omp.yield + } + omp.terminator } ``` @@ -665,10 +666,7 @@ def WsloopOp : OpenMP_Op<"wsloop", [AttrSizedOperandSegments, passed by reference. }]; - let arguments = (ins Variadic:$lowerBound, - Variadic:$upperBound, - Variadic:$step, - Variadic:$linear_vars, + let arguments = (ins Variadic:$linear_vars, Variadic:$linear_step_vars, Variadic:$reduction_vars, OptionalAttr:$reductions, @@ -679,22 +677,16 @@ def WsloopOp : OpenMP_Op<"wsloop", [AttrSizedOperandSegments, UnitAttr:$nowait, UnitAttr:$byref, ConfinedAttr, [IntMinValue<0>]>:$ordered_val, - OptionalAttr:$order_val, - UnitAttr:$inclusive); + OptionalAttr:$order_val); let builders = [ - OpBuilder<(ins "ValueRange":$lowerBound, "ValueRange":$upperBound, - "ValueRange":$step, - CArg<"ArrayRef", "{}">:$attributes)>, + OpBuilder<(ins CArg<"ArrayRef", "{}">:$attributes)>, OpBuilder<(ins CArg<"const WsloopClauseOps &">:$clauses)> ]; let regions = (region AnyRegion:$region); let extraClassDeclaration = [{ - /// Returns the number of loops in the worksharing-loop nest. - unsigned getNumLoops() { return getLowerBound().size(); } - /// Returns the number of reduction variables. unsigned getNumReductionVars() { return getReductionVars().size(); } }]; @@ -711,9 +703,8 @@ def WsloopOp : OpenMP_Op<"wsloop", [AttrSizedOperandSegments, |`byref` $byref |`ordered` `(` $ordered_val `)` |`order` `(` custom($order_val) `)` - ) custom($region, $lowerBound, $upperBound, $step, type($step), - $reduction_vars, type($reduction_vars), $reductions, - $inclusive) attr-dict + ) custom($region, $reduction_vars, type($reduction_vars), + $reductions) attr-dict }]; let hasVerifier = 1; } @@ -732,7 +723,7 @@ def SimdOp : OpenMP_Op<"simd", [AttrSizedOperandSegments, transformed into a SIMD loop (that is, multiple iterations of the loop can be executed concurrently using SIMD instructions). - The body region can contain a single block which must contain a single + The body region can only contain a single block which must contain a single operation and a terminator. The operation must be another compatible loop wrapper or an `omp.loop_nest`. @@ -766,6 +757,7 @@ def SimdOp : OpenMP_Op<"simd", [AttrSizedOperandSegments, store %sum, %arrC[%i1, %i2] : memref omp.yield } + omp.terminator } ``` }]; @@ -805,8 +797,8 @@ def SimdOp : OpenMP_Op<"simd", [AttrSizedOperandSegments, def YieldOp : OpenMP_Op<"yield", [Pure, ReturnLike, Terminator, - ParentOneOf<["LoopNestOp", "WsloopOp", "DeclareReductionOp", - "AtomicUpdateOp", "PrivateClauseOp"]>]> { + ParentOneOf<["AtomicUpdateOp", "DeclareReductionOp", "LoopNestOp", + "PrivateClauseOp"]>]> { let summary = "loop yield and termination operation"; let description = [{ "omp.yield" yields SSA values from the OpenMP dialect op region and @@ -846,7 +838,7 @@ def DistributeOp : OpenMP_Op<"distribute", [AttrSizedOperandSegments, iterations are spread across threads that already exist in the enclosing region. - The body region can contain a single block which must contain a single + The body region can only contain a single block which must contain a single operation and a terminator. The operation must be another compatible loop wrapper or an `omp.loop_nest`. @@ -864,6 +856,7 @@ def DistributeOp : OpenMP_Op<"distribute", [AttrSizedOperandSegments, store %sum, %arrC[%i1, %i2] : memref omp.yield } + omp.terminator } ``` // TODO: private_var, firstprivate_var, lastprivate_var, collapse @@ -1029,7 +1022,7 @@ def TaskloopOp : OpenMP_Op<"taskloop", [AttrSizedOperandSegments, iterations are distributed across tasks generated by the construct and scheduled to be executed. - The body region can contain a single block which must contain a single + The body region can only contain a single block which must contain a single operation and a terminator. The operation must be another compatible loop wrapper or an `omp.loop_nest`. @@ -1042,6 +1035,7 @@ def TaskloopOp : OpenMP_Op<"taskloop", [AttrSizedOperandSegments, store %sum, %arrC[%i1, %i2] : memref omp.yield } + omp.terminator } ``` diff --git a/mlir/include/mlir/Dialect/SCF/Transforms/Passes.h b/mlir/include/mlir/Dialect/SCF/Transforms/Passes.h index 90b315e83a8cfdb5765c4912d27bc4a94e7004bf..31c3d0eb629d28056930ebe7935937f067541d6d 100644 --- a/mlir/include/mlir/Dialect/SCF/Transforms/Passes.h +++ b/mlir/include/mlir/Dialect/SCF/Transforms/Passes.h @@ -59,6 +59,9 @@ createParallelLoopTilingPass(llvm::ArrayRef tileSize = {}, /// loop range. std::unique_ptr createForLoopRangeFoldingPass(); +/// Creates a pass that converts SCF forall loops to SCF for loops. +std::unique_ptr createForallToForLoopPass(); + // Creates a pass which lowers for loops into while loops. std::unique_ptr createForToWhileLoopPass(); diff --git a/mlir/include/mlir/Dialect/SCF/Transforms/Passes.td b/mlir/include/mlir/Dialect/SCF/Transforms/Passes.td index 350611ad86873d08d831aa9537575ce010f78961..a7aeb42d60c0e975525b56619766e4590c4e0de8 100644 --- a/mlir/include/mlir/Dialect/SCF/Transforms/Passes.td +++ b/mlir/include/mlir/Dialect/SCF/Transforms/Passes.td @@ -120,6 +120,11 @@ def SCFForLoopRangeFolding : Pass<"scf-for-loop-range-folding"> { let constructor = "mlir::createForLoopRangeFoldingPass()"; } +def SCFForallToForLoop : Pass<"scf-forall-to-for"> { + let summary = "Convert SCF forall loops to SCF for loops"; + let constructor = "mlir::createForallToForLoopPass()"; +} + def SCFForToWhileLoop : Pass<"scf-for-to-while"> { let summary = "Convert SCF for loops to SCF while loops"; let constructor = "mlir::createForToWhileLoopPass()"; diff --git a/mlir/include/mlir/Dialect/SCF/Transforms/Transforms.h b/mlir/include/mlir/Dialect/SCF/Transforms/Transforms.h index 220dcb35571d27bb0cef3455a4872bb246963d80..b063e6e775e63402990b666e93c280a3accf239d 100644 --- a/mlir/include/mlir/Dialect/SCF/Transforms/Transforms.h +++ b/mlir/include/mlir/Dialect/SCF/Transforms/Transforms.h @@ -28,10 +28,17 @@ class Value; namespace scf { class IfOp; +class ForallOp; class ForOp; class ParallelOp; class WhileOp; +/// Try converting scf.forall into a set of nested scf.for loops. +/// The newly created scf.for ops will be returned through the `results` +/// vector if provided. +LogicalResult forallToForLoop(RewriterBase &rewriter, ForallOp forallOp, + SmallVectorImpl *results = nullptr); + /// Fuses all adjacent scf.parallel operations with identical bounds and step /// into one scf.parallel operations. Uses a naive aliasing and dependency /// analysis. diff --git a/mlir/include/mlir/Dialect/SparseTensor/IR/SparseTensorAttrDefs.td b/mlir/include/mlir/Dialect/SparseTensor/IR/SparseTensorAttrDefs.td index 4a9b9169ae4b86904d1eeb7465b82b2c98e86004..eefa4c71bbd2caed84a47d1f1d1c63ffdf79a518 100644 --- a/mlir/include/mlir/Dialect/SparseTensor/IR/SparseTensorAttrDefs.td +++ b/mlir/include/mlir/Dialect/SparseTensor/IR/SparseTensorAttrDefs.td @@ -167,7 +167,7 @@ def SparseTensorEncodingAttr : SparseTensor_Attr<"SparseTensorEncoding", - **soa** : only applicable to singleton levels, fuses the singleton level in SoA (structure of arrays) scheme. - In addition to the map, the following two fields are optional: + In addition to the map, the following fields are optional: - The required bitwidth for position storage (integral offsets into the sparse storage scheme). A narrow width reduces the memory @@ -183,6 +183,23 @@ def SparseTensorEncodingAttr : SparseTensor_Attr<"SparseTensorEncoding", coordinate over all levels). The choices are `8`, `16`, `32`, `64`, or, the default, `0` to indicate a native bitwidth. + - The explicit value for the sparse tensor. If explicitVal is set, + then all the non-zero values in the tensor have the same explicit value. + The default value Attribute() indicates that it is not set. This + is useful for binary-valued sparse tensors whose values can either + be an implicit value (0 by default) or an explicit value (such as 1). + In this approach, we don't store explicit/implicit values, and metadata + (such as position and coordinate arrays) alone fully defines the original tensor. + This yields additional savings for the storage requirements, + as well as for the computational time, since we skip operating on + implicit values and can constant fold the explicit values where they are used. + + - The implicit value for the sparse tensor. If implicitVal is set, + then the "zero" value in the tensor is equal to the implicit value. + For now, we only support `0` as the implicit value but it could be + extended in the future. The default value Attribute() indicates that + the implicit value is `0` (same type as the tensor element type). + Examples: ```mlir @@ -226,6 +243,15 @@ def SparseTensorEncodingAttr : SparseTensor_Attr<"SparseTensorEncoding", }> ... tensor<8x8xf64, #DCSC> ... + // Doubly compressed sparse column storage with specific + // explicit and implicit values. + #DCSC = #sparse_tensor.encoding<{ + map = (i, j) -> (j : compressed, i : compressed), + explicitVal = 1 : i64, + implicitVal = 0 : i64 + }> + ... tensor<8x8xi64, #DCSC> ... + // Block sparse row storage (2x3 blocks). #BSR = #sparse_tensor.encoding<{ map = ( i, j ) -> @@ -307,6 +333,12 @@ def SparseTensorEncodingAttr : SparseTensor_Attr<"SparseTensorEncoding", // The required bitwidth for coordinate storage. "unsigned":$crdWidth, + // The required explicit value. + "::mlir::Attribute":$explicitVal, + + // The required implicit value. + "::mlir::Attribute":$implicitVal, + // A slice attribute for each dimension of the tensor type. ArrayRefParameter< "::mlir::sparse_tensor::SparseTensorDimSliceAttr", @@ -319,7 +351,9 @@ def SparseTensorEncodingAttr : SparseTensor_Attr<"SparseTensorEncoding", CArg<"AffineMap", "{}">:$dimToLvl, CArg<"AffineMap", "{}">:$lvlToDim, CArg<"unsigned", "0">:$posWidth, - CArg<"unsigned", "0">:$crdWidth), [{ + CArg<"unsigned", "0">:$crdWidth, + CArg<"::mlir::Attribute", "{}">:$explicitVal, + CArg<"::mlir::Attribute", "{}">:$implicitVal), [{ if (!dimToLvl) { dimToLvl = ::mlir::AffineMap::getMultiDimIdentityMap(lvlTypes.size(), $_ctxt); } @@ -327,6 +361,7 @@ def SparseTensorEncodingAttr : SparseTensor_Attr<"SparseTensorEncoding", lvlToDim = ::mlir::sparse_tensor::inferLvlToDim(dimToLvl, $_ctxt); } return $_get($_ctxt, lvlTypes, dimToLvl, lvlToDim, posWidth, crdWidth, + explicitVal, implicitVal, ArrayRef<::mlir::sparse_tensor::SparseTensorDimSliceAttr>{}); }]> ]; @@ -353,6 +388,22 @@ def SparseTensorEncodingAttr : SparseTensor_Attr<"SparseTensorEncoding", /// reset to the default, and all other fields inherited from `this`. SparseTensorEncodingAttr withoutBitWidths() const; + /// Constructs a new encoding with the given explicit value + /// and all other fields inherited from `this`. + SparseTensorEncodingAttr withExplicitVal(Attribute explicitVal) const; + + /// Constructs a new encoding with the explicit value + /// reset to the default, and all other fields inherited from `this`. + SparseTensorEncodingAttr withoutExplicitVal() const; + + /// Constructs a new encoding with the given implicit value + /// and all other fields inherited from `this`. + SparseTensorEncodingAttr withImplicitVal(Attribute implicitVal) const; + + /// Constructs a new encoding with the implicit value + /// reset to the default, and all other fields inherited from `this`. + SparseTensorEncodingAttr withoutImplicitVal() const; + /// Constructs a new encoding with the given dimSlices, and all /// other fields inherited from `this`. SparseTensorEncodingAttr withDimSlices(ArrayRef<::mlir::sparse_tensor::SparseTensorDimSliceAttr> dimSlices) const; diff --git a/mlir/include/mlir/Dialect/SparseTensor/IR/SparseTensorType.h b/mlir/include/mlir/Dialect/SparseTensor/IR/SparseTensorType.h index 825d89a408febe43d729f0364bd3b6de596ca7e4..34d99913fbd51beef8f6de3b11df4eedaf59a93d 100644 --- a/mlir/include/mlir/Dialect/SparseTensor/IR/SparseTensorType.h +++ b/mlir/include/mlir/Dialect/SparseTensor/IR/SparseTensorType.h @@ -115,6 +115,22 @@ public: return withEncoding(enc.withoutBitWidths()); } + SparseTensorType withExplicitVal(Attribute explicitVal) const { + return withEncoding(enc.withExplicitVal(explicitVal)); + } + + SparseTensorType withoutExplicitVal() const { + return withEncoding(enc.withoutExplicitVal()); + } + + SparseTensorType withImplicitVal(Attribute implicitVal) const { + return withEncoding(enc.withImplicitVal(implicitVal)); + } + + SparseTensorType withoutImplicitVal() const { + return withEncoding(enc.withoutImplicitVal()); + } + SparseTensorType withDimSlices(ArrayRef dimSlices) const { return withEncoding(enc.withDimSlices(dimSlices)); @@ -327,6 +343,12 @@ public: /// Returns the position-overhead bitwidth, defaulting to zero. unsigned getPosWidth() const { return enc ? enc.getPosWidth() : 0; } + /// Returns the explicit value, defaulting to null Attribute for unset. + Attribute getExplicitVal() const { return enc.getExplicitVal(); } + + /// Returns the implicit value, defaulting to null Attribute for 0. + Attribute getImplicitVal() const { return enc.getImplicitVal(); } + /// Returns the coordinate-overhead MLIR type, defaulting to `IndexType`. Type getCrdType() const { return enc.getCrdElemType(); } diff --git a/mlir/include/mlir/Dialect/Vector/Utils/VectorUtils.h b/mlir/include/mlir/Dialect/Vector/Utils/VectorUtils.h index 8a57c6094c41c0b35341d5d90e5657f0e9fa4f12..030be328e97fd0060be203177670bf7306ec3412 100644 --- a/mlir/include/mlir/Dialect/Vector/Utils/VectorUtils.h +++ b/mlir/include/mlir/Dialect/Vector/Utils/VectorUtils.h @@ -194,7 +194,7 @@ bool isLinearizableVector(VectorType type); /// for each dimension of the passed in tensor. Value createReadOrMaskedRead(OpBuilder &builder, Location loc, Value source, ArrayRef readShape, Value padValue, - bool useInBoundsInsteadOfMasking = true); + bool useInBoundsInsteadOfMasking); /// Returns success if `inputVectorSizes` is a valid masking configuraion for /// given `shape`, i.e., it meets: diff --git a/mlir/include/mlir/Dialect/XeGPU/IR/CMakeLists.txt b/mlir/include/mlir/Dialect/XeGPU/IR/CMakeLists.txt index f1740e9ed929a6ce0321a69a79ec016d7a189887..3f8cac4dc07c3cf7c45e05479811ea22edce5162 100644 --- a/mlir/include/mlir/Dialect/XeGPU/IR/CMakeLists.txt +++ b/mlir/include/mlir/Dialect/XeGPU/IR/CMakeLists.txt @@ -2,12 +2,12 @@ add_mlir_dialect(XeGPU xegpu) add_mlir_doc(XeGPU XeGPU Dialects/ -gen-dialect-doc -dialect=xegpu) set(LLVM_TARGET_DEFINITIONS XeGPU.td) -mlir_tablegen(XeGPUAttrs.h.inc -gen-attrdef-decls) -mlir_tablegen(XeGPUAttrs.cpp.inc -gen-attrdef-defs) +mlir_tablegen(XeGPUAttrs.h.inc -gen-attrdef-decls -attrdefs-dialect=xegpu) +mlir_tablegen(XeGPUAttrs.cpp.inc -gen-attrdef-defs -attrdefs-dialect=xegpu) add_public_tablegen_target(MLIRXeGPUAttrsIncGen) add_dependencies(mlir-headers MLIRXeGPUAttrsIncGen) -set(LLVM_TARGET_DEFINITIONS XeGPU.td) +set(LLVM_TARGET_DEFINITIONS XeGPUAttrs.td) mlir_tablegen(XeGPUEnums.h.inc -gen-enum-decls) mlir_tablegen(XeGPUEnums.cpp.inc -gen-enum-defs) add_public_tablegen_target(MLIRXeGPUEnumsIncGen) diff --git a/mlir/include/mlir/Dialect/XeGPU/IR/XeGPU.h b/mlir/include/mlir/Dialect/XeGPU/IR/XeGPU.h index eca9255ff3974b799418acb11cef4a98cf240e83..7ac0cf77fe59bb12ea59a3f4d37d054bee96db85 100644 --- a/mlir/include/mlir/Dialect/XeGPU/IR/XeGPU.h +++ b/mlir/include/mlir/Dialect/XeGPU/IR/XeGPU.h @@ -10,6 +10,7 @@ #define MLIR_DIALECT_XEGPU_IR_XEGPU_H #include "mlir/Bytecode/BytecodeOpInterface.h" +#include "mlir/Dialect/Arith/IR/Arith.h" #include "mlir/IR/BuiltinTypes.h" #include "mlir/IR/Dialect.h" #include "mlir/IR/TypeUtilities.h" @@ -19,7 +20,7 @@ namespace mlir { namespace xegpu { -// placeholder +class TensorDescType; } // namespace xegpu } // namespace mlir diff --git a/mlir/include/mlir/Dialect/XeGPU/IR/XeGPUAttrs.td b/mlir/include/mlir/Dialect/XeGPU/IR/XeGPUAttrs.td index 6579d07ec26215c727dccd110800d6b31874e86f..f3ca09a6a68ea8c5729b6cc0903cb3f7006952e9 100644 --- a/mlir/include/mlir/Dialect/XeGPU/IR/XeGPUAttrs.td +++ b/mlir/include/mlir/Dialect/XeGPU/IR/XeGPUAttrs.td @@ -10,6 +10,7 @@ #define MLIR_DIALECT_XEGPU_IR_XEGPUATTRS_TD include "mlir/Dialect/XeGPU/IR/XeGPUDialect.td" +include "mlir/IR/AttrTypeBase.td" include "mlir/IR/EnumAttr.td" class XeGPUAttr traits = [], @@ -98,4 +99,21 @@ def XeGPU_CacheHintAttr let assemblyFormat = "`<` $value `>`"; } +def XeGPU_FenceScopeWorkgroup: I32EnumAttrCase<"Workgroup", 0, "workgroup">; +def XeGPU_FenceScopeGPU: I32EnumAttrCase<"GPU", 1, "gpu">; +def XeGPU_FenceScope: I32EnumAttr<"FenceScope", + "The enumeration for the scope of fence operation.", + [XeGPU_FenceScopeWorkgroup, XeGPU_FenceScopeGPU]> { + let genSpecializedAttr = 0; + let cppNamespace = "::mlir::xegpu"; +} + +def XeGPU_FenceScopeAttr: + EnumAttr { + let summary = [{Describes the scope of fence. + "workgroup" means that the scope is within each work group. + "gpu" means the scope is across work groups within the gpu.}]; + let assemblyFormat = "$value"; +} + #endif // MLIR_DIALECT_XEGPU_IR_XEGPUATTRS_TD \ No newline at end of file diff --git a/mlir/include/mlir/Dialect/XeGPU/IR/XeGPUDialect.td b/mlir/include/mlir/Dialect/XeGPU/IR/XeGPUDialect.td index c2f09319c790e0a7183c5561b50b135071c25ee0..765f218f95d2691e19694d72b7c62ea1cd22b32a 100644 --- a/mlir/include/mlir/Dialect/XeGPU/IR/XeGPUDialect.td +++ b/mlir/include/mlir/Dialect/XeGPU/IR/XeGPUDialect.td @@ -17,12 +17,14 @@ def XeGPU_Dialect : Dialect { let summary = "The XeGPU dialect that models Intel GPU's ISA"; let description = [{ The XeGPU dialect models Intel Xe ISA semantics but works at vector and - TensorDesc data type. It provides 1:1 mappings to match Xe instructions + TensorDesc data type. It provides 1:1 mappings to match Xe instructions like DPAS and 2D block load. The matrix size being processed at this level exactly matches the hardware instructions or the intrinsic supported by the lower-level GPU compiler. }]; + let dependentDialects = ["arith::ArithDialect"]; + let useDefaultTypePrinterParser = true; let useDefaultAttributePrinterParser = true; } diff --git a/mlir/include/mlir/Dialect/XeGPU/IR/XeGPUOps.td b/mlir/include/mlir/Dialect/XeGPU/IR/XeGPUOps.td index c6f7f83441b96cf7bac64733e242265012f970bb..88f2e1acfeeb581d7a1e60738fca36e09a01eae0 100644 --- a/mlir/include/mlir/Dialect/XeGPU/IR/XeGPUOps.td +++ b/mlir/include/mlir/Dialect/XeGPU/IR/XeGPUOps.td @@ -9,7 +9,7 @@ #ifndef MLIR_DIALECT_XEGPU_IR_XEGPUOPS_TD #define MLIR_DIALECT_XEGPU_IR_XEGPUOPS_TD -include "mlir/IR/AttrTypeBase.td" +include "mlir/Dialect/Arith/IR/ArithBase.td" include "mlir/Dialect/XeGPU/IR/XeGPUAttrs.td" include "mlir/Dialect/XeGPU/IR/XeGPUDialect.td" include "mlir/Dialect/XeGPU/IR/XeGPUTypes.td" @@ -36,7 +36,7 @@ class XeGPU_Op traits = []>: static ::mlir::ParseResult parseProperties(::mlir::OpAsmParser &parser, ::mlir::OperationState &result) { - if (mlir::succeeded(parser.parseLess())) { + if (mlir::succeeded(parser.parseOptionalLess())) { if (parser.parseAttribute(result.propertiesAttr) || parser.parseGreater()) return failure(); } @@ -254,7 +254,7 @@ def XeGPU_LoadNdOp : XeGPU_Op<"load_nd", [AllElementTypesMatch<["value", "Tensor a block of data from memory to register. It takes a set of optional cache hints for each level of cache, L1, L2 and L3. If hardware does not have a correspoding cache, Corresponding cache hint attribute will be masked. - vnni transform is an hardware feature for Intel GPU, which is used to + VNNI transformation is an hardware feature for Intel GPU, which is used to do data packing during the load for B operand of matrix operation, if the bit width of the data type is less then 32 bits, e.g., fp16. And transpose is another Intel hardware feature, which will do transpose @@ -425,10 +425,6 @@ def XeGPU_CreateDescOp: XeGPU_Op<"create_tdesc", [Pure, ViewLikeOpInterface]> { %0 = memref.alloc() : memref<1024xf32> %1 = xegpu.create_tdesc %0[0, 4, 8, 12] {chunk_size = 8}: memref<1024xf32> -> TensorDesc<4x8xf32> ``` - - - - }]; let arguments = (ins XeGPU_BaseAddrType: $source, @@ -663,4 +659,153 @@ def XeGPU_UpdateOffsetOp: XeGPU_Op<"update_offset", }]; } +def XeGPU_DpasOp : XeGPU_Op<"dpas", [Pure, AllElementTypesMatch<["lhs", "rhs"]>]> { + let summary = "It performs mma computation"; + + let description = [{DPAS performs matrix multiplication on matrix A of `mxk` + size, B of `kxn` size, and accumulate on matrix C of `mxn` to the same size + matrix , `m=8`, `n=16` and `k=8 * 32/bit_width_of_elem_type`. So for fp16 + data type, the matrices are `A: vector<8x16xf16>`, `B: vector<16x16xf16>`, + and `C/D: vector<8x16xf32>`. Besides the matrix size requirements, DPAS + also requires A and B to be loaded with the required data layout. Specially, + VNNI layout is required for B operand. It is achieved via setting `vnni_axis = 0` + of the corresponding `load_nd` operator. To keep both operands as 3D vector, + operand A is loaded via setting `vnni_axis = 1` without impacting the + physical layouts change in register. Due to the VNNI transformation, A and B operands + are represented as 3D vector, with the last dimension representing the VNNI factor, + which is computed as `32/bit_width_of_elem_type`. Therefore, `A: vector<8x16xf16>` + is represented as `A: vector<8x8x2xf16>`, and `B: vector<16x16xf16>` is + represented as `B: vector<8x16x2xf16>`. + + Note: on PVC, the hardware can perform load with VNNI transformation when data + element type is 16-bit or lower precision, taking 2 or 4 elements from + the first dimension and inserted into the newly added innermost dimension. + }]; + + let arguments = (ins + XeGPU_DpasOpType : $lhs, + XeGPU_DpasOpType : $rhs, + Optional: $acc); + let results = (outs XeGPU_Vector2DType: $result); + + let extraClassDeclaration = [{ + VectorType getLhsType() { + return getLhs().getType(); + } + + VectorType getRhsType() { + return getRhs().getType(); + } + + VectorType getAccType() { + if (getAcc()) + return getAcc().getType(); + return {}; + } + + VectorType getResultType() { + return getResult().getType(); + } + }]; + + let assemblyFormat = [{ + $lhs `,` $rhs (`,` $acc^)? attr-dict `:` type($lhs)`,` type($rhs) (`,` type($acc)^)? `->` type($result) + }]; + + let hasVerifier = 1; +} + +def XeGPU_AtomicRMWOp: XeGPU_Op<"atomic_rmw", [Pure, + AllElementTypesMatch<["tensorDesc", "value", "result"]>, + AllShapesMatch<["tensorDesc", "mask", "value", "result"]>]> { + let summary = "Atomic ready-modify-write operation on the TensorDesc. "; + + let description = [{ + The `xegpu.atomic_rmw` operation provides a way to perform a read-modify-write + operation on the region described by the `TensorDesc` free from data races. The + `kind` enumeration specifies the modification to be performed, The `mask` operand + has the same shape with `TensorDesc`, and is used to enable or disable specific + data points of the `TensorDesc`. The `value` operand represents the new value to + be applied during the modification. + }]; + + let arguments = (ins + AtomicRMWKindAttr:$kind, + XeGPU_TensorDesc:$tensorDesc, + XeGPU_MaskType:$mask, + XeGPU_ValueType:$value); + + let results = (outs XeGPU_ValueType:$result); + + let assemblyFormat = [{ + $kind $tensorDesc `,` $mask `,` $value attr-dict `:` + type($tensorDesc) `,` type($mask) `,` type($value) `->` type($result) + }]; +} + +def XeGPU_AllocNbarrierOp: XeGPU_Op<"alloc_nbarrier", []> { + let summary = "It allocates a set of named barriers."; + let description = [{AllocNbarrier is to create a set of named barriers as + specified by `nbarrier_num`. Named barriers are workgroup level resources, + and are shared by all threads in the workgroup. For example, there are + up to 32 barriers (range 0-31) for each XeCore on PVC. A typical use case + is that a workgroup is partitioned into N subgroups of threads (N <= 32), + and each subgroup coordinating their work with a separate barrier with id + range from 0 to N respectively.}]; + let arguments = (ins I64Attr: $nbarrier_num); + let assemblyFormat = "$nbarrier_num attr-dict"; +} + +def XeGPU_InitNbarrierOp: XeGPU_Op<"init_nbarrier", []> { + let summary = "It assigns a named barrier to the current thread."; + let description = [{InitNbarrierOp assigns the named barrier with the specified + barrier ID (0~31) to the current thread. Multiple threads may bind to the + same named barrier, and the `participant_thread_num` specifies the total + number of threads associated with the nbarrier. It returns an object of + NbarrierType representing the barrier}]; + + let arguments = (ins I8: $nbarrier_id, + I8: $participant_thread_num); + let results = (outs XeGPU_Nbarrier: $result); + let assemblyFormat = [{ + $nbarrier_id `,` $participant_thread_num attr-dict `:` + type($nbarrier_id) `,` type($participant_thread_num) `->` qualified(type($result)) + }]; +} + +def XeGPU_NbarrierArriveOp: XeGPU_Op<"nbarrier_arrive", []> { + let summary = "It signals the arrival at the named barrier."; + let description = [{NbarrierArriveOp signals the hardware (or other threads) + that the current thread has produced its data for the consumer threads. When + the hardware signalled by `participant_thread_num` threads for the named barrier, + it will notify the threads waiting for the named barrier to continue their work.}]; + + let arguments = (ins XeGPU_Nbarrier: $nbarrier); + let assemblyFormat = [{ $nbarrier attr-dict `:` qualified(type($nbarrier))}]; +} + +def XeGPU_NbarrierWaitOp: XeGPU_Op<"nbarrier_wait", []> { + let summary = "It waits for a named barrier."; + let description = [{NbarrierWaitOp signals the hardware which named barrier + the current thread is waiting for, such that it can get notified when the + named barrier is completed.}]; + let arguments = (ins XeGPU_Nbarrier: $nbarrier); + let assemblyFormat = [{ $nbarrier attr-dict `:` qualified(type($nbarrier)) }]; +} + +def XeGPU_FenceOp: XeGPU_Op<"fence", []> { + let summary = "It synchronizes memory accesses."; + let description = [{It synchronizes the memory access between + write and following read or write. + 1. `Memory_kind` describes the memory kind. "global" means the global memory, + "slm" means the share local memory. + 2. `Fence_scope` describes the scope of fence. "Workgroup" means that the scope would be + within each workgroup. "GPU" means the scope would be across workgroups within the GPU. + }]; + let arguments = (ins XeGPU_MemoryScopeAttr: $memory_kind, + XeGPU_FenceScopeAttr: $fence_scope); + let assemblyFormat = [{`memory_kind` `=` `` $memory_kind `,` `fence_scope` `=` `` $fence_scope attr-dict}]; + let extraClassDeclaration = extraBaseClassDeclaration; +} + #endif // MLIR_DIALECT_XEGPU_IR_XEGPUOPS_TD diff --git a/mlir/include/mlir/Dialect/XeGPU/IR/XeGPUTypes.td b/mlir/include/mlir/Dialect/XeGPU/IR/XeGPUTypes.td index 4cd4e5411653c1aaa44efe5fc204bdfc17fee1f6..bab0e4afb1e5ed6d2b99f513513e549ef7089bbb 100644 --- a/mlir/include/mlir/Dialect/XeGPU/IR/XeGPUTypes.td +++ b/mlir/include/mlir/Dialect/XeGPU/IR/XeGPUTypes.td @@ -151,4 +151,15 @@ def XeGPU_TensorDesc: XeGPUTypeDef<"TensorDesc", "tensor_desc", } + +def XeGPU_Nbarrier: XeGPUTypeDef<"Nbarrier", "nbarrier", [], "mlir::Type"> { + let summary = "!xegpu.nbarrier a custom XeGPU type representing a barrier."; + + let extraClassDeclaration = [{ + static NbarrierType get(mlir::MLIRContext *context) { + return Base::get(context); + }; + }]; +} + #endif // MLIR_DIALECT_XEGPU_IR_XEGPUTYPES_TD diff --git a/mlir/include/mlir/IR/OperationSupport.h b/mlir/include/mlir/IR/OperationSupport.h index 2c1c490aac49b80c21e8d9e8e061c927ba4582fe..cdb75a3777ad80c99c562f1afc0ee0ad6cd90a3d 100644 --- a/mlir/include/mlir/IR/OperationSupport.h +++ b/mlir/include/mlir/IR/OperationSupport.h @@ -960,9 +960,12 @@ struct OperationState { /// Regions that the op will hold. SmallVector, 1> regions; - // If we're creating an unregistered operation, this Attribute is used to - // build the properties. Otherwise it is ignored. For registered operations - // see the `getOrAddProperties` method. + /// This Attribute is used to opaquely construct the properties of the + /// operation. If we're creating an unregistered operation, the Attribute is + /// used as-is as the Properties storage of the operation. Otherwise, the + /// operation properties are constructed opaquely using its + /// `setPropertiesFromAttr` hook. Note that `getOrAddProperties` is the + /// preferred method to construct properties from C++. Attribute propertiesAttr; private: diff --git a/mlir/include/mlir/InitAllDialects.h b/mlir/include/mlir/InitAllDialects.h index c4d788cf8ed316638aaaa41e8763eddc9cd13387..d9db21073e15c7a213e535f8157afd707f4edd59 100644 --- a/mlir/include/mlir/InitAllDialects.h +++ b/mlir/include/mlir/InitAllDialects.h @@ -45,6 +45,7 @@ #include "mlir/Dialect/LLVMIR/ROCDLDialect.h" #include "mlir/Dialect/Linalg/IR/Linalg.h" #include "mlir/Dialect/Linalg/Transforms/AllInterfaces.h" +#include "mlir/Dialect/Linalg/Transforms/RuntimeOpVerification.h" #include "mlir/Dialect/MLProgram/IR/MLProgram.h" #include "mlir/Dialect/MLProgram/Transforms/BufferizableOpInterfaceImpl.h" #include "mlir/Dialect/MPI/IR/MPI.h" @@ -161,6 +162,7 @@ inline void registerAllDialects(DialectRegistry ®istry) { cf::registerBufferDeallocationOpInterfaceExternalModels(registry); gpu::registerBufferDeallocationOpInterfaceExternalModels(registry); linalg::registerAllDialectInterfaceImplementations(registry); + linalg::registerRuntimeVerifiableOpInterfaceExternalModels(registry); memref::registerAllocationOpInterfaceExternalModels(registry); memref::registerBufferViewFlowOpInterfaceExternalModels(registry); memref::registerRuntimeVerifiableOpInterfaceExternalModels(registry); diff --git a/mlir/include/mlir/Interfaces/MemorySlotInterfaces.td b/mlir/include/mlir/Interfaces/MemorySlotInterfaces.td index 8c642c0ed26aca17ad78a110c47f5092529e386b..764fa6d547b2eb52c19ca8c1dd1d591b1971739a 100644 --- a/mlir/include/mlir/Interfaces/MemorySlotInterfaces.td +++ b/mlir/include/mlir/Interfaces/MemorySlotInterfaces.td @@ -128,6 +128,7 @@ def PromotableMemOpInterface : OpInterface<"PromotableMemOpInterface"> { "::mlir::Value", "getStored", (ins "const ::mlir::MemorySlot &":$slot, "::mlir::RewriterBase &":$rewriter, + "::mlir::Value":$reachingDef, "const ::mlir::DataLayout &":$dataLayout) >, InterfaceMethod<[{ diff --git a/mlir/include/mlir/Interfaces/RuntimeVerifiableOpInterface.td b/mlir/include/mlir/Interfaces/RuntimeVerifiableOpInterface.td index d5f11d00cc3d2abbb30126c084ca1012301dca1d..6fd0df59d9d2e08798a3ce4a0e9375d13f6236c8 100644 --- a/mlir/include/mlir/Interfaces/RuntimeVerifiableOpInterface.td +++ b/mlir/include/mlir/Interfaces/RuntimeVerifiableOpInterface.td @@ -35,6 +35,12 @@ def RuntimeVerifiableOpInterface : OpInterface<"RuntimeVerifiableOpInterface"> { "::mlir::Location":$loc) >, ]; + + let extraClassDeclaration = [{ + /// Generate the error message that will be printed to the user when + /// verification fails. + static std::string generateErrorMessage(Operation *op, const std::string &msg); + }]; } #endif // MLIR_INTERFACES_RUNTIMEVERIFIABLEOPINTERFACE diff --git a/mlir/include/mlir/TableGen/CodeGenHelpers.h b/mlir/include/mlir/TableGen/CodeGenHelpers.h index dd17a44c889bbe383064f73b8cf2e8a1f96c1a99..c263c69c53d1e318d411a26473b475c38b6cb6dd 100644 --- a/mlir/include/mlir/TableGen/CodeGenHelpers.h +++ b/mlir/include/mlir/TableGen/CodeGenHelpers.h @@ -99,8 +99,14 @@ private: /// class StaticVerifierFunctionEmitter { public: + /// Create a constraint uniquer with a unique prefix derived from the record + /// keeper with an optional tag. StaticVerifierFunctionEmitter(raw_ostream &os, - const llvm::RecordKeeper &records); + const llvm::RecordKeeper &records, + StringRef tag = ""); + + /// Collect and unique all the constraints used by operations. + void collectOpConstraints(ArrayRef opDefs); /// Collect and unique all compatible type, attribute, successor, and region /// constraints from the operations in the file and emit them at the top of @@ -108,7 +114,7 @@ public: /// /// Constraints that do not meet the restriction that they can only reference /// `$_self` and `$_op` are not uniqued. - void emitOpConstraints(ArrayRef opDefs, bool emitDecl); + void emitOpConstraints(ArrayRef opDefs); /// Unique all compatible type and attribute constraints from a pattern file /// and emit them at the top of the generated file. @@ -177,8 +183,6 @@ private: /// Emit pattern constraints. void emitPatternConstraints(); - /// Collect and unique all the constraints used by operations. - void collectOpConstraints(ArrayRef opDefs); /// Collect and unique all pattern constraints. void collectPatternConstraints(ArrayRef constraints); diff --git a/mlir/lib/Bindings/Python/DialectLLVM.cpp b/mlir/lib/Bindings/Python/DialectLLVM.cpp index 843707751dd84981b8bb2f0075e1881fdd29548f..42a4c8c0793ba8a5c3acb383a461d76eb9b2b33f 100644 --- a/mlir/lib/Bindings/Python/DialectLLVM.cpp +++ b/mlir/lib/Bindings/Python/DialectLLVM.cpp @@ -19,6 +19,11 @@ using namespace mlir::python; using namespace mlir::python::adaptors; void populateDialectLLVMSubmodule(const pybind11::module &m) { + + //===--------------------------------------------------------------------===// + // StructType + //===--------------------------------------------------------------------===// + auto llvmStructType = mlir_type_subclass(m, "StructType", mlirTypeIsALLVMStructType); @@ -35,8 +40,8 @@ void populateDialectLLVMSubmodule(const pybind11::module &m) { } return cls(type); }, - py::arg("cls"), py::arg("elements"), py::kw_only(), - py::arg("packed") = false, py::arg("loc") = py::none()); + "cls"_a, "elements"_a, py::kw_only(), "packed"_a = false, + "loc"_a = py::none()); llvmStructType.def_classmethod( "get_identified", @@ -44,8 +49,7 @@ void populateDialectLLVMSubmodule(const pybind11::module &m) { return cls(mlirLLVMStructTypeIdentifiedGet( context, mlirStringRefCreate(name.data(), name.size()))); }, - py::arg("cls"), py::arg("name"), py::kw_only(), - py::arg("context") = py::none()); + "cls"_a, "name"_a, py::kw_only(), "context"_a = py::none()); llvmStructType.def_classmethod( "get_opaque", @@ -53,7 +57,7 @@ void populateDialectLLVMSubmodule(const pybind11::module &m) { return cls(mlirLLVMStructTypeOpaqueGet( context, mlirStringRefCreate(name.data(), name.size()))); }, - py::arg("cls"), py::arg("name"), py::arg("context") = py::none()); + "cls"_a, "name"_a, "context"_a = py::none()); llvmStructType.def( "set_body", @@ -65,7 +69,7 @@ void populateDialectLLVMSubmodule(const pybind11::module &m) { "Struct body already set to different content."); } }, - py::arg("elements"), py::kw_only(), py::arg("packed") = false); + "elements"_a, py::kw_only(), "packed"_a = false); llvmStructType.def_classmethod( "new_identified", @@ -75,8 +79,8 @@ void populateDialectLLVMSubmodule(const pybind11::module &m) { ctx, mlirStringRefCreate(name.data(), name.length()), elements.size(), elements.data(), packed)); }, - py::arg("cls"), py::arg("name"), py::arg("elements"), py::kw_only(), - py::arg("packed") = false, py::arg("context") = py::none()); + "cls"_a, "name"_a, "elements"_a, py::kw_only(), "packed"_a = false, + "context"_a = py::none()); llvmStructType.def_property_readonly( "name", [](MlirType type) -> std::optional { @@ -105,6 +109,29 @@ void populateDialectLLVMSubmodule(const pybind11::module &m) { llvmStructType.def_property_readonly( "opaque", [](MlirType type) { return mlirLLVMStructTypeIsOpaque(type); }); + + //===--------------------------------------------------------------------===// + // PointerType + //===--------------------------------------------------------------------===// + + mlir_type_subclass(m, "PointerType", mlirTypeIsALLVMPointerType) + .def_classmethod( + "get", + [](py::object cls, std::optional addressSpace, + MlirContext context) { + CollectDiagnosticsToStringScope scope(context); + MlirType type = mlirLLVMPointerTypeGet( + context, addressSpace.has_value() ? *addressSpace : 0); + if (mlirTypeIsNull(type)) { + throw py::value_error(scope.takeMessage()); + } + return cls(type); + }, + "cls"_a, "address_space"_a = py::none(), py::kw_only(), + "context"_a = py::none()) + .def_property_readonly("address_space", [](MlirType type) { + return mlirLLVMPointerTypeGetAddressSpace(type); + }); } PYBIND11_MODULE(_mlirDialectsLLVM, m) { diff --git a/mlir/lib/Bindings/Python/DialectSparseTensor.cpp b/mlir/lib/Bindings/Python/DialectSparseTensor.cpp index 171faf9e00874623276ed7cf746f47411b749db9..584981cfe99bf161978b6748c042ffc39b76d9ff 100644 --- a/mlir/lib/Bindings/Python/DialectSparseTensor.cpp +++ b/mlir/lib/Bindings/Python/DialectSparseTensor.cpp @@ -42,16 +42,19 @@ static void populateDialectSparseTensorSubmodule(const py::module &m) { [](py::object cls, std::vector lvlTypes, std::optional dimToLvl, std::optional lvlToDim, int posWidth, int crdWidth, - MlirContext context) { + std::optional explicitVal, + std::optional implicitVal, MlirContext context) { return cls(mlirSparseTensorEncodingAttrGet( context, lvlTypes.size(), lvlTypes.data(), dimToLvl ? *dimToLvl : MlirAffineMap{nullptr}, lvlToDim ? *lvlToDim : MlirAffineMap{nullptr}, posWidth, - crdWidth)); + crdWidth, explicitVal ? *explicitVal : MlirAttribute{nullptr}, + implicitVal ? *implicitVal : MlirAttribute{nullptr})); }, py::arg("cls"), py::arg("lvl_types"), py::arg("dim_to_lvl"), py::arg("lvl_to_dim"), py::arg("pos_width"), py::arg("crd_width"), - py::arg("context") = py::none(), + py::arg("explicit_val") = py::none(), + py::arg("implicit_val") = py::none(), py::arg("context") = py::none(), "Gets a sparse_tensor.encoding from parameters.") .def_classmethod( "build_level_type", @@ -97,6 +100,24 @@ static void populateDialectSparseTensorSubmodule(const py::module &m) { mlirSparseTensorEncodingAttrGetPosWidth) .def_property_readonly("crd_width", mlirSparseTensorEncodingAttrGetCrdWidth) + .def_property_readonly( + "explicit_val", + [](MlirAttribute self) -> std::optional { + MlirAttribute ret = + mlirSparseTensorEncodingAttrGetExplicitVal(self); + if (mlirAttributeIsNull(ret)) + return {}; + return ret; + }) + .def_property_readonly( + "implicit_val", + [](MlirAttribute self) -> std::optional { + MlirAttribute ret = + mlirSparseTensorEncodingAttrGetImplicitVal(self); + if (mlirAttributeIsNull(ret)) + return {}; + return ret; + }) .def_property_readonly( "structured_n", [](MlirAttribute self) -> unsigned { diff --git a/mlir/lib/CAPI/Dialect/LLVM.cpp b/mlir/lib/CAPI/Dialect/LLVM.cpp index 21c66f38a8af036c290d6ac11f71de39084e562a..108ebe5367d567551b63c6dc9722c2fc85eecb75 100644 --- a/mlir/lib/CAPI/Dialect/LLVM.cpp +++ b/mlir/lib/CAPI/Dialect/LLVM.cpp @@ -27,6 +27,14 @@ MlirType mlirLLVMPointerTypeGet(MlirContext ctx, unsigned addressSpace) { return wrap(LLVMPointerType::get(unwrap(ctx), addressSpace)); } +bool mlirTypeIsALLVMPointerType(MlirType type) { + return isa(unwrap(type)); +} + +unsigned mlirLLVMPointerTypeGetAddressSpace(MlirType pointerType) { + return cast(unwrap(pointerType)).getAddressSpace(); +} + MlirType mlirLLVMVoidTypeGet(MlirContext ctx) { return wrap(LLVMVoidType::get(unwrap(ctx))); } diff --git a/mlir/lib/CAPI/Dialect/SparseTensor.cpp b/mlir/lib/CAPI/Dialect/SparseTensor.cpp index 3ae06f220c5281bbf3b72cb8ccc553e1c204c34e..19171d64d4094975098144f9aa389e18f1c77b12 100644 --- a/mlir/lib/CAPI/Dialect/SparseTensor.cpp +++ b/mlir/lib/CAPI/Dialect/SparseTensor.cpp @@ -44,18 +44,20 @@ bool mlirAttributeIsASparseTensorEncodingAttr(MlirAttribute attr) { return isa(unwrap(attr)); } -MlirAttribute -mlirSparseTensorEncodingAttrGet(MlirContext ctx, intptr_t lvlRank, - MlirSparseTensorLevelType const *lvlTypes, - MlirAffineMap dimToLvl, MlirAffineMap lvlToDim, - int posWidth, int crdWidth) { +MlirAttribute mlirSparseTensorEncodingAttrGet( + MlirContext ctx, intptr_t lvlRank, + MlirSparseTensorLevelType const *lvlTypes, MlirAffineMap dimToLvl, + MlirAffineMap lvlToDim, int posWidth, int crdWidth, + MlirAttribute explicitVal, MlirAttribute implicitVal) { SmallVector cppLvlTypes; + cppLvlTypes.reserve(lvlRank); for (intptr_t l = 0; l < lvlRank; ++l) cppLvlTypes.push_back(static_cast(lvlTypes[l])); - return wrap(SparseTensorEncodingAttr::get(unwrap(ctx), cppLvlTypes, - unwrap(dimToLvl), unwrap(lvlToDim), - posWidth, crdWidth)); + + return wrap(SparseTensorEncodingAttr::get( + unwrap(ctx), cppLvlTypes, unwrap(dimToLvl), unwrap(lvlToDim), posWidth, + crdWidth, unwrap(explicitVal), unwrap(implicitVal))); } MlirAffineMap mlirSparseTensorEncodingAttrGetDimToLvl(MlirAttribute attr) { @@ -91,6 +93,14 @@ int mlirSparseTensorEncodingAttrGetCrdWidth(MlirAttribute attr) { return cast(unwrap(attr)).getCrdWidth(); } +MlirAttribute mlirSparseTensorEncodingAttrGetExplicitVal(MlirAttribute attr) { + return wrap(cast(unwrap(attr)).getExplicitVal()); +} + +MlirAttribute mlirSparseTensorEncodingAttrGetImplicitVal(MlirAttribute attr) { + return wrap(cast(unwrap(attr)).getImplicitVal()); +} + MlirSparseTensorLevelType mlirSparseTensorEncodingAttrBuildLvlType( enum MlirSparseTensorLevelFormat lvlFmt, const enum MlirSparseTensorLevelPropertyNondefault *properties, diff --git a/mlir/lib/Conversion/SCFToOpenMP/SCFToOpenMP.cpp b/mlir/lib/Conversion/SCFToOpenMP/SCFToOpenMP.cpp index 7f91367ad427a29c1abed1ea4870f9052a442bbf..d6f85451ee5d304270098a66b647598766bf6fe3 100644 --- a/mlir/lib/Conversion/SCFToOpenMP/SCFToOpenMP.cpp +++ b/mlir/lib/Conversion/SCFToOpenMP/SCFToOpenMP.cpp @@ -461,18 +461,50 @@ struct ParallelOpLowering : public OpRewritePattern { // Replace the loop. { OpBuilder::InsertionGuard allocaGuard(rewriter); - auto loop = rewriter.create( + // Create worksharing loop wrapper. + auto wsloopOp = rewriter.create(parallelOp.getLoc()); + if (!reductionVariables.empty()) { + wsloopOp.setReductionsAttr( + ArrayAttr::get(rewriter.getContext(), reductionDeclSymbols)); + wsloopOp.getReductionVarsMutable().append(reductionVariables); + } + rewriter.create(loc); // omp.parallel terminator. + + // The wrapper's entry block arguments will define the reduction + // variables. + llvm::SmallVector reductionTypes; + reductionTypes.reserve(reductionVariables.size()); + llvm::transform(reductionVariables, std::back_inserter(reductionTypes), + [](mlir::Value v) { return v.getType(); }); + rewriter.createBlock( + &wsloopOp.getRegion(), {}, reductionTypes, + llvm::SmallVector(reductionVariables.size(), + parallelOp.getLoc())); + + rewriter.setInsertionPoint( + rewriter.create(parallelOp.getLoc())); + + // Create loop nest and populate region with contents of scf.parallel. + auto loopOp = rewriter.create( parallelOp.getLoc(), parallelOp.getLowerBound(), parallelOp.getUpperBound(), parallelOp.getStep()); - rewriter.create(loc); - rewriter.inlineRegionBefore(parallelOp.getRegion(), loop.getRegion(), - loop.getRegion().begin()); + rewriter.inlineRegionBefore(parallelOp.getRegion(), loopOp.getRegion(), + loopOp.getRegion().begin()); - Block *ops = rewriter.splitBlock(&*loop.getRegion().begin(), - loop.getRegion().begin()->begin()); + // Remove reduction-related block arguments from omp.loop_nest and + // redirect uses to the corresponding omp.wsloop block argument. + mlir::Block &loopOpEntryBlock = loopOp.getRegion().front(); + unsigned numLoops = parallelOp.getNumLoops(); + rewriter.replaceAllUsesWith( + loopOpEntryBlock.getArguments().drop_front(numLoops), + wsloopOp.getRegion().getArguments()); + loopOpEntryBlock.eraseArguments( + numLoops, loopOpEntryBlock.getNumArguments() - numLoops); - rewriter.setInsertionPointToStart(&*loop.getRegion().begin()); + Block *ops = + rewriter.splitBlock(&loopOpEntryBlock, loopOpEntryBlock.begin()); + rewriter.setInsertionPointToStart(&loopOpEntryBlock); auto scope = rewriter.create(parallelOp.getLoc(), TypeRange()); @@ -481,11 +513,6 @@ struct ParallelOpLowering : public OpRewritePattern { rewriter.mergeBlocks(ops, scopeBlock); rewriter.setInsertionPointToEnd(&*scope.getBodyRegion().begin()); rewriter.create(loc, ValueRange()); - if (!reductionVariables.empty()) { - loop.setReductionsAttr( - ArrayAttr::get(rewriter.getContext(), reductionDeclSymbols)); - loop.getReductionVarsMutable().append(reductionVariables); - } } } diff --git a/mlir/lib/Conversion/TosaToLinalg/TosaToLinalgNamed.cpp b/mlir/lib/Conversion/TosaToLinalg/TosaToLinalgNamed.cpp index 8fb8d16486560c08154e732a029b342022bf3096..d8fb3abc0bef8a723de5424e022fca4edfec293d 100644 --- a/mlir/lib/Conversion/TosaToLinalg/TosaToLinalgNamed.cpp +++ b/mlir/lib/Conversion/TosaToLinalg/TosaToLinalgNamed.cpp @@ -101,9 +101,18 @@ static mlir::Value linalgBroadcastAndMaybeExtSI(PatternRewriter &rewriter, // The source tensor is broadcast to all the outer dimensions of the // result tensor. SmallVector sourceDims; - for (auto dim : llvm::seq(0, sourceRank)) { - auto expr = rewriter.getAffineDimExpr(dim + resultRank - sourceRank); - sourceDims.push_back(expr); + // In the case of a rank one source tensor with a single element TOSA + // specifies that the value be broadcast meaning we need an edge case for a + // constant map. + assert(sourceTy.hasStaticShape() && + "Dynamic broadcasting shapes not supported!"); + if (sourceRank == 1 && sourceTy.getDimSize(0) == 1) { + sourceDims.push_back(rewriter.getAffineConstantExpr(0)); + } else { + for (auto dim : llvm::seq(0, sourceRank)) { + auto expr = rewriter.getAffineDimExpr(dim + resultRank - sourceRank); + sourceDims.push_back(expr); + } } // Creating maps for the input and output of the broacast-like generic op. diff --git a/mlir/lib/Dialect/LLVMIR/IR/LLVMMemorySlot.cpp b/mlir/lib/Dialect/LLVMIR/IR/LLVMMemorySlot.cpp index f2ab3eae2c343ebd754e5bb7448bdb594b0ec1ef..6eeb13ebffb51f1ee9e361285a371cfeacf19aa6 100644 --- a/mlir/lib/Dialect/LLVMIR/IR/LLVMMemorySlot.cpp +++ b/mlir/lib/Dialect/LLVMIR/IR/LLVMMemorySlot.cpp @@ -113,7 +113,7 @@ bool LLVM::LoadOp::loadsFrom(const MemorySlot &slot) { bool LLVM::LoadOp::storesTo(const MemorySlot &slot) { return false; } Value LLVM::LoadOp::getStored(const MemorySlot &slot, RewriterBase &rewriter, - const DataLayout &dataLayout) { + Value reachingDef, const DataLayout &dataLayout) { llvm_unreachable("getStored should not be called on LoadOp"); } @@ -142,9 +142,10 @@ static bool isSupportedTypeForConversion(Type type) { } /// Checks that `rhs` can be converted to `lhs` by a sequence of casts and -/// truncations. +/// truncations. Checks for narrowing or widening conversion compatibility +/// depending on `narrowingConversion`. static bool areConversionCompatible(const DataLayout &layout, Type targetType, - Type srcType) { + Type srcType, bool narrowingConversion) { if (targetType == srcType) return true; @@ -152,13 +153,18 @@ static bool areConversionCompatible(const DataLayout &layout, Type targetType, !isSupportedTypeForConversion(srcType)) return false; + uint64_t targetSize = layout.getTypeSize(targetType); + uint64_t srcSize = layout.getTypeSize(srcType); + // Pointer casts will only be sane when the bitsize of both pointer types is // the same. if (isa(targetType) && isa(srcType)) - return layout.getTypeSize(targetType) == layout.getTypeSize(srcType); + return targetSize == srcSize; - return layout.getTypeSize(targetType) <= layout.getTypeSize(srcType); + if (narrowingConversion) + return targetSize <= srcSize; + return targetSize >= srcSize; } /// Checks if `dataLayout` describes a little endian layout. @@ -167,22 +173,49 @@ static bool isBigEndian(const DataLayout &dataLayout) { return endiannessStr && endiannessStr == "big"; } -/// The size of a byte in bits. -constexpr const static uint64_t kBitsInByte = 8; +/// Converts a value to an integer type of the same size. +/// Assumes that the type can be converted. +static Value castToSameSizedInt(RewriterBase &rewriter, Location loc, Value val, + const DataLayout &dataLayout) { + Type type = val.getType(); + assert(isSupportedTypeForConversion(type) && + "expected value to have a convertible type"); + + if (isa(type)) + return val; + + uint64_t typeBitSize = dataLayout.getTypeSizeInBits(type); + IntegerType valueSizeInteger = rewriter.getIntegerType(typeBitSize); + + if (isa(type)) + return rewriter.createOrFold(loc, valueSizeInteger, val); + return rewriter.createOrFold(loc, valueSizeInteger, val); +} + +/// Converts a value with an integer type to `targetType`. +static Value castIntValueToSameSizedType(RewriterBase &rewriter, Location loc, + Value val, Type targetType) { + assert(isa(val.getType()) && + "expected value to have an integer type"); + assert(isSupportedTypeForConversion(targetType) && + "expected the target type to be supported for conversions"); + if (val.getType() == targetType) + return val; + if (isa(targetType)) + return rewriter.createOrFold(loc, targetType, val); + return rewriter.createOrFold(loc, targetType, val); +} -/// Constructs operations that convert `inputValue` into a new value of type -/// `targetType`. Assumes that this conversion is possible. -static Value createConversionSequence(RewriterBase &rewriter, Location loc, - Value srcValue, Type targetType, - const DataLayout &dataLayout) { - // Get the types of the source and target values. +/// Constructs operations that convert `srcValue` into a new value of type +/// `targetType`. Assumes the types have the same bitsize. +static Value castSameSizedTypes(RewriterBase &rewriter, Location loc, + Value srcValue, Type targetType, + const DataLayout &dataLayout) { Type srcType = srcValue.getType(); - assert(areConversionCompatible(dataLayout, targetType, srcType) && + assert(areConversionCompatible(dataLayout, targetType, srcType, + /*narrowingConversion=*/true) && "expected that the compatibility was checked before"); - uint64_t srcTypeSize = dataLayout.getTypeSize(srcType); - uint64_t targetTypeSize = dataLayout.getTypeSize(targetType); - // Nothing has to be done if the types are already the same. if (srcType == targetType) return srcValue; @@ -196,48 +229,117 @@ static Value createConversionSequence(RewriterBase &rewriter, Location loc, return rewriter.createOrFold(loc, targetType, srcValue); - IntegerType valueSizeInteger = - rewriter.getIntegerType(srcTypeSize * kBitsInByte); - Value replacement = srcValue; + // For all other castable types, casting through integers is necessary. + Value replacement = castToSameSizedInt(rewriter, loc, srcValue, dataLayout); + return castIntValueToSameSizedType(rewriter, loc, replacement, targetType); +} + +/// Constructs operations that convert `srcValue` into a new value of type +/// `targetType`. Performs bit-level extraction if the source type is larger +/// than the target type. Assumes that this conversion is possible. +static Value createExtractAndCast(RewriterBase &rewriter, Location loc, + Value srcValue, Type targetType, + const DataLayout &dataLayout) { + // Get the types of the source and target values. + Type srcType = srcValue.getType(); + assert(areConversionCompatible(dataLayout, targetType, srcType, + /*narrowingConversion=*/true) && + "expected that the compatibility was checked before"); + + uint64_t srcTypeSize = dataLayout.getTypeSizeInBits(srcType); + uint64_t targetTypeSize = dataLayout.getTypeSizeInBits(targetType); + if (srcTypeSize == targetTypeSize) + return castSameSizedTypes(rewriter, loc, srcValue, targetType, dataLayout); // First, cast the value to a same-sized integer type. - if (isa(srcType)) - replacement = rewriter.createOrFold(loc, valueSizeInteger, - replacement); - else if (replacement.getType() != valueSizeInteger) - replacement = rewriter.createOrFold(loc, valueSizeInteger, - replacement); + Value replacement = castToSameSizedInt(rewriter, loc, srcValue, dataLayout); // Truncate the integer if the size of the target is less than the value. - if (targetTypeSize != srcTypeSize) { - if (isBigEndian(dataLayout)) { - uint64_t shiftAmount = (srcTypeSize - targetTypeSize) * kBitsInByte; - auto shiftConstant = rewriter.create( - loc, rewriter.getIntegerAttr(srcType, shiftAmount)); - replacement = - rewriter.createOrFold(loc, srcValue, shiftConstant); - } - - replacement = rewriter.create( - loc, rewriter.getIntegerType(targetTypeSize * kBitsInByte), - replacement); + if (isBigEndian(dataLayout)) { + uint64_t shiftAmount = srcTypeSize - targetTypeSize; + auto shiftConstant = rewriter.create( + loc, rewriter.getIntegerAttr(srcType, shiftAmount)); + replacement = + rewriter.createOrFold(loc, srcValue, shiftConstant); } + replacement = rewriter.create( + loc, rewriter.getIntegerType(targetTypeSize), replacement); + // Now cast the integer to the actual target type if required. - if (isa(targetType)) - replacement = - rewriter.createOrFold(loc, targetType, replacement); - else if (replacement.getType() != targetType) - replacement = - rewriter.createOrFold(loc, targetType, replacement); + return castIntValueToSameSizedType(rewriter, loc, replacement, targetType); +} + +/// Constructs operations that insert the bits of `srcValue` into the +/// "beginning" of `reachingDef` (beginning is endianness dependent). +/// Assumes that this conversion is possible. +static Value createInsertAndCast(RewriterBase &rewriter, Location loc, + Value srcValue, Value reachingDef, + const DataLayout &dataLayout) { + + assert(areConversionCompatible(dataLayout, reachingDef.getType(), + srcValue.getType(), + /*narrowingConversion=*/false) && + "expected that the compatibility was checked before"); + uint64_t valueTypeSize = dataLayout.getTypeSizeInBits(srcValue.getType()); + uint64_t slotTypeSize = dataLayout.getTypeSizeInBits(reachingDef.getType()); + if (slotTypeSize == valueTypeSize) + return castSameSizedTypes(rewriter, loc, srcValue, reachingDef.getType(), + dataLayout); + + // In the case where the store only overwrites parts of the memory, + // bit fiddling is required to construct the new value. + + // First convert both values to integers of the same size. + Value defAsInt = castToSameSizedInt(rewriter, loc, reachingDef, dataLayout); + Value valueAsInt = castToSameSizedInt(rewriter, loc, srcValue, dataLayout); + // Extend the value to the size of the reaching definition. + valueAsInt = + rewriter.createOrFold(loc, defAsInt.getType(), valueAsInt); + uint64_t sizeDifference = slotTypeSize - valueTypeSize; + if (isBigEndian(dataLayout)) { + // On big endian systems, a store to the base pointer overwrites the most + // significant bits. To accomodate for this, the stored value needs to be + // shifted into the according position. + Value bigEndianShift = rewriter.create( + loc, rewriter.getIntegerAttr(defAsInt.getType(), sizeDifference)); + valueAsInt = + rewriter.createOrFold(loc, valueAsInt, bigEndianShift); + } + + // Construct the mask that is used to erase the bits that are overwritten by + // the store. + APInt maskValue; + if (isBigEndian(dataLayout)) { + // Build a mask that has the most significant bits set to zero. + // Note: This is the same as 2^sizeDifference - 1 + maskValue = APInt::getAllOnes(sizeDifference).zext(slotTypeSize); + } else { + // Build a mask that has the least significant bits set to zero. + // Note: This is the same as -(2^valueTypeSize) + maskValue = APInt::getAllOnes(valueTypeSize).zext(slotTypeSize); + maskValue.flipAllBits(); + } + + // Mask out the affected bits ... + Value mask = rewriter.create( + loc, rewriter.getIntegerAttr(defAsInt.getType(), maskValue)); + Value masked = rewriter.createOrFold(loc, defAsInt, mask); + + // ... and combine the result with the new value. + Value combined = rewriter.createOrFold(loc, masked, valueAsInt); - return replacement; + return castIntValueToSameSizedType(rewriter, loc, combined, + reachingDef.getType()); } Value LLVM::StoreOp::getStored(const MemorySlot &slot, RewriterBase &rewriter, + Value reachingDef, const DataLayout &dataLayout) { - return createConversionSequence(rewriter, getLoc(), getValue(), slot.elemType, - dataLayout); + assert(reachingDef && reachingDef.getType() == slot.elemType && + "expected the reaching definition's type to match the slot's type"); + return createInsertAndCast(rewriter, getLoc(), getValue(), reachingDef, + dataLayout); } bool LLVM::LoadOp::canUsesBeRemoved( @@ -249,11 +351,10 @@ bool LLVM::LoadOp::canUsesBeRemoved( Value blockingUse = (*blockingUses.begin())->get(); // If the blocking use is the slot ptr itself, there will be enough // context to reconstruct the result of the load at removal time, so it can - // be removed (provided it loads the exact stored value and is not - // volatile). + // be removed (provided it is not volatile). return blockingUse == slot.ptr && getAddr() == slot.ptr && areConversionCompatible(dataLayout, getResult().getType(), - slot.elemType) && + slot.elemType, /*narrowingConversion=*/true) && !getVolatile_(); } @@ -263,9 +364,8 @@ DeletionKind LLVM::LoadOp::removeBlockingUses( const DataLayout &dataLayout) { // `canUsesBeRemoved` checked this blocking use must be the loaded slot // pointer. - Value newResult = - createConversionSequence(rewriter, getLoc(), reachingDefinition, - getResult().getType(), dataLayout); + Value newResult = createExtractAndCast(rewriter, getLoc(), reachingDefinition, + getResult().getType(), dataLayout); rewriter.replaceAllUsesWith(getResult(), newResult); return DeletionKind::Delete; } @@ -283,7 +383,8 @@ bool LLVM::StoreOp::canUsesBeRemoved( return blockingUse == slot.ptr && getAddr() == slot.ptr && getValue() != slot.ptr && areConversionCompatible(dataLayout, slot.elemType, - getValue().getType()) && + getValue().getType(), + /*narrowingConversion=*/false) && !getVolatile_(); } @@ -838,6 +939,7 @@ bool LLVM::MemsetOp::storesTo(const MemorySlot &slot) { } Value LLVM::MemsetOp::getStored(const MemorySlot &slot, RewriterBase &rewriter, + Value reachingDef, const DataLayout &dataLayout) { // TODO: Support non-integer types. return TypeSwitch(slot.elemType) @@ -1149,6 +1251,7 @@ bool LLVM::MemcpyOp::storesTo(const MemorySlot &slot) { } Value LLVM::MemcpyOp::getStored(const MemorySlot &slot, RewriterBase &rewriter, + Value reachingDef, const DataLayout &dataLayout) { return memcpyGetStored(*this, slot, rewriter); } @@ -1199,7 +1302,7 @@ bool LLVM::MemcpyInlineOp::storesTo(const MemorySlot &slot) { } Value LLVM::MemcpyInlineOp::getStored(const MemorySlot &slot, - RewriterBase &rewriter, + RewriterBase &rewriter, Value reachingDef, const DataLayout &dataLayout) { return memcpyGetStored(*this, slot, rewriter); } @@ -1252,6 +1355,7 @@ bool LLVM::MemmoveOp::storesTo(const MemorySlot &slot) { } Value LLVM::MemmoveOp::getStored(const MemorySlot &slot, RewriterBase &rewriter, + Value reachingDef, const DataLayout &dataLayout) { return memcpyGetStored(*this, slot, rewriter); } diff --git a/mlir/lib/Dialect/Linalg/Transforms/CMakeLists.txt b/mlir/lib/Dialect/Linalg/Transforms/CMakeLists.txt index ee6e391d0cc682624fea5de9e523d35cf6249b22..3b5282a09569d78c8140f09838bede372681fd89 100644 --- a/mlir/lib/Dialect/Linalg/Transforms/CMakeLists.txt +++ b/mlir/lib/Dialect/Linalg/Transforms/CMakeLists.txt @@ -27,6 +27,7 @@ add_mlir_dialect_library(MLIRLinalgTransforms NamedOpConversions.cpp Padding.cpp Promotion.cpp + RuntimeOpVerification.cpp Specialize.cpp Split.cpp SplitReduction.cpp @@ -60,6 +61,7 @@ add_mlir_dialect_library(MLIRLinalgTransforms MLIRFuncDialect MLIRFuncToLLVM MLIRFuncTransforms + MLIRIndexDialect MLIRInferTypeOpInterface MLIRIR MLIRMemRefDialect diff --git a/mlir/lib/Dialect/Linalg/Transforms/RuntimeOpVerification.cpp b/mlir/lib/Dialect/Linalg/Transforms/RuntimeOpVerification.cpp new file mode 100644 index 0000000000000000000000000000000000000000..b30182dc84079fe1d40ce7982a8c4c495801212f --- /dev/null +++ b/mlir/lib/Dialect/Linalg/Transforms/RuntimeOpVerification.cpp @@ -0,0 +1,135 @@ +//===- RuntimeOpVerification.cpp - Op Verification ------------------------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#include "mlir/Dialect/Linalg/Transforms/RuntimeOpVerification.h" + +#include "mlir/Dialect/Affine/IR/AffineOps.h" +#include "mlir/Dialect/Arith/IR/Arith.h" +#include "mlir/Dialect/Arith/Utils/Utils.h" +#include "mlir/Dialect/ControlFlow/IR/ControlFlowOps.h" +#include "mlir/Dialect/Index/IR/IndexAttrs.h" +#include "mlir/Dialect/Index/IR/IndexDialect.h" +#include "mlir/Dialect/Index/IR/IndexOps.h" +#include "mlir/Dialect/Linalg/IR/Linalg.h" +#include "mlir/Dialect/MemRef/IR/MemRef.h" +#include "mlir/Dialect/Tensor/IR/Tensor.h" +#include "mlir/Interfaces/RuntimeVerifiableOpInterface.h" + +namespace mlir { +namespace linalg { +namespace { +/// Verify that the runtime sizes of the operands to linalg structured ops are +/// compatible with the runtime sizes inferred by composing the loop ranges with +/// the linalg op's indexing maps. This is similar to the verifier except that +/// here we insert IR to perform the verification at runtime. +template +struct StructuredOpInterface + : public RuntimeVerifiableOpInterface::ExternalModel< + StructuredOpInterface, T> { + void generateRuntimeVerification(Operation *op, OpBuilder &builder, + Location loc) const { + auto linalgOp = llvm::cast(op); + + SmallVector loopRanges = linalgOp.createLoopRanges(builder, loc); + auto [starts, ends, _] = getOffsetsSizesAndStrides(loopRanges); + + auto zero = builder.create(loc, 0); + auto one = builder.create(loc, 1); + + // Subtract one from the loop ends before composing with the indexing map + transform(ends, ends.begin(), [&](OpFoldResult end) { + auto endValue = getValueOrCreateConstantIndexOp(builder, loc, end); + return builder.createOrFold(loc, endValue, one); + }); + + for (OpOperand &opOperand : linalgOp->getOpOperands()) { + AffineMap indexingMap = linalgOp.getMatchingIndexingMap(&opOperand); + auto startIndices = affine::makeComposedFoldedMultiResultAffineApply( + builder, loc, indexingMap, starts); + auto endIndices = affine::makeComposedFoldedMultiResultAffineApply( + builder, loc, indexingMap, ends); + + for (auto dim : llvm::seq(linalgOp.getRank(&opOperand))) { + auto startIndex = + getValueOrCreateConstantIndexOp(builder, loc, startIndices[dim]); + auto endIndex = + getValueOrCreateConstantIndexOp(builder, loc, endIndices[dim]); + + // Generate: + // minIndex = min(startIndex, endIndex) + // assert(minIndex >= 0) + // To ensure we do not generate a negative index. We take the minimum of + // the start and end indices in order to handle reverse loops such as + // `affine_map<(i) -> (3 - i)>` + auto min = + builder.createOrFold(loc, startIndex, endIndex); + auto cmpOp = builder.createOrFold( + loc, index::IndexCmpPredicate::SGE, min, zero); + auto msg = RuntimeVerifiableOpInterface::generateErrorMessage( + linalgOp, "unexpected negative result on dimension #" + + std::to_string(dim) + " of input/output operand #" + + std::to_string(opOperand.getOperandNumber())); + builder.createOrFold(loc, cmpOp, msg); + + // Generate: + // inferredDimSize = max(startIndex, endIndex) + 1 + // actualDimSize = dim(operand) + // assert(inferredDimSize <= actualDimSize) + // To ensure that we do not index past the bounds of the operands. + auto max = + builder.createOrFold(loc, startIndex, endIndex); + + auto inferredDimSize = + builder.createOrFold(loc, max, one); + + auto actualDimSize = + createOrFoldDimOp(builder, loc, opOperand.get(), dim); + + // Similar to the verifier, when the affine expression in the indexing + // map is complicated, we just check that the inferred dimension sizes + // are in the boundary of the operands' size. Being more precise than + // that is difficult. + auto predicate = isa(indexingMap.getResult(dim)) + ? index::IndexCmpPredicate::EQ + : index::IndexCmpPredicate::SLE; + + cmpOp = builder.createOrFold( + loc, predicate, inferredDimSize, actualDimSize); + msg = RuntimeVerifiableOpInterface::generateErrorMessage( + linalgOp, "dimension #" + std::to_string(dim) + + " of input/output operand #" + + std::to_string(opOperand.getOperandNumber()) + + " is incompatible with inferred dimension size"); + builder.createOrFold(loc, cmpOp, msg); + } + } + } +}; + +template +void attachInterface(MLIRContext *ctx) { + (OpTs::template attachInterface>(*ctx), ...); +} +} // namespace +} // namespace linalg +} // namespace mlir + +void mlir::linalg::registerRuntimeVerifiableOpInterfaceExternalModels( + DialectRegistry ®istry) { + registry.addExtension(+[](MLIRContext *ctx, LinalgDialect *) { + attachInterface< +#define GET_OP_LIST +#include "mlir/Dialect/Linalg/IR/LinalgStructuredOps.cpp.inc" + >(ctx); + + // Load additional dialects of which ops may get created. + ctx->loadDialect(); + }); +} diff --git a/mlir/lib/Dialect/Linalg/Transforms/Vectorization.cpp b/mlir/lib/Dialect/Linalg/Transforms/Vectorization.cpp index e836f0dc63b4f923780673184efcede9d2b1093a..ef9a30be9a0153375c76fcab5e2b8ea9f8864ac9 100644 --- a/mlir/lib/Dialect/Linalg/Transforms/Vectorization.cpp +++ b/mlir/lib/Dialect/Linalg/Transforms/Vectorization.cpp @@ -1499,11 +1499,11 @@ vectorizeAsTensorPackOp(RewriterBase &rewriter, tensor::PackOp packOp, // If the input vector sizes are not provided, then the vector sizes are // determined by the result tensor shape. In case the vector sizes aren't // provided, we update the inBounds attribute instead of masking. - bool useInBoundsInsteadOfMasking = true; + bool useInBoundsInsteadOfMasking = false; if (inputVectorSizes.empty()) { ArrayRef resultTensorShape = packOp.getDestType().getShape(); inputVectorSizes = resultTensorShape.take_front(packOp.getSourceRank()); - useInBoundsInsteadOfMasking = false; + useInBoundsInsteadOfMasking = true; } // Create masked TransferReadOp. @@ -1612,7 +1612,8 @@ vectorizeAsTensorUnpackOp(RewriterBase &rewriter, tensor::UnPackOp unpackOp, // to shape of source, then a mask is necessary. Value readResult = vector::createReadOrMaskedRead( rewriter, loc, unpackOp.getSource(), - ArrayRef(readMaskShape.begin(), readMaskShape.end()), padValue); + ArrayRef(readMaskShape.begin(), readMaskShape.end()), padValue, + /*useInBoundsInsteadOfMasking=*/false); PackingMetadata packMetadata; SmallVector lastDimToInsertPosPerm = @@ -1669,7 +1670,8 @@ vectorizeAsTensorPadOp(RewriterBase &rewriter, tensor::PadOp padOp, (void)status; // prevent unused variable warning on non-assert builds assert(succeeded(status) && "failed to reify result shapes"); auto maskedRead = vector::createReadOrMaskedRead( - rewriter, loc, padOp.getSource(), inputVectorSizes, padValue); + rewriter, loc, padOp.getSource(), inputVectorSizes, padValue, + /*useInBoundsInsteadOfMasking=*/false); Operation *write = createWriteOrMaskedWrite( rewriter, loc, maskedRead, reifiedReturnShapes[0], inputVectorSizes); newResults.push_back(write->getResult(0)); diff --git a/mlir/lib/Dialect/MemRef/IR/MemRefMemorySlot.cpp b/mlir/lib/Dialect/MemRef/IR/MemRefMemorySlot.cpp index ebbf20f1b76b67a56e2202bb2f532e1fbb0bdfc4..958c5f0c8dbc75b09887c044eb3822105726cd71 100644 --- a/mlir/lib/Dialect/MemRef/IR/MemRefMemorySlot.cpp +++ b/mlir/lib/Dialect/MemRef/IR/MemRefMemorySlot.cpp @@ -161,6 +161,7 @@ bool memref::LoadOp::loadsFrom(const MemorySlot &slot) { bool memref::LoadOp::storesTo(const MemorySlot &slot) { return false; } Value memref::LoadOp::getStored(const MemorySlot &slot, RewriterBase &rewriter, + Value reachingDef, const DataLayout &dataLayout) { llvm_unreachable("getStored should not be called on LoadOp"); } @@ -242,6 +243,7 @@ bool memref::StoreOp::storesTo(const MemorySlot &slot) { } Value memref::StoreOp::getStored(const MemorySlot &slot, RewriterBase &rewriter, + Value reachingDef, const DataLayout &dataLayout) { return getValue(); } diff --git a/mlir/lib/Dialect/MemRef/Transforms/RuntimeOpVerification.cpp b/mlir/lib/Dialect/MemRef/Transforms/RuntimeOpVerification.cpp index 05b813a3b1e90841bcede975ca28a74b52a53ea9..450bfa0cec0c7fffbee482869a7bd95c0fb19bcf 100644 --- a/mlir/lib/Dialect/MemRef/Transforms/RuntimeOpVerification.cpp +++ b/mlir/lib/Dialect/MemRef/Transforms/RuntimeOpVerification.cpp @@ -20,25 +20,6 @@ using namespace mlir; -/// Generate an error message string for the given op and the specified error. -static std::string generateErrorMessage(Operation *op, const std::string &msg) { - std::string buffer; - llvm::raw_string_ostream stream(buffer); - OpPrintingFlags flags; - // We may generate a lot of error messages and so we need to ensure the - // printing is fast. - flags.elideLargeElementsAttrs(); - flags.printGenericOpForm(); - flags.skipRegions(); - flags.useLocalScope(); - stream << "ERROR: Runtime op verification failed\n"; - op->print(stream, flags); - stream << "\n^ " << msg; - stream << "\nLocation: "; - op->getLoc().print(stream); - return stream.str(); -} - namespace mlir { namespace memref { namespace { @@ -62,8 +43,10 @@ struct CastOpInterface builder.create(loc, resultType.getRank()); Value isSameRank = builder.create( loc, arith::CmpIPredicate::eq, srcRank, resultRank); - builder.create(loc, isSameRank, - generateErrorMessage(op, "rank mismatch")); + builder.create( + loc, isSameRank, + RuntimeVerifiableOpInterface::generateErrorMessage(op, + "rank mismatch")); } // Get source offset and strides. We do not have an op to get offsets and @@ -101,8 +84,8 @@ struct CastOpInterface loc, arith::CmpIPredicate::eq, srcDimSz, resultDimSz); builder.create( loc, isSameSz, - generateErrorMessage(op, "size mismatch of dim " + - std::to_string(it.index()))); + RuntimeVerifiableOpInterface::generateErrorMessage( + op, "size mismatch of dim " + std::to_string(it.index()))); } // Get result offset and strides. @@ -119,8 +102,10 @@ struct CastOpInterface builder.create(loc, resultOffset); Value isSameOffset = builder.create( loc, arith::CmpIPredicate::eq, srcOffset, resultOffsetVal); - builder.create(loc, isSameOffset, - generateErrorMessage(op, "offset mismatch")); + builder.create( + loc, isSameOffset, + RuntimeVerifiableOpInterface::generateErrorMessage( + op, "offset mismatch")); } // Check strides. @@ -137,8 +122,8 @@ struct CastOpInterface loc, arith::CmpIPredicate::eq, srcStride, resultStrideVal); builder.create( loc, isSameStride, - generateErrorMessage(op, "stride mismatch of dim " + - std::to_string(it.index()))); + RuntimeVerifiableOpInterface::generateErrorMessage( + op, "stride mismatch of dim " + std::to_string(it.index()))); } } }; @@ -178,7 +163,9 @@ struct LoadStoreOpInterface : andOp; } builder.create( - loc, assertCond, generateErrorMessage(op, "out-of-bounds access")); + loc, assertCond, + RuntimeVerifiableOpInterface::generateErrorMessage( + op, "out-of-bounds access")); } }; @@ -248,7 +235,7 @@ struct ReinterpretCastOpInterface builder.create( loc, assertCond, - generateErrorMessage( + RuntimeVerifiableOpInterface::generateErrorMessage( op, "result of reinterpret_cast is out-of-bounds of the base memref")); } @@ -293,8 +280,8 @@ struct SubViewOpInterface builder.create( loc, assertCond, - generateErrorMessage(op, - "subview is out-of-bounds of the base memref")); + RuntimeVerifiableOpInterface::generateErrorMessage( + op, "subview is out-of-bounds of the base memref")); } }; @@ -334,8 +321,9 @@ struct ExpandShapeOpInterface builder.create(loc, 0)); builder.create( loc, isModZero, - generateErrorMessage(op, "static result dims in reassoc group do not " - "divide src dim evenly")); + RuntimeVerifiableOpInterface::generateErrorMessage( + op, "static result dims in reassoc group do not " + "divide src dim evenly")); } } }; diff --git a/mlir/lib/Dialect/OpenMP/IR/OpenMPDialect.cpp b/mlir/lib/Dialect/OpenMP/IR/OpenMPDialect.cpp index 528a0d05b1011bd50846316293c6b4c926b510ad..f60668dd0cf995e7ab0f7f2813597c479f54dde8 100644 --- a/mlir/lib/Dialect/OpenMP/IR/OpenMPDialect.cpp +++ b/mlir/lib/Dialect/OpenMP/IR/OpenMPDialect.cpp @@ -1484,86 +1484,72 @@ LogicalResult SingleOp::verify() { // WsloopOp //===----------------------------------------------------------------------===// -/// loop-control ::= `(` ssa-id-list `)` `:` type `=` loop-bounds -/// loop-bounds := `(` ssa-id-list `)` to `(` ssa-id-list `)` inclusive? steps -/// steps := `step` `(`ssa-id-list`)` ParseResult parseWsloop(OpAsmParser &parser, Region ®ion, - SmallVectorImpl &lowerBound, - SmallVectorImpl &upperBound, - SmallVectorImpl &steps, - SmallVectorImpl &loopVarTypes, SmallVectorImpl &reductionOperands, - SmallVectorImpl &reductionTypes, ArrayAttr &reductionSymbols, - UnitAttr &inclusive) { - + SmallVectorImpl &reductionTypes, + ArrayAttr &reductionSymbols) { // Parse an optional reduction clause llvm::SmallVector privates; - bool hasReduction = succeeded(parser.parseOptionalKeyword("reduction")) && - succeeded(parseClauseWithRegionArgs( - parser, region, reductionOperands, reductionTypes, - reductionSymbols, privates)); - - if (parser.parseKeyword("for")) - return failure(); - - // Parse an opening `(` followed by induction variables followed by `)` - SmallVector ivs; - Type loopVarType; - if (parser.parseArgumentList(ivs, OpAsmParser::Delimiter::Paren) || - parser.parseColonType(loopVarType) || - // Parse loop bounds. - parser.parseEqual() || - parser.parseOperandList(lowerBound, ivs.size(), - OpAsmParser::Delimiter::Paren) || - parser.parseKeyword("to") || - parser.parseOperandList(upperBound, ivs.size(), - OpAsmParser::Delimiter::Paren)) - return failure(); - - if (succeeded(parser.parseOptionalKeyword("inclusive"))) - inclusive = UnitAttr::get(parser.getBuilder().getContext()); - - // Parse step values. - if (parser.parseKeyword("step") || - parser.parseOperandList(steps, ivs.size(), OpAsmParser::Delimiter::Paren)) - return failure(); - - // Now parse the body. - loopVarTypes = SmallVector(ivs.size(), loopVarType); - for (auto &iv : ivs) - iv.type = loopVarType; - - SmallVector regionArgs{ivs}; - if (hasReduction) - llvm::copy(privates, std::back_inserter(regionArgs)); - - return parser.parseRegion(region, regionArgs); + if (succeeded(parser.parseOptionalKeyword("reduction"))) { + if (failed(parseClauseWithRegionArgs(parser, region, reductionOperands, + reductionTypes, reductionSymbols, + privates))) + return failure(); + } + return parser.parseRegion(region, privates); } void printWsloop(OpAsmPrinter &p, Operation *op, Region ®ion, - ValueRange lowerBound, ValueRange upperBound, ValueRange steps, - TypeRange loopVarTypes, ValueRange reductionOperands, - TypeRange reductionTypes, ArrayAttr reductionSymbols, - UnitAttr inclusive) { + ValueRange reductionOperands, TypeRange reductionTypes, + ArrayAttr reductionSymbols) { if (reductionSymbols) { - auto reductionArgs = - region.front().getArguments().drop_front(loopVarTypes.size()); + auto reductionArgs = region.front().getArguments(); printClauseWithRegionArgs(p, op, reductionArgs, "reduction", reductionOperands, reductionTypes, reductionSymbols); } - - p << " for "; - auto args = region.front().getArguments().drop_back(reductionOperands.size()); - p << " (" << args << ") : " << args[0].getType() << " = (" << lowerBound - << ") to (" << upperBound << ") "; - if (inclusive) - p << "inclusive "; - p << "step (" << steps << ") "; p.printRegion(region, /*printEntryBlockArgs=*/false); } +void WsloopOp::build(OpBuilder &builder, OperationState &state, + ArrayRef attributes) { + build(builder, state, /*linear_vars=*/ValueRange(), + /*linear_step_vars=*/ValueRange(), /*reduction_vars=*/ValueRange(), + /*reductions=*/nullptr, /*schedule_val=*/nullptr, + /*schedule_chunk_var=*/nullptr, /*schedule_modifier=*/nullptr, + /*simd_modifier=*/false, /*nowait=*/false, /*byref=*/false, + /*ordered_val=*/nullptr, /*order_val=*/nullptr); + state.addAttributes(attributes); +} + +void WsloopOp::build(OpBuilder &builder, OperationState &state, + const WsloopClauseOps &clauses) { + MLIRContext *ctx = builder.getContext(); + // TODO: Store clauses in op: allocateVars, allocatorVars, privateVars, + // privatizers. + WsloopOp::build( + builder, state, clauses.linearVars, clauses.linearStepVars, + clauses.reductionVars, makeArrayAttr(ctx, clauses.reductionDeclSymbols), + clauses.scheduleValAttr, clauses.scheduleChunkVar, + clauses.scheduleModAttr, clauses.scheduleSimdAttr, clauses.nowaitAttr, + clauses.reductionByRefAttr, clauses.orderedAttr, clauses.orderAttr); +} + +LogicalResult WsloopOp::verify() { + if (!isWrapper()) + return emitOpError() << "must be a loop wrapper"; + + if (LoopWrapperInterface nested = getNestedWrapper()) { + // Check for the allowed leaf constructs that may appear in a composite + // construct directly after DO/FOR. + if (!isa(nested)) + return emitError() << "only supported nested wrapper is 'omp.simd'"; + } + + return verifyReductionVarList(*this, getReductions(), getReductionVars()); +} + //===----------------------------------------------------------------------===// // Simd construct [2.9.3.1] //===----------------------------------------------------------------------===// @@ -1947,42 +1933,6 @@ void LoopNestOp::gatherWrappers( } } -//===----------------------------------------------------------------------===// -// WsloopOp -//===----------------------------------------------------------------------===// - -void WsloopOp::build(OpBuilder &builder, OperationState &state, - ValueRange lowerBound, ValueRange upperBound, - ValueRange step, ArrayRef attributes) { - build(builder, state, lowerBound, upperBound, step, - /*linear_vars=*/ValueRange(), - /*linear_step_vars=*/ValueRange(), /*reduction_vars=*/ValueRange(), - /*reductions=*/nullptr, /*schedule_val=*/nullptr, - /*schedule_chunk_var=*/nullptr, /*schedule_modifier=*/nullptr, - /*simd_modifier=*/false, /*nowait=*/false, /*byref=*/false, - /*ordered_val=*/nullptr, - /*order_val=*/nullptr, /*inclusive=*/false); - state.addAttributes(attributes); -} - -void WsloopOp::build(OpBuilder &builder, OperationState &state, - const WsloopClauseOps &clauses) { - MLIRContext *ctx = builder.getContext(); - // TODO Store clauses in op: allocateVars, allocatorVars, privateVars, - // privatizers. - WsloopOp::build( - builder, state, clauses.loopLBVar, clauses.loopUBVar, clauses.loopStepVar, - clauses.linearVars, clauses.linearStepVars, clauses.reductionVars, - makeArrayAttr(ctx, clauses.reductionDeclSymbols), clauses.scheduleValAttr, - clauses.scheduleChunkVar, clauses.scheduleModAttr, - clauses.scheduleSimdAttr, clauses.nowaitAttr, clauses.reductionByRefAttr, - clauses.orderedAttr, clauses.orderAttr, clauses.loopInclusiveAttr); -} - -LogicalResult WsloopOp::verify() { - return verifyReductionVarList(*this, getReductions(), getReductionVars()); -} - //===----------------------------------------------------------------------===// // Critical construct (2.17.1) //===----------------------------------------------------------------------===// @@ -2014,6 +1964,39 @@ LogicalResult CriticalOp::verifySymbolUses(SymbolTableCollection &symbolTable) { // Ordered construct //===----------------------------------------------------------------------===// +static LogicalResult verifyOrderedParent(Operation &op) { + bool hasRegion = op.getNumRegions() > 0; + auto loopOp = op.getParentOfType(); + if (!loopOp) { + if (hasRegion) + return success(); + + // TODO: Consider if this needs to be the case only for the standalone + // variant of the ordered construct. + return op.emitOpError() << "must be nested inside of a loop"; + } + + Operation *wrapper = loopOp->getParentOp(); + if (auto wsloopOp = dyn_cast(wrapper)) { + IntegerAttr orderedAttr = wsloopOp.getOrderedValAttr(); + if (!orderedAttr) + return op.emitOpError() << "the enclosing worksharing-loop region must " + "have an ordered clause"; + + if (hasRegion && orderedAttr.getInt() != 0) + return op.emitOpError() << "the enclosing loop's ordered clause must not " + "have a parameter present"; + + if (!hasRegion && orderedAttr.getInt() == 0) + return op.emitOpError() << "the enclosing loop's ordered clause must " + "have a parameter present"; + } else if (!isa(wrapper)) { + return op.emitOpError() << "must be nested inside of a worksharing, simd " + "or worksharing simd loop"; + } + return success(); +} + void OrderedOp::build(OpBuilder &builder, OperationState &state, const OrderedOpClauseOps &clauses) { OrderedOp::build(builder, state, clauses.doacrossDependTypeAttr, @@ -2021,14 +2004,11 @@ void OrderedOp::build(OpBuilder &builder, OperationState &state, } LogicalResult OrderedOp::verify() { - auto container = (*this)->getParentOfType(); - if (!container || !container.getOrderedValAttr() || - container.getOrderedValAttr().getInt() == 0) - return emitOpError() << "ordered depend directive must be closely " - << "nested inside a worksharing-loop with ordered " - << "clause with parameter present"; - - if (container.getOrderedValAttr().getInt() != (int64_t)*getNumLoopsVal()) + if (failed(verifyOrderedParent(**this))) + return failure(); + + auto wrapper = (*this)->getParentOfType(); + if (!wrapper || *wrapper.getOrderedVal() != *getNumLoopsVal()) return emitOpError() << "number of variables in depend clause does not " << "match number of iteration variables in the " << "doacross loop"; @@ -2046,15 +2026,7 @@ LogicalResult OrderedRegionOp::verify() { if (getSimd()) return failure(); - if (auto container = (*this)->getParentOfType()) { - if (!container.getOrderedValAttr() || - container.getOrderedValAttr().getInt() != 0) - return emitOpError() << "ordered region must be closely nested inside " - << "a worksharing-loop region with an ordered " - << "clause without parameter present"; - } - - return success(); + return verifyOrderedParent(**this); } //===----------------------------------------------------------------------===// @@ -2199,15 +2171,19 @@ LogicalResult CancelOp::verify() { << "inside a parallel region"; } if (cct == ClauseCancellationConstructType::Loop) { - if (!isa(parentOp)) { - return emitOpError() << "cancel loop must appear " - << "inside a worksharing-loop region"; + auto loopOp = dyn_cast(parentOp); + auto wsloopOp = llvm::dyn_cast_if_present( + loopOp ? loopOp->getParentOp() : nullptr); + + if (!wsloopOp) { + return emitOpError() + << "cancel loop must appear inside a worksharing-loop region"; } - if (cast(parentOp).getNowaitAttr()) { + if (wsloopOp.getNowaitAttr()) { return emitError() << "A worksharing construct that is canceled " << "must not have a nowait clause"; } - if (cast(parentOp).getOrderedValAttr()) { + if (wsloopOp.getOrderedValAttr()) { return emitError() << "A worksharing construct that is canceled " << "must not have an ordered clause"; } @@ -2245,7 +2221,7 @@ LogicalResult CancellationPointOp::verify() { << "inside a parallel region"; } if ((cct == ClauseCancellationConstructType::Loop) && - !isa(parentOp)) { + (!isa(parentOp) || !isa(parentOp->getParentOp()))) { return emitOpError() << "cancellation point loop must appear " << "inside a worksharing-loop region"; } diff --git a/mlir/lib/Dialect/SCF/TransformOps/SCFTransformOps.cpp b/mlir/lib/Dialect/SCF/TransformOps/SCFTransformOps.cpp index 7e4faf8b73afbb9176b33ec3080ced540e95715b..69f83d8bd70da16aa1aeafc60dc35f5ca322b045 100644 --- a/mlir/lib/Dialect/SCF/TransformOps/SCFTransformOps.cpp +++ b/mlir/lib/Dialect/SCF/TransformOps/SCFTransformOps.cpp @@ -69,16 +69,12 @@ transform::ForallToForOp::apply(transform::TransformRewriter &rewriter, return diag; } - rewriter.setInsertionPoint(target); - if (!target.getOutputs().empty()) { return emitSilenceableError() << "unsupported shared outputs (didn't bufferize?)"; } SmallVector lbs = target.getMixedLowerBound(); - SmallVector ubs = target.getMixedUpperBound(); - SmallVector steps = target.getMixedStep(); if (getNumResults() != lbs.size()) { DiagnosedSilenceableFailure diag = @@ -89,28 +85,15 @@ transform::ForallToForOp::apply(transform::TransformRewriter &rewriter, return diag; } - auto loc = target.getLoc(); - SmallVector ivs; - for (auto &&[lb, ub, step] : llvm::zip(lbs, ubs, steps)) { - Value lbValue = getValueOrCreateConstantIndexOp(rewriter, loc, lb); - Value ubValue = getValueOrCreateConstantIndexOp(rewriter, loc, ub); - Value stepValue = getValueOrCreateConstantIndexOp(rewriter, loc, step); - auto loop = rewriter.create( - loc, lbValue, ubValue, stepValue, ValueRange(), - [](OpBuilder &, Location, Value, ValueRange) {}); - ivs.push_back(loop.getInductionVar()); - rewriter.setInsertionPointToStart(loop.getBody()); - rewriter.create(loc); - rewriter.setInsertionPointToStart(loop.getBody()); + SmallVector opResults; + if (failed(scf::forallToForLoop(rewriter, target, &opResults))) { + DiagnosedSilenceableFailure diag = emitSilenceableError() + << "failed to convert forall into for"; + return diag; } - rewriter.eraseOp(target.getBody()->getTerminator()); - rewriter.inlineBlockBefore(target.getBody(), &*rewriter.getInsertionPoint(), - ivs); - rewriter.eraseOp(target); - - for (auto &&[i, iv] : llvm::enumerate(ivs)) { - results.set(cast(getTransformed()[i]), - {iv.getParentBlock()->getParentOp()}); + + for (auto &&[i, res] : llvm::enumerate(opResults)) { + results.set(cast(getTransformed()[i]), {res}); } return DiagnosedSilenceableFailure::success(); } diff --git a/mlir/lib/Dialect/SCF/Transforms/CMakeLists.txt b/mlir/lib/Dialect/SCF/Transforms/CMakeLists.txt index a2925aef17ca78a3901482b3c419f33c76416884..e7671c9cc28f8bfe31e355d32cd35da8b251a10c 100644 --- a/mlir/lib/Dialect/SCF/Transforms/CMakeLists.txt +++ b/mlir/lib/Dialect/SCF/Transforms/CMakeLists.txt @@ -2,6 +2,7 @@ add_mlir_dialect_library(MLIRSCFTransforms BufferDeallocationOpInterfaceImpl.cpp BufferizableOpInterfaceImpl.cpp Bufferize.cpp + ForallToFor.cpp ForToWhile.cpp LoopCanonicalization.cpp LoopPipelining.cpp diff --git a/mlir/lib/Dialect/SCF/Transforms/ForallToFor.cpp b/mlir/lib/Dialect/SCF/Transforms/ForallToFor.cpp new file mode 100644 index 0000000000000000000000000000000000000000..198cb2e6cc69ef6e0499a7e4c31a56ec5514e3bd --- /dev/null +++ b/mlir/lib/Dialect/SCF/Transforms/ForallToFor.cpp @@ -0,0 +1,79 @@ +//===- ForallToFor.cpp - scf.forall to scf.for loop conversion ------------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// +// +// Transforms SCF.ForallOp's into SCF.ForOp's. +// +//===----------------------------------------------------------------------===// + +#include "mlir/Dialect/SCF/Transforms/Passes.h" + +#include "mlir/Dialect/SCF/IR/SCF.h" +#include "mlir/Dialect/SCF/Transforms/Transforms.h" +#include "mlir/IR/PatternMatch.h" + +namespace mlir { +#define GEN_PASS_DEF_SCFFORALLTOFORLOOP +#include "mlir/Dialect/SCF/Transforms/Passes.h.inc" +} // namespace mlir + +using namespace llvm; +using namespace mlir; +using scf::ForallOp; +using scf::ForOp; +using scf::LoopNest; + +LogicalResult +mlir::scf::forallToForLoop(RewriterBase &rewriter, scf::ForallOp forallOp, + SmallVectorImpl *results) { + OpBuilder::InsertionGuard guard(rewriter); + rewriter.setInsertionPoint(forallOp); + + Location loc = forallOp.getLoc(); + SmallVector lbs = getValueOrCreateConstantIndexOp( + rewriter, loc, forallOp.getMixedLowerBound()); + SmallVector ubs = getValueOrCreateConstantIndexOp( + rewriter, loc, forallOp.getMixedUpperBound()); + SmallVector steps = + getValueOrCreateConstantIndexOp(rewriter, loc, forallOp.getMixedStep()); + LoopNest loopNest = scf::buildLoopNest(rewriter, loc, lbs, ubs, steps); + + SmallVector ivs = llvm::map_to_vector( + loopNest.loops, [](scf::ForOp loop) { return loop.getInductionVar(); }); + + Block *innermostBlock = loopNest.loops.back().getBody(); + rewriter.eraseOp(forallOp.getBody()->getTerminator()); + rewriter.inlineBlockBefore(forallOp.getBody(), innermostBlock, + innermostBlock->getTerminator()->getIterator(), + ivs); + rewriter.eraseOp(forallOp); + + if (results) { + llvm::move(loopNest.loops, std::back_inserter(*results)); + } + + return success(); +} + +namespace { +struct ForallToForLoop : public impl::SCFForallToForLoopBase { + void runOnOperation() override { + Operation *parentOp = getOperation(); + IRRewriter rewriter(parentOp->getContext()); + + parentOp->walk([&](scf::ForallOp forallOp) { + if (failed(scf::forallToForLoop(rewriter, forallOp))) { + return signalPassFailure(); + } + }); + } +}; +} // namespace + +std::unique_ptr mlir::createForallToForLoopPass() { + return std::make_unique(); +} diff --git a/mlir/lib/Dialect/SparseTensor/IR/SparseTensorDialect.cpp b/mlir/lib/Dialect/SparseTensor/IR/SparseTensorDialect.cpp index b1d44559fa5abad9e128381789758549a3c7caf4..028a69da10c1e1c16946c32a6efb9b967edae437 100644 --- a/mlir/lib/Dialect/SparseTensor/IR/SparseTensorDialect.cpp +++ b/mlir/lib/Dialect/SparseTensor/IR/SparseTensorDialect.cpp @@ -326,9 +326,9 @@ SparseTensorDimSliceAttr::verify(function_ref emitError, SparseTensorEncodingAttr SparseTensorEncodingAttr::withDimToLvl(AffineMap dimToLvl) const { assert(getImpl() && "Uninitialized SparseTensorEncodingAttr"); - return SparseTensorEncodingAttr::get(getContext(), getLvlTypes(), dimToLvl, - AffineMap(), getPosWidth(), - getCrdWidth()); + return SparseTensorEncodingAttr::get( + getContext(), getLvlTypes(), dimToLvl, AffineMap(), getPosWidth(), + getCrdWidth(), getExplicitVal(), getImplicitVal()); } SparseTensorEncodingAttr @@ -344,20 +344,44 @@ SparseTensorEncodingAttr SparseTensorEncodingAttr::withBitWidths(unsigned posWidth, unsigned crdWidth) const { assert(getImpl() && "Uninitialized SparseTensorEncodingAttr"); - return SparseTensorEncodingAttr::get(getContext(), getLvlTypes(), - getDimToLvl(), getLvlToDim(), posWidth, - crdWidth); + return SparseTensorEncodingAttr::get( + getContext(), getLvlTypes(), getDimToLvl(), getLvlToDim(), posWidth, + crdWidth, getExplicitVal(), getImplicitVal()); } SparseTensorEncodingAttr SparseTensorEncodingAttr::withoutBitWidths() const { return withBitWidths(0, 0); } +SparseTensorEncodingAttr +SparseTensorEncodingAttr::withExplicitVal(Attribute explicitVal) const { + assert(getImpl() && "Uninitialized SparseTensorEncodingAttr"); + return SparseTensorEncodingAttr::get( + getContext(), getLvlTypes(), getDimToLvl(), getLvlToDim(), getPosWidth(), + getCrdWidth(), explicitVal, getImplicitVal()); +} + +SparseTensorEncodingAttr SparseTensorEncodingAttr::withoutExplicitVal() const { + return withExplicitVal(Attribute()); +} + +SparseTensorEncodingAttr +SparseTensorEncodingAttr::withImplicitVal(Attribute implicitVal) const { + assert(getImpl() && "Uninitialized SparseTensorEncodingAttr"); + return SparseTensorEncodingAttr::get( + getContext(), getLvlTypes(), getDimToLvl(), getLvlToDim(), getPosWidth(), + getCrdWidth(), getExplicitVal(), implicitVal); +} + +SparseTensorEncodingAttr SparseTensorEncodingAttr::withoutImplicitVal() const { + return withImplicitVal(Attribute()); +} + SparseTensorEncodingAttr SparseTensorEncodingAttr::withDimSlices( ArrayRef dimSlices) const { - return SparseTensorEncodingAttr::get(getContext(), getLvlTypes(), - getDimToLvl(), getLvlToDim(), - getPosWidth(), getCrdWidth(), dimSlices); + return SparseTensorEncodingAttr::get( + getContext(), getLvlTypes(), getDimToLvl(), getLvlToDim(), getPosWidth(), + getCrdWidth(), getExplicitVal(), getImplicitVal(), dimSlices); } SparseTensorEncodingAttr SparseTensorEncodingAttr::withoutDimSlices() const { @@ -553,8 +577,11 @@ Attribute SparseTensorEncodingAttr::parse(AsmParser &parser, Type type) { AffineMap lvlToDim = {}; unsigned posWidth = 0; unsigned crdWidth = 0; + Attribute explicitVal; + Attribute implicitVal; StringRef attrName; - SmallVector keys = {"map", "posWidth", "crdWidth"}; + SmallVector keys = {"map", "posWidth", "crdWidth", + "explicitVal", "implicitVal"}; while (succeeded(parser.parseOptionalKeyword(&attrName))) { // Detect admissible keyword. auto *it = find(keys, attrName); @@ -628,6 +655,36 @@ Attribute SparseTensorEncodingAttr::parse(AsmParser &parser, Type type) { crdWidth = intAttr.getInt(); break; } + case 3: { // explicitVal + Attribute attr; + if (failed(parser.parseAttribute(attr))) + return {}; + if (auto result = llvm::dyn_cast(attr)) { + explicitVal = result; + } else if (auto result = llvm::dyn_cast(attr)) { + explicitVal = result; + } else { + parser.emitError(parser.getNameLoc(), + "expected a numeric value for explicitVal"); + return {}; + } + break; + } + case 4: { // implicitVal + Attribute attr; + if (failed(parser.parseAttribute(attr))) + return {}; + if (auto result = llvm::dyn_cast(attr)) { + implicitVal = result; + } else if (auto result = llvm::dyn_cast(attr)) { + implicitVal = result; + } else { + parser.emitError(parser.getNameLoc(), + "expected a numeric value for implicitVal"); + return {}; + } + break; + } } // switch // Only last item can omit the comma. if (parser.parseOptionalComma().failed()) @@ -646,7 +703,7 @@ Attribute SparseTensorEncodingAttr::parse(AsmParser &parser, Type type) { } return parser.getChecked( parser.getContext(), lvlTypes, dimToLvl, lvlToDim, posWidth, crdWidth, - dimSlices); + explicitVal, implicitVal, dimSlices); } void SparseTensorEncodingAttr::print(AsmPrinter &printer) const { @@ -666,6 +723,11 @@ void SparseTensorEncodingAttr::print(AsmPrinter &printer) const { printer << ", posWidth = " << getPosWidth(); if (getCrdWidth()) printer << ", crdWidth = " << getCrdWidth(); + if (getExplicitVal()) { + printer << ", explicitVal = " << getExplicitVal(); + } + if (getImplicitVal()) + printer << ", implicitVal = " << getImplicitVal(); printer << " }>"; } @@ -715,7 +777,8 @@ void SparseTensorEncodingAttr::printLevels(AffineMap &map, AsmPrinter &printer, LogicalResult SparseTensorEncodingAttr::verify( function_ref emitError, ArrayRef lvlTypes, AffineMap dimToLvl, AffineMap lvlToDim, unsigned posWidth, - unsigned crdWidth, ArrayRef dimSlices) { + unsigned crdWidth, Attribute explicitVal, Attribute implicitVal, + ArrayRef dimSlices) { if (!acceptBitWidth(posWidth)) return emitError() << "unexpected position bitwidth: " << posWidth; if (!acceptBitWidth(crdWidth)) @@ -831,7 +894,8 @@ LogicalResult SparseTensorEncodingAttr::verifyEncoding( // Check structural integrity. In particular, this ensures that the // level-rank is coherent across all the fields. if (failed(verify(emitError, getLvlTypes(), getDimToLvl(), getLvlToDim(), - getPosWidth(), getCrdWidth(), getDimSlices()))) + getPosWidth(), getCrdWidth(), getExplicitVal(), + getImplicitVal(), getDimSlices()))) return failure(); // Check integrity with tensor type specifics. In particular, we // need only check that the dimension-rank of the tensor agrees with @@ -921,9 +985,9 @@ mlir::sparse_tensor::SparseTensorType::getCOOType(bool ordered) const { // Ends by a unique singleton level. lvlTypes.push_back(*buildLevelType(LevelFormat::Singleton, ordered, true)); } - auto enc = SparseTensorEncodingAttr::get(getContext(), lvlTypes, - getDimToLvl(), getLvlToDim(), - getPosWidth(), getCrdWidth()); + auto enc = SparseTensorEncodingAttr::get( + getContext(), lvlTypes, getDimToLvl(), getLvlToDim(), getPosWidth(), + getCrdWidth(), getExplicitVal(), getImplicitVal()); return RankedTensorType::get(getDimShape(), getElementType(), enc); } @@ -1115,7 +1179,10 @@ getNormalizedEncodingForSpecifier(SparseTensorEncodingAttr enc) { // `getPosWidth` and `getCrdWidth`. It allows us to reuse the same SSA // value for different bitwidth, it also avoids casting between index and // integer (returned by DimOp) - 0, 0, enc.getDimSlices()); + 0, 0, + Attribute(), // explicitVal (irrelevant to storage specifier) + Attribute(), // implicitVal (irrelevant to storage specifier) + enc.getDimSlices()); } StorageSpecifierType diff --git a/mlir/lib/Dialect/SparseTensor/Transforms/SparseTensorRewriting.cpp b/mlir/lib/Dialect/SparseTensor/Transforms/SparseTensorRewriting.cpp index 02375f54d7152fe534817e2f2bad4a6fb52650ea..5a39dfc6207707fb17a6d4ba4ada7d60dc556bd6 100644 --- a/mlir/lib/Dialect/SparseTensor/Transforms/SparseTensorRewriting.cpp +++ b/mlir/lib/Dialect/SparseTensor/Transforms/SparseTensorRewriting.cpp @@ -209,6 +209,86 @@ static void concatSizesFromInputs(OpBuilder &builder, namespace { +/// TODO: move it to tensor dialect instead. +/// +/// Fold `tensor.concat` and `tensor.extract_slice` +/// +/// %concat = tensor.concat dim(2) %t0, %t1 +/// : (tensor<1x64x1xf32>, tensor<1x64x1xf32>) -> tensor<1x64x2xf32> +/// %extracted0 = tensor.extract_slice %concat[0, 0, 0][1, 64, 1][1, 1, 1] +/// : tensor<1x64x2xf32> to tensor<1x64x1xf32> +/// %extracted1 = tensor.extract_slice %concat[0, 0, 1][1, 64, 1][1, 1, 1] +/// : tensor<1x64x2xf32> to tensor<1x64x1xf32> +/// +/// Becomes +/// +/// %extract0, %extract1 = %t0, %t1 +struct FuseExtractSliceWithConcat + : public OpRewritePattern { + using OpRewritePattern::OpRewritePattern; + + LogicalResult matchAndRewrite(tensor::ExtractSliceOp extractOp, + PatternRewriter &rewriter) const override { + auto concatOp = extractOp.getSource().getDefiningOp(); + if (!concatOp) + return failure(); + + Location loc = extractOp.getLoc(); + int64_t dim = concatOp.getDim(); + int64_t rank = extractOp.getResultType().getRank(); + + SmallVector srcStrides(rank, rewriter.getIndexAttr(1)); + SmallVector srcOffsets(rank, rewriter.getIndexAttr(0)); + + // Compute the partial sums for the slice offsets. + AffineExpr sum = rewriter.getAffineDimExpr(0); + SmallVector partialSums = {sum}; + SmallVector offsetStrides = {rewriter.getIndexAttr(0)}; + for (auto [idx, input] : + llvm::enumerate(concatOp.getInputs().drop_back())) { + sum = sum + rewriter.getAffineDimExpr(idx + 1); + partialSums.push_back(sum); + offsetStrides.push_back( + rewriter.createOrFold(loc, input, dim)); + } + auto partialSumMap = AffineMap::get(concatOp.getInputs().size(), 0, + partialSums, rewriter.getContext()); + SmallVector dimOffsets = + affine::makeComposedFoldedMultiResultAffineApply( + rewriter, loc, partialSumMap, offsetStrides); + + auto allEqual = [](ArrayRef lhs, ArrayRef rhs) { + for (auto [l, r] : llvm::zip(lhs, rhs)) { + std::optional staticVal = getConstantIntValue(l); + if (!staticVal.has_value() || staticVal != getConstantIntValue(r)) + return false; + } + return lhs.size() == rhs.size(); + }; + + for (auto [i, input, offset] : + llvm::enumerate(concatOp.getInputs(), dimOffsets)) { + SmallVector srcSizes = + tensor::getMixedSizes(rewriter, loc, input); + srcOffsets[dim] = offset; + + SmallVector dstSizes = extractOp.getMixedSizes(); + SmallVector dstOffsets = extractOp.getMixedOffsets(); + SmallVector dstStrides = extractOp.getMixedStrides(); + + if (allEqual(srcSizes, dstSizes) && allEqual(srcOffsets, dstOffsets) && + allEqual(srcStrides, dstStrides)) { + Value operand = concatOp.getOperand(i); + if (operand.getType() == extractOp.getResultType()) + rewriter.replaceOp(extractOp, operand); + break; + } + } + + return success(); + } +}; + /// Rewriting rule that converts direct yield of zero with initial allocation. struct FoldInvariantYield : public OpRewritePattern { public: @@ -1426,9 +1506,9 @@ struct OutRewriter : public OpRewritePattern { //===---------------------------------------------------------------------===// void mlir::populatePreSparsificationRewriting(RewritePatternSet &patterns) { - patterns.add( - patterns.getContext()); + patterns.add(patterns.getContext()); } void mlir::populateLowerSparseOpsToForeachPatterns(RewritePatternSet &patterns, diff --git a/mlir/lib/Dialect/SparseTensor/Transforms/Utils/SparseTensorIterator.h b/mlir/lib/Dialect/SparseTensor/Transforms/Utils/SparseTensorIterator.h index 9d69a23355598695f6d491ac32f0376f7399d74d..46b923250dd8930513e200749df584f1bc3aef11 100644 --- a/mlir/lib/Dialect/SparseTensor/Transforms/Utils/SparseTensorIterator.h +++ b/mlir/lib/Dialect/SparseTensor/Transforms/Utils/SparseTensorIterator.h @@ -284,9 +284,10 @@ private: }; /// Helper function to create a TensorLevel object from given `tensor`. -std::unique_ptr makeSparseTensorLevel(OpBuilder &builder, - Location loc, Value t, - unsigned tid, Level l); +std::unique_ptr makeSparseTensorLevel(OpBuilder &b, + Location l, Value t, + unsigned tid, + Level lvl); /// Helper function to create a simple SparseIterator object that iterate over /// the SparseTensorLevel. diff --git a/mlir/lib/Dialect/Tensor/IR/TensorOps.cpp b/mlir/lib/Dialect/Tensor/IR/TensorOps.cpp index 3ff41ab22fbc425ae6964bbd0ae41ccc8674fd35..5029ed4aa0387a81a90775716094e87af3a8c95b 100644 --- a/mlir/lib/Dialect/Tensor/IR/TensorOps.cpp +++ b/mlir/lib/Dialect/Tensor/IR/TensorOps.cpp @@ -1609,6 +1609,9 @@ OpFoldResult ReshapeOp::fold(FoldAdaptor adaptor) { cst.has_value() && cst.value() == static_cast(id); continue; } + + dynamicNoop = false; + break; } if (dynamicNoop) diff --git a/mlir/lib/Dialect/Vector/Transforms/LowerVectorMultiReduction.cpp b/mlir/lib/Dialect/Vector/Transforms/LowerVectorMultiReduction.cpp index 2f21c50c63473bfc99992b0c2ed737f3a27e1360..ac576ed0b4f0970cc6022e019c3e0f788bb58d74 100644 --- a/mlir/lib/Dialect/Vector/Transforms/LowerVectorMultiReduction.cpp +++ b/mlir/lib/Dialect/Vector/Transforms/LowerVectorMultiReduction.cpp @@ -437,8 +437,10 @@ struct OneDimMultiReductionToTwoDim auto loc = multiReductionOp.getLoc(); auto srcVectorType = multiReductionOp.getSourceVectorType(); auto srcShape = srcVectorType.getShape(); - auto castedType = VectorType::get(ArrayRef{1, srcShape.back()}, - srcVectorType.getElementType()); + auto castedType = VectorType::get( + ArrayRef{1, srcShape.back()}, srcVectorType.getElementType(), + ArrayRef{false, srcVectorType.getScalableDims().back()}); + auto accType = VectorType::get(ArrayRef{1}, srcVectorType.getElementType()); assert(!llvm::isa(multiReductionOp.getDestType()) && @@ -455,10 +457,11 @@ struct OneDimMultiReductionToTwoDim loc, accType, multiReductionOp.getAcc()); Value castMask; if (maskableOp.isMasked()) { - auto maskType = llvm::cast(mask.getType()); - auto castMaskType = - VectorType::get(ArrayRef{1, maskType.getShape().back()}, - maskType.getElementType()); + auto maskType = llvm::cast(mask.getType()); + auto castMaskType = VectorType::get( + ArrayRef{1, maskType.getShape().back()}, + maskType.getElementType(), + ArrayRef{false, maskType.getScalableDims().back()}); castMask = rewriter.create(loc, castMaskType, mask); } diff --git a/mlir/lib/Dialect/Vector/Utils/VectorUtils.cpp b/mlir/lib/Dialect/Vector/Utils/VectorUtils.cpp index fcaf1ec944b479adbf2d324a553eda203bd7fe13..6727f3f461722be4867c2373b8596f70cc390ded 100644 --- a/mlir/lib/Dialect/Vector/Utils/VectorUtils.cpp +++ b/mlir/lib/Dialect/Vector/Utils/VectorUtils.cpp @@ -345,7 +345,7 @@ Value vector::createReadOrMaskedRead(OpBuilder &builder, Location loc, int64_t readRank = readShape.size(); auto zero = builder.create(loc, 0); SmallVector inBoundsVal(readRank, true); - if (!useInBoundsInsteadOfMasking) { + if (useInBoundsInsteadOfMasking) { // Update the inBounds attribute. for (unsigned i = 0; i < readRank; i++) inBoundsVal[i] = (sourceShape[i] == readShape[i]) && @@ -359,7 +359,7 @@ Value vector::createReadOrMaskedRead(OpBuilder &builder, Location loc, /*padding=*/padValue, /*inBounds=*/inBoundsVal); - if (llvm::equal(readShape, sourceShape) || !useInBoundsInsteadOfMasking) + if (llvm::equal(readShape, sourceShape) || useInBoundsInsteadOfMasking) return transferReadOp; SmallVector mixedSourceDims = tensor::getMixedSizes(builder, loc, source); diff --git a/mlir/lib/Dialect/XeGPU/IR/CMakeLists.txt b/mlir/lib/Dialect/XeGPU/IR/CMakeLists.txt index 617c89a84ee077104a799b00070fe51921f387bc..a0ce7f9706cef305cdd6e88174ea72582696ba4e 100644 --- a/mlir/lib/Dialect/XeGPU/IR/CMakeLists.txt +++ b/mlir/lib/Dialect/XeGPU/IR/CMakeLists.txt @@ -11,6 +11,7 @@ add_mlir_dialect_library(MLIRXeGPUDialect MLIRXeGPUEnumsIncGen LINK_LIBS PUBLIC + MLIRArithDialect MLIRDialectUtils MLIRIR MLIRViewLikeInterface diff --git a/mlir/lib/Dialect/XeGPU/IR/XeGPUOps.cpp b/mlir/lib/Dialect/XeGPU/IR/XeGPUOps.cpp index 23c5749c2309deb673e6794dcc1a3965e07ba492..22959224d56c2f30fa7623d692f2d202b17afee1 100644 --- a/mlir/lib/Dialect/XeGPU/IR/XeGPUOps.cpp +++ b/mlir/lib/Dialect/XeGPU/IR/XeGPUOps.cpp @@ -406,6 +406,28 @@ LogicalResult StoreScatterOp::verify() { return success(); } +//===----------------------------------------------------------------------===// +// XeGPU_DpasOp +//===----------------------------------------------------------------------===// +LogicalResult DpasOp::verify() { + int64_t lhsRank = getLhsType().getRank(); + int64_t rhsRank = getRhsType().getRank(); + + if (lhsRank != rhsRank || lhsRank != 3) + return emitOpError( + "lhs and rhs rank does not match for dpas op, or their rank is not 3."); + + if (getAcc() && getAccType() != getResultType()) + return emitOpError("Accumulator and Result for dpas op should have the " + "same type (both shape and element type)."); + + auto lhsShape = getLhsType().getShape(); + auto rhsShape = getRhsType().getShape(); + if (lhsShape[1] != rhsShape[0] || lhsShape[2] != rhsShape[2]) + return emitOpError("K-dimension or vnni-factor mismatch."); + + return success(); +} } // namespace xegpu } // namespace mlir diff --git a/mlir/lib/Interfaces/RuntimeVerifiableOpInterface.cpp b/mlir/lib/Interfaces/RuntimeVerifiableOpInterface.cpp index 9205d8d8c34a291fb7b06395eed5341aba4b311c..561e8d33868748bd1056521280cb96545e3dc91e 100644 --- a/mlir/lib/Interfaces/RuntimeVerifiableOpInterface.cpp +++ b/mlir/lib/Interfaces/RuntimeVerifiableOpInterface.cpp @@ -11,6 +11,27 @@ namespace mlir { class Location; class OpBuilder; + +/// Generate an error message string for the given op and the specified error. +std::string +RuntimeVerifiableOpInterface::generateErrorMessage(Operation *op, + const std::string &msg) { + std::string buffer; + llvm::raw_string_ostream stream(buffer); + OpPrintingFlags flags; + // We may generate a lot of error messages and so we need to ensure the + // printing is fast. + flags.elideLargeElementsAttrs(); + flags.printGenericOpForm(); + flags.skipRegions(); + flags.useLocalScope(); + stream << "ERROR: Runtime op verification failed\n"; + op->print(stream, flags); + stream << "\n^ " << msg; + stream << "\nLocation: "; + op->getLoc().print(stream); + return stream.str(); +} } // namespace mlir /// Include the definitions of the interface. diff --git a/mlir/lib/TableGen/CodeGenHelpers.cpp b/mlir/lib/TableGen/CodeGenHelpers.cpp index d906de6b56afc0e5520857f28640160c87705324..59865146e20bc470896e6358fd162ae34d7d9c13 100644 --- a/mlir/lib/TableGen/CodeGenHelpers.cpp +++ b/mlir/lib/TableGen/CodeGenHelpers.cpp @@ -24,7 +24,8 @@ using namespace mlir::tblgen; /// Generate a unique label based on the current file name to prevent name /// collisions if multiple generated files are included at once. -static std::string getUniqueOutputLabel(const llvm::RecordKeeper &records) { +static std::string getUniqueOutputLabel(const llvm::RecordKeeper &records, + StringRef tag) { // Use the input file name when generating a unique name. std::string inputFilename = records.getInputFilename(); @@ -33,7 +34,7 @@ static std::string getUniqueOutputLabel(const llvm::RecordKeeper &records) { nameRef.consume_back(".td"); // Sanitize any invalid characters. - std::string uniqueName; + std::string uniqueName(tag); for (char c : nameRef) { if (llvm::isAlnum(c) || c == '_') uniqueName.push_back(c); @@ -44,15 +45,11 @@ static std::string getUniqueOutputLabel(const llvm::RecordKeeper &records) { } StaticVerifierFunctionEmitter::StaticVerifierFunctionEmitter( - raw_ostream &os, const llvm::RecordKeeper &records) - : os(os), uniqueOutputLabel(getUniqueOutputLabel(records)) {} + raw_ostream &os, const llvm::RecordKeeper &records, StringRef tag) + : os(os), uniqueOutputLabel(getUniqueOutputLabel(records, tag)) {} void StaticVerifierFunctionEmitter::emitOpConstraints( - ArrayRef opDefs, bool emitDecl) { - collectOpConstraints(opDefs); - if (emitDecl) - return; - + ArrayRef opDefs) { NamespaceEmitter namespaceEmitter(os, Operator(*opDefs[0]).getCppNamespace()); emitTypeConstraints(); emitAttrConstraints(); diff --git a/mlir/lib/Target/LLVMIR/Dialect/OpenMP/OpenMPToLLVMIRTranslation.cpp b/mlir/lib/Target/LLVMIR/Dialect/OpenMP/OpenMPToLLVMIRTranslation.cpp index ebcdbc02aadd079e8fab73591b72e64b2a9000fd..9f87f89d8c636b24915931a7b5ce2948f44f9a19 100644 --- a/mlir/lib/Target/LLVMIR/Dialect/OpenMP/OpenMPToLLVMIRTranslation.cpp +++ b/mlir/lib/Target/LLVMIR/Dialect/OpenMP/OpenMPToLLVMIRTranslation.cpp @@ -916,35 +916,37 @@ static LogicalResult inlineReductionCleanup( static LogicalResult convertOmpWsloop(Operation &opInst, llvm::IRBuilderBase &builder, LLVM::ModuleTranslation &moduleTranslation) { - auto loop = cast(opInst); - const bool isByRef = loop.getByref(); + auto wsloopOp = cast(opInst); + auto loopOp = cast(wsloopOp.getWrappedLoop()); + const bool isByRef = wsloopOp.getByref(); + // TODO: this should be in the op verifier instead. - if (loop.getLowerBound().empty()) + if (loopOp.getLowerBound().empty()) return failure(); // Static is the default. auto schedule = - loop.getScheduleVal().value_or(omp::ClauseScheduleKind::Static); + wsloopOp.getScheduleVal().value_or(omp::ClauseScheduleKind::Static); // Find the loop configuration. - llvm::Value *step = moduleTranslation.lookupValue(loop.getStep()[0]); + llvm::Value *step = moduleTranslation.lookupValue(loopOp.getStep()[0]); llvm::Type *ivType = step->getType(); llvm::Value *chunk = nullptr; - if (loop.getScheduleChunkVar()) { + if (wsloopOp.getScheduleChunkVar()) { llvm::Value *chunkVar = - moduleTranslation.lookupValue(loop.getScheduleChunkVar()); + moduleTranslation.lookupValue(wsloopOp.getScheduleChunkVar()); chunk = builder.CreateSExtOrTrunc(chunkVar, ivType); } SmallVector reductionDecls; - collectReductionDecls(loop, reductionDecls); + collectReductionDecls(wsloopOp, reductionDecls); llvm::OpenMPIRBuilder::InsertPointTy allocaIP = findAllocaInsertPoint(builder, moduleTranslation); SmallVector privateReductionVariables; DenseMap reductionVariableMap; if (!isByRef) { - allocByValReductionVars(loop, builder, moduleTranslation, allocaIP, + allocByValReductionVars(wsloopOp, builder, moduleTranslation, allocaIP, reductionDecls, privateReductionVariables, reductionVariableMap); } @@ -952,13 +954,12 @@ convertOmpWsloop(Operation &opInst, llvm::IRBuilderBase &builder, // Before the loop, store the initial values of reductions into reduction // variables. Although this could be done after allocas, we don't want to mess // up with the alloca insertion point. - MutableArrayRef reductionArgs = - loop.getRegion().getArguments().take_back(loop.getNumReductionVars()); - for (unsigned i = 0; i < loop.getNumReductionVars(); ++i) { + ArrayRef reductionArgs = wsloopOp.getRegion().getArguments(); + for (unsigned i = 0; i < wsloopOp.getNumReductionVars(); ++i) { SmallVector phis; // map block argument to initializer region - mapInitializationArg(loop, moduleTranslation, reductionDecls, i); + mapInitializationArg(wsloopOp, moduleTranslation, reductionDecls, i); if (failed(inlineConvertOmpRegions(reductionDecls[i].getInitializerRegion(), "omp.reduction.neutral", builder, @@ -977,7 +978,7 @@ convertOmpWsloop(Operation &opInst, llvm::IRBuilderBase &builder, privateReductionVariables.push_back(var); moduleTranslation.mapValue(reductionArgs[i], phis[0]); - reductionVariableMap.try_emplace(loop.getReductionVars()[i], phis[0]); + reductionVariableMap.try_emplace(wsloopOp.getReductionVars()[i], phis[0]); } else { // for by-ref case the store is inside of the reduction region builder.CreateStore(phis[0], privateReductionVariables[i]); @@ -1008,33 +1009,34 @@ convertOmpWsloop(Operation &opInst, llvm::IRBuilderBase &builder, auto bodyGen = [&](llvm::OpenMPIRBuilder::InsertPointTy ip, llvm::Value *iv) { // Make sure further conversions know about the induction variable. moduleTranslation.mapValue( - loop.getRegion().front().getArgument(loopInfos.size()), iv); + loopOp.getRegion().front().getArgument(loopInfos.size()), iv); // Capture the body insertion point for use in nested loops. BodyIP of the // CanonicalLoopInfo always points to the beginning of the entry block of // the body. bodyInsertPoints.push_back(ip); - if (loopInfos.size() != loop.getNumLoops() - 1) + if (loopInfos.size() != loopOp.getNumLoops() - 1) return; // Convert the body of the loop. builder.restoreIP(ip); - convertOmpOpRegions(loop.getRegion(), "omp.wsloop.region", builder, + convertOmpOpRegions(loopOp.getRegion(), "omp.wsloop.region", builder, moduleTranslation, bodyGenStatus); }; // Delegate actual loop construction to the OpenMP IRBuilder. - // TODO: this currently assumes Wsloop is semantically similar to SCF loop, - // i.e. it has a positive step, uses signed integer semantics. Reconsider - // this code when Wsloop clearly supports more cases. + // TODO: this currently assumes omp.loop_nest is semantically similar to SCF + // loop, i.e. it has a positive step, uses signed integer semantics. + // Reconsider this code when the nested loop operation clearly supports more + // cases. llvm::OpenMPIRBuilder *ompBuilder = moduleTranslation.getOpenMPBuilder(); - for (unsigned i = 0, e = loop.getNumLoops(); i < e; ++i) { + for (unsigned i = 0, e = loopOp.getNumLoops(); i < e; ++i) { llvm::Value *lowerBound = - moduleTranslation.lookupValue(loop.getLowerBound()[i]); + moduleTranslation.lookupValue(loopOp.getLowerBound()[i]); llvm::Value *upperBound = - moduleTranslation.lookupValue(loop.getUpperBound()[i]); - llvm::Value *step = moduleTranslation.lookupValue(loop.getStep()[i]); + moduleTranslation.lookupValue(loopOp.getUpperBound()[i]); + llvm::Value *step = moduleTranslation.lookupValue(loopOp.getStep()[i]); // Make sure loop trip count are emitted in the preheader of the outermost // loop at the latest so that they are all available for the new collapsed @@ -1047,7 +1049,7 @@ convertOmpWsloop(Operation &opInst, llvm::IRBuilderBase &builder, } loopInfos.push_back(ompBuilder->createCanonicalLoop( loc, bodyGen, lowerBound, upperBound, step, - /*IsSigned=*/true, loop.getInclusive(), computeIP)); + /*IsSigned=*/true, loopOp.getInclusive(), computeIP)); if (failed(bodyGenStatus)) return failure(); @@ -1062,13 +1064,13 @@ convertOmpWsloop(Operation &opInst, llvm::IRBuilderBase &builder, allocaIP = findAllocaInsertPoint(builder, moduleTranslation); // TODO: Handle doacross loops when the ordered clause has a parameter. - bool isOrdered = loop.getOrderedVal().has_value(); + bool isOrdered = wsloopOp.getOrderedVal().has_value(); std::optional scheduleModifier = - loop.getScheduleModifier(); - bool isSimd = loop.getSimdModifier(); + wsloopOp.getScheduleModifier(); + bool isSimd = wsloopOp.getSimdModifier(); ompBuilder->applyWorkshareLoop( - ompLoc.DL, loopInfo, allocaIP, !loop.getNowait(), + ompLoc.DL, loopInfo, allocaIP, !wsloopOp.getNowait(), convertToScheduleKind(schedule), chunk, isSimd, scheduleModifier == omp::ScheduleModifier::monotonic, scheduleModifier == omp::ScheduleModifier::nonmonotonic, isOrdered); @@ -1080,7 +1082,7 @@ convertOmpWsloop(Operation &opInst, llvm::IRBuilderBase &builder, builder.restoreIP(afterIP); // Process the reductions if required. - if (loop.getNumReductionVars() == 0) + if (wsloopOp.getNumReductionVars() == 0) return success(); // Create the reduction generators. We need to own them here because @@ -1088,7 +1090,7 @@ convertOmpWsloop(Operation &opInst, llvm::IRBuilderBase &builder, SmallVector owningReductionGens; SmallVector owningAtomicReductionGens; SmallVector reductionInfos; - collectReductionInfo(loop, builder, moduleTranslation, reductionDecls, + collectReductionInfo(wsloopOp, builder, moduleTranslation, reductionDecls, owningReductionGens, owningAtomicReductionGens, privateReductionVariables, reductionInfos); @@ -1099,9 +1101,9 @@ convertOmpWsloop(Operation &opInst, llvm::IRBuilderBase &builder, builder.SetInsertPoint(tempTerminator); llvm::OpenMPIRBuilder::InsertPointTy contInsertPoint = ompBuilder->createReductions(builder.saveIP(), allocaIP, reductionInfos, - loop.getNowait(), isByRef); + wsloopOp.getNowait(), isByRef); if (!contInsertPoint.getBlock()) - return loop->emitOpError() << "failed to convert reductions"; + return wsloopOp->emitOpError() << "failed to convert reductions"; auto nextInsertionPoint = ompBuilder->createBarrier(contInsertPoint, llvm::omp::OMPD_for); tempTerminator->eraseFromParent(); diff --git a/mlir/lib/Transforms/Mem2Reg.cpp b/mlir/lib/Transforms/Mem2Reg.cpp index 0c1ce70f070852fd632951deab0e08e8f820fa5b..71ba5bc076f0e69962e55e8ac34ae89b4a361dda 100644 --- a/mlir/lib/Transforms/Mem2Reg.cpp +++ b/mlir/lib/Transforms/Mem2Reg.cpp @@ -191,13 +191,13 @@ private: /// Lazily-constructed default value representing the content of the slot when /// no store has been executed. This function may mutate IR. - Value getLazyDefaultValue(); + Value getOrCreateDefaultValue(); MemorySlot slot; PromotableAllocationOpInterface allocator; RewriterBase &rewriter; - /// Potentially non-initialized default value. Use `getLazyDefaultValue` to - /// initialize it on demand. + /// Potentially non-initialized default value. Use `getOrCreateDefaultValue` + /// to initialize it on demand. Value defaultValue; /// Contains the reaching definition at this operation. Reaching definitions /// are only computed for promotable memory operations with blocking uses. @@ -232,7 +232,7 @@ MemorySlotPromoter::MemorySlotPromoter( #endif // NDEBUG } -Value MemorySlotPromoter::getLazyDefaultValue() { +Value MemorySlotPromoter::getOrCreateDefaultValue() { if (defaultValue) return defaultValue; @@ -438,7 +438,7 @@ Value MemorySlotPromoter::computeReachingDefInBlock(Block *block, if (memOp.storesTo(slot)) { rewriter.setInsertionPointAfter(memOp); - Value stored = memOp.getStored(slot, rewriter, dataLayout); + Value stored = memOp.getStored(slot, rewriter, reachingDef, dataLayout); assert(stored && "a memory operation storing to a slot must provide a " "new definition of the slot"); reachingDef = stored; @@ -452,6 +452,7 @@ Value MemorySlotPromoter::computeReachingDefInBlock(Block *block, void MemorySlotPromoter::computeReachingDefInRegion(Region *region, Value reachingDef) { + assert(reachingDef && "expected an initial reaching def to be provided"); if (region->hasOneBlock()) { computeReachingDefInBlock(®ion->front(), reachingDef); return; @@ -508,12 +509,11 @@ void MemorySlotPromoter::computeReachingDefInRegion(Region *region, } job.reachingDef = computeReachingDefInBlock(block, job.reachingDef); + assert(job.reachingDef); if (auto terminator = dyn_cast(block->getTerminator())) { for (BlockOperand &blockOperand : terminator->getBlockOperands()) { if (info.mergePoints.contains(blockOperand.get())) { - if (!job.reachingDef) - job.reachingDef = getLazyDefaultValue(); rewriter.modifyOpInPlace(terminator, [&]() { terminator.getSuccessorOperands(blockOperand.getOperandNumber()) .append(job.reachingDef); @@ -567,7 +567,7 @@ void MemorySlotPromoter::removeBlockingUses() { // If no reaching definition is known, this use is outside the reach of // the slot. The default value should thus be used. if (!reachingDef) - reachingDef = getLazyDefaultValue(); + reachingDef = getOrCreateDefaultValue(); rewriter.setInsertionPointAfter(toPromote); if (toPromoteMemOp.removeBlockingUses( @@ -601,7 +601,8 @@ void MemorySlotPromoter::removeBlockingUses() { } void MemorySlotPromoter::promoteSlot() { - computeReachingDefInRegion(slot.ptr.getParentRegion(), {}); + computeReachingDefInRegion(slot.ptr.getParentRegion(), + getOrCreateDefaultValue()); // Now that reaching definitions are known, remove all users. removeBlockingUses(); @@ -617,7 +618,7 @@ void MemorySlotPromoter::promoteSlot() { succOperands.size() + 1 == mergePoint->getNumArguments()); if (succOperands.size() + 1 == mergePoint->getNumArguments()) rewriter.modifyOpInPlace( - user, [&]() { succOperands.append(getLazyDefaultValue()); }); + user, [&]() { succOperands.append(getOrCreateDefaultValue()); }); } } diff --git a/mlir/python/mlir/dialects/LLVMOps.td b/mlir/python/mlir/dialects/LLVMOps.td index dcf2f4245cf49f2c6f899611145b4e1800af25ca..30f047f21698e3dba8db905879b63fdac50eb01a 100644 --- a/mlir/python/mlir/dialects/LLVMOps.td +++ b/mlir/python/mlir/dialects/LLVMOps.td @@ -10,5 +10,6 @@ #define PYTHON_BINDINGS_LLVM_OPS include "mlir/Dialect/LLVMIR/LLVMOps.td" +include "mlir/Dialect/LLVMIR/LLVMIntrinsicOps.td" #endif diff --git a/mlir/python/mlir/dialects/llvm.py b/mlir/python/mlir/dialects/llvm.py index 8aa16e4a2560308692ffbdd473076edaabf3ed5f..941a584966dcde94979d63cca0b25f239dab6318 100644 --- a/mlir/python/mlir/dialects/llvm.py +++ b/mlir/python/mlir/dialects/llvm.py @@ -5,3 +5,11 @@ from ._llvm_ops_gen import * from ._llvm_enum_gen import * from .._mlir_libs._mlirDialectsLLVM import * +from ..ir import Value +from ._ods_common import get_op_result_or_op_results as _get_op_result_or_op_results + + +def mlir_constant(value, *, loc=None, ip=None) -> Value: + return _get_op_result_or_op_results( + ConstantOp(res=value.type, value=value, loc=loc, ip=ip) + ) diff --git a/mlir/python/mlir/dialects/transform/interpreter/__init__.py b/mlir/python/mlir/dialects/transform/interpreter/__init__.py index 34cdc43cb617fdf491f8ce2e53651cfb16beff01..e69aa963038f2301f635ff95af04302853d05b64 100644 --- a/mlir/python/mlir/dialects/transform/interpreter/__init__.py +++ b/mlir/python/mlir/dialects/transform/interpreter/__init__.py @@ -29,7 +29,7 @@ def apply_named_sequence( if transform_options is None: _cextTransformInterpreter.apply_named_sequence(*args) else: - _cextTransformInterpreter(*args, transform_options) + _cextTransformInterpreter.apply_named_sequence(*args, transform_options) def copy_symbols_and_merge_into(target, other): diff --git a/mlir/test/CAPI/execution_engine.c b/mlir/test/CAPI/execution_engine.c index 38a8fb8c3e2137d734630f9eb16dfbe71ff0d162..81ff8477ffd7b73f39daac1bad2b1b0cd7c32786 100644 --- a/mlir/test/CAPI/execution_engine.c +++ b/mlir/test/CAPI/execution_engine.c @@ -99,8 +99,11 @@ void testOmpCreation(void) { " %1 = arith.constant 1 : i32 \n" " %2 = arith.constant 2 : i32 \n" " omp.parallel { \n" -" omp.wsloop for (%3) : i32 = (%0) to (%2) step (%1) { \n" -" omp.yield \n" +" omp.wsloop { \n" +" omp.loop_nest (%3) : i32 = (%0) to (%2) step (%1) { \n" +" omp.yield \n" +" } \n" +" omp.terminator \n" " } \n" " omp.terminator \n" " } \n" diff --git a/mlir/test/CAPI/sparse_tensor.c b/mlir/test/CAPI/sparse_tensor.c index f241e0e5c2fb560ea8665cda9795b2b552340e55..22b7052b732aa2bcdf67a12267c85f8ee3799d78 100644 --- a/mlir/test/CAPI/sparse_tensor.c +++ b/mlir/test/CAPI/sparse_tensor.c @@ -27,7 +27,7 @@ static int testRoundtripEncoding(MlirContext ctx) { const char *originalAsm = "#sparse_tensor.encoding<{ " "map = [s0](d0, d1) -> (s0 : dense, d0 : compressed, d1 : compressed), " - "posWidth = 32, crdWidth = 64 }>"; + "posWidth = 32, crdWidth = 64, explicitVal = 1 : i64}>"; // clang-format on MlirAttribute originalAttr = mlirAttributeParseGet(ctx, mlirStringRefCreateFromCString(originalAsm)); @@ -56,8 +56,21 @@ static int testRoundtripEncoding(MlirContext ctx) { // CHECK: crdWidth: 64 int crdWidth = mlirSparseTensorEncodingAttrGetCrdWidth(originalAttr); fprintf(stderr, "crdWidth: %d\n", crdWidth); + + // CHECK: explicitVal: 1 : i64 + MlirAttribute explicitVal = + mlirSparseTensorEncodingAttrGetExplicitVal(originalAttr); + fprintf(stderr, "explicitVal: "); + mlirAttributeDump(explicitVal); + // CHECK: implicitVal: <> + MlirAttribute implicitVal = + mlirSparseTensorEncodingAttrGetImplicitVal(originalAttr); + fprintf(stderr, "implicitVal: "); + mlirAttributeDump(implicitVal); + MlirAttribute newAttr = mlirSparseTensorEncodingAttrGet( - ctx, lvlRank, lvlTypes, dimToLvl, lvlToDim, posWidth, crdWidth); + ctx, lvlRank, lvlTypes, dimToLvl, lvlToDim, posWidth, crdWidth, + explicitVal, implicitVal); mlirAttributeDump(newAttr); // For debugging filecheck output. // CHECK: equal: 1 fprintf(stderr, "equal: %d\n", mlirAttributeEqual(originalAttr, newAttr)); diff --git a/mlir/test/Conversion/OpenMPToLLVM/convert-to-llvmir.mlir b/mlir/test/Conversion/OpenMPToLLVM/convert-to-llvmir.mlir index 9f45d139b81f212a87e4235aec830eec5886f7ee..3aeb9e70522d520f66ffa203839758a139fcc14e 100644 --- a/mlir/test/Conversion/OpenMPToLLVM/convert-to-llvmir.mlir +++ b/mlir/test/Conversion/OpenMPToLLVM/convert-to-llvmir.mlir @@ -71,15 +71,18 @@ func.func @branch_loop() { func.func @wsloop(%arg0: index, %arg1: index, %arg2: index, %arg3: index, %arg4: index, %arg5: index) { // CHECK: omp.parallel omp.parallel { - // CHECK: omp.wsloop for (%[[ARG6:.*]], %[[ARG7:.*]]) : i64 = (%[[ARG0]], %[[ARG1]]) to (%[[ARG2]], %[[ARG3]]) step (%[[ARG4]], %[[ARG5]]) { - "omp.wsloop"(%arg0, %arg1, %arg2, %arg3, %arg4, %arg5) ({ - ^bb0(%arg6: index, %arg7: index): - // CHECK-DAG: %[[CAST_ARG6:.*]] = builtin.unrealized_conversion_cast %[[ARG6]] : i64 to index - // CHECK-DAG: %[[CAST_ARG7:.*]] = builtin.unrealized_conversion_cast %[[ARG7]] : i64 to index - // CHECK: "test.payload"(%[[CAST_ARG6]], %[[CAST_ARG7]]) : (index, index) -> () - "test.payload"(%arg6, %arg7) : (index, index) -> () - omp.yield - }) {operandSegmentSizes = array} : (index, index, index, index, index, index) -> () + // CHECK: omp.wsloop { + "omp.wsloop"() ({ + // CHECK: omp.loop_nest (%[[ARG6:.*]], %[[ARG7:.*]]) : i64 = (%[[ARG0]], %[[ARG1]]) to (%[[ARG2]], %[[ARG3]]) step (%[[ARG4]], %[[ARG5]]) { + omp.loop_nest (%arg6, %arg7) : index = (%arg0, %arg1) to (%arg2, %arg3) step (%arg4, %arg5) { + // CHECK-DAG: %[[CAST_ARG6:.*]] = builtin.unrealized_conversion_cast %[[ARG6]] : i64 to index + // CHECK-DAG: %[[CAST_ARG7:.*]] = builtin.unrealized_conversion_cast %[[ARG7]] : i64 to index + // CHECK: "test.payload"(%[[CAST_ARG6]], %[[CAST_ARG7]]) : (index, index) -> () + "test.payload"(%arg6, %arg7) : (index, index) -> () + omp.yield + } + omp.terminator + }) : () -> () omp.terminator } return @@ -323,12 +326,14 @@ llvm.func @_QPsb() { // CHECK-LABEL: @_QPsimple_reduction // CHECK: %[[RED_ACCUMULATOR:.*]] = llvm.alloca %{{.*}} x i32 {bindc_name = "x", uniq_name = "_QFsimple_reductionEx"} : (i64) -> !llvm.ptr // CHECK: omp.parallel -// CHECK: omp.wsloop reduction(@eqv_reduction %{{.+}} -> %[[PRV:.+]] : !llvm.ptr) for -// CHECK: %[[LPRV:.+]] = llvm.load %[[PRV]] : !llvm.ptr -> i32 -// CHECK: %[[CMP:.+]] = llvm.icmp "eq" %{{.*}}, %[[LPRV]] : i32 -// CHECK: %[[ZEXT:.+]] = llvm.zext %[[CMP]] : i1 to i32 -// CHECK: llvm.store %[[ZEXT]], %[[PRV]] : i32, !llvm.ptr -// CHECK: omp.yield +// CHECK: omp.wsloop reduction(@eqv_reduction %{{.+}} -> %[[PRV:.+]] : !llvm.ptr) +// CHECK-NEXT: omp.loop_nest {{.*}}{ +// CHECK: %[[LPRV:.+]] = llvm.load %[[PRV]] : !llvm.ptr -> i32 +// CHECK: %[[CMP:.+]] = llvm.icmp "eq" %{{.*}}, %[[LPRV]] : i32 +// CHECK: %[[ZEXT:.+]] = llvm.zext %[[CMP]] : i1 to i32 +// CHECK: llvm.store %[[ZEXT]], %[[PRV]] : i32, !llvm.ptr +// CHECK: omp.yield +// CHECK: omp.terminator // CHECK: omp.terminator // CHECK: llvm.return @@ -354,20 +359,23 @@ llvm.func @_QPsimple_reduction(%arg0: !llvm.ptr {fir.bindc_name = "y"}) { %4 = llvm.alloca %3 x i32 {bindc_name = "x", uniq_name = "_QFsimple_reductionEx"} : (i64) -> !llvm.ptr %5 = llvm.zext %2 : i1 to i32 llvm.store %5, %4 : i32, !llvm.ptr - omp.parallel { + omp.parallel { %6 = llvm.alloca %3 x i32 {adapt.valuebyref, in_type = i32, operandSegmentSizes = array, pinned} : (i64) -> !llvm.ptr - omp.wsloop reduction(@eqv_reduction %4 -> %prv : !llvm.ptr) for (%arg1) : i32 = (%1) to (%0) inclusive step (%1) { - llvm.store %arg1, %6 : i32, !llvm.ptr - %7 = llvm.load %6 : !llvm.ptr -> i32 - %8 = llvm.sext %7 : i32 to i64 - %9 = llvm.sub %8, %3 : i64 - %10 = llvm.getelementptr %arg0[0, %9] : (!llvm.ptr, i64) -> !llvm.ptr, !llvm.array<100 x i32> - %11 = llvm.load %10 : !llvm.ptr -> i32 - %12 = llvm.load %prv : !llvm.ptr -> i32 - %13 = llvm.icmp "eq" %11, %12 : i32 - %14 = llvm.zext %13 : i1 to i32 - llvm.store %14, %prv : i32, !llvm.ptr - omp.yield + omp.wsloop reduction(@eqv_reduction %4 -> %prv : !llvm.ptr) { + omp.loop_nest (%arg1) : i32 = (%1) to (%0) inclusive step (%1) { + llvm.store %arg1, %6 : i32, !llvm.ptr + %7 = llvm.load %6 : !llvm.ptr -> i32 + %8 = llvm.sext %7 : i32 to i64 + %9 = llvm.sub %8, %3 : i64 + %10 = llvm.getelementptr %arg0[0, %9] : (!llvm.ptr, i64) -> !llvm.ptr, !llvm.array<100 x i32> + %11 = llvm.load %10 : !llvm.ptr -> i32 + %12 = llvm.load %prv : !llvm.ptr -> i32 + %13 = llvm.icmp "eq" %11, %12 : i32 + %14 = llvm.zext %13 : i1 to i32 + llvm.store %14, %prv : i32, !llvm.ptr + omp.yield + } + omp.terminator } omp.terminator } diff --git a/mlir/test/Conversion/SCFToOpenMP/reductions.mlir b/mlir/test/Conversion/SCFToOpenMP/reductions.mlir index 3b6c145d62f1a865ac56c56024bedf945c21c6f4..fc6d56559c2618125050b2bcbf61dae87488c903 100644 --- a/mlir/test/Conversion/SCFToOpenMP/reductions.mlir +++ b/mlir/test/Conversion/SCFToOpenMP/reductions.mlir @@ -28,6 +28,7 @@ func.func @reduction1(%arg0 : index, %arg1 : index, %arg2 : index, // CHECK: omp.parallel // CHECK: omp.wsloop // CHECK-SAME: reduction(@[[$REDF]] %[[BUF]] -> %[[PVT_BUF:[a-z0-9]+]] + // CHECK: omp.loop_nest // CHECK: memref.alloca_scope scf.parallel (%i0, %i1) = (%arg0, %arg1) to (%arg2, %arg3) step (%arg4, %step) init (%zero) -> (f32) { @@ -43,6 +44,7 @@ func.func @reduction1(%arg0 : index, %arg1 : index, %arg2 : index, } // CHECK: omp.yield } + // CHECK: omp.terminator // CHECK: omp.terminator // CHECK: llvm.load %[[BUF]] return @@ -107,6 +109,7 @@ func.func @reduction_muli(%arg0 : index, %arg1 : index, %arg2 : index, %one = arith.constant 1 : i32 // CHECK: %[[RED_VAR:.*]] = llvm.alloca %{{.*}} x i32 : (i64) -> !llvm.ptr // CHECK: omp.wsloop reduction(@[[$REDI]] %[[RED_VAR]] -> %[[RED_PVT_VAR:.*]] : !llvm.ptr) + // CHECK: omp.loop_nest scf.parallel (%i0, %i1) = (%arg0, %arg1) to (%arg2, %arg3) step (%arg4, %step) init (%one) -> (i32) { // CHECK: %[[C2:.*]] = arith.constant 2 : i32 @@ -208,6 +211,7 @@ func.func @reduction4(%arg0 : index, %arg1 : index, %arg2 : index, // CHECK: omp.wsloop // CHECK-SAME: reduction(@[[$REDF1]] %[[BUF1]] -> %[[PVT_BUF1:[a-z0-9]+]] // CHECK-SAME: @[[$REDF2]] %[[BUF2]] -> %[[PVT_BUF2:[a-z0-9]+]] + // CHECK: omp.loop_nest // CHECK: memref.alloca_scope %res:2 = scf.parallel (%i0, %i1) = (%arg0, %arg1) to (%arg2, %arg3) step (%arg4, %step) init (%zero, %ione) -> (f32, i64) { @@ -236,6 +240,7 @@ func.func @reduction4(%arg0 : index, %arg1 : index, %arg2 : index, } // CHECK: omp.yield } + // CHECK: omp.terminator // CHECK: omp.terminator // CHECK: %[[RES1:.*]] = llvm.load %[[BUF1]] : !llvm.ptr -> f32 // CHECK: %[[RES2:.*]] = llvm.load %[[BUF2]] : !llvm.ptr -> i64 diff --git a/mlir/test/Conversion/SCFToOpenMP/scf-to-openmp.mlir b/mlir/test/Conversion/SCFToOpenMP/scf-to-openmp.mlir index acd2690c56e2e67d5a2de9562d5e8f061f5d2140..b2f19d294cb5fe73e8b83f0ef5920383698f262b 100644 --- a/mlir/test/Conversion/SCFToOpenMP/scf-to-openmp.mlir +++ b/mlir/test/Conversion/SCFToOpenMP/scf-to-openmp.mlir @@ -2,10 +2,11 @@ // CHECK-LABEL: @parallel func.func @parallel(%arg0: index, %arg1: index, %arg2: index, - %arg3: index, %arg4: index, %arg5: index) { + %arg3: index, %arg4: index, %arg5: index) { // CHECK: %[[FOUR:.+]] = llvm.mlir.constant(4 : i32) : i32 // CHECK: omp.parallel num_threads(%[[FOUR]] : i32) { - // CHECK: omp.wsloop for (%[[LVAR1:.*]], %[[LVAR2:.*]]) : index = (%arg0, %arg1) to (%arg2, %arg3) step (%arg4, %arg5) { + // CHECK: omp.wsloop { + // CHECK: omp.loop_nest (%[[LVAR1:.*]], %[[LVAR2:.*]]) : index = (%arg0, %arg1) to (%arg2, %arg3) step (%arg4, %arg5) { // CHECK: memref.alloca_scope scf.parallel (%i, %j) = (%arg0, %arg1) to (%arg2, %arg3) step (%arg4, %arg5) { // CHECK: "test.payload"(%[[LVAR1]], %[[LVAR2]]) : (index, index) -> () @@ -13,6 +14,8 @@ func.func @parallel(%arg0: index, %arg1: index, %arg2: index, // CHECK: omp.yield // CHECK: } } + // CHECK: omp.terminator + // CHECK: } // CHECK: omp.terminator // CHECK: } return @@ -23,20 +26,26 @@ func.func @nested_loops(%arg0: index, %arg1: index, %arg2: index, %arg3: index, %arg4: index, %arg5: index) { // CHECK: %[[FOUR:.+]] = llvm.mlir.constant(4 : i32) : i32 // CHECK: omp.parallel num_threads(%[[FOUR]] : i32) { - // CHECK: omp.wsloop for (%[[LVAR_OUT1:.*]]) : index = (%arg0) to (%arg2) step (%arg4) { - // CHECK: memref.alloca_scope + // CHECK: omp.wsloop { + // CHECK: omp.loop_nest (%[[LVAR_OUT1:.*]]) : index = (%arg0) to (%arg2) step (%arg4) { + // CHECK: memref.alloca_scope scf.parallel (%i) = (%arg0) to (%arg2) step (%arg4) { // CHECK: omp.parallel - // CHECK: omp.wsloop for (%[[LVAR_IN1:.*]]) : index = (%arg1) to (%arg3) step (%arg5) { + // CHECK: omp.wsloop { + // CHECK: omp.loop_nest (%[[LVAR_IN1:.*]]) : index = (%arg1) to (%arg3) step (%arg5) { // CHECK: memref.alloca_scope scf.parallel (%j) = (%arg1) to (%arg3) step (%arg5) { // CHECK: "test.payload"(%[[LVAR_OUT1]], %[[LVAR_IN1]]) : (index, index) -> () "test.payload"(%i, %j) : (index, index) -> () // CHECK: } } - // CHECK: omp.yield + // CHECK: omp.yield + // CHECK: } + // CHECK: omp.terminator // CHECK: } } + // CHECK: omp.terminator + // CHECK: } // CHECK: omp.terminator // CHECK: } return @@ -47,7 +56,8 @@ func.func @adjacent_loops(%arg0: index, %arg1: index, %arg2: index, %arg3: index, %arg4: index, %arg5: index) { // CHECK: %[[FOUR:.+]] = llvm.mlir.constant(4 : i32) : i32 // CHECK: omp.parallel num_threads(%[[FOUR]] : i32) { - // CHECK: omp.wsloop for (%[[LVAR_AL1:.*]]) : index = (%arg0) to (%arg2) step (%arg4) { + // CHECK: omp.wsloop { + // CHECK: omp.loop_nest (%[[LVAR_AL1:.*]]) : index = (%arg0) to (%arg2) step (%arg4) { // CHECK: memref.alloca_scope scf.parallel (%i) = (%arg0) to (%arg2) step (%arg4) { // CHECK: "test.payload1"(%[[LVAR_AL1]]) : (index) -> () @@ -55,12 +65,15 @@ func.func @adjacent_loops(%arg0: index, %arg1: index, %arg2: index, // CHECK: omp.yield // CHECK: } } + // CHECK: omp.terminator + // CHECK: } // CHECK: omp.terminator // CHECK: } // CHECK: %[[FOUR:.+]] = llvm.mlir.constant(4 : i32) : i32 // CHECK: omp.parallel num_threads(%[[FOUR]] : i32) { - // CHECK: omp.wsloop for (%[[LVAR_AL2:.*]]) : index = (%arg1) to (%arg3) step (%arg5) { + // CHECK: omp.wsloop { + // CHECK: omp.loop_nest (%[[LVAR_AL2:.*]]) : index = (%arg1) to (%arg3) step (%arg5) { // CHECK: memref.alloca_scope scf.parallel (%j) = (%arg1) to (%arg3) step (%arg5) { // CHECK: "test.payload2"(%[[LVAR_AL2]]) : (index) -> () @@ -68,6 +81,8 @@ func.func @adjacent_loops(%arg0: index, %arg1: index, %arg2: index, // CHECK: omp.yield // CHECK: } } + // CHECK: omp.terminator + // CHECK: } // CHECK: omp.terminator // CHECK: } return diff --git a/mlir/test/Conversion/TosaToLinalg/tosa-to-linalg-named.mlir b/mlir/test/Conversion/TosaToLinalg/tosa-to-linalg-named.mlir index b4049000c50dc8b2b3723a63eb3ba995f14391a9..39699ee315e6cb30d28b2d0f1b7e0d80e641705d 100644 --- a/mlir/test/Conversion/TosaToLinalg/tosa-to-linalg-named.mlir +++ b/mlir/test/Conversion/TosaToLinalg/tosa-to-linalg-named.mlir @@ -503,6 +503,19 @@ func.func @avg_pool_dyn(%arg0: tensor) -> (tensor) // ----- +// CHECK: #[[$MAP1:.+]] = affine_map<(d0, d1, d2, d3) -> (0)> +// CHECK: #[[$MAP2:.+]] = affine_map<(d0, d1, d2, d3) -> (d0, d1, d2, d3)> + +// CHECK-LABEL: @conv2d_scalar_bias_f32 +func.func @conv2d_scalar_bias_f32(%input: tensor<1x49x42x27xf32>, %weights: tensor<28x3x3x27xf32>, %bias: tensor<1xf32>) -> () { + // CHECK: %[[INIT:.+]] = tensor.empty() : tensor<1x45x40x28xf32> + // CHECK: %[[BROADCAST:.+]] = linalg.generic {indexing_maps = [#[[$MAP1]], #[[$MAP2]]], iterator_types = ["parallel", "parallel", "parallel", "parallel"]} ins(%arg2 : tensor<1xf32>) outs(%[[INIT]] : tensor<1x45x40x28xf32>) { + %0 = tosa.conv2d %input, %weights, %bias {pad = array, stride = array, dilation = array} : (tensor<1x49x42x27xf32>, tensor<28x3x3x27xf32>, tensor<1xf32>) -> tensor<1x45x40x28xf32> + return +} + +// ----- + // CHECK: #[[$MAP1:.+]] = affine_map<(d0, d1, d2, d3) -> (d3)> // CHECK: #[[$MAP2:.+]] = affine_map<(d0, d1, d2, d3) -> (d0, d1, d2, d3)> diff --git a/mlir/test/Conversion/VectorToArmSME/vector-to-arm-sme.mlir b/mlir/test/Conversion/VectorToArmSME/vector-to-arm-sme.mlir index d3f02c6288a240a140506cad65f5cb1fb986e897..ce0b46e0f061a462a9b7142a5cd03f1830da89a7 100644 --- a/mlir/test/Conversion/VectorToArmSME/vector-to-arm-sme.mlir +++ b/mlir/test/Conversion/VectorToArmSME/vector-to-arm-sme.mlir @@ -620,3 +620,626 @@ func.func @vector_print_tile(%tile: vector<[4]x[4]xf32>) // CHECK-NEXT: scf.for %[[TILE_SLICE_INDEX:.*]] = %[[C0]] to %[[NUM_TILE_SLICES]] step %[[C1]] { // CHECK-NEXT: %[[TILE_SLICE:.*]] = arm_sme.move_tile_slice_to_vector %[[TILE]][%[[TILE_SLICE_INDEX]]] : vector<[4]xf32> from vector<[4]x[4]xf32> // CHECK-NEXT: vector.print %[[TILE_SLICE]] : vector<[4]xf32> + +//===----------------------------------------------------------------------===// +// vector.load +//===----------------------------------------------------------------------===// + +// ----- + +// CHECK-LABEL: @vector_load_i8_with_offset( +// CHECK-SAME: %[[MEMREF:.*]]: memref) +// CHECK: %[[C0:.*]] = arith.constant 0 : index +// CHECK: %[[C123:.*]] = arith.constant 123 : index +// CHECK: arm_sme.tile_load %[[MEMREF]][%[[C123]], %[[C0]]] : memref, vector<[16]x[16]xi8> +func.func @vector_load_i8_with_offset(%arg0 : memref) -> vector<[16]x[16]xi8> { + %c0 = arith.constant 0 : index + %c123 = arith.constant 123 : index + %tile = vector.load %arg0[%c123, %c0] : memref, vector<[16]x[16]xi8> + return %tile : vector<[16]x[16]xi8> +} + +// ----- + +// CHECK-LABEL: @vector_load_i8_from_rank_1_memref( +// CHECK-SAME: %[[MEMREF:.*]]: memref) +// CHECK: %[[C0:.*]] = arith.constant 0 : index +// CHECK: arm_sme.tile_load %[[MEMREF]][%[[C0]]] : memref, vector<[16]x[16]xi8> +func.func @vector_load_i8_from_rank_1_memref(%arg0 : memref) -> vector<[16]x[16]xi8> { + %c0 = arith.constant 0 : index + %tile = vector.load %arg0[%c0] : memref, vector<[16]x[16]xi8> + return %tile : vector<[16]x[16]xi8> +} + +// ----- + +// CHECK-LABEL: @vector_load_i16( +// CHECK: arm_sme.tile_load {{.*}} : memref, vector<[8]x[8]xi16> +func.func @vector_load_i16(%arg0 : memref) -> vector<[8]x[8]xi16> { + %c0 = arith.constant 0 : index + %tile = vector.load %arg0[%c0, %c0] : memref, vector<[8]x[8]xi16> + return %tile : vector<[8]x[8]xi16> +} + +// ----- + +// CHECK-LABEL: @vector_load_i32( +// CHECK: arm_sme.tile_load {{.*}} : memref, vector<[4]x[4]xi32> +func.func @vector_load_i32(%arg0 : memref) -> vector<[4]x[4]xi32> { + %c0 = arith.constant 0 : index + %tile = vector.load %arg0[%c0, %c0] : memref, vector<[4]x[4]xi32> + return %tile : vector<[4]x[4]xi32> +} + +// ----- + +// CHECK-LABEL: @vector_load_i64( +// CHECK: arm_sme.tile_load {{.*}} : memref, vector<[2]x[2]xi64> +func.func @vector_load_i64(%arg0 : memref) -> vector<[2]x[2]xi64> { + %c0 = arith.constant 0 : index + %tile = vector.load %arg0[%c0, %c0] : memref, vector<[2]x[2]xi64> + return %tile : vector<[2]x[2]xi64> +} + +// ----- + +// CHECK-LABEL: @vector_load_f16( +// CHECK: arm_sme.tile_load {{.*}} : memref, vector<[8]x[8]xf16> +func.func @vector_load_f16(%arg0 : memref) -> vector<[8]x[8]xf16> { + %c0 = arith.constant 0 : index + %tile = vector.load %arg0[%c0, %c0] : memref, vector<[8]x[8]xf16> + return %tile : vector<[8]x[8]xf16> +} + +// ----- + +// CHECK-LABEL: @vector_load_bf16( +// CHECK: arm_sme.tile_load {{.*}} : memref, vector<[8]x[8]xbf16> +func.func @vector_load_bf16(%arg0 : memref) -> vector<[8]x[8]xbf16> { + %c0 = arith.constant 0 : index + %tile = vector.load %arg0[%c0, %c0] : memref, vector<[8]x[8]xbf16> + return %tile : vector<[8]x[8]xbf16> +} + +// ----- + +// CHECK-LABEL: @vector_load_f32( +// CHECK: arm_sme.tile_load {{.*}} : memref, vector<[4]x[4]xf32> +func.func @vector_load_f32(%arg0 : memref) -> vector<[4]x[4]xf32> { + %c0 = arith.constant 0 : index + %tile = vector.load %arg0[%c0, %c0] : memref, vector<[4]x[4]xf32> + return %tile : vector<[4]x[4]xf32> +} + +// ----- + +// CHECK-LABEL: @vector_load_f64( +// CHECK: arm_sme.tile_load {{.*}} : memref, vector<[2]x[2]xf64> +func.func @vector_load_f64(%arg0 : memref) -> vector<[2]x[2]xf64> { + %c0 = arith.constant 0 : index + %tile = vector.load %arg0[%c0, %c0] : memref, vector<[2]x[2]xf64> + return %tile : vector<[2]x[2]xf64> +} + +// ----- + +// CHECK-LABEL: @vector_load_i128( +// CHECK: arm_sme.tile_load {{.*}} : memref, vector<[1]x[1]xi128> +func.func @vector_load_i128(%arg0 : memref) -> vector<[1]x[1]xi128> { + %c0 = arith.constant 0 : index + %tile = vector.load %arg0[%c0, %c0] : memref, vector<[1]x[1]xi128> + return %tile : vector<[1]x[1]xi128> +} + + +//===----------------------------------------------------------------------===// +// vector.store +//===----------------------------------------------------------------------===// + +// ----- + +// CHECK-LABEL: @vector_store_i8( +// CHECK-SAME: %[[MEMREF:.*]]: memref) { +// CHECK: %[[C0:.*]] = arith.constant 0 : index +// CHECK: %[[TILE:.*]] = arm_sme.get_tile : vector<[16]x[16]xi8> +// CHECK: arm_sme.tile_store %[[TILE]], %[[MEMREF]][%[[C0]], %[[C0]]] : memref, vector<[16]x[16]xi8> +func.func @vector_store_i8(%arg0 : memref) { + %c0 = arith.constant 0 : index + %tile = arm_sme.get_tile : vector<[16]x[16]xi8> + vector.store %tile, %arg0[%c0, %c0] : memref, vector<[16]x[16]xi8> + return +} + +// ----- + +// CHECK-LABEL: @vector_store_i16 +// CHECK: arm_sme.tile_store {{.*}} : memref, vector<[8]x[8]xi16> +func.func @vector_store_i16(%arg0 : memref) { + %c0 = arith.constant 0 : index + %tile = arm_sme.get_tile : vector<[8]x[8]xi16> + vector.store %tile, %arg0[%c0, %c0] : memref, vector<[8]x[8]xi16> + return +} + +// ----- + +// CHECK-LABEL: @vector_store_i32 +// CHECK: arm_sme.tile_store {{.*}} : memref, vector<[4]x[4]xi32> +func.func @vector_store_i32(%arg0 : memref) { + %c0 = arith.constant 0 : index + %tile = arm_sme.get_tile : vector<[4]x[4]xi32> + vector.store %tile, %arg0[%c0, %c0] : memref, vector<[4]x[4]xi32> + return +} + +// ----- + +// CHECK-LABEL: @vector_store_i64 +// CHECK: arm_sme.tile_store {{.*}} : memref, vector<[2]x[2]xi64> +func.func @vector_store_i64(%arg0 : memref) { + %c0 = arith.constant 0 : index + %tile = arm_sme.get_tile : vector<[2]x[2]xi64> + vector.store %tile, %arg0[%c0, %c0] : memref, vector<[2]x[2]xi64> + return +} + +// ----- + +// CHECK-LABEL: @vector_store_f16 +// CHECK: arm_sme.tile_store {{.*}} : memref, vector<[8]x[8]xf16> +func.func @vector_store_f16(%arg0 : memref) { + %c0 = arith.constant 0 : index + %tile = arm_sme.get_tile : vector<[8]x[8]xf16> + vector.store %tile, %arg0[%c0, %c0] : memref, vector<[8]x[8]xf16> + return +} + +// ----- + +// CHECK-LABEL: @vector_store_bf16 +// CHECK: arm_sme.tile_store {{.*}} : memref, vector<[8]x[8]xbf16> +func.func @vector_store_bf16(%arg0 : memref) { + %c0 = arith.constant 0 : index + %tile = arm_sme.get_tile : vector<[8]x[8]xbf16> + vector.store %tile, %arg0[%c0, %c0] : memref, vector<[8]x[8]xbf16> + return +} +// ----- + +// CHECK-LABEL: @vector_store_f32 +// CHECK: arm_sme.tile_store {{.*}} : memref, vector<[4]x[4]xf32> +func.func @vector_store_f32(%arg0 : memref) { + %c0 = arith.constant 0 : index + %tile = arm_sme.get_tile : vector<[4]x[4]xf32> + vector.store %tile, %arg0[%c0, %c0] : memref, vector<[4]x[4]xf32> + return +} + +// ----- + +// CHECK-LABEL: @vector_store_f64 +// CHECK: arm_sme.tile_store {{.*}} : memref, vector<[2]x[2]xf64> +func.func @vector_store_f64(%arg0 : memref) { + %c0 = arith.constant 0 : index + %tile = arm_sme.get_tile : vector<[2]x[2]xf64> + vector.store %tile, %arg0[%c0, %c0] : memref, vector<[2]x[2]xf64> + return +} + +// ----- + +// CHECK-LABEL: @vector_store_i128 +// CHECK: arm_sme.tile_store {{.*}} : memref, vector<[1]x[1]xi128> +func.func @vector_store_i128(%arg0 : memref) { + %c0 = arith.constant 0 : index + %tile = arm_sme.get_tile : vector<[1]x[1]xi128> + vector.store %tile, %arg0[%c0, %c0] : memref, vector<[1]x[1]xi128> + return +} + +//===----------------------------------------------------------------------===// +// vector.insert +//===----------------------------------------------------------------------===// + +// ----- + +// CHECK-LABEL: @vector_insert_slice_i32( +// CHECK-SAME: %[[SLICE:.*]]: vector<[4]xi32>, +// CHECK-SAME: %[[INDEX:.*]]: index) +func.func @vector_insert_slice_i32(%slice: vector<[4]xi32>, %row: index) -> vector<[4]x[4]xi32>{ + // CHECK-NEXT: %[[TILE:.*]] = arm_sme.get_tile : vector<[4]x[4]xi32> + // CHECK-NEXT: arm_sme.move_vector_to_tile_slice %[[SLICE]], %[[TILE]], %[[INDEX]] : vector<[4]xi32> into vector<[4]x[4]xi32> + %tile = arm_sme.get_tile : vector<[4]x[4]xi32> + %new_tile = vector.insert %slice, %tile[%row] : vector<[4]xi32> into vector<[4]x[4]xi32> + return %new_tile : vector<[4]x[4]xi32> +} + +// ----- + +// CHECK-LABEL: @vector_insert_slice_i8 +func.func @vector_insert_slice_i8(%slice: vector<[16]xi8>, %row: index) -> vector<[16]x[16]xi8> { + // CHECK: arm_sme.move_vector_to_tile_slice %{{.*}} : vector<[16]xi8> into vector<[16]x[16]xi8> + %tile = arm_sme.get_tile : vector<[16]x[16]xi8> + %new_tile = vector.insert %slice, %tile[%row] : vector<[16]xi8> into vector<[16]x[16]xi8> + return %new_tile : vector<[16]x[16]xi8> +} + +// ----- + +// CHECK-LABEL: @vector_insert_slice_i16 +func.func @vector_insert_slice_i16(%slice: vector<[8]xi16>, %row: index) -> vector<[8]x[8]xi16> { + // CHECK: arm_sme.move_vector_to_tile_slice %{{.*}} : vector<[8]xi16> into vector<[8]x[8]xi16> + %tile = arm_sme.get_tile : vector<[8]x[8]xi16> + %new_tile = vector.insert %slice, %tile[%row] : vector<[8]xi16> into vector<[8]x[8]xi16> + return %new_tile : vector<[8]x[8]xi16> +} + +// ----- + +// CHECK-LABEL: @vector_insert_slice_i64 +func.func @vector_insert_slice_i64(%slice: vector<[2]xi64>, %row: index) -> vector<[2]x[2]xi64> { + // CHECK: arm_sme.move_vector_to_tile_slice %{{.*}} : vector<[2]xi64> into vector<[2]x[2]xi64> + %tile = arm_sme.get_tile : vector<[2]x[2]xi64> + %new_tile = vector.insert %slice, %tile[%row] : vector<[2]xi64> into vector<[2]x[2]xi64> + return %new_tile : vector<[2]x[2]xi64> +} + +// ----- + +// CHECK-LABEL: @vector_insert_slice_i128 +func.func @vector_insert_slice_i128(%slice: vector<[1]xi128>, %row: index) -> vector<[1]x[1]xi128> { + // CHECK: arm_sme.move_vector_to_tile_slice %{{.*}} : vector<[1]xi128> into vector<[1]x[1]xi128> + %tile = arm_sme.get_tile : vector<[1]x[1]xi128> + %new_tile = vector.insert %slice, %tile[%row] : vector<[1]xi128> into vector<[1]x[1]xi128> + return %new_tile : vector<[1]x[1]xi128> +} + +// ----- + +// CHECK-LABEL: @vector_insert_slice_f16 +func.func @vector_insert_slice_f16(%slice: vector<[8]xf16>, %row: index) -> vector<[8]x[8]xf16> { + // CHECK: arm_sme.move_vector_to_tile_slice %{{.*}} : vector<[8]xf16> into vector<[8]x[8]xf16> + %tile = arm_sme.get_tile : vector<[8]x[8]xf16> + %new_tile = vector.insert %slice, %tile[%row] : vector<[8]xf16> into vector<[8]x[8]xf16> + return %new_tile : vector<[8]x[8]xf16> +} + +// ----- + +// CHECK-LABEL: @vector_insert_slice_bf16 +func.func @vector_insert_slice_bf16(%slice: vector<[8]xbf16>, %row: index) -> vector<[8]x[8]xbf16> { + // CHECK: arm_sme.move_vector_to_tile_slice %{{.*}} : vector<[8]xbf16> into vector<[8]x[8]xbf16> + %tile = arm_sme.get_tile : vector<[8]x[8]xbf16> + %new_tile = vector.insert %slice, %tile[%row] : vector<[8]xbf16> into vector<[8]x[8]xbf16> + return %new_tile : vector<[8]x[8]xbf16> +} + +// ----- + +// CHECK-LABEL: @vector_insert_slice_f32 +func.func @vector_insert_slice_f32(%slice: vector<[4]xf32>, %row: index) -> vector<[4]x[4]xf32> { + // CHECK: arm_sme.move_vector_to_tile_slice %{{.*}} : vector<[4]xf32> into vector<[4]x[4]xf32> + %tile = arm_sme.get_tile : vector<[4]x[4]xf32> + %new_tile = vector.insert %slice, %tile[%row] : vector<[4]xf32> into vector<[4]x[4]xf32> + return %new_tile : vector<[4]x[4]xf32> +} + +// ----- + +// CHECK-LABEL: @vector_insert_slice_f64 +func.func @vector_insert_slice_f64(%slice: vector<[2]xf64>, %row: index) -> vector<[2]x[2]xf64> { + // CHECK: arm_sme.move_vector_to_tile_slice %{{.*}} : vector<[2]xf64> into vector<[2]x[2]xf64> + %tile = arm_sme.get_tile : vector<[2]x[2]xf64> + %new_tile = vector.insert %slice, %tile[%row] : vector<[2]xf64> into vector<[2]x[2]xf64> + return %new_tile : vector<[2]x[2]xf64> +} + +// ----- + +// CHECK-LABEL: @vector_insert_element_i32( +// CHECK-SAME: %[[EL:.*]]: i32, +// CHECK-SAME: %[[ROW:.*]]: index, +// CHECK-SAME: %[[COL:.*]]: index) +func.func @vector_insert_element_i32(%el: i32, %row: index, %col: index) -> vector<[4]x[4]xi32> { + // CHECK-NEXT: %[[TILE:.*]] = arm_sme.get_tile : vector<[4]x[4]xi32> + // CHECK-NEXT: %[[SLICE:.*]] = arm_sme.move_tile_slice_to_vector %[[TILE]][%[[ROW]]] : vector<[4]xi32> from vector<[4]x[4]xi32> + // CHECK-NEXT: %[[NEW_SLICE:.*]] = vector.insert %[[EL]], %[[SLICE]] [%[[COL]]] : i32 into vector<[4]xi32> + // CHECK-NEXT: arm_sme.move_vector_to_tile_slice %[[NEW_SLICE]], %[[TILE]], %[[ROW]] : vector<[4]xi32> into vector<[4]x[4]xi32> + %tile = arm_sme.get_tile : vector<[4]x[4]xi32> + %new_tile = vector.insert %el, %tile[%row, %col] : i32 into vector<[4]x[4]xi32> + return %new_tile : vector<[4]x[4]xi32> +} + +// ----- + +// CHECK-LABEL: @vector_insert_element_i8 +func.func @vector_insert_element_i8(%el: i8, %row: index, %col: index) -> vector<[16]x[16]xi8> { + // CHECK: %[[TILE:.*]] = arm_sme.get_tile : vector<[16]x[16]xi8> + // CHECK: arm_sme.move_tile_slice_to_vector %[[TILE]]{{.*}} : vector<[16]xi8> from vector<[16]x[16]xi8> + // CHECK: arm_sme.move_vector_to_tile_slice %{{.*}}, %[[TILE]], %{{.*}} : vector<[16]xi8> into vector<[16]x[16]xi8> + %tile = arm_sme.get_tile : vector<[16]x[16]xi8> + %new_tile = vector.insert %el, %tile[%row, %col] : i8 into vector<[16]x[16]xi8> + return %new_tile : vector<[16]x[16]xi8> +} + +// ----- + +// CHECK-LABEL: @vector_insert_element_i16 +func.func @vector_insert_element_i16(%el: i16, %row: index, %col: index) -> vector<[8]x[8]xi16> { + // CHECK: %[[TILE:.*]] = arm_sme.get_tile : vector<[8]x[8]xi16> + // CHECK: arm_sme.move_tile_slice_to_vector %[[TILE]]{{.*}} : vector<[8]xi16> from vector<[8]x[8]xi16> + // CHECK: arm_sme.move_vector_to_tile_slice %{{.*}}, %[[TILE]], %{{.*}} : vector<[8]xi16> into vector<[8]x[8]xi16> + %tile = arm_sme.get_tile : vector<[8]x[8]xi16> + %new_tile = vector.insert %el, %tile[%row, %col] : i16 into vector<[8]x[8]xi16> + return %new_tile : vector<[8]x[8]xi16> +} + +// ----- + +// CHECK-LABEL: @vector_insert_element_i64 +func.func @vector_insert_element_i64(%el: i64, %row: index, %col: index) -> vector<[2]x[2]xi64> { + // CHECK: %[[TILE:.*]] = arm_sme.get_tile : vector<[2]x[2]xi64> + // CHECK: arm_sme.move_tile_slice_to_vector %[[TILE]]{{.*}} : vector<[2]xi64> from vector<[2]x[2]xi64> + // CHECK: arm_sme.move_vector_to_tile_slice %{{.*}}, %[[TILE]], %{{.*}} : vector<[2]xi64> into vector<[2]x[2]xi64> + %tile = arm_sme.get_tile : vector<[2]x[2]xi64> + %new_tile = vector.insert %el, %tile[%row, %col] : i64 into vector<[2]x[2]xi64> + return %new_tile : vector<[2]x[2]xi64> +} + +// ----- + +// CHECK-LABEL: @vector_insert_element_i128 +func.func @vector_insert_element_i128(%el: i128, %row: index, %col: index) -> vector<[1]x[1]xi128> { + // CHECK: %[[TILE:.*]] = arm_sme.get_tile : vector<[1]x[1]xi128> + // CHECK: arm_sme.move_tile_slice_to_vector %[[TILE]]{{.*}} : vector<[1]xi128> from vector<[1]x[1]xi128> + // CHECK: arm_sme.move_vector_to_tile_slice %{{.*}}, %[[TILE]], %{{.*}} : vector<[1]xi128> into vector<[1]x[1]xi128> + %tile = arm_sme.get_tile : vector<[1]x[1]xi128> + %new_tile = vector.insert %el, %tile[%row, %col] : i128 into vector<[1]x[1]xi128> + return %new_tile : vector<[1]x[1]xi128> +} + +// ----- + +// CHECK-LABEL: @vector_insert_element_f16 +func.func @vector_insert_element_f16(%el: f16, %row: index, %col: index) -> vector<[8]x[8]xf16> { + // CHECK: %[[TILE:.*]] = arm_sme.get_tile : vector<[8]x[8]xf16> + // CHECK: arm_sme.move_tile_slice_to_vector %[[TILE]]{{.*}} : vector<[8]xf16> from vector<[8]x[8]xf16> + // CHECK: arm_sme.move_vector_to_tile_slice %{{.*}}, %[[TILE]], %{{.*}} : vector<[8]xf16> into vector<[8]x[8]xf16> + %tile = arm_sme.get_tile : vector<[8]x[8]xf16> + %new_tile = vector.insert %el, %tile[%row, %col] : f16 into vector<[8]x[8]xf16> + return %new_tile : vector<[8]x[8]xf16> +} + +// ----- + +// CHECK-LABEL: @vector_insert_element_bf16 +func.func @vector_insert_element_bf16(%el: bf16, %row: index, %col: index) -> vector<[8]x[8]xbf16> { + // CHECK: %[[TILE:.*]] = arm_sme.get_tile : vector<[8]x[8]xbf16> + // CHECK: arm_sme.move_tile_slice_to_vector %[[TILE]]{{.*}} : vector<[8]xbf16> from vector<[8]x[8]xbf16> + // CHECK: arm_sme.move_vector_to_tile_slice %{{.*}}, %[[TILE]], %{{.*}} : vector<[8]xbf16> into vector<[8]x[8]xbf16> + %tile = arm_sme.get_tile : vector<[8]x[8]xbf16> + %new_tile = vector.insert %el, %tile[%row, %col] : bf16 into vector<[8]x[8]xbf16> + return %new_tile : vector<[8]x[8]xbf16> +} + +// ----- + +// CHECK-LABEL: @vector_insert_element_f32 +func.func @vector_insert_element_f32(%el: f32, %row: index, %col: index) -> vector<[4]x[4]xf32> { + // CHECK: %[[TILE:.*]] = arm_sme.get_tile : vector<[4]x[4]xf32> + // CHECK: arm_sme.move_tile_slice_to_vector %[[TILE]]{{.*}} : vector<[4]xf32> from vector<[4]x[4]xf32> + // CHECK: arm_sme.move_vector_to_tile_slice %{{.*}}, %[[TILE]], %{{.*}} : vector<[4]xf32> into vector<[4]x[4]xf32> + %tile = arm_sme.get_tile : vector<[4]x[4]xf32> + %new_tile = vector.insert %el, %tile[%row, %col] : f32 into vector<[4]x[4]xf32> + return %new_tile : vector<[4]x[4]xf32> +} + +// ----- + +// CHECK-LABEL: @vector_insert_element_f64 +func.func @vector_insert_element_f64(%el: f64, %row: index, %col: index) -> vector<[2]x[2]xf64> { + // CHECK: %[[TILE:.*]] = arm_sme.get_tile : vector<[2]x[2]xf64> + // CHECK: arm_sme.move_tile_slice_to_vector %[[TILE]]{{.*}} : vector<[2]xf64> from vector<[2]x[2]xf64> + // CHECK: arm_sme.move_vector_to_tile_slice %{{.*}}, %[[TILE]], %{{.*}} : vector<[2]xf64> into vector<[2]x[2]xf64> + %tile = arm_sme.get_tile : vector<[2]x[2]xf64> + %new_tile = vector.insert %el, %tile[%row, %col] : f64 into vector<[2]x[2]xf64> + return %new_tile : vector<[2]x[2]xf64> +} + +//===----------------------------------------------------------------------===// +// vector.extract +//===----------------------------------------------------------------------===// + +// ----- + +// CHECK-LABEL: @vector_extract_slice_i32( +// CHECK-SAME: %[[INDEX:.*]]: index) +func.func @vector_extract_slice_i32(%row: index) -> vector<[4]xi32> { + // CHECK: %[[TILE:.*]] = arm_sme.get_tile : vector<[4]x[4]xi32> + // CHECK: arm_sme.move_tile_slice_to_vector %[[TILE]][%[[INDEX]]] : vector<[4]xi32> from vector<[4]x[4]xi32> + %tile = arm_sme.get_tile : vector<[4]x[4]xi32> + %slice = vector.extract %tile[%row] : vector<[4]xi32> from vector<[4]x[4]xi32> + return %slice : vector<[4]xi32> +} + +// ----- + +// CHECK-LABEL: @vector_extract_slice_i8 +func.func @vector_extract_slice_i8(%row: index) -> vector<[16]xi8> { + // CHECK: arm_sme.move_tile_slice_to_vector {{.*}} : vector<[16]xi8> from vector<[16]x[16]xi8> + %tile = arm_sme.get_tile : vector<[16]x[16]xi8> + %slice = vector.extract %tile[%row] : vector<[16]xi8> from vector<[16]x[16]xi8> + return %slice : vector<[16]xi8> +} + +// ----- + +// CHECK-LABEL: @vector_extract_slice_i16 +func.func @vector_extract_slice_i16(%row: index) -> vector<[8]xi16> { + // CHECK: arm_sme.move_tile_slice_to_vector {{.*}} : vector<[8]xi16> from vector<[8]x[8]xi16> + %tile = arm_sme.get_tile : vector<[8]x[8]xi16> + %slice = vector.extract %tile[%row] : vector<[8]xi16> from vector<[8]x[8]xi16> + return %slice : vector<[8]xi16> +} + +// ----- + +// CHECK-LABEL: @vector_extract_slice_i64 +func.func @vector_extract_slice_i64(%row: index) -> vector<[2]xi64> { + // CHECK: arm_sme.move_tile_slice_to_vector {{.*}} : vector<[2]xi64> from vector<[2]x[2]xi64> + %tile = arm_sme.get_tile : vector<[2]x[2]xi64> + %slice = vector.extract %tile[%row] : vector<[2]xi64> from vector<[2]x[2]xi64> + return %slice : vector<[2]xi64> +} + +// ----- + +// CHECK-LABEL: @vector_extract_slice_i128 +func.func @vector_extract_slice_i128(%row: index) -> vector<[1]xi128> { + // CHECK: arm_sme.move_tile_slice_to_vector {{.*}} : vector<[1]xi128> from vector<[1]x[1]xi128> + %tile = arm_sme.get_tile : vector<[1]x[1]xi128> + %slice = vector.extract %tile[%row] : vector<[1]xi128> from vector<[1]x[1]xi128> + return %slice : vector<[1]xi128> +} + +// ----- + +// CHECK-LABEL: @vector_extract_slice_f16 +func.func @vector_extract_slice_f16(%row: index) -> vector<[8]xf16> { + // CHECK: arm_sme.move_tile_slice_to_vector {{.*}} : vector<[8]xf16> from vector<[8]x[8]xf16> + %tile = arm_sme.get_tile : vector<[8]x[8]xf16> + %slice = vector.extract %tile[%row] : vector<[8]xf16> from vector<[8]x[8]xf16> + return %slice : vector<[8]xf16> +} + +// ----- + +// CHECK-LABEL: @vector_extract_slice_bf16 +func.func @vector_extract_slice_bf16(%row: index) -> vector<[8]xbf16> { + // CHECK: arm_sme.move_tile_slice_to_vector {{.*}} : vector<[8]xbf16> from vector<[8]x[8]xbf16> + %tile = arm_sme.get_tile : vector<[8]x[8]xbf16> + %slice = vector.extract %tile[%row] : vector<[8]xbf16> from vector<[8]x[8]xbf16> + return %slice : vector<[8]xbf16> +} + +// ----- + +// CHECK-LABEL: @vector_extract_slice_f32 +func.func @vector_extract_slice_f32(%row: index) -> vector<[4]xf32> { + // CHECK: arm_sme.move_tile_slice_to_vector {{.*}} : vector<[4]xf32> from vector<[4]x[4]xf32> + %tile = arm_sme.get_tile : vector<[4]x[4]xf32> + %slice = vector.extract %tile[%row] : vector<[4]xf32> from vector<[4]x[4]xf32> + return %slice : vector<[4]xf32> +} + +// ----- + +// CHECK-LABEL: @vector_extract_slice_f64 +func.func @vector_extract_slice_f64(%row: index) -> vector<[2]xf64> { + // CHECK: arm_sme.move_tile_slice_to_vector {{.*}} : vector<[2]xf64> from vector<[2]x[2]xf64> + %tile = arm_sme.get_tile : vector<[2]x[2]xf64> + %slice = vector.extract %tile[%row] : vector<[2]xf64> from vector<[2]x[2]xf64> + return %slice : vector<[2]xf64> +} + +// ----- + +// CHECK-LABEL: @vector_extract_element( +// CHECK-SAME: %[[ROW:.*]]: index, +// CHECK-SAME: %[[COL:.*]]: index) +func.func @vector_extract_element(%row: index, %col: index) -> i32 { + // CHECK-NEXT: %[[TILE:.*]] = arm_sme.get_tile : vector<[4]x[4]xi32> + // CHECK-NEXT: %[[SLICE:.*]] = arm_sme.move_tile_slice_to_vector %[[TILE]][%[[ROW]]] : vector<[4]xi32> from vector<[4]x[4]xi32> + // CHECK-NEXT: %[[EL:.*]] = vector.extract %[[SLICE]]{{\[}}%[[COL]]] : i32 from vector<[4]xi32> + %tile = arm_sme.get_tile : vector<[4]x[4]xi32> + %el = vector.extract %tile[%row, %col] : i32 from vector<[4]x[4]xi32> + return %el : i32 +} + +// ----- + +// CHECK-LABEL: @vector_extract_element_i8 +func.func @vector_extract_element_i8(%row: index, %col: index) -> i8 { + // CHECK: %[[SLICE:.*]] = arm_sme.move_tile_slice_to_vector %{{.*}} : vector<[16]xi8> from vector<[16]x[16]xi8> + // CHECK-NEXT: %{{.*}} = vector.extract %[[SLICE]]{{\[}}%{{.*}}] : i8 from vector<[16]xi8> + %tile = arm_sme.get_tile : vector<[16]x[16]xi8> + %el = vector.extract %tile[%row, %col] : i8 from vector<[16]x[16]xi8> + return %el : i8 +} + +// ----- + +// CHECK-LABEL: @vector_extract_element_i16 +func.func @vector_extract_element_i16(%row: index, %col: index) -> i16 { + // CHECK: %[[SLICE:.*]] = arm_sme.move_tile_slice_to_vector %{{.*}} : vector<[8]xi16> from vector<[8]x[8]xi16> + // CHECK-NEXT: %{{.*}} = vector.extract %[[SLICE]]{{\[}}%{{.*}}] : i16 from vector<[8]xi16> + %tile = arm_sme.get_tile : vector<[8]x[8]xi16> + %el = vector.extract %tile[%row, %col] : i16 from vector<[8]x[8]xi16> + return %el : i16 +} + +// ----- + +// CHECK-LABEL: @vector_extract_element_i64 +func.func @vector_extract_element_i64(%row: index, %col: index) -> i64 { + // CHECK: %[[SLICE:.*]] = arm_sme.move_tile_slice_to_vector %{{.*}} : vector<[2]xi64> from vector<[2]x[2]xi64> + // CHECK-NEXT: %{{.*}} = vector.extract %[[SLICE]]{{\[}}%{{.*}}] : i64 from vector<[2]xi64> + %tile = arm_sme.get_tile : vector<[2]x[2]xi64> + %el = vector.extract %tile[%row, %col] : i64 from vector<[2]x[2]xi64> + return %el : i64 +} + +// ----- + +// CHECK-LABEL: @vector_extract_element_i128 +func.func @vector_extract_element_i128(%row: index, %col: index) -> i128 { + // CHECK: %[[SLICE:.*]] = arm_sme.move_tile_slice_to_vector %{{.*}} : vector<[1]xi128> from vector<[1]x[1]xi128> + // CHECK-NEXT: %{{.*}} = vector.extract %[[SLICE]]{{\[}}%{{.*}}] : i128 from vector<[1]xi128> + %tile = arm_sme.get_tile : vector<[1]x[1]xi128> + %el = vector.extract %tile[%row, %col] : i128 from vector<[1]x[1]xi128> + return %el : i128 +} + +// ----- + +// CHECK-LABEL: @vector_extract_element_f16 +func.func @vector_extract_element_f16(%row: index, %col: index) -> f16 { + // CHECK: %[[SLICE:.*]] = arm_sme.move_tile_slice_to_vector %{{.*}} : vector<[8]xf16> from vector<[8]x[8]xf16> + // CHECK-NEXT: %{{.*}} = vector.extract %[[SLICE]]{{\[}}%{{.*}}] : f16 from vector<[8]xf16> + %tile = arm_sme.get_tile : vector<[8]x[8]xf16> + %el = vector.extract %tile[%row, %col] : f16 from vector<[8]x[8]xf16> + return %el : f16 +} + +// ----- + +// CHECK-LABEL: @vector_extract_element_bf16 +func.func @vector_extract_element_bf16(%row: index, %col: index) -> bf16 { + // CHECK: %[[SLICE:.*]] = arm_sme.move_tile_slice_to_vector %{{.*}} : vector<[8]xbf16> from vector<[8]x[8]xbf16> + // CHECK-NEXT: %{{.*}} = vector.extract %[[SLICE]]{{\[}}%{{.*}}] : bf16 from vector<[8]xbf16> + %tile = arm_sme.get_tile : vector<[8]x[8]xbf16> + %el = vector.extract %tile[%row, %col] : bf16 from vector<[8]x[8]xbf16> + return %el : bf16 +} + +// ----- + +// CHECK-LABEL: @vector_extract_element_f32 +func.func @vector_extract_element_f32(%row: index, %col: index) -> f32 { + // CHECK: %[[SLICE:.*]] = arm_sme.move_tile_slice_to_vector %{{.*}} : vector<[4]xf32> from vector<[4]x[4]xf32> + // CHECK-NEXT: %{{.*}} = vector.extract %[[SLICE]]{{\[}}%{{.*}}] : f32 from vector<[4]xf32> + %tile = arm_sme.get_tile : vector<[4]x[4]xf32> + %el = vector.extract %tile[%row, %col] : f32 from vector<[4]x[4]xf32> + return %el : f32 +} + +// ----- + +// CHECK-LABEL: @vector_extract_element_f64 +func.func @vector_extract_element_f64(%row: index, %col: index) -> f64 { + // CHECK: %[[SLICE:.*]] = arm_sme.move_tile_slice_to_vector %{{.*}} : vector<[2]xf64> from vector<[2]x[2]xf64> + // CHECK-NEXT: %{{.*}} = vector.extract %[[SLICE]]{{\[}}%{{.*}}] : f64 from vector<[2]xf64> + %tile = arm_sme.get_tile : vector<[2]x[2]xf64> + %el = vector.extract %tile[%row, %col] : f64 from vector<[2]x[2]xf64> + return %el : f64 +} diff --git a/mlir/test/Dialect/ArmSME/vector-ops-to-llvm.mlir b/mlir/test/Dialect/ArmSME/vector-ops-to-llvm.mlir deleted file mode 100644 index 17a070999c20a05327c325574dcd801be78c270c..0000000000000000000000000000000000000000 --- a/mlir/test/Dialect/ArmSME/vector-ops-to-llvm.mlir +++ /dev/null @@ -1,877 +0,0 @@ -// RUN: mlir-opt %s -convert-vector-to-arm-sme -convert-arith-to-arm-sme -allocate-arm-sme-tiles -convert-arm-sme-to-scf -convert-arm-sme-to-llvm -cse -canonicalize -split-input-file -allow-unregistered-dialect -verify-diagnostics | FileCheck %s - -//===----------------------------------------------------------------------===// -// vector.transfer_write -//===----------------------------------------------------------------------===// - -// CHECK-LABEL: @transfer_write_2d_zero_i8( -// CHECK-SAME: %[[ARG0:.*]]: memref) -// CHECK-DAG: %[[MEM_DESC:.*]] = builtin.unrealized_conversion_cast %[[ARG0]] : memref to !llvm.struct<(ptr, ptr, i64, array<2 x i64>, array<2 x i64>)> -// CHECK-DAG: %[[C0:.*]] = arith.constant 0 : index -// CHECK-DAG: %[[C1:.*]] = arith.constant 1 : index -// CHECK-DAG: %[[MIN_SVL_B:.*]] = arith.constant 16 : index -// CHECK-DAG: %[[PTRUE_ALL:.*]] = arith.constant dense : vector<[16]xi1> -// CHECK-DAG: %[[C0_I64:.*]] = builtin.unrealized_conversion_cast %[[C0]] : index to i64 -// CHECK-DAG: "arm_sme.intr.zero"() <{tile_mask = 255 : i32}> : () -> () -// CHECK-DAG: %[[VSCALE:.*]] = vector.vscale -// CHECK-NEXT: %[[SVL_B:.*]] = arith.muli %[[VSCALE]], %[[MIN_SVL_B]] : index -// CHECK-NEXT: scf.for %[[TILE_SLICE:.*]] = %[[C0]] to %[[SVL_B]] step %[[C1]] { -// CHECK: %[[TILE_SLICE_I64:.*]] = builtin.unrealized_conversion_cast %[[TILE_SLICE]] : index to i64 -// CHECK-NEXT: %[[ALIGNED_BASE:.*]] = llvm.extractvalue %[[MEM_DESC]][1] : !llvm.struct<(ptr, ptr, i64, array<2 x i64>, array<2 x i64>)> -// CHECK-NEXT: %[[STRIDE0:.*]] = llvm.extractvalue %[[MEM_DESC]][4, 0] : !llvm.struct<(ptr, ptr, i64, array<2 x i64>, array<2 x i64>)> -// CHECK-NEXT: %[[OFF0:.*]] = llvm.mul %[[TILE_SLICE_I64]], %[[STRIDE0]] : i64 -// CHECK-NEXT: %[[OFF1:.*]] = llvm.add %[[OFF0]], %[[C0_I64]] : i64 -// CHECK-NEXT: %[[GEP:.*]] = llvm.getelementptr %[[ALIGNED_BASE]]{{\[}}%[[OFF1]]] : (!llvm.ptr, i64) -> !llvm.ptr, i8 -// CHECK-NEXT: %[[TILE_SLICE_I32:.*]] = arith.index_castui %[[TILE_SLICE]] : index to i32 -// CHECK-NEXT: "arm_sme.intr.st1b.horiz"(%[[PTRUE_ALL]], %[[GEP]], %[[TILE_SLICE_I32]]) <{tile_id = 0 : i32}> : (vector<[16]xi1>, !llvm.ptr, i32) -> () -func.func @transfer_write_2d_zero_i8(%arg0 : memref) { - %c0 = arith.constant 0 : index - %cst = arith.constant dense<0> : vector<[16]x[16]xi8> - vector.transfer_write %cst, %arg0[%c0, %c0] {in_bounds = [true, true]} : vector<[16]x[16]xi8>, memref - return -} - -//===----------------------------------------------------------------------===// -// vector.load -//===----------------------------------------------------------------------===// - -// ----- - -// Load an 8-bit tile from a rank 2 memref with a non-zero offset for the first -// memref index. This verifies the offset is preserved when materializing the -// loop of tile slice loads. - -// CHECK-LABEL: @vector_load_i8_with_offset( -// CHECK-SAME: %[[ARG0:.*]]: memref) -// CHECK-DAG: %[[MEM_DESC:.*]] = builtin.unrealized_conversion_cast %[[ARG0]] : memref to !llvm.struct<(ptr, ptr, i64, array<2 x i64>, array<2 x i64>)> -// CHECK-DAG: %[[C0:.*]] = arith.constant 0 : index -// CHECK-DAG: %[[C1:.*]] = arith.constant 1 : index -// CHECK-DAG: %[[C123:.*]] = arith.constant 123 : index -// CHECK-DAG: %[[MIN_SVL_B:.*]] = arith.constant 16 : index -// CHECK-DAG: %[[PTRUE_ALL:.*]] = arith.constant dense : vector<[16]xi1> -// CHECK-DAG: %[[C0_I64:.*]] = builtin.unrealized_conversion_cast %[[C0]] : index to i64 -// CHECK-DAG: %[[VSCALE:.*]] = vector.vscale -// CHECK-NEXT: %[[SVL_B:.*]] = arith.muli %[[VSCALE]], %[[MIN_SVL_B]] : index -// CHECK-NEXT: scf.for %[[TILE_SLICE:.*]] = %[[C0]] to %[[SVL_B]] step %[[C1]] { -// CHECK-NEXT: %[[TILE_SLICE_PLUS_OFF0:.*]] = arith.addi %[[TILE_SLICE]], %[[C123]] : index -// CHECK-NEXT: %[[TILE_SLICE_PLUS_OFF0_I64:.*]] = builtin.unrealized_conversion_cast %[[TILE_SLICE_PLUS_OFF0]] : index to i64 -// CHECK-NEXT: %[[ALIGNED_BASE:.*]] = llvm.extractvalue %[[MEM_DESC]][1] : !llvm.struct<(ptr, ptr, i64, array<2 x i64>, array<2 x i64>)> -// CHECK-NEXT: %[[STRIDE0:.*]] = llvm.extractvalue %[[MEM_DESC]][4, 0] : !llvm.struct<(ptr, ptr, i64, array<2 x i64>, array<2 x i64>)> -// CHECK-NEXT: %[[OFF0:.*]] = llvm.mul %[[TILE_SLICE_PLUS_OFF0_I64]], %[[STRIDE0]] : i64 -// CHECK-NEXT: %[[OFF1:.*]] = llvm.add %[[OFF0]], %[[C0_I64]] : i64 -// CHECK-NEXT: %[[GEP:.*]] = llvm.getelementptr %[[ALIGNED_BASE]]{{\[}}%[[OFF1]]] : (!llvm.ptr, i64) -> !llvm.ptr, i8 -// CHECK-NEXT: %[[TILE_SLICE_I32:.*]] = arith.index_castui %[[TILE_SLICE]] : index to i32 -// CHECK-NEXT: "arm_sme.intr.ld1b.horiz"(%[[PTRUE_ALL]], %[[GEP]], %[[TILE_SLICE_I32]]) <{tile_id = 0 : i32}> : (vector<[16]xi1>, !llvm.ptr, i32) -> () -// CHECK-NEXT: } -func.func @vector_load_i8_with_offset(%arg0 : memref) -> vector<[16]x[16]xi8> { - %c0 = arith.constant 0 : index - %c123 = arith.constant 123 : index - %tile = vector.load %arg0[%c123, %c0] : memref, vector<[16]x[16]xi8> - return %tile : vector<[16]x[16]xi8> -} - -// ----- - -// CHECK-LABEL: @vector_load_i8_from_rank_1_memref( -// CHECK-SAME: %[[ARG0:.*]]: memref) -// CHECK-DAG: %[[MEM_DESC:.*]] = builtin.unrealized_conversion_cast %[[ARG0]] : memref to !llvm.struct<(ptr, ptr, i64, array<1 x i64>, array<1 x i64>)> -// CHECK-DAG: %[[C0:.*]] = arith.constant 0 : index -// CHECK-DAG: %[[C1:.*]] = arith.constant 1 : index -// CHECK-DAG: %[[MIN_SVL_B:.*]] = arith.constant 16 : index -// CHECK-DAG: %[[PTRUE_ALL:.*]] = arith.constant dense : vector<[16]xi1> -// CHECK-DAG: %[[VSCALE:.*]] = vector.vscale -// CHECK-NEXT: %[[SVL_B:.*]] = arith.muli %[[VSCALE]], %[[MIN_SVL_B]] : index -// CHECK-NEXT: scf.for %[[TILE_SLICE:.*]] = %[[C0]] to %[[SVL_B]] step %[[C1]] { -// CHECK-NEXT: %[[TILE_SLICE_IDX:.*]] = arith.muli %[[TILE_SLICE]], %[[SVL_B]] : index -// CHECK-NEXT: %[[TILE_SLICE_IDX_I64:.*]] = builtin.unrealized_conversion_cast %[[TILE_SLICE_IDX]] : index to i64 -// CHECK-NEXT: %[[ALIGNED_BASE:.*]] = llvm.extractvalue %[[MEM_DESC]][1] : !llvm.struct<(ptr, ptr, i64, array<1 x i64>, array<1 x i64>)> -// CHECK-NEXT: %[[GEP:.*]] = llvm.getelementptr %[[ALIGNED_BASE]]{{\[}}%[[TILE_SLICE_IDX_I64]]] : (!llvm.ptr, i64) -> !llvm.ptr, i8 -// CHECK-NEXT: %[[TILE_SLICE_I32:.*]] = arith.index_castui %[[TILE_SLICE]] : index to i32 -// CHECK-NEXT: "arm_sme.intr.ld1b.horiz"(%[[PTRUE_ALL]], %[[GEP]], %[[TILE_SLICE_I32]]) <{tile_id = 0 : i32}> : (vector<[16]xi1>, !llvm.ptr, i32) -> () -// CHECK-NEXT: } -func.func @vector_load_i8_from_rank_1_memref(%arg0 : memref) -> vector<[16]x[16]xi8> { - %c0 = arith.constant 0 : index - %tile = vector.load %arg0[%c0] : memref, vector<[16]x[16]xi8> - return %tile : vector<[16]x[16]xi8> -} - - -// ----- - -// CHECK-LABEL: @vector_load_i16( -// CHECK-SAME: %[[ARG0:.*]]: memref) -// CHECK-DAG: %[[MIN_SVL_H:.*]] = arith.constant 8 : index -// CHECK: %[[SVL_H:.*]] = arith.muli %{{.*}}, %[[MIN_SVL_H]] : index -// CHECK: arm_sme.intr.ld1h.horiz -// CHECK-SAME: tile_id = 0 -func.func @vector_load_i16(%arg0 : memref) -> vector<[8]x[8]xi16> { - %c0 = arith.constant 0 : index - %tile = vector.load %arg0[%c0, %c0] : memref, vector<[8]x[8]xi16> - return %tile : vector<[8]x[8]xi16> -} - -// ----- - -// CHECK-LABEL: @vector_load_i32( -// CHECK-SAME: %[[ARG0:.*]]: memref) -// CHECK-DAG: %[[MIN_SVL_S:.*]] = arith.constant 4 : index -// CHECK: %[[SVL_S:.*]] = arith.muli %{{.*}}, %[[MIN_SVL_S]] : index -// CHECK: arm_sme.intr.ld1w.horiz -// CHECK-SAME: tile_id = 0 -func.func @vector_load_i32(%arg0 : memref) -> vector<[4]x[4]xi32> { - %c0 = arith.constant 0 : index - %tile = vector.load %arg0[%c0, %c0] : memref, vector<[4]x[4]xi32> - return %tile : vector<[4]x[4]xi32> -} - -// ----- - -// CHECK-LABEL: @vector_load_i64( -// CHECK-SAME: %[[ARG0:.*]]: memref) -// CHECK-DAG: %[[MIN_SVL_D:.*]] = arith.constant 2 : index -// CHECK: %[[SVL_D:.*]] = arith.muli %{{.*}}, %[[MIN_SVL_D]] : index -// CHECK: arm_sme.intr.ld1d.horiz -// CHECK-SAME: tile_id = 0 -func.func @vector_load_i64(%arg0 : memref) -> vector<[2]x[2]xi64> { - %c0 = arith.constant 0 : index - %tile = vector.load %arg0[%c0, %c0] : memref, vector<[2]x[2]xi64> - return %tile : vector<[2]x[2]xi64> -} - -// ----- - -// CHECK-LABEL: @vector_load_f16( -// CHECK-SAME: %[[ARG0:.*]]: memref) -// CHECK-DAG: %[[MIN_SVL_H:.*]] = arith.constant 8 : index -// CHECK: %[[SVL_H:.*]] = arith.muli %{{.*}}, %[[MIN_SVL_H]] : index -// CHECK: arm_sme.intr.ld1h.horiz -// CHECK-SAME: tile_id = 0 -func.func @vector_load_f16(%arg0 : memref) -> vector<[8]x[8]xf16> { - %c0 = arith.constant 0 : index - %tile = vector.load %arg0[%c0, %c0] : memref, vector<[8]x[8]xf16> - return %tile : vector<[8]x[8]xf16> -} - -// ----- - -// CHECK-LABEL: @vector_load_bf16( -// CHECK-SAME: %[[ARG0:.*]]: memref) -// CHECK-DAG: %[[MIN_SVL_H:.*]] = arith.constant 8 : index -// CHECK: %[[SVL_H:.*]] = arith.muli %{{.*}}, %[[MIN_SVL_H]] : index -// CHECK: arm_sme.intr.ld1h.horiz -// CHECK-SAME: tile_id = 0 -func.func @vector_load_bf16(%arg0 : memref) -> vector<[8]x[8]xbf16> { - %c0 = arith.constant 0 : index - %tile = vector.load %arg0[%c0, %c0] : memref, vector<[8]x[8]xbf16> - return %tile : vector<[8]x[8]xbf16> -} - -// ----- - -// CHECK-LABEL: @vector_load_f32( -// CHECK-SAME: %[[ARG0:.*]]: memref) -// CHECK-DAG: %[[MIN_SVL_S:.*]] = arith.constant 4 : index -// CHECK: %[[SVL_S:.*]] = arith.muli %{{.*}}, %[[MIN_SVL_S]] : index -// CHECK: arm_sme.intr.ld1w.horiz -// CHECK-SAME: tile_id = 0 -func.func @vector_load_f32(%arg0 : memref) -> vector<[4]x[4]xf32> { - %c0 = arith.constant 0 : index - %tile = vector.load %arg0[%c0, %c0] : memref, vector<[4]x[4]xf32> - return %tile : vector<[4]x[4]xf32> -} - -// ----- - -// CHECK-LABEL: @vector_load_f64( -// CHECK-SAME: %[[ARG0:.*]]: memref) -// CHECK-DAG: %[[MIN_SVL_D:.*]] = arith.constant 2 : index -// CHECK: %[[SVL_D:.*]] = arith.muli %{{.*}}, %[[MIN_SVL_D]] : index -// CHECK: arm_sme.intr.ld1d.horiz -// CHECK-SAME: tile_id = 0 -func.func @vector_load_f64(%arg0 : memref) -> vector<[2]x[2]xf64> { - %c0 = arith.constant 0 : index - %tile = vector.load %arg0[%c0, %c0] : memref, vector<[2]x[2]xf64> - return %tile : vector<[2]x[2]xf64> -} - -// ----- - -// CHECK-LABEL: @vector_load_i128( -// CHECK-SAME: %[[ARG0:.*]]: memref) -// CHECK: arm_sme.intr.ld1q.horiz -// CHECK-SAME: tile_id = 0 -func.func @vector_load_i128(%arg0 : memref) -> vector<[1]x[1]xi128> { - %c0 = arith.constant 0 : index - %tile = vector.load %arg0[%c0, %c0] : memref, vector<[1]x[1]xi128> - return %tile : vector<[1]x[1]xi128> -} - -//===----------------------------------------------------------------------===// -// vector.store -//===----------------------------------------------------------------------===// - -// ----- - -// CHECK-LABEL: @vector_store_i8( -// CHECK-SAME: %[[ARG0:.*]]: memref) -// CHECK-DAG: %[[MEM_DESC:.*]] = builtin.unrealized_conversion_cast %[[ARG0]] : memref to !llvm.struct<(ptr, ptr, i64, array<2 x i64>, array<2 x i64>)> -// CHECK-DAG: %[[C0:.*]] = arith.constant 0 : index -// CHECK-DAG: %[[C1:.*]] = arith.constant 1 : index -// CHECK-DAG: %[[MIN_SVL_B:.*]] = arith.constant 16 : index -// CHECK-DAG: %[[C0_I64:.*]] = builtin.unrealized_conversion_cast %[[C0]] : index to i64 -// CHECK-DAG: %[[PTRUE_ALL:.*]] = arith.constant dense : vector<[16]xi1> -// CHECK-DAG: %[[VSCALE:.*]] = vector.vscale -// CHECK-NEXT: %[[SVL_B:.*]] = arith.muli %[[VSCALE]], %[[MIN_SVL_B]] : index -// CHECK-NEXT: scf.for %[[TILE_SLICE:.*]] = %[[C0]] to %[[SVL_B]] step %[[C1]] { -// CHECK: %[[TILE_SLICE_I64:.*]] = builtin.unrealized_conversion_cast %[[TILE_SLICE]] : index to i64 -// CHECK-NEXT: %[[ALIGNED_BASE:.*]] = llvm.extractvalue %[[MEM_DESC]][1] : !llvm.struct<(ptr, ptr, i64, array<2 x i64>, array<2 x i64>)> -// CHECK-NEXT: %[[STRIDE0:.*]] = llvm.extractvalue %[[MEM_DESC]][4, 0] : !llvm.struct<(ptr, ptr, i64, array<2 x i64>, array<2 x i64>)> -// CHECK-NEXT: %[[OFF0:.*]] = llvm.mul %[[TILE_SLICE_I64]], %[[STRIDE0]] : i64 -// CHECK-NEXT: %[[OFF1:.*]] = llvm.add %[[OFF0]], %[[C0_I64]] : i64 -// CHECK-NEXT: %[[GEP:.*]] = llvm.getelementptr %[[ALIGNED_BASE]]{{\[}}%[[OFF1]]] : (!llvm.ptr, i64) -> !llvm.ptr, i8 -// CHECK-NEXT: %[[TILE_SLICE_I32:.*]] = arith.index_castui %[[TILE_SLICE]] : index to i32 -// CHECK-NEXT: "arm_sme.intr.st1b.horiz"(%[[PTRUE_ALL]], %[[GEP]], %[[TILE_SLICE_I32]]) <{tile_id = 0 : i32}> : (vector<[16]xi1>, !llvm.ptr, i32) -> () -// CHECK-NEXT: } -// CHECK-NEXT: return -func.func @vector_store_i8(%arg0 : memref) { - %c0 = arith.constant 0 : index - %tile = arm_sme.get_tile : vector<[16]x[16]xi8> - vector.store %tile, %arg0[%c0, %c0] : memref, vector<[16]x[16]xi8> - return -} - -// ----- - -// CHECK-LABEL: @vector_store_i16( -// CHECK-SAME: %[[ARG0:.*]]: memref) -// CHECK: %[[MIN_SVL_H:.*]] = arith.constant 8 : index -// CHECK: %[[SVL_H:.*]] = arith.muli %{{.*}}, %[[MIN_SVL_H]] : index -// CHECK: arm_sme.intr.st1h.horiz -// CHECK-SAME: tile_id = 0 -func.func @vector_store_i16(%arg0 : memref) { - %c0 = arith.constant 0 : index - %tile = arm_sme.get_tile : vector<[8]x[8]xi16> - vector.store %tile, %arg0[%c0, %c0] : memref, vector<[8]x[8]xi16> - return -} - -// ----- - -// CHECK-LABEL: @vector_store_i32( -// CHECK-SAME: %[[ARG0:.*]]: memref) -// CHECK: %[[MIN_SVL_S:.*]] = arith.constant 4 : index -// CHECK: %[[SVL_S:.*]] = arith.muli %{{.*}}, %[[MIN_SVL_S]] : index -// CHECK: arm_sme.intr.st1w.horiz -// CHECK-SAME: tile_id = 0 -func.func @vector_store_i32(%arg0 : memref) { - %c0 = arith.constant 0 : index - %tile = arm_sme.get_tile : vector<[4]x[4]xi32> - vector.store %tile, %arg0[%c0, %c0] : memref, vector<[4]x[4]xi32> - return -} - -// ----- - -// CHECK-LABEL: @vector_store_i64( -// CHECK-SAME: %[[ARG0:.*]]: memref) -// CHECK: %[[MIN_SVL_D:.*]] = arith.constant 2 : index -// CHECK: %[[SVL_D:.*]] = arith.muli %{{.*}}, %[[MIN_SVL_D]] : index -// CHECK: arm_sme.intr.st1d.horiz -// CHECK-SAME: tile_id = 0 -func.func @vector_store_i64(%arg0 : memref) { - %c0 = arith.constant 0 : index - %tile = arm_sme.get_tile : vector<[2]x[2]xi64> - vector.store %tile, %arg0[%c0, %c0] : memref, vector<[2]x[2]xi64> - return -} - -// ----- - -// CHECK-LABEL: @vector_store_f16( -// CHECK-SAME: %[[ARG0:.*]]: memref) -// CHECK: %[[MIN_SVL_H:.*]] = arith.constant 8 : index -// CHECK: %[[SVL_H:.*]] = arith.muli %{{.*}}, %[[MIN_SVL_H]] : index -// CHECK: arm_sme.intr.st1h.horiz -// CHECK-SAME: tile_id = 0 -func.func @vector_store_f16(%arg0 : memref) { - %c0 = arith.constant 0 : index - %tile = arm_sme.get_tile : vector<[8]x[8]xf16> - vector.store %tile, %arg0[%c0, %c0] : memref, vector<[8]x[8]xf16> - return -} - -// ----- - -// CHECK-LABEL: @vector_store_bf16( -// CHECK-SAME: %[[ARG0:.*]]: memref) -// CHECK: %[[MIN_SVL_H:.*]] = arith.constant 8 : index -// CHECK: %[[SVL_H:.*]] = arith.muli %{{.*}}, %[[MIN_SVL_H]] : index -// CHECK: arm_sme.intr.st1h.horiz -// CHECK-SAME: tile_id = 0 -func.func @vector_store_bf16(%arg0 : memref) { - %c0 = arith.constant 0 : index - %tile = arm_sme.get_tile : vector<[8]x[8]xbf16> - vector.store %tile, %arg0[%c0, %c0] : memref, vector<[8]x[8]xbf16> - return -} -// ----- - -// CHECK-LABEL: @vector_store_f32( -// CHECK-SAME: %[[ARG0:.*]]: memref) -// CHECK: %[[MIN_SVL_S:.*]] = arith.constant 4 : index -// CHECK: %[[SVL_S:.*]] = arith.muli %{{.*}}, %[[MIN_SVL_S]] : index -// CHECK: arm_sme.intr.st1w.horiz -// CHECK-SAME: tile_id = 0 -func.func @vector_store_f32(%arg0 : memref) { - %c0 = arith.constant 0 : index - %tile = arm_sme.get_tile : vector<[4]x[4]xf32> - vector.store %tile, %arg0[%c0, %c0] : memref, vector<[4]x[4]xf32> - return -} - -// ----- - -// CHECK-LABEL: @vector_store_f64( -// CHECK-SAME: %[[ARG0:.*]]: memref) -// CHECK: %[[MIN_SVL_D:.*]] = arith.constant 2 : index -// CHECK: %[[SVL_D:.*]] = arith.muli %{{.*}}, %[[MIN_SVL_D]] : index -// CHECK: arm_sme.intr.st1d.horiz -// CHECK-SAME: tile_id = 0 -func.func @vector_store_f64(%arg0 : memref) { - %c0 = arith.constant 0 : index - %tile = arm_sme.get_tile : vector<[2]x[2]xf64> - vector.store %tile, %arg0[%c0, %c0] : memref, vector<[2]x[2]xf64> - return -} - -// ----- - -// CHECK-LABEL: @vector_store_i128( -// CHECK-SAME: %[[ARG0:.*]]: memref) -// CHECK: arm_sme.intr.st1q.horiz -// CHECK-SAME: tile_id = 0 -func.func @vector_store_i128(%arg0 : memref) { - %c0 = arith.constant 0 : index - %tile = arm_sme.get_tile : vector<[1]x[1]xi128> - vector.store %tile, %arg0[%c0, %c0] : memref, vector<[1]x[1]xi128> - return -} - -//===----------------------------------------------------------------------===// -// vector.outerproduct -//===----------------------------------------------------------------------===// - -// ----- - -// CHECK-LABEL: @vector_outerproduct_add_f16 -// CHECK-SAME: (%[[LHS:.*]]: vector<[8]xf16>, %[[RHS:.*]]: vector<[8]xf16>) -func.func @vector_outerproduct_add_f16(%lhs : vector<[8]xf16>, %rhs : vector<[8]xf16>) { - // CHECK: %[[PTRUE_ALL:.*]] = arith.constant dense : vector<[8]xi1> - // CHECK: "arm_sme.intr.mopa"(%[[PTRUE_ALL]], %[[PTRUE_ALL]], %[[LHS]], %[[RHS]]) <{tile_id = 0 : i32}> : (vector<[8]xi1>, vector<[8]xi1>, vector<[8]xf16>, vector<[8]xf16>) - %acc = arm_sme.get_tile : vector<[8]x[8]xf16> - %0 = vector.outerproduct %lhs, %rhs, %acc {kind = #vector.kind} : vector<[8]xf16>, vector<[8]xf16> - "prevent.dce"(%0) : (vector<[8]x[8]xf16>) -> () -} - -// ----- - -// CHECK-LABEL: @vector_outerproduct_add_bf16 -func.func @vector_outerproduct_add_bf16(%lhs : vector<[8]xbf16>, %rhs : vector<[8]xbf16>) { - // CHECK: "arm_sme.intr.mopa"({{.*}}) <{tile_id = 0 : i32}> : (vector<[8]xi1>, vector<[8]xi1>, vector<[8]xbf16>, vector<[8]xbf16>) - %acc = arm_sme.get_tile : vector<[8]x[8]xbf16> - %0 = vector.outerproduct %lhs, %rhs, %acc {kind = #vector.kind} : vector<[8]xbf16>, vector<[8]xbf16> - "prevent.dce"(%0) : (vector<[8]x[8]xbf16>) -> () -} - -// ----- - -// CHECK-LABEL: @vector_outerproduct_add_f32 -func.func @vector_outerproduct_add_f32(%lhs : vector<[4]xf32>, %rhs : vector<[4]xf32>) { - // CHECK: "arm_sme.intr.mopa"({{.*}}) <{tile_id = 0 : i32}> : (vector<[4]xi1>, vector<[4]xi1>, vector<[4]xf32>, vector<[4]xf32>) - %acc = arm_sme.get_tile : vector<[4]x[4]xf32> - %0 = vector.outerproduct %lhs, %rhs, %acc {kind = #vector.kind} : vector<[4]xf32>, vector<[4]xf32> - "prevent.dce"(%0) : (vector<[4]x[4]xf32>) -> () -} - -// ----- - -// CHECK-LABEL: @vector_outerproduct_add_f64 -func.func @vector_outerproduct_add_f64(%lhs : vector<[2]xf64>, %rhs : vector<[2]xf64>) { - // CHECK: "arm_sme.intr.mopa"({{.*}}) <{tile_id = 0 : i32}> : (vector<[2]xi1>, vector<[2]xi1>, vector<[2]xf64>, vector<[2]xf64>) - %acc = arm_sme.get_tile : vector<[2]x[2]xf64> - %0 = vector.outerproduct %lhs, %rhs, %acc {kind = #vector.kind} : vector<[2]xf64>, vector<[2]xf64> - "prevent.dce"(%0) : (vector<[2]x[2]xf64>) -> () -} - -// ----- - -// CHECK-LABEL: @vector_outerproduct_no_accumulator -func.func @vector_outerproduct_no_accumulator(%lhs : vector<[2]xf64>, %rhs : vector<[2]xf64>) { - // CHECK: "arm_sme.intr.zero"() <{tile_mask = 1 : i32}> : () -> () - // CHECK: "arm_sme.intr.mopa"({{.*}}) <{tile_id = 0 : i32}> : (vector<[2]xi1>, vector<[2]xi1>, vector<[2]xf64>, vector<[2]xf64>) - %0 = vector.outerproduct %lhs, %rhs {kind = #vector.kind} : vector<[2]xf64>, vector<[2]xf64> - "prevent.dce"(%0) : (vector<[2]x[2]xf64>) -> () -} - -// ----- - -// CHECK-LABEL: @vector_outerproduct_masked_f32 -// CHECK-SAME: (%[[LHS:.*]]: vector<[4]xf32>, %[[RHS:.*]]: vector<[4]xf32>, %[[DIM0:.*]]: index, %[[DIM1:.*]]: index -func.func @vector_outerproduct_masked_f32(%lhs : vector<[4]xf32>, %rhs : vector<[4]xf32>, %dim0 : index, %dim1 : index) { - // CHECK: %[[LHS_MASK:.*]] = vector.create_mask %[[DIM0]] : vector<[4]xi1> - // CHECK: %[[RHS_MASK:.*]] = vector.create_mask %[[DIM1]] : vector<[4]xi1> - // CHECK: "arm_sme.intr.mopa"(%[[LHS_MASK]], %[[RHS_MASK]], %[[LHS]], %[[RHS]]) <{tile_id = 0 : i32}> : (vector<[4]xi1>, vector<[4]xi1>, vector<[4]xf32>, vector<[4]xf32>) - %acc = arm_sme.get_tile : vector<[4]x[4]xf32> - %mask = vector.create_mask %dim0, %dim1 : vector<[4]x[4]xi1> - %result = vector.mask %mask { vector.outerproduct %lhs, %rhs, %acc {kind = #vector.kind} : vector<[4]xf32>, vector<[4]xf32> } : vector<[4]x[4]xi1> -> vector<[4]x[4]xf32> - "prevent.dce"(%result) : (vector<[4]x[4]xf32>) -> () -} - -// ----- - -// CHECK-LABEL: @vector_outerproduct_masked_f16 -// CHECK-SAME: (%[[LHS:.*]]: vector<[8]xf16>, %[[RHS:.*]]: vector<[8]xf16>, -func.func @vector_outerproduct_masked_f16(%lhs : vector<[8]xf16>, %rhs : vector<[8]xf16>, %dim0 : index, %dim1 : index) { - // CHECK: vector.create_mask {{.*}} : vector<[8]xi1> - // CHECK: vector.create_mask {{.*}} : vector<[8]xi1> - // CHECK: "arm_sme.intr.mopa"({{.*}}) <{tile_id = 0 : i32}> : (vector<[8]xi1>, vector<[8]xi1>, vector<[8]xf16>, vector<[8]xf16>) - %acc = arm_sme.get_tile : vector<[8]x[8]xf16> - %mask = vector.create_mask %dim0, %dim1 : vector<[8]x[8]xi1> - %result = vector.mask %mask { vector.outerproduct %lhs, %rhs, %acc {kind = #vector.kind} : vector<[8]xf16>, vector<[8]xf16> } : vector<[8]x[8]xi1> -> vector<[8]x[8]xf16> - "prevent.dce"(%result) : (vector<[8]x[8]xf16>) -> () -} - -// ----- - -// CHECK-LABEL: @vector_outerproduct_masked_bf16 -// CHECK-SAME: (%[[LHS:.*]]: vector<[8]xbf16>, %[[RHS:.*]]: vector<[8]xbf16> -func.func @vector_outerproduct_masked_bf16(%lhs : vector<[8]xbf16>, %rhs : vector<[8]xbf16>, %dim0 : index, %dim1 : index) { - // CHECK: vector.create_mask {{.*}} : vector<[8]xi1> - // CHECK: vector.create_mask {{.*}} : vector<[8]xi1> - // CHECK: "arm_sme.intr.mopa"({{.*}}) <{tile_id = 0 : i32}> : (vector<[8]xi1>, vector<[8]xi1>, vector<[8]xbf16>, vector<[8]xbf16>) - %acc = arm_sme.get_tile : vector<[8]x[8]xbf16> - %mask = vector.create_mask %dim0, %dim1 : vector<[8]x[8]xi1> - %result = vector.mask %mask { vector.outerproduct %lhs, %rhs, %acc {kind = #vector.kind} : vector<[8]xbf16>, vector<[8]xbf16> } : vector<[8]x[8]xi1> -> vector<[8]x[8]xbf16> - "prevent.dce"(%result) : (vector<[8]x[8]xbf16>) -> () -} - -// ----- - -// CHECK-LABEL: @vector_outerproduct_masked_f64 -// CHECK-SAME: (%[[LHS:.*]]: vector<[2]xf64>, %[[RHS:.*]]: vector<[2]xf64>, -func.func @vector_outerproduct_masked_f64(%lhs : vector<[2]xf64>, %rhs : vector<[2]xf64>, %dim0 : index, %dim1 : index) { - // CHECK: vector.create_mask {{.*}} : vector<[2]xi1> - // CHECK: vector.create_mask {{.*}} : vector<[2]xi1> - // CHECK: "arm_sme.intr.mopa"({{.*}}) <{tile_id = 0 : i32}> : (vector<[2]xi1>, vector<[2]xi1>, vector<[2]xf64>, vector<[2]xf64>) - %acc = arm_sme.get_tile : vector<[2]x[2]xf64> - %mask = vector.create_mask %dim0, %dim1 : vector<[2]x[2]xi1> - %result = vector.mask %mask { vector.outerproduct %lhs, %rhs, %acc {kind = #vector.kind} : vector<[2]xf64>, vector<[2]xf64> } : vector<[2]x[2]xi1> -> vector<[2]x[2]xf64> - "prevent.dce"(%result) : (vector<[2]x[2]xf64>) -> () -} - -//===----------------------------------------------------------------------===// -// vector.insert -//===----------------------------------------------------------------------===// - -// ----- - -// CHECK-LABEL: @vector_insert_slice_i32( -// CHECK-SAME: %[[SLICE:.*]]: vector<[4]xi32>, -// CHECK-SAME: %[[INDEX:.*]]: index) -func.func @vector_insert_slice_i32(%slice: vector<[4]xi32>, %row: index) -> vector<[4]x[4]xi32>{ - // CHECK-NEXT: %[[PTRUE:.*]] = arith.constant dense : vector<[4]xi1> - // CHECK: %[[TILE_SLICE_INDEX:.*]] = arith.index_castui %[[INDEX]] : index to i32 - // CHECK-NEXT: "arm_sme.intr.write.horiz"(%[[TILE_SLICE_INDEX]], %[[PTRUE]], %[[SLICE]]) <{tile_id = 0 : i32}> : (i32, vector<[4]xi1>, vector<[4]xi32>) -> () - %tile = arm_sme.get_tile : vector<[4]x[4]xi32> - %new_tile = vector.insert %slice, %tile[%row] : vector<[4]xi32> into vector<[4]x[4]xi32> - return %new_tile : vector<[4]x[4]xi32> -} - -// ----- - -// CHECK-LABEL: @vector_insert_slice_i8 -func.func @vector_insert_slice_i8(%slice: vector<[16]xi8>, %row: index) -> vector<[16]x[16]xi8> { - // CHECK: "arm_sme.intr.write.horiz"(%{{.*}}) <{tile_id = 0 : i32}> : (i32, vector<[16]xi1>, vector<[16]xi8>) -> () - %tile = arm_sme.get_tile : vector<[16]x[16]xi8> - %new_tile = vector.insert %slice, %tile[%row] : vector<[16]xi8> into vector<[16]x[16]xi8> - return %new_tile : vector<[16]x[16]xi8> -} - -// ----- - -// CHECK-LABEL: @vector_insert_slice_i16 -func.func @vector_insert_slice_i16(%slice: vector<[8]xi16>, %row: index) -> vector<[8]x[8]xi16> { - // CHECK: "arm_sme.intr.write.horiz"(%{{.*}}) <{tile_id = 0 : i32}> : (i32, vector<[8]xi1>, vector<[8]xi16>) -> () - %tile = arm_sme.get_tile : vector<[8]x[8]xi16> - %new_tile = vector.insert %slice, %tile[%row] : vector<[8]xi16> into vector<[8]x[8]xi16> - return %new_tile : vector<[8]x[8]xi16> -} - -// ----- - -// CHECK-LABEL: @vector_insert_slice_i64 -func.func @vector_insert_slice_i64(%slice: vector<[2]xi64>, %row: index) -> vector<[2]x[2]xi64> { - // CHECK: "arm_sme.intr.write.horiz"(%{{.*}}) <{tile_id = 0 : i32}> : (i32, vector<[2]xi1>, vector<[2]xi64>) -> () - %tile = arm_sme.get_tile : vector<[2]x[2]xi64> - %new_tile = vector.insert %slice, %tile[%row] : vector<[2]xi64> into vector<[2]x[2]xi64> - return %new_tile : vector<[2]x[2]xi64> -} - -// ----- - -// CHECK-LABEL: @vector_insert_slice_i128 -func.func @vector_insert_slice_i128(%slice: vector<[1]xi128>, %row: index) -> vector<[1]x[1]xi128> { - // CHECK: "arm_sme.intr.write.horiz"(%{{.*}}) <{tile_id = 0 : i32}> : (i32, vector<[1]xi1>, vector<[1]xi128>) -> () - %tile = arm_sme.get_tile : vector<[1]x[1]xi128> - %new_tile = vector.insert %slice, %tile[%row] : vector<[1]xi128> into vector<[1]x[1]xi128> - return %new_tile : vector<[1]x[1]xi128> -} - -// ----- - -// CHECK-LABEL: @vector_insert_slice_f16 -func.func @vector_insert_slice_f16(%slice: vector<[8]xf16>, %row: index) -> vector<[8]x[8]xf16> { - // CHECK: "arm_sme.intr.write.horiz"(%{{.*}}) <{tile_id = 0 : i32}> : (i32, vector<[8]xi1>, vector<[8]xf16>) -> () - %tile = arm_sme.get_tile : vector<[8]x[8]xf16> - %new_tile = vector.insert %slice, %tile[%row] : vector<[8]xf16> into vector<[8]x[8]xf16> - return %new_tile : vector<[8]x[8]xf16> -} - -// ----- - -// CHECK-LABEL: @vector_insert_slice_bf16 -func.func @vector_insert_slice_bf16(%slice: vector<[8]xbf16>, %row: index) -> vector<[8]x[8]xbf16> { - // CHECK: "arm_sme.intr.write.horiz"(%{{.*}}) <{tile_id = 0 : i32}> : (i32, vector<[8]xi1>, vector<[8]xbf16>) -> () - %tile = arm_sme.get_tile : vector<[8]x[8]xbf16> - %new_tile = vector.insert %slice, %tile[%row] : vector<[8]xbf16> into vector<[8]x[8]xbf16> - return %new_tile : vector<[8]x[8]xbf16> -} - -// ----- - -// CHECK-LABEL: @vector_insert_slice_f32 -func.func @vector_insert_slice_f32(%slice: vector<[4]xf32>, %row: index) -> vector<[4]x[4]xf32> { - // CHECK: "arm_sme.intr.write.horiz"(%{{.*}}) <{tile_id = 0 : i32}> : (i32, vector<[4]xi1>, vector<[4]xf32>) -> () - %tile = arm_sme.get_tile : vector<[4]x[4]xf32> - %new_tile = vector.insert %slice, %tile[%row] : vector<[4]xf32> into vector<[4]x[4]xf32> - return %new_tile : vector<[4]x[4]xf32> -} - -// ----- - -// CHECK-LABEL: @vector_insert_slice_f64 -func.func @vector_insert_slice_f64(%slice: vector<[2]xf64>, %row: index) -> vector<[2]x[2]xf64> { - // CHECK: "arm_sme.intr.write.horiz"(%{{.*}}) <{tile_id = 0 : i32}> : (i32, vector<[2]xi1>, vector<[2]xf64>) -> () - %tile = arm_sme.get_tile : vector<[2]x[2]xf64> - %new_tile = vector.insert %slice, %tile[%row] : vector<[2]xf64> into vector<[2]x[2]xf64> - return %new_tile : vector<[2]x[2]xf64> -} - -// ----- - -// CHECK-LABEL: @vector_insert_element_i32( -// CHECK-SAME: %[[EL:.*]]: i32, -// CHECK-SAME: %[[ROW:.*]]: index, -// CHECK-SAME: %[[COL:.*]]: index) -func.func @vector_insert_element_i32(%el: i32, %row: index, %col: index) -> vector<[4]x[4]xi32> { - // CHECK-DAG: %[[ZERO_VEC:.*]] = arith.constant dense<0> : vector<[4]xi32> - // CHECK-DAG: %[[PTRUE:.*]] = arith.constant dense : vector<[4]xi1> - // CHECK-DAG: %[[ROW_I32:.*]] = arith.index_cast %[[ROW]] : index to i32 - // CHECK-NEXT: %[[SLICE:.*]] = "arm_sme.intr.read.horiz"(%[[ZERO_VEC]], %[[PTRUE]], %[[ROW_I32]]) <{tile_id = 0 : i32}> : (vector<[4]xi32>, vector<[4]xi1>, i32) -> vector<[4]xi32> - // CHECK-NEXT: %[[NEW_SLICE:.*]] = vector.insert %[[EL]], %[[SLICE]] [%[[COL]]] : i32 into vector<[4]xi32> - // CHECK-NEXT: %[[SLICE_INDEX:.*]] = arith.index_castui %[[ROW]] : index to i32 - // CHECK-NEXT: "arm_sme.intr.write.horiz"(%[[SLICE_INDEX]], %[[PTRUE]], %[[NEW_SLICE]]) <{tile_id = 0 : i32}> : (i32, vector<[4]xi1>, vector<[4]xi32>) -> () - %tile = arm_sme.get_tile : vector<[4]x[4]xi32> - %new_tile = vector.insert %el, %tile[%row, %col] : i32 into vector<[4]x[4]xi32> - return %new_tile : vector<[4]x[4]xi32> -} - -// ----- - -// CHECK-LABEL: @vector_insert_element_i8 -func.func @vector_insert_element_i8(%el: i8, %row: index, %col: index) -> vector<[16]x[16]xi8> { - // CHECK: %{{.*}} = "arm_sme.intr.read.horiz"(%{{.*}}) <{tile_id = 0 : i32}> : (vector<[16]xi8>, vector<[16]xi1>, i32) -> vector<[16]xi8> - // CHECK: "arm_sme.intr.write.horiz"(%{{.*}}) <{tile_id = 0 : i32}> : (i32, vector<[16]xi1>, vector<[16]xi8>) -> () - %tile = arm_sme.get_tile : vector<[16]x[16]xi8> - %new_tile = vector.insert %el, %tile[%row, %col] : i8 into vector<[16]x[16]xi8> - return %new_tile : vector<[16]x[16]xi8> -} - -// ----- - -// CHECK-LABEL: @vector_insert_element_i16 -func.func @vector_insert_element_i16(%el: i16, %row: index, %col: index) -> vector<[8]x[8]xi16> { - // CHECK: %{{.*}} = "arm_sme.intr.read.horiz"(%{{.*}}) <{tile_id = 0 : i32}> : (vector<[8]xi16>, vector<[8]xi1>, i32) -> vector<[8]xi16> - // CHECK: "arm_sme.intr.write.horiz"(%{{.*}}) <{tile_id = 0 : i32}> : (i32, vector<[8]xi1>, vector<[8]xi16>) -> () - %tile = arm_sme.get_tile : vector<[8]x[8]xi16> - %new_tile = vector.insert %el, %tile[%row, %col] : i16 into vector<[8]x[8]xi16> - return %new_tile : vector<[8]x[8]xi16> -} - -// ----- - -// CHECK-LABEL: @vector_insert_element_i64 -func.func @vector_insert_element_i64(%el: i64, %row: index, %col: index) -> vector<[2]x[2]xi64> { - // CHECK: %{{.*}} = "arm_sme.intr.read.horiz"(%{{.*}}) <{tile_id = 0 : i32}> : (vector<[2]xi64>, vector<[2]xi1>, i32) -> vector<[2]xi64> - // CHECK: "arm_sme.intr.write.horiz"(%{{.*}}) <{tile_id = 0 : i32}> : (i32, vector<[2]xi1>, vector<[2]xi64>) -> () - %tile = arm_sme.get_tile : vector<[2]x[2]xi64> - %new_tile = vector.insert %el, %tile[%row, %col] : i64 into vector<[2]x[2]xi64> - return %new_tile : vector<[2]x[2]xi64> -} - -// ----- - -// CHECK-LABEL: @vector_insert_element_i128 -func.func @vector_insert_element_i128(%el: i128, %row: index, %col: index) -> vector<[1]x[1]xi128> { - // CHECK: %{{.*}} = "arm_sme.intr.read.horiz"(%{{.*}}) <{tile_id = 0 : i32}> : (vector<[1]xi128>, vector<[1]xi1>, i32) -> vector<[1]xi128> - // CHECK: "arm_sme.intr.write.horiz"(%{{.*}}) <{tile_id = 0 : i32}> : (i32, vector<[1]xi1>, vector<[1]xi128>) -> () - %tile = arm_sme.get_tile : vector<[1]x[1]xi128> - %new_tile = vector.insert %el, %tile[%row, %col] : i128 into vector<[1]x[1]xi128> - return %new_tile : vector<[1]x[1]xi128> -} - -// ----- - -// CHECK-LABEL: @vector_insert_element_f16 -func.func @vector_insert_element_f16(%el: f16, %row: index, %col: index) -> vector<[8]x[8]xf16> { - // CHECK: %{{.*}} = "arm_sme.intr.read.horiz"(%{{.*}}) <{tile_id = 0 : i32}> : (vector<[8]xf16>, vector<[8]xi1>, i32) -> vector<[8]xf16> - // CHECK: "arm_sme.intr.write.horiz"(%{{.*}}) <{tile_id = 0 : i32}> : (i32, vector<[8]xi1>, vector<[8]xf16>) -> () - %tile = arm_sme.get_tile : vector<[8]x[8]xf16> - %new_tile = vector.insert %el, %tile[%row, %col] : f16 into vector<[8]x[8]xf16> - return %new_tile : vector<[8]x[8]xf16> -} - -// ----- - -// CHECK-LABEL: @vector_insert_element_bf16 -func.func @vector_insert_element_bf16(%el: bf16, %row: index, %col: index) -> vector<[8]x[8]xbf16> { - // CHECK: %{{.*}} = "arm_sme.intr.read.horiz"(%{{.*}}) <{tile_id = 0 : i32}> : (vector<[8]xbf16>, vector<[8]xi1>, i32) -> vector<[8]xbf16> - // CHECK: "arm_sme.intr.write.horiz"(%{{.*}}) <{tile_id = 0 : i32}> : (i32, vector<[8]xi1>, vector<[8]xbf16>) -> () - %tile = arm_sme.get_tile : vector<[8]x[8]xbf16> - %new_tile = vector.insert %el, %tile[%row, %col] : bf16 into vector<[8]x[8]xbf16> - return %new_tile : vector<[8]x[8]xbf16> -} - -// ----- - -// CHECK-LABEL: @vector_insert_element_f32 -func.func @vector_insert_element_f32(%el: f32, %row: index, %col: index) -> vector<[4]x[4]xf32> { - // CHECK: %{{.*}} = "arm_sme.intr.read.horiz"(%{{.*}}) <{tile_id = 0 : i32}> : (vector<[4]xf32>, vector<[4]xi1>, i32) -> vector<[4]xf32> - // CHECK: "arm_sme.intr.write.horiz"(%{{.*}}) <{tile_id = 0 : i32}> : (i32, vector<[4]xi1>, vector<[4]xf32>) -> () - %tile = arm_sme.get_tile : vector<[4]x[4]xf32> - %new_tile = vector.insert %el, %tile[%row, %col] : f32 into vector<[4]x[4]xf32> - return %new_tile : vector<[4]x[4]xf32> -} - -// ----- - -// CHECK-LABEL: @vector_insert_element_f64 -func.func @vector_insert_element_f64(%el: f64, %row: index, %col: index) -> vector<[2]x[2]xf64> { - // CHECK: %{{.*}} = "arm_sme.intr.read.horiz"(%{{.*}}) <{tile_id = 0 : i32}> : (vector<[2]xf64>, vector<[2]xi1>, i32) -> vector<[2]xf64> - // CHECK: "arm_sme.intr.write.horiz"(%{{.*}}) <{tile_id = 0 : i32}> : (i32, vector<[2]xi1>, vector<[2]xf64>) -> () - %tile = arm_sme.get_tile : vector<[2]x[2]xf64> - %new_tile = vector.insert %el, %tile[%row, %col] : f64 into vector<[2]x[2]xf64> - return %new_tile : vector<[2]x[2]xf64> -} - -//===----------------------------------------------------------------------===// -// vector.extract -//===----------------------------------------------------------------------===// - -// ----- - -// CHECK-LABEL: @vector_extract_slice_i32( -// CHECK-SAME: %[[INDEX:.*]]: index) -func.func @vector_extract_slice_i32(%row: index) -> vector<[4]xi32> { - // CHECK-NEXT: %[[PTRUE:.*]] = arith.constant dense : vector<[4]xi1> - // CHECK-NEXT: %[[ZERO_VEC:.*]] = arith.constant dense<0> : vector<[4]xi32> - // CHECK-NEXT: %[[TILE_SLICE_INDEX:.*]] = arith.index_cast %[[INDEX]] : index to i32 - // CHECK-NEXT: %[[SLICE:.*]] = "arm_sme.intr.read.horiz"(%[[ZERO_VEC]], %[[PTRUE]], %[[TILE_SLICE_INDEX]]) <{tile_id = 0 : i32}> : (vector<[4]xi32>, vector<[4]xi1>, i32) -> vector<[4]xi32> - %tile = arm_sme.get_tile : vector<[4]x[4]xi32> - %slice = vector.extract %tile[%row] : vector<[4]xi32> from vector<[4]x[4]xi32> - return %slice : vector<[4]xi32> -} - -// ----- - -// CHECK-LABEL: @vector_extract_slice_i8 -func.func @vector_extract_slice_i8(%row: index) -> vector<[16]xi8> { - // CHECK: %{{.*}} = "arm_sme.intr.read.horiz"(%{{.*}}) <{tile_id = 0 : i32}> : (vector<[16]xi8>, vector<[16]xi1>, i32) -> vector<[16]xi8> - %tile = arm_sme.get_tile : vector<[16]x[16]xi8> - %slice = vector.extract %tile[%row] : vector<[16]xi8> from vector<[16]x[16]xi8> - return %slice : vector<[16]xi8> -} - -// ----- - -// CHECK-LABEL: @vector_extract_slice_i16 -func.func @vector_extract_slice_i16(%row: index) -> vector<[8]xi16> { - // CHECK: %{{.*}} = "arm_sme.intr.read.horiz"(%{{.*}}) <{tile_id = 0 : i32}> : (vector<[8]xi16>, vector<[8]xi1>, i32) -> vector<[8]xi16> - %tile = arm_sme.get_tile : vector<[8]x[8]xi16> - %slice = vector.extract %tile[%row] : vector<[8]xi16> from vector<[8]x[8]xi16> - return %slice : vector<[8]xi16> -} - -// ----- - -// CHECK-LABEL: @vector_extract_slice_i64 -func.func @vector_extract_slice_i64(%row: index) -> vector<[2]xi64> { - // CHECK: %{{.*}} = "arm_sme.intr.read.horiz"(%{{.*}}) <{tile_id = 0 : i32}> : (vector<[2]xi64>, vector<[2]xi1>, i32) -> vector<[2]xi64> - %tile = arm_sme.get_tile : vector<[2]x[2]xi64> - %slice = vector.extract %tile[%row] : vector<[2]xi64> from vector<[2]x[2]xi64> - return %slice : vector<[2]xi64> -} - -// ----- - -// CHECK-LABEL: @vector_extract_slice_i128 -func.func @vector_extract_slice_i128(%row: index) -> vector<[1]xi128> { - // CHECK: %{{.*}} = "arm_sme.intr.read.horiz"(%{{.*}}) <{tile_id = 0 : i32}> : (vector<[1]xi128>, vector<[1]xi1>, i32) -> vector<[1]xi128> - %tile = arm_sme.get_tile : vector<[1]x[1]xi128> - %slice = vector.extract %tile[%row] : vector<[1]xi128> from vector<[1]x[1]xi128> - return %slice : vector<[1]xi128> -} - -// ----- - -// CHECK-LABEL: @vector_extract_slice_f16 -func.func @vector_extract_slice_f16(%row: index) -> vector<[8]xf16> { - // CHECK: %{{.*}} = "arm_sme.intr.read.horiz"(%{{.*}}) <{tile_id = 0 : i32}> : (vector<[8]xf16>, vector<[8]xi1>, i32) -> vector<[8]xf16> - %tile = arm_sme.get_tile : vector<[8]x[8]xf16> - %slice = vector.extract %tile[%row] : vector<[8]xf16> from vector<[8]x[8]xf16> - return %slice : vector<[8]xf16> -} - -// ----- - -// CHECK-LABEL: @vector_extract_slice_bf16 -func.func @vector_extract_slice_bf16(%row: index) -> vector<[8]xbf16> { - // CHECK: %{{.*}} = "arm_sme.intr.read.horiz"(%{{.*}}) <{tile_id = 0 : i32}> : (vector<[8]xbf16>, vector<[8]xi1>, i32) -> vector<[8]xbf16> - %tile = arm_sme.get_tile : vector<[8]x[8]xbf16> - %slice = vector.extract %tile[%row] : vector<[8]xbf16> from vector<[8]x[8]xbf16> - return %slice : vector<[8]xbf16> -} - -// ----- - -// CHECK-LABEL: @vector_extract_slice_f32 -func.func @vector_extract_slice_f32(%row: index) -> vector<[4]xf32> { - // CHECK: %{{.*}} = "arm_sme.intr.read.horiz"(%{{.*}}) <{tile_id = 0 : i32}> : (vector<[4]xf32>, vector<[4]xi1>, i32) -> vector<[4]xf32> - %tile = arm_sme.get_tile : vector<[4]x[4]xf32> - %slice = vector.extract %tile[%row] : vector<[4]xf32> from vector<[4]x[4]xf32> - return %slice : vector<[4]xf32> -} - -// ----- - -// CHECK-LABEL: @vector_extract_slice_f64 -func.func @vector_extract_slice_f64(%row: index) -> vector<[2]xf64> { - // CHECK: %{{.*}} = "arm_sme.intr.read.horiz"(%{{.*}}) <{tile_id = 0 : i32}> : (vector<[2]xf64>, vector<[2]xi1>, i32) -> vector<[2]xf64> - %tile = arm_sme.get_tile : vector<[2]x[2]xf64> - %slice = vector.extract %tile[%row] : vector<[2]xf64> from vector<[2]x[2]xf64> - return %slice : vector<[2]xf64> -} - -// ----- - -// CHECK-LABEL: @vector_extract_element( -// CHECK-SAME: %[[ROW:.*]]: index, -// CHECK-SAME: %[[COL:.*]]: index) -func.func @vector_extract_element(%row: index, %col: index) -> i32 { - // CHECK-NEXT: %[[PTRUE:.*]] = arith.constant dense : vector<[4]xi1> - // CHECK-NEXT: %[[ZERO_VEC:.*]] = arith.constant dense<0> : vector<[4]xi32> - // CHECK-NEXT: %[[ROW_I32:.*]] = arith.index_cast %[[ROW]] : index to i32 - // CHECK-NEXT: %[[SLICE:.*]] = "arm_sme.intr.read.horiz"(%[[ZERO_VEC]], %[[PTRUE]], %[[ROW_I32]]) <{tile_id = 0 : i32}> : (vector<[4]xi32>, vector<[4]xi1>, i32) -> vector<[4]xi32> - // CHECK-NEXT: %[[EL:.*]] = vector.extract %[[SLICE]]{{\[}}%[[COL]]] : i32 from vector<[4]xi32> - %tile = arm_sme.get_tile : vector<[4]x[4]xi32> - %el = vector.extract %tile[%row, %col] : i32 from vector<[4]x[4]xi32> - return %el : i32 -} - -// ----- - -// CHECK-LABEL: @vector_extract_element_i8 -func.func @vector_extract_element_i8(%row: index, %col: index) -> i8 { - // CHECK: %[[SLICE:.*]] = "arm_sme.intr.read.horiz"(%{{.*}}) <{tile_id = 0 : i32}> : (vector<[16]xi8>, vector<[16]xi1>, i32) -> vector<[16]xi8> - // CHECK-NEXT: %{{.*}} = vector.extract %[[SLICE]]{{\[}}%{{.*}}] : i8 from vector<[16]xi8> - %tile = arm_sme.get_tile : vector<[16]x[16]xi8> - %el = vector.extract %tile[%row, %col] : i8 from vector<[16]x[16]xi8> - return %el : i8 -} - -// ----- - -// CHECK-LABEL: @vector_extract_element_i16 -func.func @vector_extract_element_i16(%row: index, %col: index) -> i16 { - // CHECK: %[[SLICE:.*]] = "arm_sme.intr.read.horiz"(%{{.*}}) <{tile_id = 0 : i32}> : (vector<[8]xi16>, vector<[8]xi1>, i32) -> vector<[8]xi16> - // CHECK-NEXT: %{{.*}} = vector.extract %[[SLICE]]{{\[}}%{{.*}}] : i16 from vector<[8]xi16> - %tile = arm_sme.get_tile : vector<[8]x[8]xi16> - %el = vector.extract %tile[%row, %col] : i16 from vector<[8]x[8]xi16> - return %el : i16 -} - -// ----- - -// CHECK-LABEL: @vector_extract_element_i64 -func.func @vector_extract_element_i64(%row: index, %col: index) -> i64 { - // CHECK: %[[SLICE:.*]] = "arm_sme.intr.read.horiz"(%{{.*}}) <{tile_id = 0 : i32}> : (vector<[2]xi64>, vector<[2]xi1>, i32) -> vector<[2]xi64> - // CHECK-NEXT: %{{.*}} = vector.extract %[[SLICE]]{{\[}}%{{.*}}] : i64 from vector<[2]xi64> - %tile = arm_sme.get_tile : vector<[2]x[2]xi64> - %el = vector.extract %tile[%row, %col] : i64 from vector<[2]x[2]xi64> - return %el : i64 -} - -// ----- - -// CHECK-LABEL: @vector_extract_element_i128 -func.func @vector_extract_element_i128(%row: index, %col: index) -> i128 { - // CHECK: %[[SLICE:.*]] = "arm_sme.intr.read.horiz"(%{{.*}}) <{tile_id = 0 : i32}> : (vector<[1]xi128>, vector<[1]xi1>, i32) -> vector<[1]xi128> - // CHECK-NEXT: %{{.*}} = vector.extract %[[SLICE]]{{\[}}%{{.*}}] : i128 from vector<[1]xi128> - %tile = arm_sme.get_tile : vector<[1]x[1]xi128> - %el = vector.extract %tile[%row, %col] : i128 from vector<[1]x[1]xi128> - return %el : i128 -} - -// ----- - -// CHECK-LABEL: @vector_extract_element_f16 -func.func @vector_extract_element_f16(%row: index, %col: index) -> f16 { - // CHECK: %[[SLICE:.*]] = "arm_sme.intr.read.horiz"(%{{.*}}) <{tile_id = 0 : i32}> : (vector<[8]xf16>, vector<[8]xi1>, i32) -> vector<[8]xf16> - // CHECK-NEXT: %{{.*}} = vector.extract %[[SLICE]]{{\[}}%{{.*}}] : f16 from vector<[8]xf16> - %tile = arm_sme.get_tile : vector<[8]x[8]xf16> - %el = vector.extract %tile[%row, %col] : f16 from vector<[8]x[8]xf16> - return %el : f16 -} - -// ----- - -// CHECK-LABEL: @vector_extract_element_bf16 -func.func @vector_extract_element_bf16(%row: index, %col: index) -> bf16 { - // CHECK: %[[SLICE:.*]] = "arm_sme.intr.read.horiz"(%{{.*}}) <{tile_id = 0 : i32}> : (vector<[8]xbf16>, vector<[8]xi1>, i32) -> vector<[8]xbf16> - // CHECK-NEXT: %{{.*}} = vector.extract %[[SLICE]]{{\[}}%{{.*}}] : bf16 from vector<[8]xbf16> - %tile = arm_sme.get_tile : vector<[8]x[8]xbf16> - %el = vector.extract %tile[%row, %col] : bf16 from vector<[8]x[8]xbf16> - return %el : bf16 -} - -// ----- - -// CHECK-LABEL: @vector_extract_element_f32 -func.func @vector_extract_element_f32(%row: index, %col: index) -> f32 { - // CHECK: %[[SLICE:.*]] = "arm_sme.intr.read.horiz"(%{{.*}}) <{tile_id = 0 : i32}> : (vector<[4]xf32>, vector<[4]xi1>, i32) -> vector<[4]xf32> - // CHECK-NEXT: %{{.*}} = vector.extract %[[SLICE]]{{\[}}%{{.*}}] : f32 from vector<[4]xf32> - %tile = arm_sme.get_tile : vector<[4]x[4]xf32> - %el = vector.extract %tile[%row, %col] : f32 from vector<[4]x[4]xf32> - return %el : f32 -} - -// ----- - -// CHECK-LABEL: @vector_extract_element_f64 -func.func @vector_extract_element_f64(%row: index, %col: index) -> f64 { - // CHECK: %[[SLICE:.*]] = "arm_sme.intr.read.horiz"(%{{.*}}) <{tile_id = 0 : i32}> : (vector<[2]xf64>, vector<[2]xi1>, i32) -> vector<[2]xf64> - // CHECK-NEXT: %{{.*}} = vector.extract %[[SLICE]]{{\[}}%{{.*}}] : f64 from vector<[2]xf64> - %tile = arm_sme.get_tile : vector<[2]x[2]xf64> - %el = vector.extract %tile[%row, %col] : f64 from vector<[2]x[2]xf64> - return %el : f64 -} diff --git a/mlir/test/Dialect/LLVMIR/legalize-for-export.mlir b/mlir/test/Dialect/LLVMIR/legalize-for-export.mlir index 37720e98d92a9e85a34b7f387e11680aaf781343..b1b06740f194422ee4a50c96cd0024949f13a4df 100644 --- a/mlir/test/Dialect/LLVMIR/legalize-for-export.mlir +++ b/mlir/test/Dialect/LLVMIR/legalize-for-export.mlir @@ -32,14 +32,17 @@ llvm.func @repeated_successor_no_args(%arg0: i1) { // CHECK: @repeated_successor_openmp llvm.func @repeated_successor_openmp(%arg0: i64, %arg1: i64, %arg2: i64, %arg3: i1) { - omp.wsloop for (%arg4) : i64 = (%arg0) to (%arg1) step (%arg2) { - // CHECK: llvm.cond_br %{{.*}}, ^[[BB1:.*]]({{.*}}), ^[[BB2:.*]]({{.*}}) - llvm.cond_br %arg3, ^bb1(%arg0 : i64), ^bb1(%arg1 : i64) - // CHECK: ^[[BB1]] - ^bb1(%0: i64): // 2 preds: ^bb0, ^bb0 - omp.yield - // CHECK: ^[[BB2]](%[[ARG:.*]]: i64): - // CHECK: llvm.br ^[[BB1]](%[[ARG]] : i64) + omp.wsloop { + omp.loop_nest (%arg4) : i64 = (%arg0) to (%arg1) step (%arg2) { + // CHECK: llvm.cond_br %{{.*}}, ^[[BB1:.*]]({{.*}}), ^[[BB2:.*]]({{.*}}) + llvm.cond_br %arg3, ^bb1(%arg0 : i64), ^bb1(%arg1 : i64) + // CHECK: ^[[BB1]] + ^bb1(%0: i64): // 2 preds: ^bb0, ^bb0 + omp.yield + // CHECK: ^[[BB2]](%[[ARG:.*]]: i64): + // CHECK: llvm.br ^[[BB1]](%[[ARG]] : i64) + } + omp.terminator } llvm.return } diff --git a/mlir/test/Dialect/LLVMIR/mem2reg.mlir b/mlir/test/Dialect/LLVMIR/mem2reg.mlir index 644d30f9f9f13318b47bd67abaeebb085b194617..38c836c139da622ffe4585eb84eb9533f7c8ae2e 100644 --- a/mlir/test/Dialect/LLVMIR/mem2reg.mlir +++ b/mlir/test/Dialect/LLVMIR/mem2reg.mlir @@ -856,28 +856,6 @@ llvm.func @stores_with_different_types(%arg0: i64, %arg1: f64, %cond: i1) -> f64 // ----- -// Verifies that stores with smaller bitsize inputs are not replaced. A trivial -// implementation will be incorrect due to endianness considerations. - -// CHECK-LABEL: @stores_with_different_type_sizes -llvm.func @stores_with_different_type_sizes(%arg0: i64, %arg1: f32, %cond: i1) -> f64 { - %0 = llvm.mlir.constant(1 : i32) : i32 - // CHECK: llvm.alloca - %1 = llvm.alloca %0 x i64 {alignment = 4 : i64} : (i32) -> !llvm.ptr - llvm.cond_br %cond, ^bb1, ^bb2 -^bb1: - llvm.store %arg0, %1 {alignment = 4 : i64} : i64, !llvm.ptr - llvm.br ^bb3 -^bb2: - llvm.store %arg1, %1 {alignment = 4 : i64} : f32, !llvm.ptr - llvm.br ^bb3 -^bb3: - %2 = llvm.load %1 {alignment = 4 : i64} : !llvm.ptr -> f64 - llvm.return %2 : f64 -} - -// ----- - // CHECK-LABEL: @load_smaller_int llvm.func @load_smaller_int() -> i16 { %0 = llvm.mlir.constant(1 : i32) : i32 @@ -1047,3 +1025,135 @@ llvm.func @scalable_llvm_vector() -> i16 { %2 = llvm.load %1 : !llvm.ptr -> i16 llvm.return %2 : i16 } + +// ----- + +// CHECK-LABEL: @smaller_store_forwarding +// CHECK-SAME: %[[ARG:.+]]: i16 +llvm.func @smaller_store_forwarding(%arg : i16) { + %0 = llvm.mlir.constant(1 : i32) : i32 + // CHECK-NOT: llvm.alloca + // CHECK: %[[UNDEF:.+]] = llvm.mlir.undef : i32 + %1 = llvm.alloca %0 x i32 : (i32) -> !llvm.ptr + + // CHECK: %[[ZEXT:.+]] = llvm.zext %[[ARG]] : i16 to i32 + // CHECK: %[[MASK:.+]] = llvm.mlir.constant(-65536 : i32) : i32 + // CHECK: %[[MASKED:.+]] = llvm.and %[[UNDEF]], %[[MASK]] + // CHECK: %[[NEW_DEF:.+]] = llvm.or %[[MASKED]], %[[ZEXT]] + llvm.store %arg, %1 : i16, !llvm.ptr + llvm.return +} + +// ----- + +module attributes { dlti.dl_spec = #dlti.dl_spec< + #dlti.dl_entry<"dlti.endianness", "big"> +>} { + // CHECK-LABEL: @smaller_store_forwarding_big_endian + // CHECK-SAME: %[[ARG:.+]]: i16 + llvm.func @smaller_store_forwarding_big_endian(%arg : i16) { + %0 = llvm.mlir.constant(1 : i32) : i32 + // CHECK-NOT: llvm.alloca + // CHECK: %[[UNDEF:.+]] = llvm.mlir.undef : i32 + %1 = llvm.alloca %0 x i32 : (i32) -> !llvm.ptr + + // CHECK: %[[ZEXT:.+]] = llvm.zext %[[ARG]] : i16 to i32 + // CHECK: %[[SHIFT_WIDTH:.+]] = llvm.mlir.constant(16 : i32) : i32 + // CHECK: %[[SHIFTED:.+]] = llvm.shl %[[ZEXT]], %[[SHIFT_WIDTH]] + // CHECK: %[[MASK:.+]] = llvm.mlir.constant(65535 : i32) : i32 + // CHECK: %[[MASKED:.+]] = llvm.and %[[UNDEF]], %[[MASK]] + // CHECK: %[[NEW_DEF:.+]] = llvm.or %[[MASKED]], %[[SHIFTED]] + llvm.store %arg, %1 : i16, !llvm.ptr + llvm.return + } +} + +// ----- + +// CHECK-LABEL: @smaller_store_forwarding_type_mix +// CHECK-SAME: %[[ARG:.+]]: vector<1xi8> +llvm.func @smaller_store_forwarding_type_mix(%arg : vector<1xi8>) { + %0 = llvm.mlir.constant(1 : i32) : i32 + // CHECK-NOT: llvm.alloca + // CHECK: %[[UNDEF:.+]] = llvm.mlir.undef : f32 + %1 = llvm.alloca %0 x f32 : (i32) -> !llvm.ptr + + // CHECK: %[[CASTED_DEF:.+]] = llvm.bitcast %[[UNDEF]] : f32 to i32 + // CHECK: %[[CASTED_ARG:.+]] = llvm.bitcast %[[ARG]] : vector<1xi8> to i8 + // CHECK: %[[ZEXT:.+]] = llvm.zext %[[CASTED_ARG]] : i8 to i32 + // CHECK: %[[MASK:.+]] = llvm.mlir.constant(-256 : i32) : i32 + // CHECK: %[[MASKED:.+]] = llvm.and %[[CASTED_DEF]], %[[MASK]] + // CHECK: %[[NEW_DEF:.+]] = llvm.or %[[MASKED]], %[[ZEXT]] + // CHECK: %[[CASTED_NEW_DEF:.+]] = llvm.bitcast %[[NEW_DEF]] : i32 to f32 + llvm.store %arg, %1 : vector<1xi8>, !llvm.ptr + llvm.return +} + +// ----- + +module attributes { dlti.dl_spec = #dlti.dl_spec< + #dlti.dl_entry<"dlti.endianness", "big"> +>} { + // CHECK-LABEL: @smaller_store_forwarding_type_mix + // CHECK-SAME: %[[ARG:.+]]: vector<1xi8> + llvm.func @smaller_store_forwarding_type_mix(%arg : vector<1xi8>) { + %0 = llvm.mlir.constant(1 : i32) : i32 + // CHECK-NOT: llvm.alloca + // CHECK: %[[UNDEF:.+]] = llvm.mlir.undef : f32 + %1 = llvm.alloca %0 x f32 : (i32) -> !llvm.ptr + + // CHECK: %[[CASTED_DEF:.+]] = llvm.bitcast %[[UNDEF]] : f32 to i32 + // CHECK: %[[CASTED_ARG:.+]] = llvm.bitcast %[[ARG]] : vector<1xi8> to i8 + // CHECK: %[[ZEXT:.+]] = llvm.zext %[[CASTED_ARG]] : i8 to i32 + // CHECK: %[[SHIFT_WIDTH:.+]] = llvm.mlir.constant(24 : i32) : i32 + // CHECK: %[[SHIFTED:.+]] = llvm.shl %[[ZEXT]], %[[SHIFT_WIDTH]] + // CHECK: %[[MASK:.+]] = llvm.mlir.constant(16777215 : i32) : i32 + // CHECK: %[[MASKED:.+]] = llvm.and %[[CASTED_DEF]], %[[MASK]] + // CHECK: %[[NEW_DEF:.+]] = llvm.or %[[MASKED]], %[[SHIFTED]] + // CHECK: %[[CASTED_NEW_DEF:.+]] = llvm.bitcast %[[NEW_DEF]] : i32 to f32 + llvm.store %arg, %1 : vector<1xi8>, !llvm.ptr + llvm.return + } +} + +// ----- + +// CHECK-LABEL: @stores_with_different_types_branches +// CHECK-SAME: %[[ARG0:.+]]: i64 +// CHECK-SAME: %[[ARG1:.+]]: f32 +llvm.func @stores_with_different_types_branches(%arg0: i64, %arg1: f32, %cond: i1) -> f64 { + %0 = llvm.mlir.constant(1 : i32) : i32 + // CHECK-NOT: llvm.alloca + // CHECK: %[[UNDEF:.+]] = llvm.mlir.undef : i64 + %1 = llvm.alloca %0 x i64 {alignment = 4 : i64} : (i32) -> !llvm.ptr + llvm.cond_br %cond, ^bb1, ^bb2 +^bb1: + llvm.store %arg0, %1 {alignment = 4 : i64} : i64, !llvm.ptr + // CHECK: llvm.br ^[[BB3:.+]](%[[ARG0]] : i64) + llvm.br ^bb3 +^bb2: + llvm.store %arg1, %1 {alignment = 4 : i64} : f32, !llvm.ptr + // CHECK: %[[CAST:.+]] = llvm.bitcast %[[ARG1]] : f32 to i32 + // CHECK: %[[ZEXT:.+]] = llvm.zext %[[CAST]] : i32 to i64 + // CHECK: %[[MASK:.+]] = llvm.mlir.constant(-4294967296 : i64) : i64 + // CHECK: %[[MASKED:.+]] = llvm.and %[[UNDEF]], %[[MASK]] + // CHECK: %[[NEW_DEF:.+]] = llvm.or %[[MASKED]], %[[ZEXT]] + // CHECK: llvm.br ^[[BB3]](%[[NEW_DEF]] : i64) + llvm.br ^bb3 +^bb3: + %2 = llvm.load %1 {alignment = 4 : i64} : !llvm.ptr -> f64 + llvm.return %2 : f64 +} + +// ----- + +// Verifiy that mem2reg does not touch stores with undefined semantics. + +// CHECK-LABEL: @store_out_of_bounds +llvm.func @store_out_of_bounds(%arg : i64) { + %0 = llvm.mlir.constant(1 : i32) : i32 + // CHECK: llvm.alloca + %1 = llvm.alloca %0 x i32 : (i32) -> !llvm.ptr + llvm.store %arg, %1 : i64, !llvm.ptr + llvm.return +} diff --git a/mlir/test/Dialect/Linalg/match-ops-interpreter.mlir b/mlir/test/Dialect/Linalg/match-ops-interpreter.mlir index 24c7bdd9e1050ee19e46c787ee478183d55f9b66..4bfed475d44f603d16541fd89996afcfed5d9059 100644 --- a/mlir/test/Dialect/Linalg/match-ops-interpreter.mlir +++ b/mlir/test/Dialect/Linalg/match-ops-interpreter.mlir @@ -1062,6 +1062,28 @@ module attributes { transform.target_tag = "start_here" } { return %result : tensor<10x18x15xf64> } + func.func @convolution_depthwise(%input: tensor<1x10x196x48xf32>, %filter: tensor<1x4x48xf32>) -> tensor<1x10x191x48xf32> { + %cst = arith.constant 0.0 : f32 + %empty = tensor.empty() : tensor<1x10x191x48xf32> + %fill = linalg.fill ins(%cst : f32) outs(%empty : tensor<1x10x191x48xf32>) -> tensor<1x10x191x48xf32> + // expected-remark @below {{convolution}} + // expected-remark @below {{batch dims 0}} + // expected-remark @below {{output image dims 1 : i64, 2 : i64}} + // expected-remark @below {{output channel dims}} + // expected-remark @below {{filter loop dims 4 : i64, 5 : i64}} + // expected-remark @below {{input channel dims}} + // expected-remark @below {{depth dims 3}} + // expected-remark @below {{strides 1 : i64, 1 : i64}} + // expected-remark @below {{dilations 1 : i64, 1 : i64}} + %result = linalg.depthwise_conv_2d_nhwc_hwc { + dilations = dense<1> : tensor<2xi64>, + strides = dense<1> : tensor<2xi64>} + ins(%input, %filter : tensor<1x10x196x48xf32>, tensor<1x4x48xf32>) + outs(%fill : tensor<1x10x191x48xf32>) -> tensor<1x10x191x48xf32> + + return %result : tensor<1x10x191x48xf32> + } + func.func @convolution_multi_channel(%input: tensor<2x34x68x16xf32>, %filter: tensor<8x2x3x5x16x16xf32>) -> tensor<8x32x32x16xf32> { %cst = arith.constant 0.0 : f32 %empty = tensor.empty() : tensor<8x32x32x16xf32> diff --git a/mlir/test/Dialect/Linalg/runtime-verification.mlir b/mlir/test/Dialect/Linalg/runtime-verification.mlir new file mode 100644 index 0000000000000000000000000000000000000000..a4f29d8457e58958f4561ba3eee2a7db0bd1e064 --- /dev/null +++ b/mlir/test/Dialect/Linalg/runtime-verification.mlir @@ -0,0 +1,43 @@ +// RUN: mlir-opt %s -generate-runtime-verification | FileCheck %s + +// Most of the tests for linalg runtime-verification are implemented as integration tests. + +#identity = affine_map<(d0) -> (d0)> + +// CHECK-LABEL: @static_dims +func.func @static_dims(%arg0: tensor<5xf32>, %arg1: tensor<5xf32>) -> (tensor<5xf32>) { + // CHECK: %[[TRUE:.*]] = index.bool.constant true + // CHECK: cf.assert %[[TRUE]] + %result = tensor.empty() : tensor<5xf32> + %0 = linalg.generic { + indexing_maps = [#identity, #identity, #identity], + iterator_types = ["parallel"] + } ins(%arg0, %arg1 : tensor<5xf32>, tensor<5xf32>) + outs(%result : tensor<5xf32>) { + ^bb0(%gen_arg1: f32, %gen_arg2: f32, %out: f32) : + %tmp1 = arith.addf %gen_arg1, %gen_arg2 : f32 + linalg.yield %tmp1 : f32 + } -> tensor<5xf32> + return %0 : tensor<5xf32> +} + +// ----- + +#map = affine_map<() -> ()> + +// CHECK-LABEL: @scalars +func.func @scalars(%arg0: tensor, %arg1: tensor) -> (tensor) { + // No runtime checks are required if the operands are all scalars + // CHECK-NOT: cf.assert + %result = tensor.empty() : tensor + %0 = linalg.generic { + indexing_maps = [#map, #map, #map], + iterator_types = [] + } ins(%arg0, %arg1 : tensor, tensor) + outs(%result : tensor) { + ^bb0(%gen_arg1: f32, %gen_arg2: f32, %out: f32) : + %tmp1 = arith.addf %gen_arg1, %gen_arg2 : f32 + linalg.yield %tmp1 : f32 + } -> tensor + return %0 : tensor +} diff --git a/mlir/test/Dialect/OpenMP/invalid.mlir b/mlir/test/Dialect/OpenMP/invalid.mlir index 2f24dce4233e48ecce30ea1f24a5633f8e44b7c1..e329b3010017cf594846f099cd51430e5b198592 100644 --- a/mlir/test/Dialect/OpenMP/invalid.mlir +++ b/mlir/test/Dialect/OpenMP/invalid.mlir @@ -149,50 +149,74 @@ func.func @invalid_parent(%lb : index, %ub : index, %step : index) { // ----- func.func @invalid_wrapper(%lb : index, %ub : index, %step : index) { - // TODO Remove induction variables from omp.wsloop. - omp.wsloop for (%iv) : index = (%lb) to (%ub) step (%step) { + omp.parallel { %0 = arith.constant 0 : i32 // expected-error@+1 {{op expects parent op to be a valid loop wrapper}} omp.loop_nest (%iv2) : index = (%lb) to (%ub) step (%step) { omp.yield } - omp.yield + omp.terminator } } // ----- func.func @type_mismatch(%lb : index, %ub : index, %step : index) { - // TODO Remove induction variables from omp.wsloop. - omp.wsloop for (%iv) : index = (%lb) to (%ub) step (%step) { + omp.wsloop { // expected-error@+1 {{range argument type does not match corresponding IV type}} "omp.loop_nest" (%lb, %ub, %step) ({ ^bb0(%iv2: i32): omp.yield }) : (index, index, index) -> () - omp.yield + omp.terminator } } // ----- func.func @iv_number_mismatch(%lb : index, %ub : index, %step : index) { - // TODO Remove induction variables from omp.wsloop. - omp.wsloop for (%iv) : index = (%lb) to (%ub) step (%step) { + omp.wsloop { // expected-error@+1 {{number of range arguments and IVs do not match}} "omp.loop_nest" (%lb, %ub, %step) ({ ^bb0(%iv1 : index, %iv2 : index): omp.yield }) : (index, index, index) -> () - omp.yield + omp.terminator + } +} + +// ----- + +func.func @no_wrapper(%lb : index, %ub : index, %step : index) { + // expected-error @below {{op must be a loop wrapper}} + omp.wsloop { + %0 = arith.constant 0 : i32 + omp.loop_nest (%iv) : index = (%lb) to (%ub) step (%step) { + omp.yield + } + omp.terminator + } +} + +// ----- + +func.func @invalid_nested_wrapper(%lb : index, %ub : index, %step : index) { + // expected-error @below {{only supported nested wrapper is 'omp.simd'}} + omp.wsloop { + omp.distribute { + omp.loop_nest (%iv) : index = (%lb) to (%ub) step (%step) { + omp.yield + } + omp.terminator + } + omp.terminator } } // ----- func.func @no_loops(%lb : index, %ub : index, %step : index) { - // TODO Remove induction variables from omp.wsloop. - omp.wsloop for (%iv) : index = (%lb) to (%ub) step (%step) { + omp.wsloop { // expected-error@+1 {{op must represent at least one loop}} "omp.loop_nest" () ({ ^bb0(): @@ -205,10 +229,12 @@ func.func @no_loops(%lb : index, %ub : index, %step : index) { // ----- func.func @inclusive_not_a_clause(%lb : index, %ub : index, %step : index) { - // expected-error @below {{expected 'for'}} - omp.wsloop nowait inclusive - for (%iv) : index = (%lb) to (%ub) step (%step) { - omp.yield + // expected-error @below {{expected '{'}} + omp.wsloop nowait inclusive { + omp.loop_nest (%iv) : index = (%lb) to (%ub) step (%step) { + omp.yield + } + omp.terminator } } @@ -216,39 +242,47 @@ func.func @inclusive_not_a_clause(%lb : index, %ub : index, %step : index) { func.func @order_value(%lb : index, %ub : index, %step : index) { // expected-error @below {{invalid clause value: 'default'}} - omp.wsloop order(default) - for (%iv) : index = (%lb) to (%ub) step (%step) { - omp.yield + omp.wsloop order(default) { + omp.loop_nest (%iv) : index = (%lb) to (%ub) step (%step) { + omp.yield + } + omp.terminator } } // ----- func.func @if_not_allowed(%lb : index, %ub : index, %step : index, %bool_var : i1) { - // expected-error @below {{expected 'for'}} - omp.wsloop if(%bool_var: i1) - for (%iv) : index = (%lb) to (%ub) step (%step) { - omp.yield + // expected-error @below {{expected '{'}} + omp.wsloop if(%bool_var: i1) { + omp.loop_nest (%iv) : index = (%lb) to (%ub) step (%step) { + omp.yield + } + omp.terminator } } // ----- func.func @num_threads_not_allowed(%lb : index, %ub : index, %step : index, %int_var : i32) { - // expected-error @below {{expected 'for'}} - omp.wsloop num_threads(%int_var: i32) - for (%iv) : index = (%lb) to (%ub) step (%step) { - omp.yield + // expected-error @below {{expected '{'}} + omp.wsloop num_threads(%int_var: i32) { + omp.loop_nest (%iv) : index = (%lb) to (%ub) step (%step) { + omp.yield + } + omp.terminator } } // ----- func.func @proc_bind_not_allowed(%lb : index, %ub : index, %step : index) { - // expected-error @below {{expected 'for'}} - omp.wsloop proc_bind(close) - for (%iv) : index = (%lb) to (%ub) step (%step) { - omp.yield + // expected-error @below {{expected '{'}} + omp.wsloop proc_bind(close) { + omp.loop_nest (%iv) : index = (%lb) to (%ub) step (%step) { + omp.yield + } + omp.terminator } } @@ -256,9 +290,11 @@ func.func @proc_bind_not_allowed(%lb : index, %ub : index, %step : index) { llvm.func @test_omp_wsloop_dynamic_bad_modifier(%lb : i64, %ub : i64, %step : i64) -> () { // expected-error @+1 {{unknown modifier type: ginandtonic}} - omp.wsloop schedule(dynamic, ginandtonic) - for (%iv) : i64 = (%lb) to (%ub) step (%step) { - omp.yield + omp.wsloop schedule(dynamic, ginandtonic) { + omp.loop_nest (%iv) : i64 = (%lb) to (%ub) step (%step) { + omp.yield + } + omp.terminator } llvm.return } @@ -267,9 +303,11 @@ llvm.func @test_omp_wsloop_dynamic_bad_modifier(%lb : i64, %ub : i64, %step : i6 llvm.func @test_omp_wsloop_dynamic_many_modifier(%lb : i64, %ub : i64, %step : i64) -> () { // expected-error @+1 {{unexpected modifier(s)}} - omp.wsloop schedule(dynamic, monotonic, monotonic, monotonic) - for (%iv) : i64 = (%lb) to (%ub) step (%step) { - omp.yield + omp.wsloop schedule(dynamic, monotonic, monotonic, monotonic) { + omp.loop_nest (%iv) : i64 = (%lb) to (%ub) step (%step) { + omp.yield + } + omp.terminator } llvm.return } @@ -278,9 +316,11 @@ llvm.func @test_omp_wsloop_dynamic_many_modifier(%lb : i64, %ub : i64, %step : i llvm.func @test_omp_wsloop_dynamic_wrong_modifier(%lb : i64, %ub : i64, %step : i64) -> () { // expected-error @+1 {{incorrect modifier order}} - omp.wsloop schedule(dynamic, simd, monotonic) - for (%iv) : i64 = (%lb) to (%ub) step (%step) { - omp.yield + omp.wsloop schedule(dynamic, simd, monotonic) { + omp.loop_nest (%iv) : i64 = (%lb) to (%ub) step (%step) { + omp.yield + } + omp.terminator } llvm.return } @@ -289,9 +329,11 @@ llvm.func @test_omp_wsloop_dynamic_wrong_modifier(%lb : i64, %ub : i64, %step : llvm.func @test_omp_wsloop_dynamic_wrong_modifier2(%lb : i64, %ub : i64, %step : i64) -> () { // expected-error @+1 {{incorrect modifier order}} - omp.wsloop schedule(dynamic, monotonic, monotonic) - for (%iv) : i64 = (%lb) to (%ub) step (%step) { - omp.yield + omp.wsloop schedule(dynamic, monotonic, monotonic) { + omp.loop_nest (%iv) : i64 = (%lb) to (%ub) step (%step) { + omp.yield + } + omp.terminator } llvm.return } @@ -300,9 +342,11 @@ llvm.func @test_omp_wsloop_dynamic_wrong_modifier2(%lb : i64, %ub : i64, %step : llvm.func @test_omp_wsloop_dynamic_wrong_modifier3(%lb : i64, %ub : i64, %step : i64) -> () { // expected-error @+1 {{incorrect modifier order}} - omp.wsloop schedule(dynamic, simd, simd) - for (%iv) : i64 = (%lb) to (%ub) step (%step) { - omp.yield + omp.wsloop schedule(dynamic, simd, simd) { + omp.loop_nest (%iv) : i64 = (%lb) to (%ub) step (%step) { + omp.yield + } + omp.terminator } llvm.return } @@ -601,11 +645,13 @@ func.func @foo(%lb : index, %ub : index, %step : index) { %1 = llvm.alloca %c1 x i32 : (i32) -> !llvm.ptr // expected-error @below {{expected symbol reference @foo to point to a reduction declaration}} - omp.wsloop reduction(@foo %0 -> %prv : !llvm.ptr) - for (%iv) : index = (%lb) to (%ub) step (%step) { - %2 = arith.constant 2.0 : f32 - omp.reduction %2, %1 : f32, !llvm.ptr - omp.yield + omp.wsloop reduction(@foo %0 -> %prv : !llvm.ptr) { + omp.loop_nest (%iv) : index = (%lb) to (%ub) step (%step) { + %2 = arith.constant 2.0 : f32 + omp.reduction %2, %1 : f32, !llvm.ptr + omp.yield + } + omp.terminator } return } @@ -629,11 +675,13 @@ func.func @foo(%lb : index, %ub : index, %step : index) { %0 = llvm.alloca %c1 x i32 : (i32) -> !llvm.ptr // expected-error @below {{accumulator variable used more than once}} - omp.wsloop reduction(@add_f32 %0 -> %prv : !llvm.ptr, @add_f32 %0 -> %prv1 : !llvm.ptr) - for (%iv) : index = (%lb) to (%ub) step (%step) { - %2 = arith.constant 2.0 : f32 - omp.reduction %2, %0 : f32, !llvm.ptr - omp.yield + omp.wsloop reduction(@add_f32 %0 -> %prv : !llvm.ptr, @add_f32 %0 -> %prv1 : !llvm.ptr) { + omp.loop_nest (%iv) : index = (%lb) to (%ub) step (%step) { + %2 = arith.constant 2.0 : f32 + omp.reduction %2, %0 : f32, !llvm.ptr + omp.yield + } + omp.terminator } return } @@ -662,11 +710,13 @@ func.func @foo(%lb : index, %ub : index, %step : index, %mem : memref<1xf32>) { %c1 = arith.constant 1 : i32 // expected-error @below {{expected accumulator ('memref<1xf32>') to be the same type as reduction declaration ('!llvm.ptr')}} - omp.wsloop reduction(@add_f32 %mem -> %prv : memref<1xf32>) - for (%iv) : index = (%lb) to (%ub) step (%step) { - %2 = arith.constant 2.0 : f32 - omp.reduction %2, %mem : f32, memref<1xf32> - omp.yield + omp.wsloop reduction(@add_f32 %mem -> %prv : memref<1xf32>) { + omp.loop_nest (%iv) : index = (%lb) to (%ub) step (%step) { + %2 = arith.constant 2.0 : f32 + omp.reduction %2, %mem : f32, memref<1xf32> + omp.yield + } + omp.terminator } return } @@ -698,60 +748,112 @@ omp.critical.declare @mutex hint(invalid_hint) // ----- -func.func @omp_ordered1(%arg1 : i32, %arg2 : i32, %arg3 : i32) -> () { - omp.wsloop ordered(1) - for (%0) : i32 = (%arg1) to (%arg2) step (%arg3) { - // expected-error @below {{ordered region must be closely nested inside a worksharing-loop region with an ordered clause without parameter present}} - omp.ordered.region { - omp.terminator +func.func @omp_ordered_region1(%x : i32) -> () { + omp.distribute { + omp.loop_nest (%i) : i32 = (%x) to (%x) step (%x) { + // expected-error @below {{op must be nested inside of a worksharing, simd or worksharing simd loop}} + omp.ordered.region { + omp.terminator + } + omp.yield } - omp.yield + omp.terminator } return } // ----- -func.func @omp_ordered2(%arg1 : i32, %arg2 : i32, %arg3 : i32) -> () { - omp.wsloop for (%0) : i32 = (%arg1) to (%arg2) step (%arg3) { - // expected-error @below {{ordered region must be closely nested inside a worksharing-loop region with an ordered clause without parameter present}} - omp.ordered.region { - omp.terminator +func.func @omp_ordered_region2(%x : i32) -> () { + omp.wsloop { + omp.loop_nest (%i) : i32 = (%x) to (%x) step (%x) { + // expected-error @below {{the enclosing worksharing-loop region must have an ordered clause}} + omp.ordered.region { + omp.terminator + } + omp.yield } - omp.yield + omp.terminator } return } // ----- -func.func @omp_ordered3(%vec0 : i64) -> () { - // expected-error @below {{ordered depend directive must be closely nested inside a worksharing-loop with ordered clause with parameter present}} +func.func @omp_ordered_region3(%x : i32) -> () { + omp.wsloop ordered(1) { + omp.loop_nest (%i) : i32 = (%x) to (%x) step (%x) { + // expected-error @below {{the enclosing loop's ordered clause must not have a parameter present}} + omp.ordered.region { + omp.terminator + } + omp.yield + } + omp.terminator + } + return +} + +// ----- + +func.func @omp_ordered1(%vec0 : i64) -> () { + // expected-error @below {{op must be nested inside of a loop}} omp.ordered depend_type(dependsink) depend_vec(%vec0 : i64) {num_loops_val = 1 : i64} return } // ----- -func.func @omp_ordered4(%arg1 : i32, %arg2 : i32, %arg3 : i32, %vec0 : i64) -> () { - omp.wsloop ordered(0) - for (%0) : i32 = (%arg1) to (%arg2) step (%arg3) { - // expected-error @below {{ordered depend directive must be closely nested inside a worksharing-loop with ordered clause with parameter present}} - omp.ordered depend_type(dependsink) depend_vec(%vec0 : i64) {num_loops_val = 1 : i64} +func.func @omp_ordered2(%arg1 : i32, %arg2 : i32, %arg3 : i32, %vec0 : i64) -> () { + omp.distribute { + omp.loop_nest (%0) : i32 = (%arg1) to (%arg2) step (%arg3) { + // expected-error @below {{op must be nested inside of a worksharing, simd or worksharing simd loop}} + omp.ordered depend_type(dependsink) depend_vec(%vec0 : i64) {num_loops_val = 1 : i64} + omp.yield + } + omp.terminator + } + return +} - omp.yield +// ----- + +func.func @omp_ordered3(%arg1 : i32, %arg2 : i32, %arg3 : i32, %vec0 : i64) -> () { + omp.wsloop { + omp.loop_nest (%0) : i32 = (%arg1) to (%arg2) step (%arg3) { + // expected-error @below {{the enclosing worksharing-loop region must have an ordered clause}} + omp.ordered depend_type(dependsink) depend_vec(%vec0 : i64) {num_loops_val = 1 : i64} + omp.yield + } + omp.terminator } return } + // ----- -func.func @omp_ordered5(%arg1 : i32, %arg2 : i32, %arg3 : i32, %vec0 : i64, %vec1 : i64) -> () { - omp.wsloop ordered(1) - for (%0) : i32 = (%arg1) to (%arg2) step (%arg3) { - // expected-error @below {{number of variables in depend clause does not match number of iteration variables in the doacross loop}} - omp.ordered depend_type(dependsource) depend_vec(%vec0, %vec1 : i64, i64) {num_loops_val = 2 : i64} +func.func @omp_ordered4(%arg1 : i32, %arg2 : i32, %arg3 : i32, %vec0 : i64) -> () { + omp.wsloop ordered(0) { + omp.loop_nest (%0) : i32 = (%arg1) to (%arg2) step (%arg3) { + // expected-error @below {{the enclosing loop's ordered clause must have a parameter present}} + omp.ordered depend_type(dependsink) depend_vec(%vec0 : i64) {num_loops_val = 1 : i64} + omp.yield + } + omp.terminator + } + return +} - omp.yield +// ----- + +func.func @omp_ordered5(%arg1 : i32, %arg2 : i32, %arg3 : i32, %vec0 : i64, %vec1 : i64) -> () { + omp.wsloop ordered(1) { + omp.loop_nest (%0) : i32 = (%arg1) to (%arg2) step (%arg3) { + // expected-error @below {{number of variables in depend clause does not match number of iteration variables in the doacross loop}} + omp.ordered depend_type(dependsource) depend_vec(%vec0, %vec1 : i64, i64) {num_loops_val = 2 : i64} + omp.yield + } + omp.terminator } return } @@ -1590,11 +1692,13 @@ func.func @omp_cancel2() { // ----- func.func @omp_cancel3(%arg1 : i32, %arg2 : i32, %arg3 : i32) -> () { - omp.wsloop nowait - for (%0) : i32 = (%arg1) to (%arg2) step (%arg3) { - // expected-error @below {{A worksharing construct that is canceled must not have a nowait clause}} - omp.cancel cancellation_construct_type(loop) - // CHECK: omp.terminator + omp.wsloop nowait { + omp.loop_nest (%0) : i32 = (%arg1) to (%arg2) step (%arg3) { + // expected-error @below {{A worksharing construct that is canceled must not have a nowait clause}} + omp.cancel cancellation_construct_type(loop) + // CHECK: omp.yield + omp.yield + } omp.terminator } return @@ -1603,11 +1707,13 @@ func.func @omp_cancel3(%arg1 : i32, %arg2 : i32, %arg3 : i32) -> () { // ----- func.func @omp_cancel4(%arg1 : i32, %arg2 : i32, %arg3 : i32) -> () { - omp.wsloop ordered(1) - for (%0) : i32 = (%arg1) to (%arg2) step (%arg3) { - // expected-error @below {{A worksharing construct that is canceled must not have an ordered clause}} - omp.cancel cancellation_construct_type(loop) - // CHECK: omp.terminator + omp.wsloop ordered(1) { + omp.loop_nest (%0) : i32 = (%arg1) to (%arg2) step (%arg3) { + // expected-error @below {{A worksharing construct that is canceled must not have an ordered clause}} + omp.cancel cancellation_construct_type(loop) + // CHECK: omp.yield + omp.yield + } omp.terminator } return @@ -2143,4 +2249,4 @@ func.func @undefined_privatizer(%arg0: !llvm.ptr) { omp.terminator }) : (!llvm.ptr) -> () return -} +} \ No newline at end of file diff --git a/mlir/test/Dialect/OpenMP/ops.mlir b/mlir/test/Dialect/OpenMP/ops.mlir index c10fc88211c36718d9414f95d992683efec1beb7..a012588f0b552152b6751d86e9a26a8d3518c2ef 100644 --- a/mlir/test/Dialect/OpenMP/ops.mlir +++ b/mlir/test/Dialect/OpenMP/ops.mlir @@ -90,10 +90,9 @@ func.func @omp_parallel(%data_var : memref, %if_cond : i1, %num_threads : i // CHECK-NEXT: omp.parallel omp.parallel { // CHECK-NEXT: omp.wsloop - // TODO Remove induction variables from omp.wsloop. - omp.wsloop for (%iv) : index = (%idx) to (%idx) step (%idx) { + omp.wsloop { // CHECK-NEXT: omp.loop_nest - omp.loop_nest (%iv2) : index = (%idx) to (%idx) step (%idx) { + omp.loop_nest (%iv) : index = (%idx) to (%idx) step (%idx) { omp.yield } omp.terminator @@ -153,49 +152,45 @@ func.func @omp_parallel_pretty(%data_var : memref, %if_cond : i1, %num_thre // CHECK-LABEL: omp_loop_nest func.func @omp_loop_nest(%lb : index, %ub : index, %step : index) -> () { - // TODO Remove induction variables from omp.wsloop. - omp.wsloop for (%iv) : index = (%lb) to (%ub) step (%step) { + omp.wsloop { // CHECK: omp.loop_nest // CHECK-SAME: (%{{.*}}) : index = // CHECK-SAME: (%{{.*}}) to (%{{.*}}) step (%{{.*}}) "omp.loop_nest" (%lb, %ub, %step) ({ - ^bb0(%iv2: index): + ^bb0(%iv: index): omp.yield }) : (index, index, index) -> () - omp.yield + omp.terminator } - // TODO Remove induction variables from omp.wsloop. - omp.wsloop for (%iv) : index = (%lb) to (%ub) step (%step) { + omp.wsloop { // CHECK: omp.loop_nest // CHECK-SAME: (%{{.*}}) : index = // CHECK-SAME: (%{{.*}}) to (%{{.*}}) inclusive step (%{{.*}}) "omp.loop_nest" (%lb, %ub, %step) ({ - ^bb0(%iv2: index): + ^bb0(%iv: index): omp.yield }) {inclusive} : (index, index, index) -> () - omp.yield + omp.terminator } - // TODO Remove induction variables from omp.wsloop. - omp.wsloop for (%iv) : index = (%lb) to (%ub) step (%step) { + omp.wsloop { // CHECK: omp.loop_nest // CHECK-SAME: (%{{.*}}, %{{.*}}) : index = // CHECK-SAME: (%{{.*}}, %{{.*}}) to (%{{.*}}, %{{.*}}) step (%{{.*}}, %{{.*}}) "omp.loop_nest" (%lb, %lb, %ub, %ub, %step, %step) ({ - ^bb0(%iv2: index, %iv3: index): + ^bb0(%iv: index, %iv3: index): omp.yield }) : (index, index, index, index, index, index) -> () - omp.yield + omp.terminator } - // TODO Remove induction variables from omp.wsloop. - omp.wsloop for (%iv) : index = (%lb) to (%ub) step (%step) { + omp.wsloop { // CHECK: omp.loop_nest // CHECK-SAME: (%{{.*}}) : index = // CHECK-SAME: (%{{.*}}) to (%{{.*}}) step (%{{.*}}) "omp.loop_nest" (%lb, %ub, %step) ({ - ^bb0(%iv2: index): + ^bb0(%iv: index): // CHECK: test.op1 "test.op1"(%lb) : (index) -> () // CHECK: test.op2 @@ -203,7 +198,7 @@ func.func @omp_loop_nest(%lb : index, %ub : index, %step : index) -> () { // CHECK: omp.yield omp.yield }) : (index, index, index) -> () - omp.yield + omp.terminator } return @@ -211,45 +206,41 @@ func.func @omp_loop_nest(%lb : index, %ub : index, %step : index) -> () { // CHECK-LABEL: omp_loop_nest_pretty func.func @omp_loop_nest_pretty(%lb : index, %ub : index, %step : index) -> () { - // TODO Remove induction variables from omp.wsloop. - omp.wsloop for (%iv) : index = (%lb) to (%ub) step (%step) { + omp.wsloop { // CHECK: omp.loop_nest // CHECK-SAME: (%{{.*}}) : index = // CHECK-SAME: (%{{.*}}) to (%{{.*}}) step (%{{.*}}) - omp.loop_nest (%iv2) : index = (%lb) to (%ub) step (%step) { + omp.loop_nest (%iv) : index = (%lb) to (%ub) step (%step) { omp.yield } - omp.yield + omp.terminator } - // TODO Remove induction variables from omp.wsloop. - omp.wsloop for (%iv) : index = (%lb) to (%ub) step (%step) { + omp.wsloop { // CHECK: omp.loop_nest // CHECK-SAME: (%{{.*}}) : index = // CHECK-SAME: (%{{.*}}) to (%{{.*}}) inclusive step (%{{.*}}) - omp.loop_nest (%iv2) : index = (%lb) to (%ub) inclusive step (%step) { + omp.loop_nest (%iv) : index = (%lb) to (%ub) inclusive step (%step) { omp.yield } - omp.yield + omp.terminator } - // TODO Remove induction variables from omp.wsloop. - omp.wsloop for (%iv) : index = (%lb) to (%ub) step (%step) { + omp.wsloop { // CHECK: omp.loop_nest // CHECK-SAME: (%{{.*}}) : index = // CHECK-SAME: (%{{.*}}, %{{.*}}) to (%{{.*}}, %{{.*}}) step (%{{.*}}, %{{.*}}) - omp.loop_nest (%iv2, %iv3) : index = (%lb, %lb) to (%ub, %ub) step (%step, %step) { + omp.loop_nest (%iv1, %iv2) : index = (%lb, %lb) to (%ub, %ub) step (%step, %step) { omp.yield } - omp.yield + omp.terminator } - // TODO Remove induction variables from omp.wsloop. - omp.wsloop for (%iv) : index = (%lb) to (%ub) step (%step) { + omp.wsloop { // CHECK: omp.loop_nest // CHECK-SAME: (%{{.*}}) : index = // CHECK-SAME: (%{{.*}}) to (%{{.*}}) step (%{{.*}}) - omp.loop_nest (%iv2) : index = (%lb) to (%ub) step (%step) { + omp.loop_nest (%iv) : index = (%lb) to (%ub) step (%step) { // CHECK: test.op1 "test.op1"(%lb) : (index) -> () // CHECK: test.op2 @@ -257,201 +248,271 @@ func.func @omp_loop_nest_pretty(%lb : index, %ub : index, %step : index) -> () { // CHECK: omp.yield omp.yield } - omp.yield + omp.terminator } return } -// CHECK-LABEL: omp_wsloop -func.func @omp_wsloop(%lb : index, %ub : index, %step : index, %data_var : memref, %linear_var : i32, %chunk_var : i32) -> () { +// CHECK-LABEL: omp_loop_nest_pretty_multi_block +func.func @omp_loop_nest_pretty_multi_block(%lb : index, %ub : index, + %step : index, %data1 : memref, %data2 : memref) -> () { - // CHECK: omp.wsloop ordered(1) - // CHECK-SAME: for (%{{.*}}) : index = (%{{.*}}) to (%{{.*}}) step (%{{.*}}) - "omp.wsloop" (%lb, %ub, %step) ({ - ^bb0(%iv: index): + omp.wsloop { + // CHECK: omp.loop_nest (%{{.*}}) : index = (%{{.*}}) to (%{{.*}}) step (%{{.*}}) + omp.loop_nest (%iv) : index = (%lb) to (%ub) step (%step) { + %1 = "test.payload"(%iv) : (index) -> (i32) + cf.br ^bb1(%1: i32) + ^bb1(%arg: i32): + memref.store %arg, %data1[%iv] : memref omp.yield - }) {operandSegmentSizes = array, ordered_val = 1} : - (index, index, index) -> () + } + omp.terminator + } - // CHECK: omp.wsloop linear(%{{.*}} = %{{.*}} : memref) schedule(static) - // CHECK-SAME: for (%{{.*}}) : index = (%{{.*}}) to (%{{.*}}) step (%{{.*}}) - "omp.wsloop" (%lb, %ub, %step, %data_var, %linear_var) ({ - ^bb0(%iv: index): + omp.wsloop { + // CHECK: omp.loop_nest (%{{.*}}) : index = (%{{.*}}) to (%{{.*}}) step (%{{.*}}) + omp.loop_nest (%iv) : index = (%lb) to (%ub) step (%step) { + %c = "test.condition"(%iv) : (index) -> (i1) + %v1 = "test.payload"(%iv) : (index) -> (i32) + cf.cond_br %c, ^bb1(%v1: i32), ^bb2(%v1: i32) + ^bb1(%arg0: i32): + memref.store %arg0, %data1[%iv] : memref + cf.br ^bb3 + ^bb2(%arg1: i32): + memref.store %arg1, %data2[%iv] : memref + cf.br ^bb3 + ^bb3: omp.yield - }) {operandSegmentSizes = array, schedule_val = #omp} : - (index, index, index, memref, i32) -> () + } + omp.terminator + } - // CHECK: omp.wsloop linear(%{{.*}} = %{{.*}} : memref, %{{.*}} = %{{.*}} : memref) schedule(static) - // CHECK-SAME: for (%{{.*}}) : index = (%{{.*}}) to (%{{.*}}) step (%{{.*}}) - "omp.wsloop" (%lb, %ub, %step, %data_var, %data_var, %linear_var, %linear_var) ({ - ^bb0(%iv: index): + omp.wsloop { + // CHECK: omp.loop_nest (%{{.*}}) : index = (%{{.*}}) to (%{{.*}}) step (%{{.*}}) + omp.loop_nest (%iv) : index = (%lb) to (%ub) step (%step) { + %c = "test.condition"(%iv) : (index) -> (i1) + %v1 = "test.payload"(%iv) : (index) -> (i32) + cf.cond_br %c, ^bb1(%v1: i32), ^bb2(%v1: i32) + ^bb1(%arg0: i32): + memref.store %arg0, %data1[%iv] : memref + omp.yield + ^bb2(%arg1: i32): + memref.store %arg1, %data2[%iv] : memref omp.yield - }) {operandSegmentSizes = array, schedule_val = #omp} : - (index, index, index, memref, memref, i32, i32) -> () + } + omp.terminator + } - // CHECK: omp.wsloop linear(%{{.*}} = %{{.*}} : memref) schedule(dynamic = %{{.*}}) ordered(2) - // CHECK-SAME: for (%{{.*}}) : index = (%{{.*}}) to (%{{.*}}) step (%{{.*}}) - "omp.wsloop" (%lb, %ub, %step, %data_var, %linear_var, %chunk_var) ({ - ^bb0(%iv: index): + return +} + +// CHECK-LABEL: omp_loop_nest_pretty_non_index +func.func @omp_loop_nest_pretty_non_index(%lb1 : i32, %ub1 : i32, %step1 : i32, + %lb2 : i64, %ub2 : i64, %step2 : i64, %data1 : memref, + %data2 : memref) -> () { + + omp.wsloop { + // CHECK: omp.loop_nest (%{{.*}}) : i32 = (%{{.*}}) to (%{{.*}}) step (%{{.*}}) + omp.loop_nest (%iv1) : i32 = (%lb1) to (%ub1) step (%step1) { + %1 = "test.payload"(%iv1) : (i32) -> (index) + cf.br ^bb1(%1: index) + ^bb1(%arg1: index): + memref.store %iv1, %data1[%arg1] : memref omp.yield - }) {operandSegmentSizes = array, schedule_val = #omp, ordered_val = 2} : - (index, index, index, memref, i32, i32) -> () + } + omp.terminator + } - // CHECK: omp.wsloop schedule(auto) nowait - // CHECK-SAME: for (%{{.*}}) : index = (%{{.*}}) to (%{{.*}}) step (%{{.*}}) - "omp.wsloop" (%lb, %ub, %step) ({ - ^bb0(%iv: index): + omp.wsloop { + // CHECK: omp.loop_nest (%{{.*}}) : i64 = (%{{.*}}) to (%{{.*}}) step (%{{.*}}) + omp.loop_nest (%iv) : i64 = (%lb2) to (%ub2) step (%step2) { + %2 = "test.payload"(%iv) : (i64) -> (index) + cf.br ^bb1(%2: index) + ^bb1(%arg2: index): + memref.store %iv, %data2[%arg2] : memref omp.yield - }) {operandSegmentSizes = array, nowait, schedule_val = #omp} : - (index, index, index) -> () + } + omp.terminator + } return } -// CHECK-LABEL: omp_wsloop_pretty -func.func @omp_wsloop_pretty(%lb : index, %ub : index, %step : index, %data_var : memref, %linear_var : i32, %chunk_var : i32, %chunk_var2 : i16) -> () { +// CHECK-LABEL: omp_loop_nest_pretty_multiple +func.func @omp_loop_nest_pretty_multiple(%lb1 : i32, %ub1 : i32, %step1 : i32, + %lb2 : i32, %ub2 : i32, %step2 : i32, %data1 : memref) -> () { - // CHECK: omp.wsloop ordered(2) - // CHECK-SAME: for (%{{.*}}) : index = (%{{.*}}) to (%{{.*}}) step (%{{.*}}) - omp.wsloop ordered(2) - for (%iv) : index = (%lb) to (%ub) step (%step) { - omp.yield + omp.wsloop { + // CHECK: omp.loop_nest (%{{.*}}, %{{.*}}) : i32 = (%{{.*}}, %{{.*}}) to (%{{.*}}, %{{.*}}) step (%{{.*}}, %{{.*}}) + omp.loop_nest (%iv1, %iv2) : i32 = (%lb1, %lb2) to (%ub1, %ub2) step (%step1, %step2) { + %1 = "test.payload"(%iv1) : (i32) -> (index) + %2 = "test.payload"(%iv2) : (i32) -> (index) + memref.store %iv1, %data1[%1] : memref + memref.store %iv2, %data1[%2] : memref + omp.yield + } + omp.terminator } - // CHECK: omp.wsloop linear(%{{.*}} = %{{.*}} : memref) schedule(static) - // CHECK-SAME: for (%{{.*}}) : index = (%{{.*}}) to (%{{.*}}) step (%{{.*}}) - omp.wsloop schedule(static) linear(%data_var = %linear_var : memref) - for (%iv) : index = (%lb) to (%ub) step (%step) { - omp.yield - } + return +} - // CHECK: omp.wsloop linear(%{{.*}} = %{{.*}} : memref) schedule(static = %{{.*}} : i32) ordered(2) - // CHECK-SAME: for (%{{.*}}) : index = (%{{.*}}) to (%{{.*}}) step (%{{.*}}) - omp.wsloop ordered(2) linear(%data_var = %linear_var : memref) schedule(static = %chunk_var : i32) - for (%iv) : index = (%lb) to (%ub) step (%step) { - omp.yield - } +// CHECK-LABEL: omp_wsloop +func.func @omp_wsloop(%lb : index, %ub : index, %step : index, %data_var : memref, %linear_var : i32, %chunk_var : i32) -> () { - // CHECK: omp.wsloop linear(%{{.*}} = %{{.*}} : memref) schedule(dynamic = %{{.*}} : i32, nonmonotonic) ordered(2) - // CHECK-SAME: for (%{{.*}}) : index = (%{{.*}}) to (%{{.*}}) step (%{{.*}}) - omp.wsloop ordered(2) linear(%data_var = %linear_var : memref) schedule(dynamic = %chunk_var : i32, nonmonotonic) - for (%iv) : index = (%lb) to (%ub) step (%step) { - omp.yield - } + // CHECK: omp.wsloop ordered(1) { + // CHECK-NEXT: omp.loop_nest + "omp.wsloop" () ({ + omp.loop_nest (%iv) : index = (%lb) to (%ub) step (%step) { + omp.yield + } + omp.terminator + }) {operandSegmentSizes = array, ordered_val = 1} : + () -> () - // CHECK: omp.wsloop linear(%{{.*}} = %{{.*}} : memref) schedule(dynamic = %{{.*}} : i16, monotonic) ordered(2) - // CHECK-SAME: for (%{{.*}}) : index = (%{{.*}}) to (%{{.*}}) step (%{{.*}}) - omp.wsloop ordered(2) linear(%data_var = %linear_var : memref) schedule(dynamic = %chunk_var2 : i16, monotonic) - for (%iv) : index = (%lb) to (%ub) step (%step) { - omp.yield - } + // CHECK: omp.wsloop linear(%{{.*}} = %{{.*}} : memref) schedule(static) { + // CHECK-NEXT: omp.loop_nest + "omp.wsloop" (%data_var, %linear_var) ({ + omp.loop_nest (%iv) : index = (%lb) to (%ub) step (%step) { + omp.yield + } + omp.terminator + }) {operandSegmentSizes = array, schedule_val = #omp} : + (memref, i32) -> () - // CHECK: omp.wsloop for (%{{.*}}) : index = (%{{.*}}) to (%{{.*}}) step (%{{.*}}) - omp.wsloop for (%iv) : index = (%lb) to (%ub) step (%step) { - omp.yield - } + // CHECK: omp.wsloop linear(%{{.*}} = %{{.*}} : memref, %{{.*}} = %{{.*}} : memref) schedule(static) { + // CHECK-NEXT: omp.loop_nest + "omp.wsloop" (%data_var, %data_var, %linear_var, %linear_var) ({ + omp.loop_nest (%iv) : index = (%lb) to (%ub) step (%step) { + omp.yield + } + omp.terminator + }) {operandSegmentSizes = array, schedule_val = #omp} : + (memref, memref, i32, i32) -> () - // CHECK: omp.wsloop for (%{{.*}}) : index = (%{{.*}}) to (%{{.*}}) inclusive step (%{{.*}}) - omp.wsloop for (%iv) : index = (%lb) to (%ub) inclusive step (%step) { - omp.yield - } + // CHECK: omp.wsloop linear(%{{.*}} = %{{.*}} : memref) schedule(dynamic = %{{.*}}) ordered(2) { + // CHECK-NEXT: omp.loop_nest + "omp.wsloop" (%data_var, %linear_var, %chunk_var) ({ + omp.loop_nest (%iv) : index = (%lb) to (%ub) step (%step) { + omp.yield + } + omp.terminator + }) {operandSegmentSizes = array, schedule_val = #omp, ordered_val = 2} : + (memref, i32, i32) -> () - // CHECK: omp.wsloop nowait - // CHECK-SAME: for (%{{.*}}) : index = (%{{.*}}) to (%{{.*}}) step (%{{.*}}) - omp.wsloop nowait - for (%iv) : index = (%lb) to (%ub) step (%step) { - omp.yield - } + // CHECK: omp.wsloop schedule(auto) nowait { + // CHECK-NEXT: omp.loop_nest + "omp.wsloop" () ({ + omp.loop_nest (%iv) : index = (%lb) to (%ub) step (%step) { + omp.yield + } + omp.terminator + }) {operandSegmentSizes = array, nowait, schedule_val = #omp} : + () -> () - // CHECK: omp.wsloop nowait order(concurrent) - // CHECK-SAME: for (%{{.*}}) : index = (%{{.*}}) to (%{{.*}}) step (%{{.*}}) - omp.wsloop order(concurrent) nowait - for (%iv) : index = (%lb) to (%ub) step (%step) { - omp.yield - } + // CHECK: omp.wsloop { + // CHECK-NEXT: omp.simd + // CHECK-NEXT: omp.loop_nest + "omp.wsloop" () ({ + omp.simd { + omp.loop_nest (%iv) : index = (%lb) to (%ub) step (%step) { + omp.yield + } + omp.terminator + } + omp.terminator + }) : () -> () return } -// CHECK-LABEL: omp_wsloop_pretty_multi_block -func.func @omp_wsloop_pretty_multi_block(%lb : index, %ub : index, %step : index, %data1 : memref, %data2 : memref) -> () { +// CHECK-LABEL: omp_wsloop_pretty +func.func @omp_wsloop_pretty(%lb : index, %ub : index, %step : index, %data_var : memref, %linear_var : i32, %chunk_var : i32, %chunk_var2 : i16) -> () { - // CHECK: omp.wsloop for (%{{.*}}) : index = (%{{.*}}) to (%{{.*}}) step (%{{.*}}) - omp.wsloop for (%iv) : index = (%lb) to (%ub) step (%step) { - %1 = "test.payload"(%iv) : (index) -> (i32) - cf.br ^bb1(%1: i32) - ^bb1(%arg: i32): - memref.store %arg, %data1[%iv] : memref - omp.yield + // CHECK: omp.wsloop ordered(2) { + // CHECK-NEXT: omp.loop_nest + omp.wsloop ordered(2) { + omp.loop_nest (%iv) : index = (%lb) to (%ub) step (%step) { + omp.yield + } + omp.terminator } - // CHECK: omp.wsloop for (%{{.*}}) : index = (%{{.*}}) to (%{{.*}}) step (%{{.*}}) - omp.wsloop for (%iv) : index = (%lb) to (%ub) step (%step) { - %c = "test.condition"(%iv) : (index) -> (i1) - %v1 = "test.payload"(%iv) : (index) -> (i32) - cf.cond_br %c, ^bb1(%v1: i32), ^bb2(%v1: i32) - ^bb1(%arg0: i32): - memref.store %arg0, %data1[%iv] : memref - cf.br ^bb3 - ^bb2(%arg1: i32): - memref.store %arg1, %data2[%iv] : memref - cf.br ^bb3 - ^bb3: - omp.yield + // CHECK: omp.wsloop linear(%{{.*}} = %{{.*}} : memref) schedule(static) { + // CHECK-NEXT: omp.loop_nest + omp.wsloop schedule(static) linear(%data_var = %linear_var : memref) { + omp.loop_nest (%iv) : index = (%lb) to (%ub) step (%step) { + omp.yield + } + omp.terminator } - // CHECK: omp.wsloop for (%{{.*}}) : index = (%{{.*}}) to (%{{.*}}) step (%{{.*}}) - omp.wsloop for (%iv) : index = (%lb) to (%ub) step (%step) { - %c = "test.condition"(%iv) : (index) -> (i1) - %v1 = "test.payload"(%iv) : (index) -> (i32) - cf.cond_br %c, ^bb1(%v1: i32), ^bb2(%v1: i32) - ^bb1(%arg0: i32): - memref.store %arg0, %data1[%iv] : memref - omp.yield - ^bb2(%arg1: i32): - memref.store %arg1, %data2[%iv] : memref - omp.yield + // CHECK: omp.wsloop linear(%{{.*}} = %{{.*}} : memref) schedule(static = %{{.*}} : i32) ordered(2) { + // CHECK-NEXT: omp.loop_nest + omp.wsloop ordered(2) linear(%data_var = %linear_var : memref) schedule(static = %chunk_var : i32) { + omp.loop_nest (%iv) : index = (%lb) to (%ub) step (%step) { + omp.yield + } + omp.terminator } - return -} - -// CHECK-LABEL: omp_wsloop_pretty_non_index -func.func @omp_wsloop_pretty_non_index(%lb1 : i32, %ub1 : i32, %step1 : i32, %lb2 : i64, %ub2 : i64, %step2 : i64, - %data1 : memref, %data2 : memref) -> () { + // CHECK: omp.wsloop linear(%{{.*}} = %{{.*}} : memref) schedule(dynamic = %{{.*}} : i32, nonmonotonic) ordered(2) { + // CHECK-NEXT: omp.loop_nest + omp.wsloop ordered(2) linear(%data_var = %linear_var : memref) schedule(dynamic = %chunk_var : i32, nonmonotonic) { + omp.loop_nest (%iv) : index = (%lb) to (%ub) step (%step) { + omp.yield + } + omp.terminator + } - // CHECK: omp.wsloop for (%{{.*}}) : i32 = (%{{.*}}) to (%{{.*}}) step (%{{.*}}) - omp.wsloop for (%iv1) : i32 = (%lb1) to (%ub1) step (%step1) { - %1 = "test.payload"(%iv1) : (i32) -> (index) - cf.br ^bb1(%1: index) - ^bb1(%arg1: index): - memref.store %iv1, %data1[%arg1] : memref - omp.yield + // CHECK: omp.wsloop linear(%{{.*}} = %{{.*}} : memref) schedule(dynamic = %{{.*}} : i16, monotonic) ordered(2) { + // CHECK-NEXT: omp.loop_nest + omp.wsloop ordered(2) linear(%data_var = %linear_var : memref) schedule(dynamic = %chunk_var2 : i16, monotonic) { + omp.loop_nest (%iv) : index = (%lb) to (%ub) step (%step) { + omp.yield + } + omp.terminator } - // CHECK: omp.wsloop for (%{{.*}}) : i64 = (%{{.*}}) to (%{{.*}}) step (%{{.*}}) - omp.wsloop for (%iv2) : i64 = (%lb2) to (%ub2) step (%step2) { - %2 = "test.payload"(%iv2) : (i64) -> (index) - cf.br ^bb1(%2: index) - ^bb1(%arg2: index): - memref.store %iv2, %data2[%arg2] : memref - omp.yield + // CHECK: omp.wsloop { + // CHECK-NEXT: omp.loop_nest + omp.wsloop { + omp.loop_nest (%iv) : index = (%lb) to (%ub) step (%step) { + omp.yield + } + omp.terminator } - return -} + // CHECK: omp.wsloop nowait { + // CHECK-NEXT: omp.loop_nest + omp.wsloop nowait { + omp.loop_nest (%iv) : index = (%lb) to (%ub) step (%step) { + omp.yield + } + omp.terminator + } -// CHECK-LABEL: omp_wsloop_pretty_multiple -func.func @omp_wsloop_pretty_multiple(%lb1 : i32, %ub1 : i32, %step1 : i32, %lb2 : i32, %ub2 : i32, %step2 : i32, %data1 : memref) -> () { + // CHECK: omp.wsloop nowait order(concurrent) { + // CHECK-NEXT: omp.loop_nest + omp.wsloop order(concurrent) nowait { + omp.loop_nest (%iv) : index = (%lb) to (%ub) step (%step) { + omp.yield + } + omp.terminator + } - // CHECK: omp.wsloop for (%{{.*}}, %{{.*}}) : i32 = (%{{.*}}, %{{.*}}) to (%{{.*}}, %{{.*}}) step (%{{.*}}, %{{.*}}) - omp.wsloop for (%iv1, %iv2) : i32 = (%lb1, %lb2) to (%ub1, %ub2) step (%step1, %step2) { - %1 = "test.payload"(%iv1) : (i32) -> (index) - %2 = "test.payload"(%iv2) : (i32) -> (index) - memref.store %iv1, %data1[%1] : memref - memref.store %iv2, %data1[%2] : memref - omp.yield + // CHECK: omp.wsloop { + // CHECK-NEXT: omp.simd + // CHECK-NEXT: omp.loop_nest + omp.wsloop { + omp.simd { + omp.loop_nest (%iv) : index = (%lb) to (%ub) step (%step) { + omp.yield + } + omp.terminator + } + omp.terminator } return @@ -659,7 +720,7 @@ func.func @omp_distribute(%chunk_size : i32, %data_var : memref, %arg0 : i3 // CHECK: omp.distribute omp.distribute { omp.simd { - omp.loop_nest (%iv2) : i32 = (%arg0) to (%arg0) step (%arg0) { + omp.loop_nest (%iv) : i32 = (%arg0) to (%arg0) step (%arg0) { omp.yield } } @@ -791,17 +852,19 @@ func.func @wsloop_reduction(%lb : index, %ub : index, %step : index) { %c1 = arith.constant 1 : i32 %0 = llvm.alloca %c1 x i32 : (i32) -> !llvm.ptr // CHECK: reduction(@add_f32 %{{.+}} -> %[[PRV:.+]] : !llvm.ptr) - omp.wsloop reduction(@add_f32 %0 -> %prv : !llvm.ptr) - for (%iv) : index = (%lb) to (%ub) step (%step) { - // CHECK: %[[CST:.+]] = arith.constant 2.0{{.*}} : f32 - %cst = arith.constant 2.0 : f32 - // CHECK: %[[LPRV:.+]] = llvm.load %[[PRV]] : !llvm.ptr -> f32 - %lprv = llvm.load %prv : !llvm.ptr -> f32 - // CHECK: %[[RES:.+]] = llvm.fadd %[[LPRV]], %[[CST]] : f32 - %res = llvm.fadd %lprv, %cst: f32 - // CHECK: llvm.store %[[RES]], %[[PRV]] : f32, !llvm.ptr - llvm.store %res, %prv : f32, !llvm.ptr - omp.yield + omp.wsloop reduction(@add_f32 %0 -> %prv : !llvm.ptr) { + omp.loop_nest (%iv) : index = (%lb) to (%ub) step (%step) { + // CHECK: %[[CST:.+]] = arith.constant 2.0{{.*}} : f32 + %cst = arith.constant 2.0 : f32 + // CHECK: %[[LPRV:.+]] = llvm.load %[[PRV]] : !llvm.ptr -> f32 + %lprv = llvm.load %prv : !llvm.ptr -> f32 + // CHECK: %[[RES:.+]] = llvm.fadd %[[LPRV]], %[[CST]] : f32 + %res = llvm.fadd %lprv, %cst: f32 + // CHECK: llvm.store %[[RES]], %[[PRV]] : f32, !llvm.ptr + llvm.store %res, %prv : f32, !llvm.ptr + omp.yield + } + omp.terminator } return } @@ -828,14 +891,19 @@ func.func @parallel_wsloop_reduction(%lb : index, %ub : index, %step : index) { %0 = llvm.alloca %c1 x i32 : (i32) -> !llvm.ptr // CHECK: omp.parallel reduction(@add_f32 %{{.*}} -> %{{.+}} : !llvm.ptr) { omp.parallel reduction(@add_f32 %0 -> %prv : !llvm.ptr) { - // CHECK: omp.wsloop for (%{{.+}}) : index = (%{{.+}}) to (%{{.+}}) step (%{{.+}}) - omp.wsloop for (%iv) : index = (%lb) to (%ub) step (%step) { - %1 = arith.constant 2.0 : f32 - %2 = llvm.load %prv : !llvm.ptr -> f32 - // CHECK: llvm.fadd %{{.+}}, %{{.+}} : f32 - llvm.fadd %1, %2 : f32 - // CHECK: omp.yield - omp.yield + // CHECK: omp.wsloop { + omp.wsloop { + // CHECK: omp.loop_nest (%{{.+}}) : index = (%{{.+}}) to (%{{.+}}) step (%{{.+}}) { + omp.loop_nest (%iv) : index = (%lb) to (%ub) step (%step) { + %1 = arith.constant 2.0 : f32 + %2 = llvm.load %prv : !llvm.ptr -> f32 + // CHECK: llvm.fadd %{{.+}}, %{{.+}} : f32 + llvm.fadd %1, %2 : f32 + // CHECK: omp.yield + omp.yield + } + // CHECK: omp.terminator + omp.terminator } // CHECK: omp.terminator omp.terminator @@ -959,16 +1027,18 @@ combiner { // CHECK-LABEL: func @wsloop_reduction2 func.func @wsloop_reduction2(%lb : index, %ub : index, %step : index) { %0 = memref.alloca() : memref<1xf32> - // CHECK: omp.wsloop reduction(@add2_f32 %{{.+}} -> %{{.+}} : memref<1xf32>) - omp.wsloop reduction(@add2_f32 %0 -> %prv : memref<1xf32>) - for (%iv) : index = (%lb) to (%ub) step (%step) { - %1 = arith.constant 2.0 : f32 - %2 = arith.constant 0 : index - %3 = memref.load %prv[%2] : memref<1xf32> - // CHECK: llvm.fadd - %4 = llvm.fadd %1, %3 : f32 - memref.store %4, %prv[%2] : memref<1xf32> - omp.yield + // CHECK: omp.wsloop reduction(@add2_f32 %{{.+}} -> %{{.+}} : memref<1xf32>) { + omp.wsloop reduction(@add2_f32 %0 -> %prv : memref<1xf32>) { + omp.loop_nest (%iv) : index = (%lb) to (%ub) step (%step) { + %1 = arith.constant 2.0 : f32 + %2 = arith.constant 0 : index + %3 = memref.load %prv[%2] : memref<1xf32> + // CHECK: llvm.fadd + %4 = llvm.fadd %1, %3 : f32 + memref.store %4, %prv[%2] : memref<1xf32> + omp.yield + } + omp.terminator } return } @@ -995,14 +1065,19 @@ func.func @parallel_wsloop_reduction2(%lb : index, %ub : index, %step : index) { %0 = llvm.alloca %c1 x i32 : (i32) -> !llvm.ptr // CHECK: omp.parallel reduction(@add2_f32 %{{.*}} -> %{{.+}} : !llvm.ptr) { omp.parallel reduction(@add2_f32 %0 -> %prv : !llvm.ptr) { - // CHECK: omp.wsloop for (%{{.+}}) : index = (%{{.+}}) to (%{{.+}}) step (%{{.+}}) - omp.wsloop for (%iv) : index = (%lb) to (%ub) step (%step) { - %1 = arith.constant 2.0 : f32 - %2 = llvm.load %prv : !llvm.ptr -> f32 - // CHECK: llvm.fadd %{{.+}}, %{{.+}} : f32 - %3 = llvm.fadd %1, %2 : f32 - // CHECK: omp.yield - omp.yield + // CHECK: omp.wsloop { + omp.wsloop { + // CHECK: omp.loop_nest (%{{.+}}) : index = (%{{.+}}) to (%{{.+}}) step (%{{.+}}) { + omp.loop_nest (%iv) : index = (%lb) to (%ub) step (%step) { + %1 = arith.constant 2.0 : f32 + %2 = llvm.load %prv : !llvm.ptr -> f32 + // CHECK: llvm.fadd %{{.+}}, %{{.+}} : f32 + %3 = llvm.fadd %1, %2 : f32 + // CHECK: omp.yield + omp.yield + } + // CHECK: omp.terminator + omp.terminator } // CHECK: omp.terminator omp.terminator @@ -1076,36 +1151,44 @@ func.func @omp_ordered(%arg1 : i32, %arg2 : i32, %arg3 : i32, omp.terminator } - omp.wsloop ordered(0) - for (%0) : i32 = (%arg1) to (%arg2) step (%arg3) { - omp.ordered.region { - omp.terminator + omp.wsloop ordered(0) { + omp.loop_nest (%0) : i32 = (%arg1) to (%arg2) step (%arg3) { + // CHECK: omp.ordered.region + omp.ordered.region { + // CHECK: omp.terminator + omp.terminator + } + omp.yield } - omp.yield + omp.terminator } - omp.wsloop ordered(1) - for (%0) : i32 = (%arg1) to (%arg2) step (%arg3) { - // Only one DEPEND(SINK: vec) clause - // CHECK: omp.ordered depend_type(dependsink) depend_vec(%{{.*}} : i64) {num_loops_val = 1 : i64} - omp.ordered depend_type(dependsink) depend_vec(%vec0 : i64) {num_loops_val = 1 : i64} + omp.wsloop ordered(1) { + omp.loop_nest (%0) : i32 = (%arg1) to (%arg2) step (%arg3) { + // Only one DEPEND(SINK: vec) clause + // CHECK: omp.ordered depend_type(dependsink) depend_vec(%{{.*}} : i64) {num_loops_val = 1 : i64} + omp.ordered depend_type(dependsink) depend_vec(%vec0 : i64) {num_loops_val = 1 : i64} - // CHECK: omp.ordered depend_type(dependsource) depend_vec(%{{.*}} : i64) {num_loops_val = 1 : i64} - omp.ordered depend_type(dependsource) depend_vec(%vec0 : i64) {num_loops_val = 1 : i64} + // CHECK: omp.ordered depend_type(dependsource) depend_vec(%{{.*}} : i64) {num_loops_val = 1 : i64} + omp.ordered depend_type(dependsource) depend_vec(%vec0 : i64) {num_loops_val = 1 : i64} - omp.yield + omp.yield + } + omp.terminator } - omp.wsloop ordered(2) - for (%0) : i32 = (%arg1) to (%arg2) step (%arg3) { - // Multiple DEPEND(SINK: vec) clauses - // CHECK: omp.ordered depend_type(dependsink) depend_vec(%{{.*}}, %{{.*}}, %{{.*}}, %{{.*}} : i64, i64, i64, i64) {num_loops_val = 2 : i64} - omp.ordered depend_type(dependsink) depend_vec(%vec0, %vec1, %vec2, %vec3 : i64, i64, i64, i64) {num_loops_val = 2 : i64} + omp.wsloop ordered(2) { + omp.loop_nest (%0) : i32 = (%arg1) to (%arg2) step (%arg3) { + // Multiple DEPEND(SINK: vec) clauses + // CHECK: omp.ordered depend_type(dependsink) depend_vec(%{{.*}}, %{{.*}}, %{{.*}}, %{{.*}} : i64, i64, i64, i64) {num_loops_val = 2 : i64} + omp.ordered depend_type(dependsink) depend_vec(%vec0, %vec1, %vec2, %vec3 : i64, i64, i64, i64) {num_loops_val = 2 : i64} - // CHECK: omp.ordered depend_type(dependsource) depend_vec(%{{.*}}, %{{.*}} : i64, i64) {num_loops_val = 2 : i64} - omp.ordered depend_type(dependsource) depend_vec(%vec0, %vec1 : i64, i64) {num_loops_val = 2 : i64} + // CHECK: omp.ordered depend_type(dependsource) depend_vec(%{{.*}}, %{{.*}} : i64, i64) {num_loops_val = 2 : i64} + omp.ordered depend_type(dependsource) depend_vec(%vec0, %vec1 : i64, i64) {num_loops_val = 2 : i64} - omp.yield + omp.yield + } + omp.terminator } return @@ -1956,11 +2039,13 @@ func.func @omp_cancel_parallel(%if_cond : i1) -> () { } func.func @omp_cancel_wsloop(%lb : index, %ub : index, %step : index) { - omp.wsloop - for (%iv) : index = (%lb) to (%ub) step (%step) { - // CHECK: omp.cancel cancellation_construct_type(loop) - omp.cancel cancellation_construct_type(loop) - // CHECK: omp.terminator + omp.wsloop { + omp.loop_nest (%iv) : index = (%lb) to (%ub) step (%step) { + // CHECK: omp.cancel cancellation_construct_type(loop) + omp.cancel cancellation_construct_type(loop) + // CHECK: omp.yield + omp.yield + } omp.terminator } return @@ -1991,13 +2076,15 @@ func.func @omp_cancellationpoint_parallel() -> () { } func.func @omp_cancellationpoint_wsloop(%lb : index, %ub : index, %step : index) { - omp.wsloop - for (%iv) : index = (%lb) to (%ub) step (%step) { - // CHECK: omp.cancellation_point cancellation_construct_type(loop) - omp.cancellation_point cancellation_construct_type(loop) - // CHECK: omp.cancel cancellation_construct_type(loop) - omp.cancel cancellation_construct_type(loop) - // CHECK: omp.terminator + omp.wsloop { + omp.loop_nest (%iv) : index = (%lb) to (%ub) step (%step) { + // CHECK: omp.cancellation_point cancellation_construct_type(loop) + omp.cancellation_point cancellation_construct_type(loop) + // CHECK: omp.cancel cancellation_construct_type(loop) + omp.cancel cancellation_construct_type(loop) + // CHECK: omp.yield + omp.yield + } omp.terminator } return diff --git a/mlir/test/Dialect/SCF/forall-to-for.mlir b/mlir/test/Dialect/SCF/forall-to-for.mlir new file mode 100644 index 0000000000000000000000000000000000000000..e7d183fb9d2b54d379adb0391b00d75d406ec8fd --- /dev/null +++ b/mlir/test/Dialect/SCF/forall-to-for.mlir @@ -0,0 +1,57 @@ +// RUN: mlir-opt %s -pass-pipeline='builtin.module(func.func(scf-forall-to-for))' -split-input-file | FileCheck %s + +func.func private @callee(%i: index, %j: index) + +// CHECK-LABEL: @two_iters +// CHECK-SAME: %[[UB1:.+]]: index, %[[UB2:.+]]: index +func.func @two_iters(%ub1: index, %ub2: index) { + scf.forall (%i, %j) in (%ub1, %ub2) { + func.call @callee(%i, %j) : (index, index) -> () + } + // CHECK: scf.for %[[IV1:.+]] = %{{.*}} to %[[UB1]] + // CHECK: scf.for %[[IV2:.+]] = %{{.*}} to %[[UB2]] + // CHECK: func.call @callee(%[[IV1]], %[[IV2]]) + return +} + +// ----- + +func.func private @callee(%i: index, %j: index) + +// CHECK-LABEL: @repeated +// CHECK-SAME: %[[UB1:.+]]: index, %[[UB2:.+]]: index +func.func @repeated(%ub1: index, %ub2: index) { + scf.forall (%i, %j) in (%ub1, %ub2) { + func.call @callee(%i, %j) : (index, index) -> () + } + // CHECK: scf.for %[[IV1:.+]] = %{{.*}} to %[[UB1]] + // CHECK: scf.for %[[IV2:.+]] = %{{.*}} to %[[UB2]] + // CHECK: func.call @callee(%[[IV1]], %[[IV2]]) + scf.forall (%i, %j) in (%ub1, %ub2) { + func.call @callee(%i, %j) : (index, index) -> () + } + // CHECK: scf.for %[[IV1:.+]] = %{{.*}} to %[[UB1]] + // CHECK: scf.for %[[IV2:.+]] = %{{.*}} to %[[UB2]] + // CHECK: func.call @callee(%[[IV1]], %[[IV2]]) + return +} + +// ----- + +func.func private @callee(%i: index, %j: index, %k: index, %l: index) + +// CHECK-LABEL: @nested +// CHECK-SAME: %[[UB1:.+]]: index, %[[UB2:.+]]: index, %[[UB3:.+]]: index, %[[UB4:.+]]: index +func.func @nested(%ub1: index, %ub2: index, %ub3: index, %ub4: index) { + // CHECK: scf.for %[[IV1:.+]] = %{{.*}} to %[[UB1]] + // CHECK: scf.for %[[IV2:.+]] = %{{.*}} to %[[UB2]] + // CHECK: scf.for %[[IV3:.+]] = %{{.*}} to %[[UB3]] + // CHECK: scf.for %[[IV4:.+]] = %{{.*}} to %[[UB4]] + // CHECK: func.call @callee(%[[IV1]], %[[IV2]], %[[IV3]], %[[IV4]]) + scf.forall (%i, %j) in (%ub1, %ub2) { + scf.forall (%k, %l) in (%ub3, %ub4) { + func.call @callee(%i, %j, %k, %l) : (index, index, index, index) -> () + } + } + return +} diff --git a/mlir/test/Dialect/SparseTensor/fuse_sparse_concat_with_extract_slice.mlir b/mlir/test/Dialect/SparseTensor/fuse_sparse_concat_with_extract_slice.mlir new file mode 100644 index 0000000000000000000000000000000000000000..5d93301bc8ca76489242024c51082272df45c0cb --- /dev/null +++ b/mlir/test/Dialect/SparseTensor/fuse_sparse_concat_with_extract_slice.mlir @@ -0,0 +1,23 @@ +// RUN: mlir-opt %s --pre-sparsification-rewrite | FileCheck %s + +#CCCD = #sparse_tensor.encoding<{ map = (d0, d1, d2, d3) -> (d0 : compressed, d1 : compressed, d2 : compressed, d3 : dense) }> + + + +// CHECK-LABEL: func.func @fuse_concat_with_extract( +// CHECK-SAME: %[[VAL_0:.*0]]: tensor<128x32x32x1xf32, #sparse{{[0-9]*}}>, +// CHECK-SAME: %[[VAL_1:.*1]]: tensor<128x32x32x1xf32, #sparse{{[0-9]*}}>, +// CHECK-SAME: %[[VAL_2:.*2]]: tensor<128x32x32x1xf32, #sparse{{[0-9]*}}>) +// CHECK-NOT: tensor.concat +// CHECK-NOT: tensor.extract_slice +// CHECK: return %[[VAL_0]], %[[VAL_1]], %[[VAL_2]] +// CHECK: } +func.func @fuse_concat_with_extract(%t0 : tensor<128x32x32x1xf32, #CCCD>, + %t1 : tensor<128x32x32x1xf32, #CCCD>, + %t2 : tensor<128x32x32x1xf32, #CCCD>) -> (tensor<128x32x32x1xf32, #CCCD>, tensor<128x32x32x1xf32, #CCCD>, tensor<128x32x32x1xf32, #CCCD>) { + %concat = tensor.concat dim(3) %t0, %t1, %t2 : (tensor<128x32x32x1xf32, #CCCD>, tensor<128x32x32x1xf32, #CCCD>, tensor<128x32x32x1xf32, #CCCD>) -> tensor<128x32x32x3xf32, #CCCD> + %r0 = tensor.extract_slice %concat[0, 0, 0, 0] [128, 32, 32, 1] [1, 1, 1, 1] : tensor<128x32x32x3xf32, #CCCD> to tensor<128x32x32x1xf32, #CCCD> + %r1 = tensor.extract_slice %concat[0, 0, 0, 1] [128, 32, 32, 1] [1, 1, 1, 1] : tensor<128x32x32x3xf32, #CCCD> to tensor<128x32x32x1xf32, #CCCD> + %r2 = tensor.extract_slice %concat[0, 0, 0, 2] [128, 32, 32, 1] [1, 1, 1, 1] : tensor<128x32x32x3xf32, #CCCD> to tensor<128x32x32x1xf32, #CCCD> + return %r0, %r1, %r2 : tensor<128x32x32x1xf32, #CCCD>, tensor<128x32x32x1xf32, #CCCD>, tensor<128x32x32x1xf32, #CCCD> +} diff --git a/mlir/test/Dialect/SparseTensor/roundtrip_encoding.mlir b/mlir/test/Dialect/SparseTensor/roundtrip_encoding.mlir index 66e61afd897dd13747427eecba8206b8f978c871..7eeda9a988026885b54f05e04afcb6101e117a85 100644 --- a/mlir/test/Dialect/SparseTensor/roundtrip_encoding.mlir +++ b/mlir/test/Dialect/SparseTensor/roundtrip_encoding.mlir @@ -22,6 +22,64 @@ func.func private @sparse_csr(tensor) // ----- +#CSR_OnlyOnes = #sparse_tensor.encoding<{ + map = (d0, d1) -> (d0 : dense, d1 : compressed), + posWidth = 64, + crdWidth = 64, + explicitVal = 1.0 : f32, + implicitVal = 0.0 : f32 +}> + +// CHECK: #[[$CSR_OnlyOnes:.*]] = #sparse_tensor.encoding<{ map = (d0, d1) -> (d0 : dense, d1 : compressed), posWidth = 64, crdWidth = 64, explicitVal = 1.000000e+00 : f32, implicitVal = 0.000000e+00 : f32 }> +// CHECK-LABEL: func private @sparse_csr( +// CHECK-SAME: tensor) +func.func private @sparse_csr(tensor) + +// ----- + +#CSR_OnlyOnes = #sparse_tensor.encoding<{ + map = (d0, d1) -> (d0 : dense, d1 : compressed), + explicitVal = 1.0 : f64, + implicitVal = 0.0 : f64 +}> + +// CHECK: #[[$CSR_OnlyOnes:.*]] = #sparse_tensor.encoding<{ map = (d0, d1) -> (d0 : dense, d1 : compressed), explicitVal = 1.000000e+00 : f64, implicitVal = 0.000000e+00 : f64 }> +// CHECK-LABEL: func private @sparse_csr( +// CHECK-SAME: tensor) +func.func private @sparse_csr(tensor) + +// ----- + +#CSR_OnlyOnes = #sparse_tensor.encoding<{ + map = (d0, d1) -> (d0 : dense, d1 : compressed), + posWidth = 64, + crdWidth = 64, + explicitVal = 1 : i32, + implicitVal = 0 : i32 +}> + +// CHECK: #[[$CSR_OnlyOnes:.*]] = #sparse_tensor.encoding<{ map = (d0, d1) -> (d0 : dense, d1 : compressed), posWidth = 64, crdWidth = 64, explicitVal = 1 : i32, implicitVal = 0 : i32 }> +// CHECK-LABEL: func private @sparse_csr( +// CHECK-SAME: tensor) +func.func private @sparse_csr(tensor) + +// ----- + +#CSR_OnlyOnes = #sparse_tensor.encoding<{ + map = (d0, d1) -> (d0 : dense, d1 : compressed), + posWidth = 64, + crdWidth = 64, + explicitVal = 1 : i64, + implicitVal = 0 : i64 +}> + +// CHECK: #[[$CSR_OnlyOnes:.*]] = #sparse_tensor.encoding<{ map = (d0, d1) -> (d0 : dense, d1 : compressed), posWidth = 64, crdWidth = 64, explicitVal = 1 : i64, implicitVal = 0 : i64 }> +// CHECK-LABEL: func private @sparse_csr( +// CHECK-SAME: tensor) +func.func private @sparse_csr(tensor) + +// ----- + #BCSR = #sparse_tensor.encoding<{ map = (d0, d1, d2) -> (d0 : batch, d1: dense, d2 : compressed), }> diff --git a/mlir/test/Dialect/Tensor/canonicalize.mlir b/mlir/test/Dialect/Tensor/canonicalize.mlir index 751c57eacd7ae5a33a7cd1b5c616c4316ce17f75..9a4dd2f3b5cc11e4af567eb97479bec3e9d9b5e2 100644 --- a/mlir/test/Dialect/Tensor/canonicalize.mlir +++ b/mlir/test/Dialect/Tensor/canonicalize.mlir @@ -2431,6 +2431,15 @@ func.func @reshape_nofold_2d(%arg0 : tensor) -> tensor { return %reshape : tensor } +// ----- + +// CHECK-LABEL: @reshape_nofold_2d_ins +func.func @reshape_nofold_2d_ins(%arg0 : tensor, %arg1: index, %arg2: index) -> tensor { + %ds = tensor.from_elements %arg1, %arg2 : tensor<2xindex> + // CHECK: tensor.reshape + %reshape = tensor.reshape %arg0(%ds) : (tensor, tensor<2xindex>) -> tensor + return %reshape : tensor +} // ----- diff --git a/mlir/test/Dialect/Vector/vector-multi-reduction-lowering.mlir b/mlir/test/Dialect/Vector/vector-multi-reduction-lowering.mlir index 22808aa7d6acc352d35afdd7470715869056f43e..f70d23a193229750d216fed2572f457b70947f2f 100644 --- a/mlir/test/Dialect/Vector/vector-multi-reduction-lowering.mlir +++ b/mlir/test/Dialect/Vector/vector-multi-reduction-lowering.mlir @@ -281,6 +281,23 @@ func.func private @scalable_dims(%A : vector<8x[4]x2xf32>, %B: vector<8x[4]xf32> // CHECK: %[[VAL_163:.*]] = vector.shape_cast %[[VAL_162]] : vector<[32]xf32> to vector<8x[4]xf32> // CHECK: return %[[VAL_163]] : vector<8x[4]xf32> +// Check that OneDimMultiReductionToTwoDim handles scalable dim +func.func @scalable_dim_1d(%A: vector<[4]xf32>, %B: f32, %C: vector<[4]xi1>) -> f32 { + %0 = vector.mask %C { vector.multi_reduction , %A, %B [0] : vector<[4]xf32> to f32 } : vector<[4]xi1> -> f32 + return %0 : f32 +} + +// CHECK-LABEL: func.func @scalable_dim_1d( +// CHECK-SAME: %[[ARG_0:.*]]: vector<[4]xf32>, +// CHECK-SAME: %[[ARG_1:.*]]: f32, +// CHECK-SAME: %[[ARG_2:.*]]: vector<[4]xi1>) -> f32 { +// CHECK-DAG: %[[VAL_0:.*]] = arith.constant 0 : index +// CHECK-DAG: %[[VAL_1:.*]] = arith.constant dense<0.000000e+00> : vector<1xf32> +// CHECK: %[[VAL_2:.*]] = vector.mask %[[ARG_2]] { vector.reduction , %[[ARG_0]], %[[ARG_1]] : vector<[4]xf32> into f32 } : vector<[4]xi1> -> f32 +// CHECK: %[[VAL_3:.*]] = vector.insertelement %[[VAL_2]], %[[VAL_1]][%[[VAL_0]] : index] : vector<1xf32> +// CHECK: %[[VAL_4:.*]] = vector.extract %[[VAL_3]][0] : f32 from vector<1xf32> +// CHECK: return %[[VAL_4]] : f32 + module attributes {transform.with_named_sequence} { transform.named_sequence @__transform_main(%root : !transform.any_op {transform.readonly}) { %func_op = transform.structured.match ops{["func.func"]} in %root : (!transform.any_op) -> !transform.op<"func.func"> diff --git a/mlir/test/Dialect/XeGPU/XeGPUOps.mlir b/mlir/test/Dialect/XeGPU/XeGPUOps.mlir index f0945c79a94ac3db85e3dc4f1c03759049dabf51..00d32d2a2ee9436d08650d968db303fde829f32e 100644 --- a/mlir/test/Dialect/XeGPU/XeGPUOps.mlir +++ b/mlir/test/Dialect/XeGPU/XeGPUOps.mlir @@ -80,7 +80,7 @@ gpu.func @test_prefetch_vc(%src: ui64) { //CHECK: %[[R0:.*]] = xegpu.create_tdesc %arg0 [0, 8, 16, 24] {chunk_size = 2 : i64} : ui64 -> !xegpu.tensor_desc<4x2xf32, #xegpu.tdesc_attr> %1 = xegpu.create_tdesc %src[0, 8, 16, 24] {chunk_size = 2} : ui64 -> !xegpu.tensor_desc<4x2xf32, #xegpu.tdesc_attr> // CHECK: xegpu.prefetch %[[R0]] <{l1_hint = #xegpu.cache_hint, l2_hint = #xegpu.cache_hint}> : !xegpu.tensor_desc<4x2xf32, #xegpu.tdesc_attr> - xegpu.prefetch %1 <{l1_hint = #xegpu.cache_hint, l2_hint = #xegpu.cache_hint}>: !xegpu.tensor_desc<4x2xf32, #xegpu.tdesc_attr> + xegpu.prefetch %1 <{l1_hint = #xegpu.cache_hint, l2_hint = #xegpu.cache_hint}>: !xegpu.tensor_desc<4x2xf32, #xegpu.tdesc_attr> gpu.return } @@ -121,4 +121,59 @@ gpu.func @test_create_update_tdesc_vc(%src: ui64) { gpu.return } -} \ No newline at end of file +// CHECK: gpu.func @test_dpas_vc(%[[arg0:.*]]: vector<8x8x2xf16>, %[[arg1:.*]]: vector<8x16x2xf16>) +gpu.func @test_dpas_vc(%a : vector<8x8x2xf16>, %b: vector<8x16x2xf16>) { + // CHECK: %0 = xegpu.dpas %[[arg0]], %[[arg1]] : vector<8x8x2xf16>, vector<8x16x2xf16> -> vector<8x16xf32> + %1 = xegpu.dpas %a, %b: vector<8x8x2xf16>, vector<8x16x2xf16> -> vector<8x16xf32> + gpu.return +} + +// CHECK: gpu.func @test_atomic_rmw(%[[arg0:.*]]: ui64, %[[arg1:.*]]: vector<16xf32>, %[[arg2:.*]]: vector<16xi1>) +gpu.func @test_atomic_rmw(%src: ui64, %value : vector<16xf32>, %mask : vector<16xi1>) { + //CHECK: %[[R0:.*]] = xegpu.create_tdesc %[[arg0]] [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15] : ui64 -> !xegpu.tensor_desc<16xf32, #xegpu.tdesc_attr> + %1 = xegpu.create_tdesc %src[0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15]: ui64 -> !xegpu.tensor_desc<16xf32, #xegpu.tdesc_attr> + //CHECK: %[[R1:.*]] = xegpu.atomic_rmw addf %[[R0]], %[[arg2]], %[[arg1]] : <16xf32, #xegpu.tdesc_attr>, vector<16xi1>, vector<16xf32> -> vector<16xf32> + xegpu.atomic_rmw addf %1, %mask, %value: !xegpu.tensor_desc<16xf32, #xegpu.tdesc_attr>, vector<16xi1>, vector<16xf32> -> vector<16xf32> + gpu.return +} + +// CHECK: gpu.func @alloc_nbarrier({{.*}}) { +gpu.func @alloc_nbarrier() { + // CHECK: xegpu.alloc_nbarrier + xegpu.alloc_nbarrier 8 + gpu.return +} + +// CHECK: gpu.func @init_nbarrier({{.*}}) { +gpu.func @init_nbarrier() { + //CHECK: %[[c1:.*]] = arith.constant 1 : i8 + //CHECK: %[[c16:.*]] = arith.constant 16 : i8 + %nbarrier_id = arith.constant 1 : i8 + %threads_count = arith.constant 16 : i8 + //CHECK: xegpu.init_nbarrier %[[c1]], %[[c16]] : i8, i8 -> !xegpu.nbarrier + %nbarrier = xegpu.init_nbarrier %nbarrier_id, %threads_count : i8, i8 -> !xegpu.nbarrier + gpu.return +} + +// CHECK: gpu.func @nbarrier_arrive(%[[arg0:.*]]: !xegpu.nbarrier) { +gpu.func @nbarrier_arrive(%nbarrier : !xegpu.nbarrier) { + //CHECK: xegpu.nbarrier_arrive %[[arg0]] : !xegpu.nbarrier + xegpu.nbarrier_arrive %nbarrier : !xegpu.nbarrier + gpu.return +} + +// CHECK: gpu.func @nbarrier_wait(%[[arg0:.*]]: !xegpu.nbarrier) { +gpu.func @nbarrier_wait(%nbarrier : !xegpu.nbarrier) { + //CHECK: xegpu.nbarrier_wait %[[arg0]] : !xegpu.nbarrier + xegpu.nbarrier_wait %nbarrier : !xegpu.nbarrier + gpu.return +} + +// CHECK-LABEL: gpu.func @fence({{.*}}) { +gpu.func @fence() { + //CHECK: xegpu.fence memory_kind = global, fence_scope = workgroup + xegpu.fence memory_kind = global, fence_scope = workgroup + gpu.return +} + +} diff --git a/mlir/test/Dialect/XeGPU/invalid.mlir b/mlir/test/Dialect/XeGPU/invalid.mlir index 5e29361ec690873bf1bbfb60326f6f4ee2bc0619..7819ad60b97d923abb56eb96d8fda19fe21eca49 100644 --- a/mlir/test/Dialect/XeGPU/invalid.mlir +++ b/mlir/test/Dialect/XeGPU/invalid.mlir @@ -156,4 +156,32 @@ func.func @test_store_scatter_vc_2(%src: ui64) { xegpu.store %1, %2, %0 <{l1_hint = #xegpu.cache_hint}> : vector<4x2xf32>, !xegpu.tensor_desc<4x2xf32, #xegpu.tdesc_attr>, vector<4xi1> return +} + +// ----- +func.func @test_dpas_vc_1(%a : vector<8x4x2xf16>, %b: vector<8x16x2xf16>) { + // expected-error@+1 {{K-dimension or vnni-factor mismatch}} + %1 = xegpu.dpas %a, %b : vector<8x4x2xf16>, vector<8x16x2xf16> -> vector<8x16xf32> + return +} + +// ----- +func.func @test_dpas_vc_2(%a : vector<8x16xf16>, %b: vector<8x16x2xf16>) { + // expected-error@+1 {{lhs and rhs rank does not match for dpas op, or their rank is not 3}} + %1 = xegpu.dpas %a, %b : vector<8x16xf16>, vector<8x16x2xf16> -> vector<8x16xf32> + return +} + +// ----- +func.func @test_dpas_vc_3(%a : vector<8x16xf16>, %b: vector<16x16xf16>) { + // expected-error@+1 {{lhs and rhs rank does not match for dpas op, or their rank is not 3}} + %1 = xegpu.dpas %a, %b : vector<8x16xf16>, vector<16x16xf16> -> vector<8x16xf32> + return +} + +// ----- +func.func @test_dpas_vc_4(%a : vector<8x8x2xf16>, %b: vector<8x16x2xf16>, %c : vector<8x16xf16>) { + // expected-error@+1 {{Accumulator and Result for dpas op should have the same type}} + %1 = xegpu.dpas %a, %b, %c : vector<8x8x2xf16>, vector<8x16x2xf16>, vector<8x16xf16> -> vector<8x16xf32> + return } \ No newline at end of file diff --git a/mlir/test/Examples/NVGPU/Ch0.py b/mlir/test/Examples/NVGPU/Ch0.py new file mode 100644 index 0000000000000000000000000000000000000000..8f60088178d11952aab22dd99c9a7fd244fd2c81 --- /dev/null +++ b/mlir/test/Examples/NVGPU/Ch0.py @@ -0,0 +1,50 @@ +# RUN: env SUPPORT_LIB=%mlir_cuda_runtime \ +# RUN: %PYTHON %s | FileCheck %s + +# ===----------------------------------------------------------------------===// +# Chapter 0 : Hello World +# ===----------------------------------------------------------------------===// +# +# This program demonstrates Hello World: +# 1. Build MLIR function with arguments +# 2. Build MLIR GPU kernel +# 3. Print from a GPU thread +# 4. Pass arguments, JIT compile and run the MLIR function +# +# ===----------------------------------------------------------------------===// + + +from mlir.dialects import gpu +from tools.nvdsl import * + + +# 1. The decorator generates a MLIR func.func. +# Everything inside the Python function becomes the body of the func. +# The decorator also translates `alpha` to an `index` type. +@NVDSL.mlir_func +def main(alpha): + # 2. The decorator generates a MLIR gpu.launch. + # Everything inside the Python function becomes the body of the gpu.launch. + # This allows for late outlining of the GPU kernel, enabling optimizations + # like constant folding from host to device. + @NVDSL.mlir_gpu_launch(grid=(1, 1, 1), block=(4, 1, 1)) + def kernel(): + tidx = gpu.thread_id(gpu.Dimension.x) + # + operator generates arith.addi + myValue = alpha + tidx + # Print from a GPU thread + gpu.printf("GPU thread %llu has %llu\n", [tidx, myValue]) + + # 3. Call the GPU kernel + kernel() + + +alpha = 100 +# 4. The `mlir_func` decorator JIT compiles the IR and executes the MLIR function. +main(alpha) + + +# CHECK: GPU thread 0 has 100 +# CHECK: GPU thread 1 has 101 +# CHECK: GPU thread 2 has 102 +# CHECK: GPU thread 3 has 103 diff --git a/mlir/test/Examples/NVGPU/Ch1.py b/mlir/test/Examples/NVGPU/Ch1.py new file mode 100644 index 0000000000000000000000000000000000000000..da65aa2ef6a172a33628c6f764250dbf5622e46b --- /dev/null +++ b/mlir/test/Examples/NVGPU/Ch1.py @@ -0,0 +1,66 @@ +# RUN: env SUPPORT_LIB=%mlir_cuda_runtime \ +# RUN: %PYTHON %s | FileCheck %s + +# ===----------------------------------------------------------------------===// +# Chapter 1 : 2D Saxpy +# ===----------------------------------------------------------------------===// +# +# This program demonstrates 2D Saxpy: +# 1. Use GPU dialect to allocate and copy memory host to gpu and vice versa +# 2. Computes 2D SAXPY kernel using operator overloading +# 3. Pass numpy arrays to MLIR as memref arguments +# 4. Verify MLIR program with reference computation in python +# +# ===----------------------------------------------------------------------===// + + +from mlir import ir +from mlir.dialects import gpu, memref +from tools.nvdsl import * +import numpy as np + + +@NVDSL.mlir_func +def saxpy(x, y, alpha): + # 1. Use MLIR GPU dialect to allocate and copy memory + token_ty = ir.Type.parse("!gpu.async.token") + t1 = gpu.wait(token_ty, []) + x_dev, t2 = gpu.alloc(x.type, token_ty, [t1], [], []) + y_dev, t3 = gpu.alloc(y.type, token_ty, [t2], [], []) + t4 = gpu.memcpy(token_ty, [t3], x_dev, x) + t5 = gpu.memcpy(token_ty, [t4], y_dev, y) + t6 = gpu.wait(token_ty, [t5]) + + # 2. Compute 2D SAXPY kernel + @NVDSL.mlir_gpu_launch(grid=(M, 1, 1), block=(N, 1, 1)) + def saxpy_kernel(): + bidx = gpu.block_id(gpu.Dimension.x) + tidx = gpu.thread_id(gpu.Dimension.x) + x_val = memref.load(x_dev, [bidx, tidx]) + y_val = memref.load(y_dev, [bidx, tidx]) + + # SAXPY: y[i] += a * x[i]; + y_val += x_val * alpha + + memref.store(y_val, y_dev, [bidx, tidx]) + + saxpy_kernel() + + t7 = gpu.memcpy(token_ty, [t6], y, y_dev) + gpu.wait(token_ty, [t7]) + + +# 3. Pass numpy arrays to MLIR +M = 256 +N = 32 +alpha = 2.0 +x = np.random.randn(M, N).astype(np.float32) +y = np.ones((M, N), np.float32) +saxpy(x, y, alpha) + +# 4. Verify MLIR with reference computation +ref = np.ones((M, N), np.float32) +ref += x * alpha +np.testing.assert_allclose(y, ref, rtol=5e-03, atol=1e-01) +print("PASS") +# CHECK-NOT: Mismatched elements diff --git a/mlir/test/Examples/NVGPU/Ch2.py b/mlir/test/Examples/NVGPU/Ch2.py new file mode 100644 index 0000000000000000000000000000000000000000..78c14cb2c7ad8ce5040cff496bff2f6fd0160855 --- /dev/null +++ b/mlir/test/Examples/NVGPU/Ch2.py @@ -0,0 +1,93 @@ +# RUN: env SUPPORT_LIB=%mlir_cuda_runtime \ +# RUN: %PYTHON %s | FileCheck %s + +# ===----------------------------------------------------------------------===// +# Chapter 2 : 2D Saxpy with TMA +# ===----------------------------------------------------------------------===// +# +# This program demonstrates 2D Saxpy. It is same as Chapter 1, +# but it loads data using TMA (Tensor Memory Accelerator) +# +# This chapter introduces demonstrates: +# 1. Computes 2D SAXPY in the same way as Ch1.py but loads data using TMA +# 2. Create and initialize 1 asynchronous transactional barrier (mbarrier) +# 3. Thread-0 Load request data load from TMA for each thread block +# 4. Each thread block loads <1x32xf32> for x and y. +# 5. Wait for completion of TMA load with mbarrier +# +# ===----------------------------------------------------------------------===// + +from mlir import ir +from mlir.dialects import nvgpu, scf, arith, memref, vector, gpu +from tools.nvdsl import * +from mlir import runtime as rt +from mlir.extras import types as T +import numpy as np + + +@NVDSL.mlir_func +def saxpy(x, y, alpha): + token_ty = ir.Type.parse("!gpu.async.token") + t1 = gpu.wait(token_ty, []) + x_dev, t2 = gpu.alloc(x.type, token_ty, [t1], [], []) + y_dev, t3 = gpu.alloc(y.type, token_ty, [t2], [], []) + t4 = gpu.memcpy(token_ty, [t3], x_dev, x) + t5 = gpu.memcpy(token_ty, [t4], y_dev, y) + t6 = gpu.wait(token_ty, [t5]) + + x_tma = TMA([1, N], x.type) + y_tma = TMA([1, N], y.type) + x_tma.create_descriptor(x_dev) + y_tma.create_descriptor(y_dev) + sz_x = get_type_size(x_tma.tma_memref) + sz_y = get_type_size(x_tma.tma_memref) + sz = sz_x + sz_y + + @NVDSL.mlir_gpu_launch(grid=(M, 1, 1), block=(N, 1, 1), smem=sz) + def saxpy_tma_kernel(): + bidx = gpu.block_id(gpu.Dimension.x) + tidx = gpu.thread_id(gpu.Dimension.x) + isThread0 = tidx == 0 + + # 1. Create and initialize asynchronous transactional barrier (mbarrier) + mbar_group = Mbarriers(number_of_barriers=1) + mbar_group[0].init(1, predicate=isThread0) + + # 2. Execute Tensor Memory Accelerator (TMA) Load + x_smem = get_dynamic_shared_memory([1, N], T.f32()) + y_smem = get_dynamic_shared_memory([1, N], T.f32(), offset=sz_x) + x_tma.load(x_smem, mbar_group[0], coords=[0, bidx], predicate=isThread0) + y_tma.load(y_smem, mbar_group[0], coords=[0, bidx], predicate=isThread0) + mbar_group[0].arrive(txcount=sz, predicate=isThread0) + + # 3. Wait for completion of TMA load with mbarrier + mbar_group[0].try_wait() + + x_val = memref.load(x_smem, [const(0), tidx]) + y_val = memref.load(y_smem, [const(0), tidx]) + + # SAXPY: y[i] += a * x[i]; + y_val += x_val * alpha + + memref.store(y_val, y_dev, [bidx, tidx]) + + saxpy_tma_kernel() + + t7 = gpu.memcpy(token_ty, [t6], y, y_dev) + gpu.wait(token_ty, [t7]) + + +# 3. Pass numpy arrays to MLIR +M = 256 +N = 32 +alpha = 2.0 +x = np.random.randn(M, N).astype(np.float32) +y = np.ones((M, N), np.float32) +saxpy(x, y, alpha) + +# 4. Verify MLIR with reference computation +ref = np.ones((M, N), np.float32) +ref += x * alpha +np.testing.assert_allclose(y, ref, rtol=5e-03, atol=1e-01) +print("PASS") +# CHECK-NOT: Mismatched elements diff --git a/mlir/test/Examples/NVGPU/Ch3.py b/mlir/test/Examples/NVGPU/Ch3.py new file mode 100644 index 0000000000000000000000000000000000000000..a417014de8b49a4d9afabcff110ea288581363ce --- /dev/null +++ b/mlir/test/Examples/NVGPU/Ch3.py @@ -0,0 +1,129 @@ +# RUN: env SUPPORT_LIB=%mlir_cuda_runtime \ +# RUN: %PYTHON %s | FileCheck %s + +# ===----------------------------------------------------------------------===// +# Chapter 3 : GEMM 128x128x64 with Tensor Core +# ===----------------------------------------------------------------------===// +# +# This program demonstrates a GEMM operation with 128x128x64 matrix multiplication +# +# This chapter introduces demonstrates: +# 1. Execute TMA Load for two input matrices +# 2. Performs Tensor Core GEMM 128x128x64 by warpgroup +# 3. Stores fragmented registers to global memory by warpgroup +# +# ===----------------------------------------------------------------------===// + + +from mlir import ir +from mlir.dialects import nvgpu, scf, arith, memref, vector, gpu +from tools.nvdsl import * +from mlir.extras import types as T +import numpy as np + + +def tma_load( + mbar_group: Mbarriers, + a_tma: TMA, + b_tma: TMA, + p, +): + """ + TMA loads two input matrices from global memory to shared memory. It performs the following operations: + + - tma.load a_shared_memory[0] at coordinate [0, 0] (Loads 128x64) + - tma.load b_shared_memory[0] at coordinate [0, 0] (Loads 64x64) + - tma.load b_shared_memory[0] at coordinate [64, 0] (Loads 64x64) + + mbarrier.arrive ta_count = 128x64xf16 + 64x128xf16 + """ + + size_tma_a = get_type_size(a_tma.tma_memref) + size_tma_b = get_type_size(b_tma.tma_memref) + ta_count = size_tma_a + (size_tma_b * 2) + + off_b = size_tma_a + off_b2 = off_b + size_tma_b + a_elem_ty = a_tma.tma_memref.element_type + b_elem_ty = b_tma.tma_memref.element_type + a = get_dynamic_shared_memory(a_tma.tma_memref.shape, a_elem_ty) + b1 = get_dynamic_shared_memory(b_tma.tma_memref.shape, b_elem_ty, off_b) + b2 = get_dynamic_shared_memory(b_tma.tma_memref.shape, b_elem_ty, off_b2) + + mbar_group[0].arrive(ta_count, predicate=p) + + a_tma.load(a, mbar_group[0], coords=[0, 0], predicate=p) + b_tma.load(b1, mbar_group[0], coords=[0, 0], predicate=p) + b_tma.load(b2, mbar_group[0], coords=[64, 0], predicate=p) + + +@NVDSL.mlir_func +def gemm_128_128_64(a, b, d): + token_ty = ir.Type.parse("!gpu.async.token") + t1 = gpu.wait(token_ty, []) + a_dev, t2 = gpu.alloc(a.type, token_ty, [t1], [], []) + b_dev, t3 = gpu.alloc(b.type, token_ty, [t2], [], []) + d_dev, t4 = gpu.alloc(d.type, token_ty, [t3], [], []) + t5 = gpu.memcpy(token_ty, [t4], a_dev, a) + t6 = gpu.memcpy(token_ty, [t5], b_dev, b) + t7 = gpu.wait(token_ty, [t6]) + + sw = nvgpu.TensorMapSwizzleKind.SWIZZLE_128B + a_tma = TMA([128, 64], a.type, swizzle=sw) + b_tma = TMA([64, 64], b.type, swizzle=sw) + a_tma.create_descriptor(a_dev) + b_tma.create_descriptor(b_dev) + a_size = get_type_size(a.type) + b_size = get_type_size(b.type) + smem_size_in_bytes = a_size + b_size + + @NVDSL.mlir_gpu_launch(grid=(1, 1, 1), block=(128, 1, 1), smem=smem_size_in_bytes) + def gemm_tma_kernel(): + tidx = gpu.thread_id(gpu.Dimension.x) + + mbar_group = Mbarriers(number_of_barriers=1) + isThread0 = tidx == 0 + + mbar_group[0].init(1, predicate=isThread0) + a_tma.prefetch(predicate=isThread0) + b_tma.prefetch(predicate=isThread0) + + a_smem = get_dynamic_shared_memory((M, K), T.f16()) + b_smem = get_dynamic_shared_memory((K, N), T.f16(), offset=a_size) + + # 1. TMA Load for two input matrices + tma_load(mbar_group, a_tma, b_tma, isThread0) + + # 2. All threads wait TMA load completion + mbar_group[0].try_wait() + + # 3. Performs Tensor Core GEMM 128x128x64 by warpgroup + A = WGMMAMatrix(WGMMAType.Descriptor, [M, K], desc=a_tma, smem=a_smem) + B = WGMMAMatrix(WGMMAType.Descriptor, [K, N], desc=b_tma, smem=b_smem) + D = WGMMAMatrix(WGMMAType.Accumulator, shape=[M, N], ty=T.f32()) + + # Matrix Multiply + D += A @ B + + # 4. Stores fragmented registers to global memory by warpgroup + D.store_accumulator(d_dev) + + gemm_tma_kernel() + + t8 = gpu.memcpy(token_ty, [t7], d, d_dev) + gpu.wait(None, [t8]) + + +# Python pass arguments to MLIR +M = 128 +N = 128 +K = 64 +a = np.random.randn(M, K).astype(np.float16) +b = np.random.randn(K, N).astype(np.float16) +d = np.zeros((M, N), np.float32) +gemm_128_128_64(a, b, d) + +ref_d = a.astype(np.float16) @ b.astype(np.float16) +np.testing.assert_allclose(d, ref_d, rtol=5e-03, atol=1e-01) +print("PASS") +# CHECK-NOT: Mismatched elements diff --git a/mlir/test/Examples/NVGPU/Ch4.py b/mlir/test/Examples/NVGPU/Ch4.py new file mode 100644 index 0000000000000000000000000000000000000000..8f38d8a90add31c30d45b7a3d3635258eeecc3ef --- /dev/null +++ b/mlir/test/Examples/NVGPU/Ch4.py @@ -0,0 +1,323 @@ +# RUN: env SUPPORT_LIB=%mlir_cuda_runtime \ +# RUN: %PYTHON %s | FileCheck %s + +# ===----------------------------------------------------------------------===// +# Chapter 4 : Multistage GEMM with Tensor Core +# ===----------------------------------------------------------------------===// +# +# This program exemplifies a GEMM operation for `f32+=f16*f16`, utilizing the +# Multistage method with a tile size of 128x128x64. The code completely +# parallelizes the two outermost loops into thread blocks. It launches one Warp +# Groups (128 threads in total) and allocates multiple slots/stage in the +# shared memory. The program consists of three main parts: prologue, mainloop, +# and epilogue. In the prologue, thread0 requests for TMA to load data into +# shared memory slots. The mainloop executes MMA while simultaneously loading +# TMA for the utilized slots. This overlap of TMA and MMA operations enhances +# performance by maximizing computational throughput. +# +# Loops illustration: +# +# for s in range(num_stages): +# TMA_128x64_64x128... +# for ti in range(M//128): # -> blockIdx.x +# for tj in range(N//128): # -> blockIdx.y +# for tk in range(K//64): +# MMA_128x128x64... +# TMA_128x64_64x128... +# Epilogue... +# +# This chapter introduces demonstrates: +# 1. Partition shape based on block IDs +# 2. Prologue +# 2.1 Execute TMA Load for two input matrices for each stage +# 3. Main loop +# 3.1 Wait for completion of TMA load with mbarrier +# 3.2 Performs Tensor Core GEMM 64x128x64 by warpgroup +# 3.3 Load next stage if needed +# 4. Epilogue +# 4.1 Store fragmented registers to shared memory +# 4.2 Store shared memory to global +# +# ===----------------------------------------------------------------------===// + + +from mlir import ir +from mlir.dialects import gpu, scf, nvgpu, nvvm +from mlir.extras import types as T +from tools.nvdsl import * +import numpy as np + + +def partition_shape(): + """ + Calculate the partition shape based on the block IDs. + + It partitions the shape like below: + for(.. i < M ...) --> blockIdx.x + for(.. j < N ...) --> blockIdx.y + for(.. k < K ...) + + Returns: + dimX (int): Dimension along the x-axis. + dimY (int): Dimension along the y-axis. + """ + bidx = gpu.block_id(gpu.Dimension.x) + bidy = gpu.block_id(gpu.Dimension.y) + dimX = bidx * TILE_M + dimY = bidy * TILE_N + return dimX, dimY + + +def tma_load( + mbar_group: Mbarriers, + a_tma: TMA, + b_tma: TMA, + slot, + stage, + num_stages, + p=None, +): + """ + TMA loads two input matrices from global memory to shared memory. It performs the following operations: + + - tma.load a_shared_memory[off_x] at coordinate [x, z] (Loads 128x64) + - tma.load b_shared_memory[off_y1] at coordinate [y, x] (Loads 64x64) + - tma.load b_shared_memory[off_y2] at coordinate [y + 64, x] (Loads 64x64) + + mbarrier.arrive ta_count = 128x64x2x4 + """ + dimX, dimY = partition_shape() + + tidx = gpu.thread_id(gpu.Dimension.x) + begin_b = num_stages * get_type_size(a_tma.tma_memref) + size_tma_a = get_type_size(a_tma.tma_memref) + size_tma_b = get_type_size(b_tma.tma_memref) + ta_count = size_tma_a + (size_tma_b * 2) + tidx = gpu.thread_id(gpu.Dimension.x) + + p = tidx == 0 if p is None else p + + off_a = slot * size_tma_a + off_b = (slot * size_tma_a) + begin_b + off_b2 = off_b + size_tma_b + a_elem_ty = a_tma.tma_memref.element_type + b_elem_ty = b_tma.tma_memref.element_type + a = get_dynamic_shared_memory(a_tma.tma_memref.shape, a_elem_ty, off_a) + b1 = get_dynamic_shared_memory(b_tma.tma_memref.shape, b_elem_ty, off_b) + b2 = get_dynamic_shared_memory(b_tma.tma_memref.shape, b_elem_ty, off_b2) + + mbar_group[slot].arrive(ta_count, predicate=p) + + c1 = stage * 64 + a_tma.load(a, mbar_group[slot], coords=[c1, dimX], predicate=p) + b_tma.load(b1, mbar_group[slot], coords=[dimY, c1], predicate=p) + b_tma.load(b2, mbar_group[slot], coords=[dimY + 64, c1], predicate=p) + + +def initialize(a_tma: TMA, b_tma: TMA, num_stages): + """ + Initialize mbarriers and prefetch TMA descriptors. + """ + tidx = gpu.thread_id(gpu.Dimension.x) + mbar_group = Mbarriers(number_of_barriers=num_stages) + isThread0 = tidx == const(0) + with ir.InsertionPoint(scf.IfOp(isThread0).then_block): + for i in scf.for_(0, num_stages, 1): + mbar_group[i].init(1) + scf.yield_([]) + a_tma.prefetch() + b_tma.prefetch() + scf.yield_([]) + + return mbar_group + + +def prologue(mbar_group: Mbarriers, a_tma: TMA, b_tma: TMA, num_stages): + """ + Prologue of the GEMM kernel. It loads 2 input matrices for each stage in loop like below: + + for stage in range(NUM_STAGES): + tma_load x, y, stage + + """ + ns = num_stages if num_stages == 1 else num_stages - 1 + for iv in scf.for_(0, ns, 1): + tma_load(mbar_group, a_tma, b_tma, iv, iv, num_stages) + scf.yield_([]) + + +def mainloop(mbar_group: Mbarriers, a_tma: TMA, b_tma: TMA, num_stages): + """ + Main loop of the Multistage GEMM kernel. It iterates through + stages and performs matrix multiplication, loading data by TMA to shared memory. It like following + + MatrixAccumulator D + for k in range(K // TILE_K): + + try_wait(stage, ...) # Wait TMA load + + Matrix A(stage, ...) # Find shared memory slot + Matrix B(stage, ...) # Find shared memory slot + D += A @ B # Multiply and accumulate + + if(needLoad) # Load next stage if needed + tma_load(x, y, nextSlot, nextStage) + + """ + ns = num_stages if num_stages == 1 else num_stages - 1 + + tidx = gpu.thread_id(gpu.Dimension.x) + begin_b = num_stages * get_type_size(a_tma.tma_memref) + + size_a = TILE_M * TILE_K * get_type_size(T.f16()) + + # Initialize A and B (input matrices) and C (accumulator) + A = WGMMAMatrix(WGMMAType.Descriptor, [TILE_M, TILE_K], desc=a_tma) + B = WGMMAMatrix(WGMMAType.Descriptor, [TILE_K, TILE_N], desc=b_tma) + D = WGMMAMatrix(WGMMAType.Accumulator, shape=[TILE_M, TILE_N], ty=T.f32()) + + phase = const(False, ty=T.bool()) + + # Main Loop + for_op = scf.ForOp(const(0), const(K // TILE_K), const(1), [D.acc_op, phase]) + with ir.InsertionPoint(for_op.body): + phase = for_op.inner_iter_args[1] + iv = for_op.induction_variable + stage = iv % num_stages + + # Wait for current stage + mbar_group[stage].try_wait(phase=phase) + + # Find shared memory slot + offset_a = stage * size_a + offset_b = offset_a + begin_b + a_smem = get_dynamic_shared_memory([TILE_M, TILE_K], T.f16(), offset_a) + b_smem = get_dynamic_shared_memory([TILE_K, TILE_N], T.f16(), offset_b) + + # Iterate input matrices, update accumulator + A.update_smem(a_smem) + B.update_smem(b_smem) + D.update_accumulator(for_op.inner_iter_args[0]) + + # Matrix Multiply + D += A @ B + + # Wait Tensor Core for single stage + if num_stages == 1: + nvvm.WgmmaWaitGroupSyncOp(0) + + # Load next stage + pred = ((iv + ns) < const(K // TILE_K)) & (tidx == 0) + nextStage = iv + ns + nextSlot = nextStage % num_stages + tma_load(mbar_group, a_tma, b_tma, nextSlot, nextStage, num_stages, pred) + + # Switch phase parity for the mbarrier + newPhase = arith.select( + stage == (num_stages - 1), + (phase ^ const(True, ty=T.bool())), + phase, + ) + scf.yield_([D.acc_op, newPhase]) + + nvvm.WgmmaWaitGroupSyncOp(0) + + D.update_accumulator(for_op.results[0]) + return D + + +def epilogue(D: WGMMAMatrix, d_dev): + """ + Epilogue of the GEMM kernel. It stores the fragmented registers to global memory. + + MatrixAccumulator D # Fragmented results + store D -> Shared Memory # Store Shared Memory + Shared Memory -> Z[dimX][dimY] # Store Shared Memory to Global Memory + + """ + tidx = gpu.thread_id(gpu.Dimension.x) + dimX, dimY = partition_shape() + + d_smem = get_dynamic_shared_memory([TILE_M, TILE_N], T.f32()) + d_gmem = memref.subview(d_dev, [dimX, dimY], [TILE_M, TILE_N], [1, 1]) + + # Store (registers -> shared memory) + D.store_accumulator(d_smem) + gpu.barrier() + + # Store (shared memory --> global memory) + for i in scf.for_(0, TILE_M, 1): + val = memref.load(d_smem, [i, tidx]) + memref.store(val, d_gmem, [i, tidx]) + scf.yield_([]) + + +# The decorator generates +# a -> memref +# b -> memref +# d -> memref +@NVDSL.mlir_func +def gemm_multistage(a, b, d, num_stages): + token_ty = ir.Type.parse("!gpu.async.token") + t1 = gpu.wait(token_ty, []) + a_dev, t2 = gpu.alloc(a.type, token_ty, [t1], [], []) + b_dev, t3 = gpu.alloc(b.type, token_ty, [t2], [], []) + d_dev, t4 = gpu.alloc(d.type, token_ty, [t3], [], []) + t5 = gpu.memcpy(token_ty, [t4], a_dev, a) + t6 = gpu.memcpy(token_ty, [t5], b_dev, b) + t7 = gpu.wait(token_ty, [t6]) + + sw = nvgpu.TensorMapSwizzleKind.SWIZZLE_128B + a_tma = TMA([128, 64], a.type, swizzle=sw) + b_tma = TMA([64, 64], b.type, swizzle=sw) + a_tma.create_descriptor(a_dev) + b_tma.create_descriptor(b_dev) + + grid = [(M // TILE_M), (N // TILE_N), 1] + block = [128, 1, 1] + + size_a = get_type_size(a.type.element_type) * TILE_M * TILE_K + size_b = get_type_size(b.type.element_type) * TILE_N * TILE_K + smem_size_in_bytes = (size_a + size_b) * num_stages + + @NVDSL.mlir_gpu_launch(grid=grid, block=block, smem=smem_size_in_bytes) + def gemm_multistage_kernel(): + # Initialize mbarriers and prefetch TMA descriptors + mbar_group = initialize(a_tma, b_tma, num_stages) + + # Fill the pipeline stages + prologue(mbar_group, a_tma, b_tma, num_stages) + + # Main loop + D = mainloop(mbar_group, a_tma, b_tma, num_stages) + + # Store registers to global memory + epilogue(D, d_dev) + + gemm_multistage_kernel() + + t8 = gpu.memcpy(token_ty, [t7], d, d_dev) + gpu.wait(None, [t8]) + + +# Python pass arguments to MLIR +N = 256 +M = 512 +K = 1024 +TILE_M = 128 +TILE_N = 128 +TILE_K = 64 +a = np.random.randn(M, K).astype(np.float16) +b = np.random.randn(K, N).astype(np.float16) +d = np.zeros((M, N), np.float32) + +gemm_multistage(a, b, d, num_stages=7) + + +# Verify MLIR with reference computation +ref_d = a.astype(np.float16) @ b.astype(np.float16) +np.testing.assert_allclose(d, ref_d, rtol=5e-03, atol=1e-01) + + +print("PASS") +# CHECK-NOT: Mismatched elements diff --git a/mlir/test/Examples/NVGPU/Ch5.py b/mlir/test/Examples/NVGPU/Ch5.py new file mode 100644 index 0000000000000000000000000000000000000000..92e9314e1b812d5a36d23c76c47ad73ed9bcb30f --- /dev/null +++ b/mlir/test/Examples/NVGPU/Ch5.py @@ -0,0 +1,321 @@ +# RUN: env SUPPORT_LIB=%mlir_cuda_runtime \ +# RUN: %PYTHON %s | FileCheck %s + +# ===----------------------------------------------------------------------===// +# Chapter 5 : Warp Specialized GEMM with Tensor Core +# ===----------------------------------------------------------------------===// +# +# This program demonstrates a GEMM operation for `f32+=f16*f16`, utilizing the +# Warp Specialized method with a tile size of 128x128x64. The code completely +# parallelizes the two outermost loops into thread blocks. It launches two Warp +# Groups (256 threads in total): one for the producer and the other for the consumer. +# Each group takes a different control-flow. The producer thread group is responsible +# for loading data into shared memory, while the consumer group executes the Tensor +# Core GEMM operation and epilogue. +# +# for ti in range(M//128): # -> blockIdx.x +# for tj in range(N//128): # -> blockIdx.y +# with wg_producer: +# for tk in range(K//64): +# TMA_128x64_64x128... +# with wg_consumer: +# for tk in range(K//64): +# MMA_128x128x64... +# Epilogue.. +# +# This chapter demonstrates: +# 2 WG (warpgroups) +# Producer: +# 2.1.1 Wait MMA Barrier +# 2.1.1 Load TMA with TMA barrier +# 2.1.1 Arrive TMA barrier with txcount +# Consumer: +# Loop +# Wait TMA barrier +# Performs Tensor Core GEMM 64x128x64 by warpgroup +# Arrive MMA Barrier +# Epilogue +# Store fragmented registers to shared memory +# Store shared memory to global +# +# ===----------------------------------------------------------------------===// + + +from mlir import ir +from mlir.dialects import gpu, scf, nvgpu, nvvm +from mlir.extras import types as T +from tools.nvdsl import * +import numpy as np + + +def partition_shape(): + """ + Calculate the partition shape based on the block IDs. + + It parallelizes the two outermost loops into thread blocks. + for ti in range(M//128): # -> blockIdx.x + for tj in range(N//128): # -> blockIdx.y + D = 0 + for tk in range(K//64): + for i in range(128): + for j in range(128): + for k in range(64): + FMA + + Returns: + dimX (int): Dimension along the x-axis. + dimY (int): Dimension along the y-axis. + """ + bidx = gpu.block_id(gpu.Dimension.x) + bidy = gpu.block_id(gpu.Dimension.y) + dimX = bidx * TILE_M + dimY = bidy * TILE_N + return dimX, dimY + + +def tma_load( + mbar_group: Mbarriers, + a_tma: TMA, + b_tma: TMA, + slot, + stage, + num_stages, + p=None, +): + """ + TMA loads two input matrices from global memory to shared memory. It performs the following operations: + + - tma.load a_shared_memory[off_x] at coordinate [x, z] (Loads 128x64) + - tma.load b_shared_memory[off_y1] at coordinate [y, x] (Loads 64x64) + - tma.load b_shared_memory[off_y2] at coordinate [y + 64, x] (Loads 64x64) + + mbarrier.arrive ta_count = 128x64x2x4 + """ + dimX, dimY = partition_shape() + + tidx = gpu.thread_id(gpu.Dimension.x) + begin_b = num_stages * get_type_size(a_tma.tma_memref) + size_tma_a = get_type_size(a_tma.tma_memref) + size_tma_b = get_type_size(b_tma.tma_memref) + ta_count = size_tma_a + (size_tma_b * 2) + + off_a = slot * size_tma_a + off_b = (slot * size_tma_a) + begin_b + off_b2 = off_b + size_tma_b + a_elem_ty = a_tma.tma_memref.element_type + b_elem_ty = b_tma.tma_memref.element_type + a = get_dynamic_shared_memory(a_tma.tma_memref.shape, a_elem_ty, off_a) + b1 = get_dynamic_shared_memory(b_tma.tma_memref.shape, b_elem_ty, off_b) + b2 = get_dynamic_shared_memory(b_tma.tma_memref.shape, b_elem_ty, off_b2) + + mbar_group[slot].arrive(ta_count, predicate=p) + p = (tidx % WARP_GROUP_SIZE) == 0 + c1 = stage * 64 + a_tma.load(a, mbar_group[slot], coords=[c1, dimX], predicate=p) + b_tma.load(b1, mbar_group[slot], coords=[dimY, c1], predicate=p) + b_tma.load(b2, mbar_group[slot], coords=[dimY + 64, c1], predicate=p) + + +def initialize(a_tma: TMA, b_tma: TMA, num_stages): + """ + Initialize mbarriers and prefetch TMA descriptors. + """ + tidx = gpu.thread_id(gpu.Dimension.x) + mbar_group_tma = Mbarriers(number_of_barriers=num_stages) + mbar_group_mma = Mbarriers(number_of_barriers=num_stages) + isThread0 = tidx == const(0) + with ir.InsertionPoint(scf.IfOp(isThread0).then_block): + for i in scf.for_(0, num_stages, 1): + mbar_group_tma[i].init(1) + mbar_group_mma[i].init(1) + scf.yield_([]) + a_tma.prefetch() + b_tma.prefetch() + scf.yield_([]) + + return mbar_group_tma, mbar_group_mma + + +def switch_phase(stage, phase, num_stages): + p = stage == (num_stages - 1) + phase = arith.select( + p, + (phase ^ const(True, ty=T.bool())), + phase, + ) + return phase + + +def producer_loop( + mbar_tma: Mbarriers, + mbar_mma: Mbarriers, + a_tma: TMA, + b_tma: TMA, + wg_me: Warpgroup, + num_stages, +): + phase = const(True, ty=T.bool()) + + for iv, phase in scf.for_(0, (K // TILE_K), 1, [phase]): + stage = iv % num_stages + # Wait MMA to be done + mbar_mma[stage].try_wait(phase) + # New phase for mbarrier + phase = switch_phase(stage, phase, num_stages) + # TMA Load + tma_load(mbar_tma, a_tma, b_tma, stage, iv, num_stages, wg_me.is_wg_primary) + scf.yield_([phase]) + + +def consumer_loop( + mbar_tma: Mbarriers, + mbar_mma: Mbarriers, + a_tma: TMA, + b_tma: TMA, + wg_me: Warpgroup, + num_stages, +): + begin_b = num_stages * get_type_size(a_tma.tma_memref) + + size_a = TILE_M * TILE_K * get_type_size(T.f16()) + + phase = const(False, ty=T.bool()) + A = WGMMAMatrix(WGMMAType.Descriptor, [TILE_M, TILE_K], desc=a_tma) + B = WGMMAMatrix(WGMMAType.Descriptor, [TILE_K, TILE_N], desc=b_tma) + D = WGMMAMatrix(WGMMAType.Accumulator, shape=[TILE_M, TILE_N], ty=T.f32()) + + for_op = scf.ForOp(const(0), const(K // TILE_K), const(1), [D.acc_op, phase]) + with ir.InsertionPoint(for_op.body): + phase = for_op.inner_iter_args[1] + iv = for_op.induction_variable + stage = iv % num_stages + + # Wait TMA for current stage + mbar_tma[stage].try_wait(phase) + + # Find shared memory slot + offset_a = stage * size_a + offset_b = offset_a + begin_b + a_smem = get_dynamic_shared_memory([TILE_M, TILE_K], T.f16(), offset_a) + b_smem = get_dynamic_shared_memory([TILE_K, TILE_N], T.f16(), offset_b) + + # Iterate input matrices, update accumulator + A.update_smem(a_smem) + B.update_smem(b_smem) + D.update_accumulator(for_op.inner_iter_args[0]) + + # Matrix Multiply + D += A @ B + + # MMA Barrier Arrive + p_arrive = (iv > 0) & wg_me.is_wg_primary + with ir.InsertionPoint(scf.IfOp(p_arrive).then_block): + barId = arith.select((stage == 0), const(num_stages - 1), (stage - 1)) + mbar_mma[barId].arrive() + scf.yield_([]) + + phase = switch_phase(stage, phase, num_stages) + scf.yield_([D.acc_op, phase]) + + nvvm.WgmmaWaitGroupSyncOp(0) + D.update_accumulator(for_op.results[0]) + return D + + +def epilogue(D: WGMMAMatrix, d_dev): + """ + Epilogue of the GEMM kernel. It stores the fragmented registers to global memory. + + MatrixAccumulator D # Fragmented results + store D -> Shared Memory # Store Shared Memory + Shared Memory -> Z[dimX][dimY] # Store Shared Memory to Global Memory + + """ + tidx = gpu.thread_id(gpu.Dimension.x) + dimX, dimY = partition_shape() + # s = tidx - WARP_GROUP_SIZE + # debug_print("[Epilogue] store to global memory @ s={}", s) + + d_smem = get_dynamic_shared_memory([TILE_M, TILE_N], T.f32()) + d_gmem = memref.subview(d_dev, [dimX, dimY], [TILE_M, TILE_N], [1, 1]) + + # Store (registers -> shared memory) + D.store_accumulator(d_smem) + gpu.barrier() + + # Store (shared memory --> global memory) + for i in scf.for_(0, TILE_M, 1): + val = memref.load(d_smem, [i, tidx]) + memref.store(val, d_gmem, [i, tidx]) + scf.yield_([]) + + +@NVDSL.mlir_func +def gemm_warp_specialized(a, b, d, num_stages): + token_ty = ir.Type.parse("!gpu.async.token") + t1 = gpu.wait(token_ty, []) + a_dev, t2 = gpu.alloc(a.type, token_ty, [t1], [], []) + b_dev, t3 = gpu.alloc(b.type, token_ty, [t2], [], []) + d_dev, t4 = gpu.alloc(d.type, token_ty, [t3], [], []) + t5 = gpu.memcpy(token_ty, [t4], a_dev, a) + t6 = gpu.memcpy(token_ty, [t5], b_dev, b) + t7 = gpu.wait(token_ty, [t6]) + + sw = nvgpu.TensorMapSwizzleKind.SWIZZLE_128B + a_tma = TMA([128, 64], a.type, swizzle=sw) + b_tma = TMA([64, 64], b.type, swizzle=sw) + a_tma.create_descriptor(a_dev) + b_tma.create_descriptor(b_dev) + + grid = [(M // TILE_M), (N // TILE_N), 1] + block = [256, 1, 1] + + size_a = get_type_size(a.type.element_type) * TILE_M * TILE_K + size_b = get_type_size(b.type.element_type) * TILE_N * TILE_K + smem_size_in_bytes = (size_a + size_b) * num_stages + + @NVDSL.mlir_gpu_launch(grid=grid, block=block, smem=smem_size_in_bytes) + def gemm_warp_specialized_kernel(): + # Init Warpgroups + wg_producer = Warpgroup(primary_thread=128, register_size=40) + wg_consumer = Warpgroup(primary_thread=0, register_size=232) + + # Initialize mbarriers and prefetch TMA descriptors + mbar_mma, mbar_tma = initialize(a_tma, b_tma, num_stages) + + # Producer performs TMA + with wg_producer: + producer_loop(mbar_tma, mbar_mma, a_tma, b_tma, wg_producer, num_stages) + + # Consumer performs MMA/Tensor Core + with wg_consumer: + D = consumer_loop(mbar_tma, mbar_mma, a_tma, b_tma, wg_consumer, num_stages) + epilogue(D, d_dev) + + gemm_warp_specialized_kernel() + + t8 = gpu.memcpy(token_ty, [t7], d, d_dev) + gpu.wait(None, [t8]) + + +# Python pass arguments to MLIR +N = 256 +M = 512 +K = 1024 +TILE_M = 128 +TILE_N = 128 +TILE_K = 64 +a = np.random.randn(M, K).astype(np.float16) +b = np.random.randn(K, N).astype(np.float16) +d = np.zeros((M, N), np.float32) + +gemm_warp_specialized(a, b, d, num_stages=7) + + +# Verify MLIR with reference computation +ref_d = a.astype(np.float16) @ b.astype(np.float16) +np.testing.assert_allclose(d, ref_d, rtol=5e-03, atol=1e-01) + + +print("PASS") +# CHECK-NOT: Mismatched elements diff --git a/mlir/test/Examples/NVGPU/lit.local.cfg b/mlir/test/Examples/NVGPU/lit.local.cfg new file mode 100644 index 0000000000000000000000000000000000000000..689cd252e7a254f0b6276673d9aefa0f009c27ea --- /dev/null +++ b/mlir/test/Examples/NVGPU/lit.local.cfg @@ -0,0 +1,4 @@ +config.unsupported = False +if not config.enable_cuda_runner or not config.mlir_run_cuda_sm90_tests: + config.unsupported = True + \ No newline at end of file diff --git a/mlir/test/Examples/NVGPU/tools/lit.local.cfg b/mlir/test/Examples/NVGPU/tools/lit.local.cfg new file mode 100644 index 0000000000000000000000000000000000000000..d9f34f219c4d955fdf66804369eff8524edf60e2 --- /dev/null +++ b/mlir/test/Examples/NVGPU/tools/lit.local.cfg @@ -0,0 +1,3 @@ +# Files in this directory are tools, not tests. +config.unsupported = True + diff --git a/mlir/test/Examples/NVGPU/tools/nvdsl.py b/mlir/test/Examples/NVGPU/tools/nvdsl.py new file mode 100644 index 0000000000000000000000000000000000000000..600cae5b47eeecdae5f79b961f0f483c90a254ee --- /dev/null +++ b/mlir/test/Examples/NVGPU/tools/nvdsl.py @@ -0,0 +1,456 @@ +from enum import Enum +import functools, sys, ctypes, os, errno +import numpy as np +from functools import partialmethod +from mlir import ir +from mlir.dialects import arith, func, gpu, memref, nvgpu, scf, nvvm +from mlir.extras import types as T +from mlir import runtime as rt +from tools import nvgpucompiler + +MLIR_DYNAMIC = -9223372036854775808 + + +def const(value: int, ty=None): + ty = T.index() if ty is None else ty + if isinstance(value, ir.Value) and ( + value.type.isinstance(value.type) or T.bool().isinstance(value.type) + ): + return value + return arith.constant(ty, value) + + +def get_type_size(ty): + if ir.MemRefType.isinstance(ty): + size = get_type_size(ty.element_type) + for sz in ty.shape: + size *= sz + return size + if ir.FloatType.isinstance(ty): + return ir.FloatType(ty).width // 8 + if ir.IntegerType.isinstance(ty): + return ir.IntegerType(ty).width // 8 + raise NotImplementedError(ty) + + +def get_mlir_func_obj_ty(inputArgs): + args = [] + c_int_p = ctypes.c_int * 1 + c_float_p = ctypes.c_float * 1 + c_bool_p = ctypes.c_bool * 1 + for arg in inputArgs: + if isinstance(arg, bool): + args.append(c_bool_p(arg)) + elif isinstance(arg, int): + args.append(c_int_p(arg)) + elif isinstance(arg, float): + args.append(c_float_p(arg)) + elif isinstance(arg, np.ndarray): + args.append( + ctypes.pointer(ctypes.pointer(rt.get_ranked_memref_descriptor(arg))) + ) + else: + raise NotImplementedError(arg) + return args + + +class Mbarriers: + def __init__(self, number_of_barriers=1): + self.mbar_ty = ir.Type.parse( + "!nvgpu.mbarrier.group, num_barriers = " + + str(number_of_barriers) + + ">" + ) + self.mbar_group_op = nvgpu.mbarrier_create(self.mbar_ty) + self.number_of_barriers = number_of_barriers + + def __getitem__(self, key): + self.id_op = const(key) + return self + + def init(self, count: int, predicate=None): + count_op = const(count) + if predicate is None: + nvgpu.mbarrier_init(self.mbar_group_op, count_op, self.id_op) + else: + nvgpu.mbarrier_init( + self.mbar_group_op, count_op, self.id_op, predicate=predicate + ) + + def arrive(self, txcount: int = 0, predicate=None): + if txcount != 0: + txcount_op = const(txcount) + nvgpu.mbarrier_arrive_expect_tx( + self.mbar_group_op, txcount_op, self.id_op, predicate=predicate + ) + else: + nvgpu.mbarrier_arrive( + ir.Type.parse("!nvgpu.mbarrier.token"), self.mbar_group_op, self.id_op + ) + + def try_wait(self, phase: bool = False, ticks: int = 10000000): + ticks_op = const(ticks) + phase_op = const(phase, T.bool()) + nvgpu.MBarrierTryWaitParityOp( + self.mbar_group_op, + phase_op, + ticks_op, + mbarId=self.id_op, + ) + + +class TMA: + """A class that builds a TMA descriptor.""" + + def __init__( + self, + tma_box_shape, + memref_ty, + swizzle=nvgpu.TensorMapSwizzleKind.SWIZZLE_NONE, + l2promo=nvgpu.TensorMapL2PromoKind.L2PROMO_NONE, + oob=nvgpu.TensorMapOOBKind.OOB_ZERO, + interleave=nvgpu.TensorMapInterleaveKind.INTERLEAVE_NONE, + ): + self.swizzle = swizzle # mlir.nvgpu.TensorMapSwizzleKind + self.l2promo = l2promo # mlir.nvgpu.TensorMapL2PromoKind + self.oob = oob # mlir.nvgpu.TensorMapOOBKind + self.interleave = interleave # mlir.nvgpu.TensorMapInterleaveKind + self.tma_box_shape = tma_box_shape + self.memref_ty = memref_ty # MemRefType + self.tma_memref = ir.MemRefType.get(tma_box_shape, memref_ty.element_type) + + @property + def tensormap_descriptor_ty(self): + """Returns a tensormap descriptor type.""" + tensorMemrefType = ir.MemRefType.get( + self.tma_box_shape, + self.memref_ty.element_type, + memory_space=ir.Attribute.parse("3"), + ) + return nvgpu.TensorMapDescriptorType.get( + tensorMemrefType, + self.swizzle, + self.l2promo, + self.oob, + self.interleave, + ) + + def create_descriptor(self, device_ptr): + tma_descriptor_ty = self.tensormap_descriptor_ty + device_unranked_memref = memref.CastOp( + ir.UnrankedMemRefType.get( + self.memref_ty.element_type, self.memref_ty.memory_space + ), + device_ptr, + ) + self.tma_descriptor = nvgpu.TmaCreateDescriptorOp( + tma_descriptor_ty, device_unranked_memref, map(const, self.tma_box_shape) + ) + return self.tma_descriptor.result + + def prefetch(self, predicate=None): + nvgpu.tma_prefetch_descriptor(self.tma_descriptor, predicate=predicate) + + def load(self, dest, mbarrier: Mbarriers, coords=[0], predicate=None): + nvgpu.TmaAsyncLoadOp( + dest, + mbarrier.mbar_group_op, + self.tma_descriptor, + coordinates=map(const, coords), + mbarId=mbarrier.id_op, + predicate=predicate, + ) + + +WARP_GROUP_SIZE = 128 # Number of threads in a warpgroup + + +class Warpgroup: + def __init__(self, primary_thread, register_size): + assert (primary_thread % WARP_GROUP_SIZE) == 0 + tidx = gpu.thread_id(gpu.Dimension.x) + self.primary_thread = primary_thread + self.register_size = register_size + self.is_wg_primary = (tidx % WARP_GROUP_SIZE) == 0 + self.wg_id = tidx / WARP_GROUP_SIZE + self.is_me = self.wg_id == (primary_thread // WARP_GROUP_SIZE) + + def __enter__(self): + if_op = scf.IfOp(self.is_me) + self.ipoint_op = ir.InsertionPoint(if_op.then_block) + self.ipoint_op.__enter__() + if self.register_size < 64: + nvvm.setmaxregister(self.register_size, nvvm.SetMaxRegisterAction.decrease) + else: + nvvm.setmaxregister(self.register_size, nvvm.SetMaxRegisterAction.increase) + + def __exit__(self, exc_type, exc_value, traceback): + scf.yield_([]) + self.ipoint_op.__exit__(exc_type, exc_value, traceback) + return True + + +class WGMMAType(Enum): + Accumulator = 1 + Descriptor = 2 + + +class WGMMAMatrix: + def __init__( + self, + matrix_type: WGMMAType, + shape: list = None, + desc: TMA = None, + smem=None, + ty=None, + acc_op=None, + ): + if acc_op is None: + self.M = shape[0] + self.N = shape[1] + self.ty = ty + self.matrix_type = matrix_type + self.desc = desc + self.smem = smem + if matrix_type is WGMMAType.Accumulator: + self.acc_op = nvgpu.warpgroup_mma_init_accumulator(self.acc_ty) + elif acc_op: + self.acc_op = acc_op + self.matrix_type = WGMMAType.Accumulator + + @property + def acc_ty(self): + parse_str = f"!nvgpu.warpgroup.accumulator>" + return ir.Type.parse(parse_str) + + @property + def wgmma_ty(self): + parse_str = f"!nvgpu.warpgroup.descriptor>>" + return ir.Type.parse(parse_str) + + def store_accumulator(self, dest): + assert self.matrix_type == WGMMAType.Accumulator + nvgpu.warpgroup_mma_store(self.acc_op, dest) + + def update_smem(self, smem): + self.smem = smem + + def update_accumulator(self, acc_op): + self.acc_op = acc_op + + def __matmul__(self, rhs): + lhs = nvgpu.warpgroup_generate_descriptor( + self.wgmma_ty, self.smem, self.desc.tma_descriptor + ) + rhs = nvgpu.warpgroup_generate_descriptor( + rhs.wgmma_ty, rhs.smem, rhs.desc.tma_descriptor + ) + return [lhs, rhs] + + def __iadd__(self, matmulResult): + lhs = matmulResult[0] + rhs = matmulResult[1] + acc_op = nvgpu.WarpgroupMmaOp( + self.acc_op.type, lhs, rhs, self.acc_op, transposeB=True + ) + return WGMMAMatrix(WGMMAType.Accumulator, acc_op=acc_op) + + +def get_dynamic_shared_memory(shape=None, ty=None, offset: int = 0): + smem_space_str = "#gpu.address_space" + smem_space = ir.Attribute.parse(smem_space_str) + dynamic_smem = gpu.dynamic_shared_memory( + ir.MemRefType.get((MLIR_DYNAMIC,), T.i8(), memory_space=smem_space) + ) + if shape is None: + return dynamic_smem + memref_ty = ir.MemRefType.get(shape, ty, memory_space=smem_space) + return memref.view( + ir.MemRefType.get( + memref_ty.shape, memref_ty.element_type, memory_space=smem_space + ), + dynamic_smem, + const(offset), + [], + ) + + +def get_mlir_ty(arg): + def get_mlir_ty_from_np(dtype): + if dtype == np.float16: + return T.f16() + if dtype == np.float32: + return T.f32() + if dtype == np.float64: + return T.f64() + if dtype == np.int32: + return T.i32() + if dtype == np.int64: + return T.i64() + raise NotImplementedError(dtype) + + if isinstance(arg, bool): + return T.bool() + elif isinstance(arg, int): + return T.index() + elif isinstance(arg, float): + return T.f32() + elif isinstance(arg, np.ndarray): + descriptor = rt.get_ranked_memref_descriptor(arg) + dtype = get_mlir_ty_from_np(arg.dtype) + shape = descriptor.shape + return memref.MemRefType.get(shape, dtype) + raise NotImplementedError(arg) + + +class NVDSL: + @staticmethod + def mlir_gpu_launch(grid=(1, 1, 1), block=(1, 1, 1), smem=0): + def decorator(func): + @functools.wraps(func) + def wrapper(*args, **kwargs): + launch_op = gpu.LaunchOp( + None, + [], + *map(const, grid), + *map(const, block), + dynamicSharedMemorySize=arith.constant(T.i32(), smem), + ) + launch_op.body.blocks.append(*([T.index()] * 12)) + with ir.InsertionPoint(launch_op.body.blocks[0]): + result = func(*args, **kwargs) + gpu.terminator() + return result + + return wrapper + + return decorator + + @staticmethod + def mlir_func(funcBody): + @functools.wraps(funcBody) + def wrapper(*args, **kwargs): + function_name = funcBody.__name__ + + def saveIR(module): + """Save generated IR""" + if True: # self.saveIR: + # print(mlir_nvgpu_module) + original_stdout = sys.stdout + with open("nvdsl.mlir", "w") as f: + sys.stdout = f + print(module) + sys.stdout = original_stdout + + def _binary_op(lhs, rhs, op: str, predAtt="") -> "ArithValue": + """Generate MLIR's Arith dialects binary operations.""" + rhs = const(rhs) + if arith._is_float_type(lhs.type) and arith._is_float_type(rhs.type): + op += "F" + if op.startswith("Cmp"): + predicateAttr = getattr(arith, f"CmpFPredicate").__dict__[ + predAtt + ] + elif arith._is_integer_like_type( + lhs.type + ) and arith._is_integer_like_type(lhs.type): + if op == "Div" or op == "Rem": + op += "U" + op += "I" + if op.startswith("Cmp"): + predicateAttr = getattr(arith, f"CmpIPredicate").__dict__[ + predAtt + ] + else: + raise NotImplementedError( + f"Unsupported '{op}' operands: {lhs}, {rhs}" + ) + + if op.startswith("Cmp"): + op = getattr(arith, f"{op}Op") + + return op(predicateAttr, lhs, rhs).result + else: + op = getattr(arith, f"{op}Op") + return op(lhs, rhs).result + + @ir.register_value_caster(ir.IndexType.static_typeid) + @ir.register_value_caster(ir.F32Type.static_typeid) + @ir.register_value_caster(ir.F16Type.static_typeid) + @ir.register_value_caster(ir.F64Type.static_typeid) + @ir.register_value_caster(ir.IntegerType.static_typeid) + class ArithValue(ir.Value): + """Overloads operators for MLIR's Arith dialects binary operations.""" + + def __init__(self, v): + super().__init__(v) + + __add__ = partialmethod(_binary_op, op="Add") + __sub__ = partialmethod(_binary_op, op="Sub") + __mul__ = partialmethod(_binary_op, op="Mul") + __truediv__ = partialmethod(_binary_op, op="Div") + __mod__ = partialmethod(_binary_op, op="Rem") + __xor__ = partialmethod(_binary_op, op="XOr") + __lt__ = partialmethod(_binary_op, op="Cmp", predAtt="ult") + __le__ = partialmethod(_binary_op, op="Cmp", predAtt="ule") + __eq__ = partialmethod(_binary_op, op="Cmp", predAtt="eq") + __ne__ = partialmethod(_binary_op, op="Cmp", predAtt="ne") + __gt__ = partialmethod(_binary_op, op="Cmp", predAtt="ugt") + __ge__ = partialmethod(_binary_op, op="Cmp", predAtt="uge") + __and__ = partialmethod(_binary_op, op="And") + __or__ = partialmethod(_binary_op, op="Or") + + def __str__(self): + return ( + super() + .__str__() + .replace(ir.Value.__name__, ArithValue.__name__) + ) + + # Generate MLIR Context and start generating IR + with ir.Context(), ir.Location.unknown(): + types = [] + for arg in args: + types.append(get_mlir_ty(arg)) + + # Build IR + module = ir.Module.create() + with ir.InsertionPoint(module.body): + fop = func.FuncOp(function_name, (types, [])) + fop.attributes["llvm.emit_c_interface"] = ir.UnitAttr.get() + with ir.InsertionPoint(fop.add_entry_block()): + fargs = [] + for i, a in enumerate(types): + fargs.append(fop.arguments[i]) + + # Call user function body + result = funcBody(*fargs, **kwargs) + func.ReturnOp([]) + + # Save IR in a file + # saveIR(module) + + # Verify the module + # module.operation.verify() + + # Compile and JIT MLIR module + options = f"cubin-chip=sm_90a cubin-features=+ptx80 opt-level=3" + support_lib = os.getenv("SUPPORT_LIB") + if not os.path.exists(support_lib): + raise FileNotFoundError( + errno.ENOENT, os.strerror(errno.ENOENT), support_lib + ) + compiler = nvgpucompiler.NvgpuCompiler( + options, opt_level=3, shared_libs=[support_lib] + ) + engine = compiler.compile_and_jit(module) + + # Convert input arguments to MLIR arguments + newArgs = get_mlir_func_obj_ty(args) + + # Run the compiled program + engine.invoke(function_name, *newArgs) + + return result + + return wrapper diff --git a/mlir/test/Examples/NVGPU/tools/nvgpucompiler.py b/mlir/test/Examples/NVGPU/tools/nvgpucompiler.py new file mode 100644 index 0000000000000000000000000000000000000000..1c9cc74fcd169cb523e8c81bf8d4749e5cad50e0 --- /dev/null +++ b/mlir/test/Examples/NVGPU/tools/nvgpucompiler.py @@ -0,0 +1,45 @@ +# Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +# See https://llvm.org/LICENSE.txt for license information. +# SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception + +# This file contains the Nvgpu class. + +from mlir import execution_engine +from mlir import ir +from mlir import passmanager +from typing import Sequence +import errno +import os +import sys + +_SCRIPT_PATH = os.path.dirname(os.path.abspath(__file__)) +sys.path.append(_SCRIPT_PATH) + + +class NvgpuCompiler: + """Nvgpu class for compiling and building MLIR modules.""" + + def __init__(self, options: str, opt_level: int, shared_libs: Sequence[str]): + pipeline = f"builtin.module(gpu-lower-to-nvvm-pipeline{{{options}}})" + self.pipeline = pipeline + self.shared_libs = shared_libs + self.opt_level = opt_level + + def __call__(self, module: ir.Module): + """Convenience application method.""" + self.compile(module) + + def compile(self, module: ir.Module): + """Compiles the module by invoking the nvgpu pipeline.""" + passmanager.PassManager.parse(self.pipeline).run(module.operation) + + def jit(self, module: ir.Module) -> execution_engine.ExecutionEngine: + """Wraps the module in a JIT execution engine.""" + return execution_engine.ExecutionEngine( + module, opt_level=self.opt_level, shared_libs=self.shared_libs + ) + + def compile_and_jit(self, module: ir.Module) -> execution_engine.ExecutionEngine: + """Compiles and jits the module.""" + self.compile(module) + return self.jit(module) diff --git a/mlir/test/Integration/Dialect/Linalg/CPU/runtime-verification.mlir b/mlir/test/Integration/Dialect/Linalg/CPU/runtime-verification.mlir new file mode 100644 index 0000000000000000000000000000000000000000..b05ef9422e596749eac7d5598cad7e1f26f299cb --- /dev/null +++ b/mlir/test/Integration/Dialect/Linalg/CPU/runtime-verification.mlir @@ -0,0 +1,298 @@ +// RUN: mlir-opt %s -generate-runtime-verification \ +// RUN: -one-shot-bufferize="bufferize-function-boundaries" \ +// RUN: -convert-linalg-to-loops \ +// RUN: -expand-strided-metadata \ +// RUN: -lower-affine \ +// RUN: -convert-scf-to-cf \ +// RUN: -test-cf-assert \ +// RUN: -convert-index-to-llvm \ +// RUN: -finalize-memref-to-llvm \ +// RUN: -convert-func-to-llvm \ +// RUN: -reconcile-unrealized-casts | \ +// RUN: mlir-cpu-runner -e main -entry-point-result=void \ +// RUN: -shared-libs=%mlir_runner_utils \ +// RUN: -shared-libs=%mlir_c_runner_utils 2>&1 | \ +// RUN: FileCheck %s + +func.func @main() { + %c5x = arith.constant dense<0.0> : tensor<5xf32> + %c4x = arith.constant dense<0.0> : tensor<4xf32> + %d5x = tensor.cast %c5x : tensor<5xf32> to tensor + %d4x = tensor.cast %c4x : tensor<4xf32> to tensor + + // CHECK-NOT: ERROR: Runtime op verification failed + func.call @simple_add(%d5x, %d5x) : (tensor, tensor) -> (tensor) + + // CHECK: ERROR: Runtime op verification failed + // CHECK: linalg.generic + // CHECK: ^ dimension #0 of input/output operand #1 is incompatible with inferred dimension size + func.call @simple_add(%d5x, %d4x) : (tensor, tensor) -> (tensor) + + // CHECK: ERROR: Runtime op verification failed + // CHECK: linalg.generic + // CHECK: ^ dimension #0 of input/output operand #1 is incompatible with inferred dimension size + func.call @simple_add(%d4x, %d5x) : (tensor, tensor) -> (tensor) + + %c1x1 = arith.constant dense<0.0> : tensor<1x1xf32> + %c1x4 = arith.constant dense<0.0> : tensor<1x4xf32> + %c4x4 = arith.constant dense<0.0> : tensor<4x4xf32> + %c4x5 = arith.constant dense<0.0> : tensor<4x5xf32> + %c5x4 = arith.constant dense<0.0> : tensor<5x4xf32> + %d1x1 = tensor.cast %c1x1 : tensor<1x1xf32> to tensor + %d1x4 = tensor.cast %c1x4 : tensor<1x4xf32> to tensor + %d4x4 = tensor.cast %c4x4 : tensor<4x4xf32> to tensor + %d4x5 = tensor.cast %c4x5 : tensor<4x5xf32> to tensor + %d5x4 = tensor.cast %c5x4 : tensor<5x4xf32> to tensor + + // CHECK-NOT: ERROR: Runtime op verification failed + func.call @broadcast_add(%d1x1, %d1x1) : (tensor, tensor) -> (tensor) + + // CHECK-NOT: ERROR: Runtime op verification failed + func.call @broadcast_add(%d1x1, %d4x5) : (tensor, tensor) -> (tensor) + + // CHECK-NOT: ERROR: Runtime op verification failed + func.call @broadcast_add(%d4x4, %d1x4) : (tensor, tensor) -> (tensor) + + // CHECK: ERROR: Runtime op verification failed + // CHECK: linalg.generic + // CHECK: ^ dimension #1 of input/output operand #1 is incompatible with inferred dimension size + func.call @broadcast_add(%d1x4, %d4x5) : (tensor, tensor) -> (tensor) + + // CHECK: ERROR: Runtime op verification failed + // CHECK: linalg.generic + // CHECK: ^ dimension #0 of input/output operand #1 is incompatible with inferred dimension size + // CHECK: ERROR: Runtime op verification failed + // CHECK: linalg.generic + // CHECK: ^ dimension #1 of input/output operand #1 is incompatible with inferred dimension size + // CHECK: ERROR: Runtime op verification failed + // CHECK: linalg.generic + // CHECK: ^ dimension #1 of input/output operand #2 is incompatible with inferred dimension size + func.call @broadcast_add(%d5x4, %d4x5) : (tensor, tensor) -> (tensor) + + // CHECK-NOT: ERROR: Runtime op verification failed + func.call @matmul_generic(%d5x4, %d4x5) : (tensor, tensor) -> (tensor) + + // CHECK: ERROR: Runtime op verification failed + // CHECK: linalg.generic + // CHECK: ^ dimension #0 of input/output operand #1 is incompatible with inferred dimension size + func.call @matmul_generic(%d4x5, %d4x5) : (tensor, tensor) -> (tensor) + + // CHECK-NOT: ERROR: Runtime op verification failed + func.call @matmul_named(%d5x4, %d4x5) : (tensor, tensor) -> (tensor) + + // CHECK: ERROR: Runtime op verification failed + // CHECK: linalg.matmul + // CHECK: ^ dimension #0 of input/output operand #1 is incompatible with inferred dimension size + func.call @matmul_named(%d4x5, %d4x5) : (tensor, tensor) -> (tensor) + + %c64x57 = arith.constant dense<0.0> : tensor<16x29xf32> + %c3x4 = arith.constant dense<0.0> : tensor<3x4xf32> + + // CHECK-NOT: ERROR: Runtime op verification failed + func.call @conv(%c64x57, %c3x4) : (tensor<16x29xf32>, tensor<3x4xf32>) -> (tensor<5x7xf32>) + + // CHECK-NOT: ERROR: Runtime op verification failed + func.call @reverse_from_3(%d4x) : (tensor) -> (tensor) + + // CHECK: ERROR: Runtime op verification failed + // CHECK: linalg.generic + // CHECK: unexpected negative result on dimension #0 of input/output operand #0 + func.call @reverse_from_3(%d5x) : (tensor) -> (tensor) + + return +} + + +#identity1D = affine_map<(d0) -> (d0)> + +func.func @simple_add(%arg0: tensor, %arg1: tensor) -> (tensor) { + %c0 = arith.constant 0 : index + %dim = tensor.dim %arg0, %c0 : tensor + %result = tensor.empty(%dim) : tensor + %0 = linalg.generic { + indexing_maps = [#identity1D, #identity1D, #identity1D], + iterator_types = ["parallel"] + } ins(%arg0, %arg1 : tensor, tensor) + outs(%result : tensor) { + ^bb0(%gen_arg1: f32, %gen_arg2: f32, %out: f32) : + %tmp1 = arith.addf %gen_arg1, %gen_arg2 : f32 + linalg.yield %tmp1 : f32 + } -> tensor + return %0 : tensor +} + +#broadcastD0 = affine_map<(d0, d1) -> (0, d1)> +#broadcastD1 = affine_map<(d0, d1) -> (d0, 0)> +#identity2D = affine_map<(d0, d1) -> (d0, d1)> + +func.func @broadcast_add(%arg0: tensor, %arg1: tensor) -> tensor { + // Calculate maximum dimension 0 + %c0 = arith.constant 0 : index + %dim = tensor.dim %arg0, %c0 : tensor + %dim_0 = tensor.dim %arg1, %c0 : tensor + %0 = arith.maxui %dim, %dim_0 : index + + // Calculate maximum dimension 1 + %c1 = arith.constant 1 : index + %dim_1 = tensor.dim %arg0, %c1 : tensor + %dim_2 = tensor.dim %arg1, %c1 : tensor + %1 = arith.maxui %dim_1, %dim_2 : index + + // Broadcast dimension 0 of %arg0 + %dim_3 = tensor.dim %arg0, %c0 : tensor + %2 = arith.cmpi eq, %dim_3, %c1 : index + %3 = scf.if %2 -> (tensor) { + %dim_7 = tensor.dim %arg0, %c1 : tensor + %12 = tensor.empty(%0, %dim_7) : tensor + %13 = linalg.generic { + indexing_maps = [#broadcastD0, #identity2D], + iterator_types = ["parallel", "parallel"] + } ins(%arg0 : tensor) outs(%12 : tensor) { + ^bb0(%in: f32, %out: f32): + linalg.yield %in : f32 + } -> tensor + scf.yield %13 : tensor + } else { + scf.yield %arg0 : tensor + } + + // Broadcast dimension 1 of %arg0 + %dim_4 = tensor.dim %3, %c1 : tensor + %4 = arith.cmpi eq, %dim_4, %c1 : index + %5 = scf.if %4 -> (tensor) { + %dim_7 = tensor.dim %3, %c0 : tensor + %12 = tensor.empty(%dim_7, %1) : tensor + %13 = linalg.generic { + indexing_maps = [#broadcastD1, #identity2D], + iterator_types = ["parallel", "parallel"] + } ins(%3 : tensor) outs(%12 : tensor) { + ^bb0(%in: f32, %out: f32): + linalg.yield %in : f32 + } -> tensor + scf.yield %13 : tensor + } else { + scf.yield %3 : tensor + } + + // Broadcast dimension 0 of %arg1 + %dim_5 = tensor.dim %arg1, %c0 : tensor + %6 = arith.cmpi eq, %dim_5, %c1 : index + %7 = scf.if %6 -> (tensor) { + %dim_7 = tensor.dim %arg1, %c1 : tensor + %12 = tensor.empty(%0, %dim_7) : tensor + %13 = linalg.generic { + indexing_maps = [#broadcastD0, #identity2D], + iterator_types = ["parallel", "parallel"] + } ins(%arg1 : tensor) outs(%12 : tensor) { + ^bb0(%in: f32, %out: f32): + linalg.yield %in : f32 + } -> tensor + scf.yield %13 : tensor + } else { + scf.yield %arg1 : tensor + } + + // Broadcast dimension 1 of %arg1 + %dim_6 = tensor.dim %7, %c1 : tensor + %8 = arith.cmpi eq, %dim_6, %c1 : index + %9 = scf.if %8 -> (tensor) { + %dim_7 = tensor.dim %7, %c0 : tensor + %12 = tensor.empty(%dim_7, %1) : tensor + %13 = linalg.generic { + indexing_maps = [#broadcastD1, #identity2D], + iterator_types = ["parallel", "parallel"] + } ins(%7 : tensor) outs(%12 : tensor) { + ^bb0(%in: f32, %out: f32): + linalg.yield %in : f32 + } -> tensor + scf.yield %13 : tensor + } else { + scf.yield %7 : tensor + } + + // Perform element-wise computation + %10 = tensor.empty(%0, %1) : tensor + %11 = linalg.generic { + indexing_maps = [#identity2D, #identity2D, #identity2D], + iterator_types = ["parallel", "parallel"] + } ins(%5, %9 : tensor, tensor) outs(%10 : tensor) { + ^bb0(%in: f32, %in_7: f32, %out: f32): + %12 = arith.addf %in, %in_7 : f32 + linalg.yield %12 : f32 + } -> tensor + return %11 : tensor +} + +#matmul_accesses = [ + affine_map<(m, n, k) -> (m, k)>, + affine_map<(m, n, k) -> (k, n)>, + affine_map<(m, n, k) -> (m, n)> +] +#matmul_trait = { + iterator_types = ["parallel", "parallel", "reduction"], + indexing_maps = #matmul_accesses +} + +func.func @matmul_generic(%arg0: tensor, %arg1: tensor) -> tensor { + %cf0 = arith.constant 0.0 : f32 + %ci0 = arith.constant 0 : index + %ci1 = arith.constant 1 : index + %d0 = tensor.dim %arg0, %ci0 : tensor + %d1 = tensor.dim %arg1, %ci1 : tensor + %splat = tensor.splat %cf0[%d0, %d1] : tensor + %0 = linalg.generic #matmul_trait ins(%arg0, %arg1 : tensor, tensor) outs(%splat : tensor) { + ^bb0(%in: f32, %in_0: f32, %out: f32): + %1 = arith.mulf %in, %in_0 : f32 + %2 = arith.addf %out, %1 : f32 + linalg.yield %2 : f32 + } -> tensor + return %0 : tensor +} + +func.func @matmul_named(%arg0: tensor, %arg1: tensor) -> tensor { + %cf0 = arith.constant 0.0 : f32 + %ci0 = arith.constant 0 : index + %ci1 = arith.constant 1 : index + %d0 = tensor.dim %arg0, %ci0 : tensor + %d1 = tensor.dim %arg1, %ci1 : tensor + %splat = tensor.splat %cf0[%d0, %d1] : tensor + %0 = linalg.matmul ins(%arg0, %arg1 : tensor, tensor) outs(%splat : tensor) -> tensor + return %0 : tensor +} + +#conv_trait = { + indexing_maps = [affine_map<(d0, d1, d2, d3) -> (d0 * 3 + d2, d1 * 4 + d3)>, affine_map<(d0, d1, d2, d3) -> (d2, d3)>, affine_map<(d0, d1, d2, d3) -> (d0, d1)>], + iterator_types = ["parallel", "parallel", "reduction", "reduction"] +} + +func.func @conv(%arg0: tensor<16x29xf32>, %arg1: tensor<3x4xf32>) -> (tensor<5x7xf32>) { + %c0 = arith.constant 0.0 : f32 + %splat = tensor.splat %c0 : tensor<5x7xf32> + %result = linalg.generic #conv_trait ins(%arg0, %arg1 : tensor<16x29xf32>, tensor<3x4xf32>) outs(%splat : tensor<5x7xf32>) { + ^bb0(%in: f32, %in_64: f32, %out: f32): + %5 = arith.mulf %in, %in_64 : f32 + %6 = arith.addf %out, %5 : f32 + linalg.yield %6 : f32 + } -> tensor<5x7xf32> + return %result : tensor<5x7xf32> +} + +#reverse_trait = { + indexing_maps = [ + affine_map<(i) -> (3 - i)>, + affine_map<(i) -> (i)> + ], + iterator_types = ["parallel"] +} + +func.func @reverse_from_3(%arg0: tensor) -> (tensor) { + %cf0 = arith.constant 0.0 : f32 + %ci0 = arith.constant 0 : index + %d0 = tensor.dim %arg0, %ci0 : tensor + %splat = tensor.splat %cf0[%d0] : tensor + %result = linalg.generic #reverse_trait ins(%arg0: tensor) outs(%splat: tensor) { + ^bb0(%a: f32, %b: f32): + linalg.yield %a : f32 + } -> tensor + return %result : tensor +} diff --git a/mlir/test/Target/LLVMIR/omptarget-parallel-wsloop.mlir b/mlir/test/Target/LLVMIR/omptarget-parallel-wsloop.mlir index b0fe642238f14f5e2b0a17aeffb9ab95ec41fe9e..360b3b0c0e60c1791e7fed19c8cf1761f4bce881 100644 --- a/mlir/test/Target/LLVMIR/omptarget-parallel-wsloop.mlir +++ b/mlir/test/Target/LLVMIR/omptarget-parallel-wsloop.mlir @@ -12,10 +12,13 @@ module attributes {dlti.dl_spec = #dlti.dl_spec<#dlti.dl_entry<"dlti.alloca_memo %loop_ub = llvm.mlir.constant(9 : i32) : i32 %loop_lb = llvm.mlir.constant(0 : i32) : i32 %loop_step = llvm.mlir.constant(1 : i32) : i32 - omp.wsloop for (%loop_cnt) : i32 = (%loop_lb) to (%loop_ub) inclusive step (%loop_step) { - %gep = llvm.getelementptr %arg0[0, %loop_cnt] : (!llvm.ptr, i32) -> !llvm.ptr, !llvm.array<10 x i32> - llvm.store %loop_cnt, %gep : i32, !llvm.ptr - omp.yield + omp.wsloop { + omp.loop_nest (%loop_cnt) : i32 = (%loop_lb) to (%loop_ub) inclusive step (%loop_step) { + %gep = llvm.getelementptr %arg0[0, %loop_cnt] : (!llvm.ptr, i32) -> !llvm.ptr, !llvm.array<10 x i32> + llvm.store %loop_cnt, %gep : i32, !llvm.ptr + omp.yield + } + omp.terminator } omp.terminator } diff --git a/mlir/test/Target/LLVMIR/omptarget-wsloop-collapsed.mlir b/mlir/test/Target/LLVMIR/omptarget-wsloop-collapsed.mlir index 0d77423abcb4f1354e13551fbb5b13ebd255c481..13d34b7e58f77e19b1dd2ab25645f78e0f1f73c2 100644 --- a/mlir/test/Target/LLVMIR/omptarget-wsloop-collapsed.mlir +++ b/mlir/test/Target/LLVMIR/omptarget-wsloop-collapsed.mlir @@ -8,13 +8,16 @@ module attributes {dlti.dl_spec = #dlti.dl_spec<#dlti.dl_entry<"dlti.alloca_memo %loop_ub = llvm.mlir.constant(99 : i32) : i32 %loop_lb = llvm.mlir.constant(0 : i32) : i32 %loop_step = llvm.mlir.constant(1 : index) : i32 - omp.wsloop for (%arg1, %arg2) : i32 = (%loop_lb, %loop_lb) to (%loop_ub, %loop_ub) inclusive step (%loop_step, %loop_step) { - %1 = llvm.add %arg1, %arg2 : i32 - %2 = llvm.mul %arg2, %loop_ub overflow : i32 - %3 = llvm.add %arg1, %2 :i32 - %4 = llvm.getelementptr %arg0[%3] : (!llvm.ptr, i32) -> !llvm.ptr, i32 - llvm.store %1, %4 : i32, !llvm.ptr - omp.yield + omp.wsloop { + omp.loop_nest (%arg1, %arg2) : i32 = (%loop_lb, %loop_lb) to (%loop_ub, %loop_ub) inclusive step (%loop_step, %loop_step) { + %1 = llvm.add %arg1, %arg2 : i32 + %2 = llvm.mul %arg2, %loop_ub overflow : i32 + %3 = llvm.add %arg1, %2 :i32 + %4 = llvm.getelementptr %arg0[%3] : (!llvm.ptr, i32) -> !llvm.ptr, i32 + llvm.store %1, %4 : i32, !llvm.ptr + omp.yield + } + omp.terminator } llvm.return } diff --git a/mlir/test/Target/LLVMIR/omptarget-wsloop.mlir b/mlir/test/Target/LLVMIR/omptarget-wsloop.mlir index 0f3f503dfa5377b2eaa1287885862103c9d4ca24..ee851eaf71ac0b726bb52a74c36a5f90a6f94975 100644 --- a/mlir/test/Target/LLVMIR/omptarget-wsloop.mlir +++ b/mlir/test/Target/LLVMIR/omptarget-wsloop.mlir @@ -8,10 +8,13 @@ module attributes {dlti.dl_spec = #dlti.dl_spec<#dlti.dl_entry<"dlti.alloca_memo %loop_ub = llvm.mlir.constant(9 : i32) : i32 %loop_lb = llvm.mlir.constant(0 : i32) : i32 %loop_step = llvm.mlir.constant(1 : i32) : i32 - omp.wsloop for (%loop_cnt) : i32 = (%loop_lb) to (%loop_ub) inclusive step (%loop_step) { - %gep = llvm.getelementptr %arg0[0, %loop_cnt] : (!llvm.ptr, i32) -> !llvm.ptr, !llvm.array<10 x i32> - llvm.store %loop_cnt, %gep : i32, !llvm.ptr - omp.yield + omp.wsloop { + omp.loop_nest (%loop_cnt) : i32 = (%loop_lb) to (%loop_ub) inclusive step (%loop_step) { + %gep = llvm.getelementptr %arg0[0, %loop_cnt] : (!llvm.ptr, i32) -> !llvm.ptr, !llvm.array<10 x i32> + llvm.store %loop_cnt, %gep : i32, !llvm.ptr + omp.yield + } + omp.terminator } llvm.return } @@ -20,8 +23,11 @@ module attributes {dlti.dl_spec = #dlti.dl_spec<#dlti.dl_entry<"dlti.alloca_memo %loop_ub = llvm.mlir.constant(9 : i32) : i32 %loop_lb = llvm.mlir.constant(0 : i32) : i32 %loop_step = llvm.mlir.constant(1 : i32) : i32 - omp.wsloop for (%loop_cnt) : i32 = (%loop_lb) to (%loop_ub) inclusive step (%loop_step) { - omp.yield + omp.wsloop { + omp.loop_nest (%loop_cnt) : i32 = (%loop_lb) to (%loop_ub) inclusive step (%loop_step) { + omp.yield + } + omp.terminator } llvm.return } diff --git a/mlir/test/Target/LLVMIR/openmp-data-target-device.mlir b/mlir/test/Target/LLVMIR/openmp-data-target-device.mlir index d41429a6de066f51643d0fee4f60dd8f71ff3ed7..4ea9df369af66c62793f58149c939f6d9ce079f9 100644 --- a/mlir/test/Target/LLVMIR/openmp-data-target-device.mlir +++ b/mlir/test/Target/LLVMIR/openmp-data-target-device.mlir @@ -31,20 +31,23 @@ module attributes { } { %18 = llvm.mlir.constant(1 : i64) : i64 %19 = llvm.alloca %18 x i32 {pinned} : (i64) -> !llvm.ptr<5> %20 = llvm.addrspacecast %19 : !llvm.ptr<5> to !llvm.ptr - omp.wsloop for (%arg2) : i32 = (%16) to (%15) inclusive step (%16) { - llvm.store %arg2, %20 : i32, !llvm.ptr - %21 = llvm.load %20 : !llvm.ptr -> i32 - %22 = llvm.sext %21 : i32 to i64 - %23 = llvm.mlir.constant(1 : i64) : i64 - %24 = llvm.mlir.constant(0 : i64) : i64 - %25 = llvm.sub %22, %23 overflow : i64 - %26 = llvm.mul %25, %23 overflow : i64 - %27 = llvm.mul %26, %23 overflow : i64 - %28 = llvm.add %27, %24 overflow : i64 - %29 = llvm.mul %23, %17 overflow : i64 - %30 = llvm.getelementptr %arg0[%28] : (!llvm.ptr, i64) -> !llvm.ptr, i32 - llvm.store %21, %30 : i32, !llvm.ptr - omp.yield + omp.wsloop { + omp.loop_nest (%arg2) : i32 = (%16) to (%15) inclusive step (%16) { + llvm.store %arg2, %20 : i32, !llvm.ptr + %21 = llvm.load %20 : !llvm.ptr -> i32 + %22 = llvm.sext %21 : i32 to i64 + %23 = llvm.mlir.constant(1 : i64) : i64 + %24 = llvm.mlir.constant(0 : i64) : i64 + %25 = llvm.sub %22, %23 overflow : i64 + %26 = llvm.mul %25, %23 overflow : i64 + %27 = llvm.mul %26, %23 overflow : i64 + %28 = llvm.add %27, %24 overflow : i64 + %29 = llvm.mul %23, %17 overflow : i64 + %30 = llvm.getelementptr %arg0[%28] : (!llvm.ptr, i64) -> !llvm.ptr, i32 + llvm.store %21, %30 : i32, !llvm.ptr + omp.yield + } + omp.terminator } omp.terminator } diff --git a/mlir/test/Target/LLVMIR/openmp-llvm.mlir b/mlir/test/Target/LLVMIR/openmp-llvm.mlir index d1390022c1dc442b8e24350fe9cab02b3d548b20..ad40ca26bec9f821ffd8e3f17b7b8c8347a480ba 100644 --- a/mlir/test/Target/LLVMIR/openmp-llvm.mlir +++ b/mlir/test/Target/LLVMIR/openmp-llvm.mlir @@ -320,18 +320,20 @@ llvm.func @wsloop_simple(%arg0: !llvm.ptr) { %1 = llvm.mlir.constant(10 : index) : i64 %2 = llvm.mlir.constant(1 : index) : i64 omp.parallel { - "omp.wsloop"(%1, %0, %2) ({ - ^bb0(%arg1: i64): - // The form of the emitted IR is controlled by OpenMPIRBuilder and - // tested there. Just check that the right functions are called. - // CHECK: call i32 @__kmpc_global_thread_num - // CHECK: call void @__kmpc_for_static_init_{{.*}}(ptr @[[$loc_struct]], - %3 = llvm.mlir.constant(2.000000e+00 : f32) : f32 - %4 = llvm.getelementptr %arg0[%arg1] : (!llvm.ptr, i64) -> !llvm.ptr, f32 - llvm.store %3, %4 : f32, !llvm.ptr - omp.yield + "omp.wsloop"() ({ + omp.loop_nest (%arg1) : i64 = (%1) to (%0) step (%2) { + // The form of the emitted IR is controlled by OpenMPIRBuilder and + // tested there. Just check that the right functions are called. + // CHECK: call i32 @__kmpc_global_thread_num + // CHECK: call void @__kmpc_for_static_init_{{.*}}(ptr @[[$loc_struct]], + %3 = llvm.mlir.constant(2.000000e+00 : f32) : f32 + %4 = llvm.getelementptr %arg0[%arg1] : (!llvm.ptr, i64) -> !llvm.ptr, f32 + llvm.store %3, %4 : f32, !llvm.ptr + omp.yield + } + omp.terminator // CHECK: call void @__kmpc_for_static_fini(ptr @[[$loc_struct]], - }) {operandSegmentSizes = array} : (i64, i64, i64) -> () + }) : () -> () omp.terminator } llvm.return @@ -345,13 +347,15 @@ llvm.func @wsloop_inclusive_1(%arg0: !llvm.ptr) { %1 = llvm.mlir.constant(10 : index) : i64 %2 = llvm.mlir.constant(1 : index) : i64 // CHECK: store i64 31, ptr %{{.*}}upperbound - "omp.wsloop"(%1, %0, %2) ({ - ^bb0(%arg1: i64): - %3 = llvm.mlir.constant(2.000000e+00 : f32) : f32 - %4 = llvm.getelementptr %arg0[%arg1] : (!llvm.ptr, i64) -> !llvm.ptr, f32 - llvm.store %3, %4 : f32, !llvm.ptr - omp.yield - }) {operandSegmentSizes = array} : (i64, i64, i64) -> () + "omp.wsloop"() ({ + omp.loop_nest (%arg1) : i64 = (%1) to (%0) step (%2) { + %3 = llvm.mlir.constant(2.000000e+00 : f32) : f32 + %4 = llvm.getelementptr %arg0[%arg1] : (!llvm.ptr, i64) -> !llvm.ptr, f32 + llvm.store %3, %4 : f32, !llvm.ptr + omp.yield + } + omp.terminator + }) : () -> () llvm.return } @@ -363,13 +367,15 @@ llvm.func @wsloop_inclusive_2(%arg0: !llvm.ptr) { %1 = llvm.mlir.constant(10 : index) : i64 %2 = llvm.mlir.constant(1 : index) : i64 // CHECK: store i64 32, ptr %{{.*}}upperbound - "omp.wsloop"(%1, %0, %2) ({ - ^bb0(%arg1: i64): - %3 = llvm.mlir.constant(2.000000e+00 : f32) : f32 - %4 = llvm.getelementptr %arg0[%arg1] : (!llvm.ptr, i64) -> !llvm.ptr, f32 - llvm.store %3, %4 : f32, !llvm.ptr - omp.yield - }) {inclusive, operandSegmentSizes = array} : (i64, i64, i64) -> () + "omp.wsloop"() ({ + omp.loop_nest (%arg1) : i64 = (%1) to (%0) inclusive step (%2) { + %3 = llvm.mlir.constant(2.000000e+00 : f32) : f32 + %4 = llvm.getelementptr %arg0[%arg1] : (!llvm.ptr, i64) -> !llvm.ptr, f32 + llvm.store %3, %4 : f32, !llvm.ptr + omp.yield + } + omp.terminator + }) : () -> () llvm.return } @@ -379,14 +385,16 @@ llvm.func @body(i32) // CHECK-LABEL: @test_omp_wsloop_static_defchunk llvm.func @test_omp_wsloop_static_defchunk(%lb : i32, %ub : i32, %step : i32) -> () { - omp.wsloop schedule(static) - for (%iv) : i32 = (%lb) to (%ub) step (%step) { - // CHECK: call void @__kmpc_for_static_init_4u(ptr @{{.*}}, i32 %{{.*}}, i32 34, ptr %{{.*}}, ptr %{{.*}}, ptr %{{.*}}, ptr %{{.*}}, i32 1, i32 0) - // CHECK: call void @__kmpc_for_static_fini - llvm.call @body(%iv) : (i32) -> () - omp.yield - } - llvm.return + omp.wsloop schedule(static) { + omp.loop_nest (%iv) : i32 = (%lb) to (%ub) step (%step) { + // CHECK: call void @__kmpc_for_static_init_4u(ptr @{{.*}}, i32 %{{.*}}, i32 34, ptr %{{.*}}, ptr %{{.*}}, ptr %{{.*}}, ptr %{{.*}}, i32 1, i32 0) + // CHECK: call void @__kmpc_for_static_fini + llvm.call @body(%iv) : (i32) -> () + omp.yield + } + omp.terminator + } + llvm.return } // ----- @@ -395,15 +403,17 @@ llvm.func @body(i32) // CHECK-LABEL: @test_omp_wsloop_static_1 llvm.func @test_omp_wsloop_static_1(%lb : i32, %ub : i32, %step : i32) -> () { - %static_chunk_size = llvm.mlir.constant(1 : i32) : i32 - omp.wsloop schedule(static = %static_chunk_size : i32) - for (%iv) : i32 = (%lb) to (%ub) step (%step) { - // CHECK: call void @__kmpc_for_static_init_4u(ptr @{{.*}}, i32 %{{.*}}, i32 33, ptr %{{.*}}, ptr %{{.*}}, ptr %{{.*}}, ptr %{{.*}}, i32 1, i32 1) - // CHECK: call void @__kmpc_for_static_fini - llvm.call @body(%iv) : (i32) -> () - omp.yield - } - llvm.return + %static_chunk_size = llvm.mlir.constant(1 : i32) : i32 + omp.wsloop schedule(static = %static_chunk_size : i32) { + omp.loop_nest (%iv) : i32 = (%lb) to (%ub) step (%step) { + // CHECK: call void @__kmpc_for_static_init_4u(ptr @{{.*}}, i32 %{{.*}}, i32 33, ptr %{{.*}}, ptr %{{.*}}, ptr %{{.*}}, ptr %{{.*}}, i32 1, i32 1) + // CHECK: call void @__kmpc_for_static_fini + llvm.call @body(%iv) : (i32) -> () + omp.yield + } + omp.terminator + } + llvm.return } // ----- @@ -412,15 +422,17 @@ llvm.func @body(i32) // CHECK-LABEL: @test_omp_wsloop_static_2 llvm.func @test_omp_wsloop_static_2(%lb : i32, %ub : i32, %step : i32) -> () { - %static_chunk_size = llvm.mlir.constant(2 : i32) : i32 - omp.wsloop schedule(static = %static_chunk_size : i32) - for (%iv) : i32 = (%lb) to (%ub) step (%step) { - // CHECK: call void @__kmpc_for_static_init_4u(ptr @{{.*}}, i32 %{{.*}}, i32 33, ptr %{{.*}}, ptr %{{.*}}, ptr %{{.*}}, ptr %{{.*}}, i32 1, i32 2) - // CHECK: call void @__kmpc_for_static_fini - llvm.call @body(%iv) : (i32) -> () - omp.yield - } - llvm.return + %static_chunk_size = llvm.mlir.constant(2 : i32) : i32 + omp.wsloop schedule(static = %static_chunk_size : i32) { + omp.loop_nest (%iv) : i32 = (%lb) to (%ub) step (%step) { + // CHECK: call void @__kmpc_for_static_init_4u(ptr @{{.*}}, i32 %{{.*}}, i32 33, ptr %{{.*}}, ptr %{{.*}}, ptr %{{.*}}, ptr %{{.*}}, i32 1, i32 2) + // CHECK: call void @__kmpc_for_static_fini + llvm.call @body(%iv) : (i32) -> () + omp.yield + } + omp.terminator + } + llvm.return } // ----- @@ -428,16 +440,18 @@ llvm.func @test_omp_wsloop_static_2(%lb : i32, %ub : i32, %step : i32) -> () { llvm.func @body(i64) llvm.func @test_omp_wsloop_dynamic(%lb : i64, %ub : i64, %step : i64) -> () { - omp.wsloop schedule(dynamic) - for (%iv) : i64 = (%lb) to (%ub) step (%step) { - // CHECK: call void @__kmpc_dispatch_init_8u - // CHECK: %[[continue:.*]] = call i32 @__kmpc_dispatch_next_8u - // CHECK: %[[cond:.*]] = icmp ne i32 %[[continue]], 0 - // CHECK: br i1 %[[cond]], label %omp_loop.header{{.*}}, label %omp_loop.exit{{.*}} - llvm.call @body(%iv) : (i64) -> () - omp.yield - } - llvm.return + omp.wsloop schedule(dynamic) { + omp.loop_nest (%iv) : i64 = (%lb) to (%ub) step (%step) { + // CHECK: call void @__kmpc_dispatch_init_8u + // CHECK: %[[continue:.*]] = call i32 @__kmpc_dispatch_next_8u + // CHECK: %[[cond:.*]] = icmp ne i32 %[[continue]], 0 + // CHECK: br i1 %[[cond]], label %omp_loop.header{{.*}}, label %omp_loop.exit{{.*}} + llvm.call @body(%iv) : (i64) -> () + omp.yield + } + omp.terminator + } + llvm.return } // ----- @@ -445,17 +459,19 @@ llvm.func @test_omp_wsloop_dynamic(%lb : i64, %ub : i64, %step : i64) -> () { llvm.func @body(i64) llvm.func @test_omp_wsloop_dynamic_chunk_const(%lb : i64, %ub : i64, %step : i64) -> () { - %chunk_size_const = llvm.mlir.constant(2 : i16) : i16 - omp.wsloop schedule(dynamic = %chunk_size_const : i16) - for (%iv) : i64 = (%lb) to (%ub) step (%step) { - // CHECK: call void @__kmpc_dispatch_init_8u(ptr @{{.*}}, i32 %{{.*}}, i32 1073741859, i64 {{.*}}, i64 %{{.*}}, i64 {{.*}}, i64 2) - // CHECK: %[[continue:.*]] = call i32 @__kmpc_dispatch_next_8u - // CHECK: %[[cond:.*]] = icmp ne i32 %[[continue]], 0 - // CHECK: br i1 %[[cond]], label %omp_loop.header{{.*}}, label %omp_loop.exit{{.*}} - llvm.call @body(%iv) : (i64) -> () - omp.yield - } - llvm.return + %chunk_size_const = llvm.mlir.constant(2 : i16) : i16 + omp.wsloop schedule(dynamic = %chunk_size_const : i16) { + omp.loop_nest (%iv) : i64 = (%lb) to (%ub) step (%step) { + // CHECK: call void @__kmpc_dispatch_init_8u(ptr @{{.*}}, i32 %{{.*}}, i32 1073741859, i64 {{.*}}, i64 %{{.*}}, i64 {{.*}}, i64 2) + // CHECK: %[[continue:.*]] = call i32 @__kmpc_dispatch_next_8u + // CHECK: %[[cond:.*]] = icmp ne i32 %[[continue]], 0 + // CHECK: br i1 %[[cond]], label %omp_loop.header{{.*}}, label %omp_loop.exit{{.*}} + llvm.call @body(%iv) : (i64) -> () + omp.yield + } + omp.terminator + } + llvm.return } // ----- @@ -463,20 +479,22 @@ llvm.func @test_omp_wsloop_dynamic_chunk_const(%lb : i64, %ub : i64, %step : i64 llvm.func @body(i32) llvm.func @test_omp_wsloop_dynamic_chunk_var(%lb : i32, %ub : i32, %step : i32) -> () { - %1 = llvm.mlir.constant(1 : i64) : i64 - %chunk_size_alloca = llvm.alloca %1 x i16 {bindc_name = "chunk_size", in_type = i16, uniq_name = "_QFsub1Echunk_size"} : (i64) -> !llvm.ptr - %chunk_size_var = llvm.load %chunk_size_alloca : !llvm.ptr -> i16 - omp.wsloop schedule(dynamic = %chunk_size_var : i16) - for (%iv) : i32 = (%lb) to (%ub) step (%step) { - // CHECK: %[[CHUNK_SIZE:.*]] = sext i16 %{{.*}} to i32 - // CHECK: call void @__kmpc_dispatch_init_4u(ptr @{{.*}}, i32 %{{.*}}, i32 1073741859, i32 {{.*}}, i32 %{{.*}}, i32 {{.*}}, i32 %[[CHUNK_SIZE]]) - // CHECK: %[[continue:.*]] = call i32 @__kmpc_dispatch_next_4u - // CHECK: %[[cond:.*]] = icmp ne i32 %[[continue]], 0 - // CHECK: br i1 %[[cond]], label %omp_loop.header{{.*}}, label %omp_loop.exit{{.*}} - llvm.call @body(%iv) : (i32) -> () - omp.yield - } - llvm.return + %1 = llvm.mlir.constant(1 : i64) : i64 + %chunk_size_alloca = llvm.alloca %1 x i16 {bindc_name = "chunk_size", in_type = i16, uniq_name = "_QFsub1Echunk_size"} : (i64) -> !llvm.ptr + %chunk_size_var = llvm.load %chunk_size_alloca : !llvm.ptr -> i16 + omp.wsloop schedule(dynamic = %chunk_size_var : i16) { + omp.loop_nest (%iv) : i32 = (%lb) to (%ub) step (%step) { + // CHECK: %[[CHUNK_SIZE:.*]] = sext i16 %{{.*}} to i32 + // CHECK: call void @__kmpc_dispatch_init_4u(ptr @{{.*}}, i32 %{{.*}}, i32 1073741859, i32 {{.*}}, i32 %{{.*}}, i32 {{.*}}, i32 %[[CHUNK_SIZE]]) + // CHECK: %[[continue:.*]] = call i32 @__kmpc_dispatch_next_4u + // CHECK: %[[cond:.*]] = icmp ne i32 %[[continue]], 0 + // CHECK: br i1 %[[cond]], label %omp_loop.header{{.*}}, label %omp_loop.exit{{.*}} + llvm.call @body(%iv) : (i32) -> () + omp.yield + } + omp.terminator + } + llvm.return } // ----- @@ -484,20 +502,22 @@ llvm.func @test_omp_wsloop_dynamic_chunk_var(%lb : i32, %ub : i32, %step : i32) llvm.func @body(i32) llvm.func @test_omp_wsloop_dynamic_chunk_var2(%lb : i32, %ub : i32, %step : i32) -> () { - %1 = llvm.mlir.constant(1 : i64) : i64 - %chunk_size_alloca = llvm.alloca %1 x i64 {bindc_name = "chunk_size", in_type = i64, uniq_name = "_QFsub1Echunk_size"} : (i64) -> !llvm.ptr - %chunk_size_var = llvm.load %chunk_size_alloca : !llvm.ptr -> i64 - omp.wsloop schedule(dynamic = %chunk_size_var : i64) - for (%iv) : i32 = (%lb) to (%ub) step (%step) { - // CHECK: %[[CHUNK_SIZE:.*]] = trunc i64 %{{.*}} to i32 - // CHECK: call void @__kmpc_dispatch_init_4u(ptr @{{.*}}, i32 %{{.*}}, i32 1073741859, i32 {{.*}}, i32 %{{.*}}, i32 {{.*}}, i32 %[[CHUNK_SIZE]]) - // CHECK: %[[continue:.*]] = call i32 @__kmpc_dispatch_next_4u - // CHECK: %[[cond:.*]] = icmp ne i32 %[[continue]], 0 - // CHECK: br i1 %[[cond]], label %omp_loop.header{{.*}}, label %omp_loop.exit{{.*}} - llvm.call @body(%iv) : (i32) -> () - omp.yield - } - llvm.return + %1 = llvm.mlir.constant(1 : i64) : i64 + %chunk_size_alloca = llvm.alloca %1 x i64 {bindc_name = "chunk_size", in_type = i64, uniq_name = "_QFsub1Echunk_size"} : (i64) -> !llvm.ptr + %chunk_size_var = llvm.load %chunk_size_alloca : !llvm.ptr -> i64 + omp.wsloop schedule(dynamic = %chunk_size_var : i64) { + omp.loop_nest (%iv) : i32 = (%lb) to (%ub) step (%step) { + // CHECK: %[[CHUNK_SIZE:.*]] = trunc i64 %{{.*}} to i32 + // CHECK: call void @__kmpc_dispatch_init_4u(ptr @{{.*}}, i32 %{{.*}}, i32 1073741859, i32 {{.*}}, i32 %{{.*}}, i32 {{.*}}, i32 %[[CHUNK_SIZE]]) + // CHECK: %[[continue:.*]] = call i32 @__kmpc_dispatch_next_4u + // CHECK: %[[cond:.*]] = icmp ne i32 %[[continue]], 0 + // CHECK: br i1 %[[cond]], label %omp_loop.header{{.*}}, label %omp_loop.exit{{.*}} + llvm.call @body(%iv) : (i32) -> () + omp.yield + } + omp.terminator + } + llvm.return } // ----- @@ -505,16 +525,18 @@ llvm.func @test_omp_wsloop_dynamic_chunk_var2(%lb : i32, %ub : i32, %step : i32) llvm.func @body(i32) llvm.func @test_omp_wsloop_dynamic_chunk_var3(%lb : i32, %ub : i32, %step : i32, %chunk_size : i32) -> () { - omp.wsloop schedule(dynamic = %chunk_size : i32) - for (%iv) : i32 = (%lb) to (%ub) step (%step) { - // CHECK: call void @__kmpc_dispatch_init_4u(ptr @{{.*}}, i32 %{{.*}}, i32 1073741859, i32 {{.*}}, i32 %{{.*}}, i32 {{.*}}, i32 %{{.*}}) - // CHECK: %[[continue:.*]] = call i32 @__kmpc_dispatch_next_4u - // CHECK: %[[cond:.*]] = icmp ne i32 %[[continue]], 0 - // CHECK: br i1 %[[cond]], label %omp_loop.header{{.*}}, label %omp_loop.exit{{.*}} - llvm.call @body(%iv) : (i32) -> () - omp.yield - } - llvm.return + omp.wsloop schedule(dynamic = %chunk_size : i32) { + omp.loop_nest (%iv) : i32 = (%lb) to (%ub) step (%step) { + // CHECK: call void @__kmpc_dispatch_init_4u(ptr @{{.*}}, i32 %{{.*}}, i32 1073741859, i32 {{.*}}, i32 %{{.*}}, i32 {{.*}}, i32 %{{.*}}) + // CHECK: %[[continue:.*]] = call i32 @__kmpc_dispatch_next_4u + // CHECK: %[[cond:.*]] = icmp ne i32 %[[continue]], 0 + // CHECK: br i1 %[[cond]], label %omp_loop.header{{.*}}, label %omp_loop.exit{{.*}} + llvm.call @body(%iv) : (i32) -> () + omp.yield + } + omp.terminator + } + llvm.return } // ----- @@ -522,16 +544,18 @@ llvm.func @test_omp_wsloop_dynamic_chunk_var3(%lb : i32, %ub : i32, %step : i32, llvm.func @body(i64) llvm.func @test_omp_wsloop_auto(%lb : i64, %ub : i64, %step : i64) -> () { - omp.wsloop schedule(auto) - for (%iv) : i64 = (%lb) to (%ub) step (%step) { - // CHECK: call void @__kmpc_dispatch_init_8u - // CHECK: %[[continue:.*]] = call i32 @__kmpc_dispatch_next_8u - // CHECK: %[[cond:.*]] = icmp ne i32 %[[continue]], 0 - // CHECK br i1 %[[cond]], label %omp_loop.header{{.*}}, label %omp_loop.exit{{.*}} - llvm.call @body(%iv) : (i64) -> () - omp.yield - } - llvm.return + omp.wsloop schedule(auto) { + omp.loop_nest (%iv) : i64 = (%lb) to (%ub) step (%step) { + // CHECK: call void @__kmpc_dispatch_init_8u + // CHECK: %[[continue:.*]] = call i32 @__kmpc_dispatch_next_8u + // CHECK: %[[cond:.*]] = icmp ne i32 %[[continue]], 0 + // CHECK br i1 %[[cond]], label %omp_loop.header{{.*}}, label %omp_loop.exit{{.*}} + llvm.call @body(%iv) : (i64) -> () + omp.yield + } + omp.terminator + } + llvm.return } // ----- @@ -539,14 +563,16 @@ llvm.func @test_omp_wsloop_auto(%lb : i64, %ub : i64, %step : i64) -> () { llvm.func @body(i64) llvm.func @test_omp_wsloop_runtime(%lb : i64, %ub : i64, %step : i64) -> () { - omp.wsloop schedule(runtime) - for (%iv) : i64 = (%lb) to (%ub) step (%step) { - // CHECK: call void @__kmpc_dispatch_init_8u - // CHECK: %[[continue:.*]] = call i32 @__kmpc_dispatch_next_8u - // CHECK: %[[cond:.*]] = icmp ne i32 %[[continue]], 0 - // CHECK br i1 %[[cond]], label %omp_loop.header{{.*}}, label %omp_loop.exit{{.*}} - llvm.call @body(%iv) : (i64) -> () - omp.yield + omp.wsloop schedule(runtime) { + omp.loop_nest (%iv) : i64 = (%lb) to (%ub) step (%step) { + // CHECK: call void @__kmpc_dispatch_init_8u + // CHECK: %[[continue:.*]] = call i32 @__kmpc_dispatch_next_8u + // CHECK: %[[cond:.*]] = icmp ne i32 %[[continue]], 0 + // CHECK br i1 %[[cond]], label %omp_loop.header{{.*}}, label %omp_loop.exit{{.*}} + llvm.call @body(%iv) : (i64) -> () + omp.yield + } + omp.terminator } llvm.return } @@ -556,14 +582,16 @@ llvm.func @test_omp_wsloop_runtime(%lb : i64, %ub : i64, %step : i64) -> () { llvm.func @body(i64) llvm.func @test_omp_wsloop_guided(%lb : i64, %ub : i64, %step : i64) -> () { - omp.wsloop schedule(guided) - for (%iv) : i64 = (%lb) to (%ub) step (%step) { - // CHECK: call void @__kmpc_dispatch_init_8u - // CHECK: %[[continue:.*]] = call i32 @__kmpc_dispatch_next_8u - // CHECK: %[[cond:.*]] = icmp ne i32 %[[continue]], 0 - // CHECK br i1 %[[cond]], label %omp_loop.header{{.*}}, label %omp_loop.exit{{.*}} - llvm.call @body(%iv) : (i64) -> () - omp.yield + omp.wsloop schedule(guided) { + omp.loop_nest (%iv) : i64 = (%lb) to (%ub) step (%step) { + // CHECK: call void @__kmpc_dispatch_init_8u + // CHECK: %[[continue:.*]] = call i32 @__kmpc_dispatch_next_8u + // CHECK: %[[cond:.*]] = icmp ne i32 %[[continue]], 0 + // CHECK br i1 %[[cond]], label %omp_loop.header{{.*}}, label %omp_loop.exit{{.*}} + llvm.call @body(%iv) : (i64) -> () + omp.yield + } + omp.terminator } llvm.return } @@ -573,14 +601,16 @@ llvm.func @test_omp_wsloop_guided(%lb : i64, %ub : i64, %step : i64) -> () { llvm.func @body(i64) llvm.func @test_omp_wsloop_dynamic_nonmonotonic(%lb : i64, %ub : i64, %step : i64) -> () { - omp.wsloop schedule(dynamic, nonmonotonic) - for (%iv) : i64 = (%lb) to (%ub) step (%step) { - // CHECK: call void @__kmpc_dispatch_init_8u(ptr @{{.*}}, i32 %{{.*}}, i32 1073741859 - // CHECK: %[[continue:.*]] = call i32 @__kmpc_dispatch_next_8u - // CHECK: %[[cond:.*]] = icmp ne i32 %[[continue]], 0 - // CHECK br i1 %[[cond]], label %omp_loop.header{{.*}}, label %omp_loop.exit{{.*}} - llvm.call @body(%iv) : (i64) -> () - omp.yield + omp.wsloop schedule(dynamic, nonmonotonic) { + omp.loop_nest (%iv) : i64 = (%lb) to (%ub) step (%step) { + // CHECK: call void @__kmpc_dispatch_init_8u(ptr @{{.*}}, i32 %{{.*}}, i32 1073741859 + // CHECK: %[[continue:.*]] = call i32 @__kmpc_dispatch_next_8u + // CHECK: %[[cond:.*]] = icmp ne i32 %[[continue]], 0 + // CHECK br i1 %[[cond]], label %omp_loop.header{{.*}}, label %omp_loop.exit{{.*}} + llvm.call @body(%iv) : (i64) -> () + omp.yield + } + omp.terminator } llvm.return } @@ -590,14 +620,16 @@ llvm.func @test_omp_wsloop_dynamic_nonmonotonic(%lb : i64, %ub : i64, %step : i6 llvm.func @body(i64) llvm.func @test_omp_wsloop_dynamic_monotonic(%lb : i64, %ub : i64, %step : i64) -> () { - omp.wsloop schedule(dynamic, monotonic) - for (%iv) : i64 = (%lb) to (%ub) step (%step) { - // CHECK: call void @__kmpc_dispatch_init_8u(ptr @{{.*}}, i32 %{{.*}}, i32 536870947 - // CHECK: %[[continue:.*]] = call i32 @__kmpc_dispatch_next_8u - // CHECK: %[[cond:.*]] = icmp ne i32 %[[continue]], 0 - // CHECK br i1 %[[cond]], label %omp_loop.header{{.*}}, label %omp_loop.exit{{.*}} - llvm.call @body(%iv) : (i64) -> () - omp.yield + omp.wsloop schedule(dynamic, monotonic) { + omp.loop_nest (%iv) : i64 = (%lb) to (%ub) step (%step) { + // CHECK: call void @__kmpc_dispatch_init_8u(ptr @{{.*}}, i32 %{{.*}}, i32 536870947 + // CHECK: %[[continue:.*]] = call i32 @__kmpc_dispatch_next_8u + // CHECK: %[[cond:.*]] = icmp ne i32 %[[continue]], 0 + // CHECK br i1 %[[cond]], label %omp_loop.header{{.*}}, label %omp_loop.exit{{.*}} + llvm.call @body(%iv) : (i64) -> () + omp.yield + } + omp.terminator } llvm.return } @@ -607,14 +639,16 @@ llvm.func @test_omp_wsloop_dynamic_monotonic(%lb : i64, %ub : i64, %step : i64) llvm.func @body(i64) llvm.func @test_omp_wsloop_runtime_simd(%lb : i64, %ub : i64, %step : i64) -> () { - omp.wsloop schedule(runtime, simd) - for (%iv) : i64 = (%lb) to (%ub) step (%step) { - // CHECK: call void @__kmpc_dispatch_init_8u(ptr @{{.*}}, i32 %{{.*}}, i32 1073741871 - // CHECK: %[[continue:.*]] = call i32 @__kmpc_dispatch_next_8u - // CHECK: %[[cond:.*]] = icmp ne i32 %[[continue]], 0 - // CHECK br i1 %[[cond]], label %omp_loop.header{{.*}}, label %omp_loop.exit{{.*}} - llvm.call @body(%iv) : (i64) -> () - omp.yield + omp.wsloop schedule(runtime, simd) { + omp.loop_nest (%iv) : i64 = (%lb) to (%ub) step (%step) { + // CHECK: call void @__kmpc_dispatch_init_8u(ptr @{{.*}}, i32 %{{.*}}, i32 1073741871 + // CHECK: %[[continue:.*]] = call i32 @__kmpc_dispatch_next_8u + // CHECK: %[[cond:.*]] = icmp ne i32 %[[continue]], 0 + // CHECK br i1 %[[cond]], label %omp_loop.header{{.*}}, label %omp_loop.exit{{.*}} + llvm.call @body(%iv) : (i64) -> () + omp.yield + } + omp.terminator } llvm.return } @@ -624,14 +658,16 @@ llvm.func @test_omp_wsloop_runtime_simd(%lb : i64, %ub : i64, %step : i64) -> () llvm.func @body(i64) llvm.func @test_omp_wsloop_guided_simd(%lb : i64, %ub : i64, %step : i64) -> () { - omp.wsloop schedule(guided, simd) - for (%iv) : i64 = (%lb) to (%ub) step (%step) { - // CHECK: call void @__kmpc_dispatch_init_8u(ptr @{{.*}}, i32 %{{.*}}, i32 1073741870 - // CHECK: %[[continue:.*]] = call i32 @__kmpc_dispatch_next_8u - // CHECK: %[[cond:.*]] = icmp ne i32 %[[continue]], 0 - // CHECK br i1 %[[cond]], label %omp_loop.header{{.*}}, label %omp_loop.exit{{.*}} - llvm.call @body(%iv) : (i64) -> () - omp.yield + omp.wsloop schedule(guided, simd) { + omp.loop_nest (%iv) : i64 = (%lb) to (%ub) step (%step) { + // CHECK: call void @__kmpc_dispatch_init_8u(ptr @{{.*}}, i32 %{{.*}}, i32 1073741870 + // CHECK: %[[continue:.*]] = call i32 @__kmpc_dispatch_next_8u + // CHECK: %[[cond:.*]] = icmp ne i32 %[[continue]], 0 + // CHECK br i1 %[[cond]], label %omp_loop.header{{.*}}, label %omp_loop.exit{{.*}} + llvm.call @body(%iv) : (i64) -> () + omp.yield + } + omp.terminator } llvm.return } @@ -793,17 +829,19 @@ llvm.func @simd_if(%arg0: !llvm.ptr {fir.bindc_name = "n"}, %arg1: !llvm.ptr {fi llvm.func @body(i64) llvm.func @test_omp_wsloop_ordered(%lb : i64, %ub : i64, %step : i64) -> () { - omp.wsloop ordered(0) - for (%iv) : i64 = (%lb) to (%ub) step (%step) { - // CHECK: call void @__kmpc_dispatch_init_8u(ptr @{{.*}}, i32 %{{.*}}, i32 66, i64 1, i64 %{{.*}}, i64 1, i64 1) - // CHECK: call void @__kmpc_dispatch_fini_8u - // CHECK: %[[continue:.*]] = call i32 @__kmpc_dispatch_next_8u - // CHECK: %[[cond:.*]] = icmp ne i32 %[[continue]], 0 - // CHECK br i1 %[[cond]], label %omp_loop.header{{.*}}, label %omp_loop.exit{{.*}} - llvm.call @body(%iv) : (i64) -> () - omp.yield - } - llvm.return + omp.wsloop ordered(0) { + omp.loop_nest (%iv) : i64 = (%lb) to (%ub) step (%step) { + // CHECK: call void @__kmpc_dispatch_init_8u(ptr @{{.*}}, i32 %{{.*}}, i32 66, i64 1, i64 %{{.*}}, i64 1, i64 1) + // CHECK: call void @__kmpc_dispatch_fini_8u + // CHECK: %[[continue:.*]] = call i32 @__kmpc_dispatch_next_8u + // CHECK: %[[cond:.*]] = icmp ne i32 %[[continue]], 0 + // CHECK br i1 %[[cond]], label %omp_loop.header{{.*}}, label %omp_loop.exit{{.*}} + llvm.call @body(%iv) : (i64) -> () + omp.yield + } + omp.terminator + } + llvm.return } // ----- @@ -811,17 +849,19 @@ llvm.func @test_omp_wsloop_ordered(%lb : i64, %ub : i64, %step : i64) -> () { llvm.func @body(i64) llvm.func @test_omp_wsloop_static_ordered(%lb : i64, %ub : i64, %step : i64) -> () { - omp.wsloop schedule(static) ordered(0) - for (%iv) : i64 = (%lb) to (%ub) step (%step) { - // CHECK: call void @__kmpc_dispatch_init_8u(ptr @{{.*}}, i32 %{{.*}}, i32 66, i64 1, i64 %{{.*}}, i64 1, i64 1) - // CHECK: call void @__kmpc_dispatch_fini_8u - // CHECK: %[[continue:.*]] = call i32 @__kmpc_dispatch_next_8u - // CHECK: %[[cond:.*]] = icmp ne i32 %[[continue]], 0 - // CHECK br i1 %[[cond]], label %omp_loop.header{{.*}}, label %omp_loop.exit{{.*}} - llvm.call @body(%iv) : (i64) -> () - omp.yield - } - llvm.return + omp.wsloop schedule(static) ordered(0) { + omp.loop_nest (%iv) : i64 = (%lb) to (%ub) step (%step) { + // CHECK: call void @__kmpc_dispatch_init_8u(ptr @{{.*}}, i32 %{{.*}}, i32 66, i64 1, i64 %{{.*}}, i64 1, i64 1) + // CHECK: call void @__kmpc_dispatch_fini_8u + // CHECK: %[[continue:.*]] = call i32 @__kmpc_dispatch_next_8u + // CHECK: %[[cond:.*]] = icmp ne i32 %[[continue]], 0 + // CHECK br i1 %[[cond]], label %omp_loop.header{{.*}}, label %omp_loop.exit{{.*}} + llvm.call @body(%iv) : (i64) -> () + omp.yield + } + omp.terminator + } + llvm.return } // ----- @@ -829,18 +869,20 @@ llvm.func @test_omp_wsloop_static_ordered(%lb : i64, %ub : i64, %step : i64) -> llvm.func @body(i32) llvm.func @test_omp_wsloop_static_chunk_ordered(%lb : i32, %ub : i32, %step : i32) -> () { - %static_chunk_size = llvm.mlir.constant(1 : i32) : i32 - omp.wsloop schedule(static = %static_chunk_size : i32) ordered(0) - for (%iv) : i32 = (%lb) to (%ub) step (%step) { - // CHECK: call void @__kmpc_dispatch_init_4u(ptr @{{.*}}, i32 %{{.*}}, i32 65, i32 1, i32 %{{.*}}, i32 1, i32 1) - // CHECK: call void @__kmpc_dispatch_fini_4u - // CHECK: %[[continue:.*]] = call i32 @__kmpc_dispatch_next_4u - // CHECK: %[[cond:.*]] = icmp ne i32 %[[continue]], 0 - // CHECK br i1 %[[cond]], label %omp_loop.header{{.*}}, label %omp_loop.exit{{.*}} - llvm.call @body(%iv) : (i32) -> () - omp.yield - } - llvm.return + %static_chunk_size = llvm.mlir.constant(1 : i32) : i32 + omp.wsloop schedule(static = %static_chunk_size : i32) ordered(0) { + omp.loop_nest (%iv) : i32 = (%lb) to (%ub) step (%step) { + // CHECK: call void @__kmpc_dispatch_init_4u(ptr @{{.*}}, i32 %{{.*}}, i32 65, i32 1, i32 %{{.*}}, i32 1, i32 1) + // CHECK: call void @__kmpc_dispatch_fini_4u + // CHECK: %[[continue:.*]] = call i32 @__kmpc_dispatch_next_4u + // CHECK: %[[cond:.*]] = icmp ne i32 %[[continue]], 0 + // CHECK br i1 %[[cond]], label %omp_loop.header{{.*}}, label %omp_loop.exit{{.*}} + llvm.call @body(%iv) : (i32) -> () + omp.yield + } + omp.terminator + } + llvm.return } // ----- @@ -848,17 +890,19 @@ llvm.func @test_omp_wsloop_static_chunk_ordered(%lb : i32, %ub : i32, %step : i3 llvm.func @body(i64) llvm.func @test_omp_wsloop_dynamic_ordered(%lb : i64, %ub : i64, %step : i64) -> () { - omp.wsloop schedule(dynamic) ordered(0) - for (%iv) : i64 = (%lb) to (%ub) step (%step) { - // CHECK: call void @__kmpc_dispatch_init_8u(ptr @{{.*}}, i32 %{{.*}}, i32 67, i64 1, i64 %{{.*}}, i64 1, i64 1) - // CHECK: call void @__kmpc_dispatch_fini_8u - // CHECK: %[[continue:.*]] = call i32 @__kmpc_dispatch_next_8u - // CHECK: %[[cond:.*]] = icmp ne i32 %[[continue]], 0 - // CHECK br i1 %[[cond]], label %omp_loop.header{{.*}}, label %omp_loop.exit{{.*}} - llvm.call @body(%iv) : (i64) -> () - omp.yield - } - llvm.return + omp.wsloop schedule(dynamic) ordered(0) { + omp.loop_nest (%iv) : i64 = (%lb) to (%ub) step (%step) { + // CHECK: call void @__kmpc_dispatch_init_8u(ptr @{{.*}}, i32 %{{.*}}, i32 67, i64 1, i64 %{{.*}}, i64 1, i64 1) + // CHECK: call void @__kmpc_dispatch_fini_8u + // CHECK: %[[continue:.*]] = call i32 @__kmpc_dispatch_next_8u + // CHECK: %[[cond:.*]] = icmp ne i32 %[[continue]], 0 + // CHECK br i1 %[[cond]], label %omp_loop.header{{.*}}, label %omp_loop.exit{{.*}} + llvm.call @body(%iv) : (i64) -> () + omp.yield + } + omp.terminator + } + llvm.return } // ----- @@ -866,17 +910,19 @@ llvm.func @test_omp_wsloop_dynamic_ordered(%lb : i64, %ub : i64, %step : i64) -> llvm.func @body(i64) llvm.func @test_omp_wsloop_auto_ordered(%lb : i64, %ub : i64, %step : i64) -> () { - omp.wsloop schedule(auto) ordered(0) - for (%iv) : i64 = (%lb) to (%ub) step (%step) { - // CHECK: call void @__kmpc_dispatch_init_8u(ptr @{{.*}}, i32 %{{.*}}, i32 70, i64 1, i64 %{{.*}}, i64 1, i64 1) - // CHECK: call void @__kmpc_dispatch_fini_8u - // CHECK: %[[continue:.*]] = call i32 @__kmpc_dispatch_next_8u - // CHECK: %[[cond:.*]] = icmp ne i32 %[[continue]], 0 - // CHECK br i1 %[[cond]], label %omp_loop.header{{.*}}, label %omp_loop.exit{{.*}} - llvm.call @body(%iv) : (i64) -> () - omp.yield - } - llvm.return + omp.wsloop schedule(auto) ordered(0) { + omp.loop_nest (%iv) : i64 = (%lb) to (%ub) step (%step) { + // CHECK: call void @__kmpc_dispatch_init_8u(ptr @{{.*}}, i32 %{{.*}}, i32 70, i64 1, i64 %{{.*}}, i64 1, i64 1) + // CHECK: call void @__kmpc_dispatch_fini_8u + // CHECK: %[[continue:.*]] = call i32 @__kmpc_dispatch_next_8u + // CHECK: %[[cond:.*]] = icmp ne i32 %[[continue]], 0 + // CHECK br i1 %[[cond]], label %omp_loop.header{{.*}}, label %omp_loop.exit{{.*}} + llvm.call @body(%iv) : (i64) -> () + omp.yield + } + omp.terminator + } + llvm.return } // ----- @@ -884,17 +930,19 @@ llvm.func @test_omp_wsloop_auto_ordered(%lb : i64, %ub : i64, %step : i64) -> () llvm.func @body(i64) llvm.func @test_omp_wsloop_runtime_ordered(%lb : i64, %ub : i64, %step : i64) -> () { - omp.wsloop schedule(runtime) ordered(0) - for (%iv) : i64 = (%lb) to (%ub) step (%step) { - // CHECK: call void @__kmpc_dispatch_init_8u(ptr @{{.*}}, i32 %{{.*}}, i32 69, i64 1, i64 %{{.*}}, i64 1, i64 1) - // CHECK: call void @__kmpc_dispatch_fini_8u - // CHECK: %[[continue:.*]] = call i32 @__kmpc_dispatch_next_8u - // CHECK: %[[cond:.*]] = icmp ne i32 %[[continue]], 0 - // CHECK br i1 %[[cond]], label %omp_loop.header{{.*}}, label %omp_loop.exit{{.*}} - llvm.call @body(%iv) : (i64) -> () - omp.yield - } - llvm.return + omp.wsloop schedule(runtime) ordered(0) { + omp.loop_nest (%iv) : i64 = (%lb) to (%ub) step (%step) { + // CHECK: call void @__kmpc_dispatch_init_8u(ptr @{{.*}}, i32 %{{.*}}, i32 69, i64 1, i64 %{{.*}}, i64 1, i64 1) + // CHECK: call void @__kmpc_dispatch_fini_8u + // CHECK: %[[continue:.*]] = call i32 @__kmpc_dispatch_next_8u + // CHECK: %[[cond:.*]] = icmp ne i32 %[[continue]], 0 + // CHECK br i1 %[[cond]], label %omp_loop.header{{.*}}, label %omp_loop.exit{{.*}} + llvm.call @body(%iv) : (i64) -> () + omp.yield + } + omp.terminator + } + llvm.return } // ----- @@ -902,17 +950,19 @@ llvm.func @test_omp_wsloop_runtime_ordered(%lb : i64, %ub : i64, %step : i64) -> llvm.func @body(i64) llvm.func @test_omp_wsloop_guided_ordered(%lb : i64, %ub : i64, %step : i64) -> () { - omp.wsloop schedule(guided) ordered(0) - for (%iv) : i64 = (%lb) to (%ub) step (%step) { - // CHECK: call void @__kmpc_dispatch_init_8u(ptr @{{.*}}, i32 %{{.*}}, i32 68, i64 1, i64 %{{.*}}, i64 1, i64 1) - // CHECK: call void @__kmpc_dispatch_fini_8u - // CHECK: %[[continue:.*]] = call i32 @__kmpc_dispatch_next_8u - // CHECK: %[[cond:.*]] = icmp ne i32 %[[continue]], 0 - // CHECK br i1 %[[cond]], label %omp_loop.header{{.*}}, label %omp_loop.exit{{.*}} - llvm.call @body(%iv) : (i64) -> () - omp.yield - } - llvm.return + omp.wsloop schedule(guided) ordered(0) { + omp.loop_nest (%iv) : i64 = (%lb) to (%ub) step (%step) { + // CHECK: call void @__kmpc_dispatch_init_8u(ptr @{{.*}}, i32 %{{.*}}, i32 68, i64 1, i64 %{{.*}}, i64 1, i64 1) + // CHECK: call void @__kmpc_dispatch_fini_8u + // CHECK: %[[continue:.*]] = call i32 @__kmpc_dispatch_next_8u + // CHECK: %[[cond:.*]] = icmp ne i32 %[[continue]], 0 + // CHECK br i1 %[[cond]], label %omp_loop.header{{.*}}, label %omp_loop.exit{{.*}} + llvm.call @body(%iv) : (i64) -> () + omp.yield + } + omp.terminator + } + llvm.return } // ----- @@ -920,17 +970,19 @@ llvm.func @test_omp_wsloop_guided_ordered(%lb : i64, %ub : i64, %step : i64) -> llvm.func @body(i64) llvm.func @test_omp_wsloop_dynamic_nonmonotonic_ordered(%lb : i64, %ub : i64, %step : i64) -> () { - omp.wsloop schedule(dynamic, nonmonotonic) ordered(0) - for (%iv) : i64 = (%lb) to (%ub) step (%step) { - // CHECK: call void @__kmpc_dispatch_init_8u(ptr @{{.*}}, i32 %{{.*}}, i32 1073741891, i64 1, i64 %{{.*}}, i64 1, i64 1) - // CHECK: call void @__kmpc_dispatch_fini_8u - // CHECK: %[[continue:.*]] = call i32 @__kmpc_dispatch_next_8u - // CHECK: %[[cond:.*]] = icmp ne i32 %[[continue]], 0 - // CHECK br i1 %[[cond]], label %omp_loop.header{{.*}}, label %omp_loop.exit{{.*}} - llvm.call @body(%iv) : (i64) -> () - omp.yield - } - llvm.return + omp.wsloop schedule(dynamic, nonmonotonic) ordered(0) { + omp.loop_nest (%iv) : i64 = (%lb) to (%ub) step (%step) { + // CHECK: call void @__kmpc_dispatch_init_8u(ptr @{{.*}}, i32 %{{.*}}, i32 1073741891, i64 1, i64 %{{.*}}, i64 1, i64 1) + // CHECK: call void @__kmpc_dispatch_fini_8u + // CHECK: %[[continue:.*]] = call i32 @__kmpc_dispatch_next_8u + // CHECK: %[[cond:.*]] = icmp ne i32 %[[continue]], 0 + // CHECK br i1 %[[cond]], label %omp_loop.header{{.*}}, label %omp_loop.exit{{.*}} + llvm.call @body(%iv) : (i64) -> () + omp.yield + } + omp.terminator + } + llvm.return } // ----- @@ -938,17 +990,19 @@ llvm.func @test_omp_wsloop_dynamic_nonmonotonic_ordered(%lb : i64, %ub : i64, %s llvm.func @body(i64) llvm.func @test_omp_wsloop_dynamic_monotonic_ordered(%lb : i64, %ub : i64, %step : i64) -> () { - omp.wsloop schedule(dynamic, monotonic) ordered(0) - for (%iv) : i64 = (%lb) to (%ub) step (%step) { - // CHECK: call void @__kmpc_dispatch_init_8u(ptr @{{.*}}, i32 %{{.*}}, i32 536870979, i64 1, i64 %{{.*}}, i64 1, i64 1) - // CHECK: call void @__kmpc_dispatch_fini_8u - // CHECK: %[[continue:.*]] = call i32 @__kmpc_dispatch_next_8u - // CHECK: %[[cond:.*]] = icmp ne i32 %[[continue]], 0 - // CHECK br i1 %[[cond]], label %omp_loop.header{{.*}}, label %omp_loop.exit{{.*}} - llvm.call @body(%iv) : (i64) -> () - omp.yield - } - llvm.return + omp.wsloop schedule(dynamic, monotonic) ordered(0) { + omp.loop_nest (%iv) : i64 = (%lb) to (%ub) step (%step) { + // CHECK: call void @__kmpc_dispatch_init_8u(ptr @{{.*}}, i32 %{{.*}}, i32 536870979, i64 1, i64 %{{.*}}, i64 1, i64 1) + // CHECK: call void @__kmpc_dispatch_fini_8u + // CHECK: %[[continue:.*]] = call i32 @__kmpc_dispatch_next_8u + // CHECK: %[[cond:.*]] = icmp ne i32 %[[continue]], 0 + // CHECK br i1 %[[cond]], label %omp_loop.header{{.*}}, label %omp_loop.exit{{.*}} + llvm.call @body(%iv) : (i64) -> () + omp.yield + } + omp.terminator + } + llvm.return } // ----- @@ -1114,14 +1168,16 @@ llvm.func @collapse_wsloop( // CHECK: %[[TOTAL_SUB_1:.*]] = sub i32 %[[TOTAL]], 1 // CHECK: store i32 %[[TOTAL_SUB_1]], ptr // CHECK: call void @__kmpc_for_static_init_4u - omp.wsloop - for (%arg0, %arg1, %arg2) : i32 = (%0, %1, %2) to (%3, %4, %5) step (%6, %7, %8) { - %31 = llvm.load %20 : !llvm.ptr -> i32 - %32 = llvm.add %31, %arg0 : i32 - %33 = llvm.add %32, %arg1 : i32 - %34 = llvm.add %33, %arg2 : i32 - llvm.store %34, %20 : i32, !llvm.ptr - omp.yield + omp.wsloop { + omp.loop_nest (%arg0, %arg1, %arg2) : i32 = (%0, %1, %2) to (%3, %4, %5) step (%6, %7, %8) { + %31 = llvm.load %20 : !llvm.ptr -> i32 + %32 = llvm.add %31, %arg0 : i32 + %33 = llvm.add %32, %arg1 : i32 + %34 = llvm.add %33, %arg2 : i32 + llvm.store %34, %20 : i32, !llvm.ptr + omp.yield + } + omp.terminator } omp.terminator } @@ -1175,14 +1231,16 @@ llvm.func @collapse_wsloop_dynamic( // CHECK: store i32 1, ptr // CHECK: store i32 %[[TOTAL]], ptr // CHECK: call void @__kmpc_dispatch_init_4u - omp.wsloop schedule(dynamic) - for (%arg0, %arg1, %arg2) : i32 = (%0, %1, %2) to (%3, %4, %5) step (%6, %7, %8) { - %31 = llvm.load %20 : !llvm.ptr -> i32 - %32 = llvm.add %31, %arg0 : i32 - %33 = llvm.add %32, %arg1 : i32 - %34 = llvm.add %33, %arg2 : i32 - llvm.store %34, %20 : i32, !llvm.ptr - omp.yield + omp.wsloop schedule(dynamic) { + omp.loop_nest (%arg0, %arg1, %arg2) : i32 = (%0, %1, %2) to (%3, %4, %5) step (%6, %7, %8) { + %31 = llvm.load %20 : !llvm.ptr -> i32 + %32 = llvm.add %31, %arg0 : i32 + %33 = llvm.add %32, %arg1 : i32 + %34 = llvm.add %33, %arg2 : i32 + llvm.store %34, %20 : i32, !llvm.ptr + omp.yield + } + omp.terminator } omp.terminator } @@ -1207,63 +1265,69 @@ llvm.func @omp_ordered(%arg0 : i32, %arg1 : i32, %arg2 : i32, %arg3 : i64, // CHECK: call void @__kmpc_end_ordered(ptr @[[GLOB1]], i32 [[OMP_THREAD]]) } - omp.wsloop ordered(0) - for (%arg7) : i32 = (%arg0) to (%arg1) step (%arg2) { - // CHECK: call void @__kmpc_ordered(ptr @[[GLOB3:[0-9]+]], i32 [[OMP_THREAD2:%.*]]) - omp.ordered.region { - omp.terminator - // CHECK: call void @__kmpc_end_ordered(ptr @[[GLOB3]], i32 [[OMP_THREAD2]]) + omp.wsloop ordered(0) { + omp.loop_nest (%arg7) : i32 = (%arg0) to (%arg1) step (%arg2) { + // CHECK: call void @__kmpc_ordered(ptr @[[GLOB3:[0-9]+]], i32 [[OMP_THREAD2:%.*]]) + omp.ordered.region { + omp.terminator + // CHECK: call void @__kmpc_end_ordered(ptr @[[GLOB3]], i32 [[OMP_THREAD2]]) + } + omp.yield } - omp.yield + omp.terminator } - omp.wsloop ordered(1) - for (%arg7) : i32 = (%arg0) to (%arg1) step (%arg2) { - // CHECK: [[TMP:%.*]] = getelementptr inbounds [1 x i64], ptr [[ADDR]], i64 0, i64 0 - // CHECK: store i64 [[ARG0:%.*]], ptr [[TMP]], align 8 - // CHECK: [[TMP2:%.*]] = getelementptr inbounds [1 x i64], ptr [[ADDR]], i64 0, i64 0 - // CHECK: [[OMP_THREAD2:%.*]] = call i32 @__kmpc_global_thread_num(ptr @[[GLOB3:[0-9]+]]) - // CHECK: call void @__kmpc_doacross_wait(ptr @[[GLOB3]], i32 [[OMP_THREAD2]], ptr [[TMP2]]) - omp.ordered depend_type(dependsink) depend_vec(%arg3 : i64) {num_loops_val = 1 : i64} + omp.wsloop ordered(1) { + omp.loop_nest (%arg7) : i32 = (%arg0) to (%arg1) step (%arg2) { + // CHECK: [[TMP:%.*]] = getelementptr inbounds [1 x i64], ptr [[ADDR]], i64 0, i64 0 + // CHECK: store i64 [[ARG0:%.*]], ptr [[TMP]], align 8 + // CHECK: [[TMP2:%.*]] = getelementptr inbounds [1 x i64], ptr [[ADDR]], i64 0, i64 0 + // CHECK: [[OMP_THREAD2:%.*]] = call i32 @__kmpc_global_thread_num(ptr @[[GLOB3:[0-9]+]]) + // CHECK: call void @__kmpc_doacross_wait(ptr @[[GLOB3]], i32 [[OMP_THREAD2]], ptr [[TMP2]]) + omp.ordered depend_type(dependsink) depend_vec(%arg3 : i64) {num_loops_val = 1 : i64} - // CHECK: [[TMP3:%.*]] = getelementptr inbounds [1 x i64], ptr [[ADDR3]], i64 0, i64 0 - // CHECK: store i64 [[ARG0]], ptr [[TMP3]], align 8 - // CHECK: [[TMP4:%.*]] = getelementptr inbounds [1 x i64], ptr [[ADDR3]], i64 0, i64 0 - // CHECK: [[OMP_THREAD4:%.*]] = call i32 @__kmpc_global_thread_num(ptr @[[GLOB5:[0-9]+]]) - // CHECK: call void @__kmpc_doacross_post(ptr @[[GLOB5]], i32 [[OMP_THREAD4]], ptr [[TMP4]]) - omp.ordered depend_type(dependsource) depend_vec(%arg3 : i64) {num_loops_val = 1 : i64} + // CHECK: [[TMP3:%.*]] = getelementptr inbounds [1 x i64], ptr [[ADDR3]], i64 0, i64 0 + // CHECK: store i64 [[ARG0]], ptr [[TMP3]], align 8 + // CHECK: [[TMP4:%.*]] = getelementptr inbounds [1 x i64], ptr [[ADDR3]], i64 0, i64 0 + // CHECK: [[OMP_THREAD4:%.*]] = call i32 @__kmpc_global_thread_num(ptr @[[GLOB5:[0-9]+]]) + // CHECK: call void @__kmpc_doacross_post(ptr @[[GLOB5]], i32 [[OMP_THREAD4]], ptr [[TMP4]]) + omp.ordered depend_type(dependsource) depend_vec(%arg3 : i64) {num_loops_val = 1 : i64} - omp.yield + omp.yield + } + omp.terminator } - omp.wsloop ordered(2) - for (%arg7) : i32 = (%arg0) to (%arg1) step (%arg2) { - // CHECK: [[TMP5:%.*]] = getelementptr inbounds [2 x i64], ptr [[ADDR5]], i64 0, i64 0 - // CHECK: store i64 [[ARG0]], ptr [[TMP5]], align 8 - // CHECK: [[TMP6:%.*]] = getelementptr inbounds [2 x i64], ptr [[ADDR5]], i64 0, i64 1 - // CHECK: store i64 [[ARG1:%.*]], ptr [[TMP6]], align 8 - // CHECK: [[TMP7:%.*]] = getelementptr inbounds [2 x i64], ptr [[ADDR5]], i64 0, i64 0 - // CHECK: [[OMP_THREAD6:%.*]] = call i32 @__kmpc_global_thread_num(ptr @[[GLOB7:[0-9]+]]) - // CHECK: call void @__kmpc_doacross_wait(ptr @[[GLOB7]], i32 [[OMP_THREAD6]], ptr [[TMP7]]) - // CHECK: [[TMP8:%.*]] = getelementptr inbounds [2 x i64], ptr [[ADDR7]], i64 0, i64 0 - // CHECK: store i64 [[ARG2:%.*]], ptr [[TMP8]], align 8 - // CHECK: [[TMP9:%.*]] = getelementptr inbounds [2 x i64], ptr [[ADDR7]], i64 0, i64 1 - // CHECK: store i64 [[ARG3:%.*]], ptr [[TMP9]], align 8 - // CHECK: [[TMP10:%.*]] = getelementptr inbounds [2 x i64], ptr [[ADDR7]], i64 0, i64 0 - // CHECK: [[OMP_THREAD8:%.*]] = call i32 @__kmpc_global_thread_num(ptr @[[GLOB7]]) - // CHECK: call void @__kmpc_doacross_wait(ptr @[[GLOB7]], i32 [[OMP_THREAD8]], ptr [[TMP10]]) - omp.ordered depend_type(dependsink) depend_vec(%arg3, %arg4, %arg5, %arg6 : i64, i64, i64, i64) {num_loops_val = 2 : i64} + omp.wsloop ordered(2) { + omp.loop_nest (%arg7) : i32 = (%arg0) to (%arg1) step (%arg2) { + // CHECK: [[TMP5:%.*]] = getelementptr inbounds [2 x i64], ptr [[ADDR5]], i64 0, i64 0 + // CHECK: store i64 [[ARG0]], ptr [[TMP5]], align 8 + // CHECK: [[TMP6:%.*]] = getelementptr inbounds [2 x i64], ptr [[ADDR5]], i64 0, i64 1 + // CHECK: store i64 [[ARG1:%.*]], ptr [[TMP6]], align 8 + // CHECK: [[TMP7:%.*]] = getelementptr inbounds [2 x i64], ptr [[ADDR5]], i64 0, i64 0 + // CHECK: [[OMP_THREAD6:%.*]] = call i32 @__kmpc_global_thread_num(ptr @[[GLOB7:[0-9]+]]) + // CHECK: call void @__kmpc_doacross_wait(ptr @[[GLOB7]], i32 [[OMP_THREAD6]], ptr [[TMP7]]) + // CHECK: [[TMP8:%.*]] = getelementptr inbounds [2 x i64], ptr [[ADDR7]], i64 0, i64 0 + // CHECK: store i64 [[ARG2:%.*]], ptr [[TMP8]], align 8 + // CHECK: [[TMP9:%.*]] = getelementptr inbounds [2 x i64], ptr [[ADDR7]], i64 0, i64 1 + // CHECK: store i64 [[ARG3:%.*]], ptr [[TMP9]], align 8 + // CHECK: [[TMP10:%.*]] = getelementptr inbounds [2 x i64], ptr [[ADDR7]], i64 0, i64 0 + // CHECK: [[OMP_THREAD8:%.*]] = call i32 @__kmpc_global_thread_num(ptr @[[GLOB7]]) + // CHECK: call void @__kmpc_doacross_wait(ptr @[[GLOB7]], i32 [[OMP_THREAD8]], ptr [[TMP10]]) + omp.ordered depend_type(dependsink) depend_vec(%arg3, %arg4, %arg5, %arg6 : i64, i64, i64, i64) {num_loops_val = 2 : i64} + + // CHECK: [[TMP11:%.*]] = getelementptr inbounds [2 x i64], ptr [[ADDR9]], i64 0, i64 0 + // CHECK: store i64 [[ARG0]], ptr [[TMP11]], align 8 + // CHECK: [[TMP12:%.*]] = getelementptr inbounds [2 x i64], ptr [[ADDR9]], i64 0, i64 1 + // CHECK: store i64 [[ARG1]], ptr [[TMP12]], align 8 + // CHECK: [[TMP13:%.*]] = getelementptr inbounds [2 x i64], ptr [[ADDR9]], i64 0, i64 0 + // CHECK: [[OMP_THREAD10:%.*]] = call i32 @__kmpc_global_thread_num(ptr @[[GLOB9:[0-9]+]]) + // CHECK: call void @__kmpc_doacross_post(ptr @[[GLOB9]], i32 [[OMP_THREAD10]], ptr [[TMP13]]) + omp.ordered depend_type(dependsource) depend_vec(%arg3, %arg4 : i64, i64) {num_loops_val = 2 : i64} - // CHECK: [[TMP11:%.*]] = getelementptr inbounds [2 x i64], ptr [[ADDR9]], i64 0, i64 0 - // CHECK: store i64 [[ARG0]], ptr [[TMP11]], align 8 - // CHECK: [[TMP12:%.*]] = getelementptr inbounds [2 x i64], ptr [[ADDR9]], i64 0, i64 1 - // CHECK: store i64 [[ARG1]], ptr [[TMP12]], align 8 - // CHECK: [[TMP13:%.*]] = getelementptr inbounds [2 x i64], ptr [[ADDR9]], i64 0, i64 0 - // CHECK: [[OMP_THREAD10:%.*]] = call i32 @__kmpc_global_thread_num(ptr @[[GLOB9:[0-9]+]]) - // CHECK: call void @__kmpc_doacross_post(ptr @[[GLOB9]], i32 [[OMP_THREAD10]], ptr [[TMP13]]) - omp.ordered depend_type(dependsource) depend_vec(%arg3, %arg4 : i64, i64) {num_loops_val = 2 : i64} - - omp.yield + omp.yield + } + omp.terminator } llvm.return @@ -2133,10 +2197,13 @@ llvm.func @omp_sections_with_clauses() -> () { // introduction mechanism itself is tested elsewhere. // CHECK-LABEL: @repeated_successor llvm.func @repeated_successor(%arg0: i64, %arg1: i64, %arg2: i64, %arg3: i1) { - omp.wsloop for (%arg4) : i64 = (%arg0) to (%arg1) step (%arg2) { - llvm.cond_br %arg3, ^bb1(%arg0 : i64), ^bb1(%arg1 : i64) - ^bb1(%0: i64): // 2 preds: ^bb0, ^bb0 - omp.yield + omp.wsloop { + omp.loop_nest (%arg4) : i64 = (%arg0) to (%arg1) step (%arg2) { + llvm.cond_br %arg3, ^bb1(%arg0 : i64), ^bb1(%arg1 : i64) + ^bb1(%0: i64): // 2 preds: ^bb0, ^bb0 + omp.yield + } + omp.terminator } llvm.return } diff --git a/mlir/test/Target/LLVMIR/openmp-nested.mlir b/mlir/test/Target/LLVMIR/openmp-nested.mlir index e1fdfdd24a3cb06a9fbc2656ad59ac16a595114c..ce5f22f10d7dce1534652bd74cb8e0f83802b30d 100644 --- a/mlir/test/Target/LLVMIR/openmp-nested.mlir +++ b/mlir/test/Target/LLVMIR/openmp-nested.mlir @@ -11,20 +11,26 @@ module { %2 = llvm.mlir.constant(0 : index) : i64 %4 = llvm.mlir.constant(0 : i32) : i32 %12 = llvm.alloca %0 x i64 : (i64) -> !llvm.ptr - omp.wsloop for (%arg2) : i64 = (%2) to (%1) step (%0) { - omp.parallel { - omp.wsloop for (%arg3) : i64 = (%2) to (%0) step (%0) { - llvm.store %2, %12 : i64, !llvm.ptr - omp.yield + omp.wsloop { + omp.loop_nest (%arg2) : i64 = (%2) to (%1) step (%0) { + omp.parallel { + omp.wsloop { + omp.loop_nest (%arg3) : i64 = (%2) to (%0) step (%0) { + llvm.store %2, %12 : i64, !llvm.ptr + omp.yield + } + omp.terminator + } + omp.terminator } - omp.terminator + %19 = llvm.load %12 : !llvm.ptr -> i64 + %20 = llvm.trunc %19 : i64 to i32 + %5 = llvm.mlir.addressof @str0 : !llvm.ptr + %6 = llvm.getelementptr %5[%4, %4] : (!llvm.ptr, i32, i32) -> !llvm.ptr, !llvm.array<29 x i8> + %21 = llvm.call @printf(%6, %20, %20) vararg(!llvm.func): (!llvm.ptr, i32, i32) -> i32 + omp.yield } - %19 = llvm.load %12 : !llvm.ptr -> i64 - %20 = llvm.trunc %19 : i64 to i32 - %5 = llvm.mlir.addressof @str0 : !llvm.ptr - %6 = llvm.getelementptr %5[%4, %4] : (!llvm.ptr, i32, i32) -> !llvm.ptr, !llvm.array<29 x i8> - %21 = llvm.call @printf(%6, %20, %20) vararg(!llvm.func): (!llvm.ptr, i32, i32) -> i32 - omp.yield + omp.terminator } omp.terminator } diff --git a/mlir/test/Target/LLVMIR/openmp-reduction.mlir b/mlir/test/Target/LLVMIR/openmp-reduction.mlir index 39b64d71a2274b0510594e1596fde4d3d552a314..bfdad8c19335e11bf8b8c19f1e98c84b4dfa0b79 100644 --- a/mlir/test/Target/LLVMIR/openmp-reduction.mlir +++ b/mlir/test/Target/LLVMIR/openmp-reduction.mlir @@ -26,13 +26,15 @@ llvm.func @simple_reduction(%lb : i64, %ub : i64, %step : i64) { %c1 = llvm.mlir.constant(1 : i32) : i32 %0 = llvm.alloca %c1 x i32 : (i32) -> !llvm.ptr omp.parallel { - omp.wsloop reduction(@add_f32 %0 -> %prv : !llvm.ptr) - for (%iv) : i64 = (%lb) to (%ub) step (%step) { - %1 = llvm.mlir.constant(2.0 : f32) : f32 - %2 = llvm.load %prv : !llvm.ptr -> f32 - %3 = llvm.fadd %1, %2 : f32 - llvm.store %3, %prv : f32, !llvm.ptr - omp.yield + omp.wsloop reduction(@add_f32 %0 -> %prv : !llvm.ptr) { + omp.loop_nest (%iv) : i64 = (%lb) to (%ub) step (%step) { + %1 = llvm.mlir.constant(2.0 : f32) : f32 + %2 = llvm.load %prv : !llvm.ptr -> f32 + %3 = llvm.fadd %1, %2 : f32 + llvm.store %3, %prv : f32, !llvm.ptr + omp.yield + } + omp.terminator } omp.terminator } @@ -105,16 +107,18 @@ llvm.func @reuse_declaration(%lb : i64, %ub : i64, %step : i64) { %0 = llvm.alloca %c1 x i32 : (i32) -> !llvm.ptr %2 = llvm.alloca %c1 x i32 : (i32) -> !llvm.ptr omp.parallel { - omp.wsloop reduction(@add_f32 %0 -> %prv0 : !llvm.ptr, @add_f32 %2 -> %prv1 : !llvm.ptr) - for (%iv) : i64 = (%lb) to (%ub) step (%step) { - %1 = llvm.mlir.constant(2.0 : f32) : f32 - %3 = llvm.load %prv0 : !llvm.ptr -> f32 - %4 = llvm.fadd %3, %1 : f32 - llvm.store %4, %prv0 : f32, !llvm.ptr - %5 = llvm.load %prv1 : !llvm.ptr -> f32 - %6 = llvm.fadd %5, %1 : f32 - llvm.store %6, %prv1 : f32, !llvm.ptr - omp.yield + omp.wsloop reduction(@add_f32 %0 -> %prv0 : !llvm.ptr, @add_f32 %2 -> %prv1 : !llvm.ptr) { + omp.loop_nest (%iv) : i64 = (%lb) to (%ub) step (%step) { + %1 = llvm.mlir.constant(2.0 : f32) : f32 + %3 = llvm.load %prv0 : !llvm.ptr -> f32 + %4 = llvm.fadd %3, %1 : f32 + llvm.store %4, %prv0 : f32, !llvm.ptr + %5 = llvm.load %prv1 : !llvm.ptr -> f32 + %6 = llvm.fadd %5, %1 : f32 + llvm.store %6, %prv1 : f32, !llvm.ptr + omp.yield + } + omp.terminator } omp.terminator } @@ -195,13 +199,15 @@ llvm.func @missing_omp_reduction(%lb : i64, %ub : i64, %step : i64) { %0 = llvm.alloca %c1 x i32 : (i32) -> !llvm.ptr %2 = llvm.alloca %c1 x i32 : (i32) -> !llvm.ptr omp.parallel { - omp.wsloop reduction(@add_f32 %0 -> %prv0 : !llvm.ptr, @add_f32 %2 -> %prv1 : !llvm.ptr) - for (%iv) : i64 = (%lb) to (%ub) step (%step) { - %1 = llvm.mlir.constant(2.0 : f32) : f32 - %3 = llvm.load %prv0 : !llvm.ptr -> f32 - %4 = llvm.fadd %3, %1 : f32 - llvm.store %4, %prv0 : f32, !llvm.ptr - omp.yield + omp.wsloop reduction(@add_f32 %0 -> %prv0 : !llvm.ptr, @add_f32 %2 -> %prv1 : !llvm.ptr) { + omp.loop_nest (%iv) : i64 = (%lb) to (%ub) step (%step) { + %1 = llvm.mlir.constant(2.0 : f32) : f32 + %3 = llvm.load %prv0 : !llvm.ptr -> f32 + %4 = llvm.fadd %3, %1 : f32 + llvm.store %4, %prv0 : f32, !llvm.ptr + omp.yield + } + omp.terminator } omp.terminator } @@ -280,16 +286,18 @@ llvm.func @double_reference(%lb : i64, %ub : i64, %step : i64) { %c1 = llvm.mlir.constant(1 : i32) : i32 %0 = llvm.alloca %c1 x i32 : (i32) -> !llvm.ptr omp.parallel { - omp.wsloop reduction(@add_f32 %0 -> %prv : !llvm.ptr) - for (%iv) : i64 = (%lb) to (%ub) step (%step) { - %1 = llvm.mlir.constant(2.0 : f32) : f32 - %2 = llvm.load %prv : !llvm.ptr -> f32 - %3 = llvm.fadd %2, %1 : f32 - llvm.store %3, %prv : f32, !llvm.ptr - %4 = llvm.load %prv : !llvm.ptr -> f32 - %5 = llvm.fadd %4, %1 : f32 - llvm.store %5, %prv : f32, !llvm.ptr - omp.yield + omp.wsloop reduction(@add_f32 %0 -> %prv : !llvm.ptr) { + omp.loop_nest (%iv) : i64 = (%lb) to (%ub) step (%step) { + %1 = llvm.mlir.constant(2.0 : f32) : f32 + %2 = llvm.load %prv : !llvm.ptr -> f32 + %3 = llvm.fadd %2, %1 : f32 + llvm.store %3, %prv : f32, !llvm.ptr + %4 = llvm.load %prv : !llvm.ptr -> f32 + %5 = llvm.fadd %4, %1 : f32 + llvm.store %5, %prv : f32, !llvm.ptr + omp.yield + } + omp.terminator } omp.terminator } @@ -374,16 +382,18 @@ llvm.func @no_atomic(%lb : i64, %ub : i64, %step : i64) { %0 = llvm.alloca %c1 x i32 : (i32) -> !llvm.ptr %2 = llvm.alloca %c1 x i32 : (i32) -> !llvm.ptr omp.parallel { - omp.wsloop reduction(@add_f32 %0 -> %prv0 : !llvm.ptr, @mul_f32 %2 -> %prv1 : !llvm.ptr) - for (%iv) : i64 = (%lb) to (%ub) step (%step) { - %1 = llvm.mlir.constant(2.0 : f32) : f32 - %3 = llvm.load %prv0 : !llvm.ptr -> f32 - %4 = llvm.fadd %3, %1 : f32 - llvm.store %4, %prv0 : f32, !llvm.ptr - %5 = llvm.load %prv1 : !llvm.ptr -> f32 - %6 = llvm.fmul %5, %1 : f32 - llvm.store %6, %prv1 : f32, !llvm.ptr - omp.yield + omp.wsloop reduction(@add_f32 %0 -> %prv0 : !llvm.ptr, @mul_f32 %2 -> %prv1 : !llvm.ptr) { + omp.loop_nest (%iv) : i64 = (%lb) to (%ub) step (%step) { + %1 = llvm.mlir.constant(2.0 : f32) : f32 + %3 = llvm.load %prv0 : !llvm.ptr -> f32 + %4 = llvm.fadd %3, %1 : f32 + llvm.store %4, %prv0 : f32, !llvm.ptr + %5 = llvm.load %prv1 : !llvm.ptr -> f32 + %6 = llvm.fmul %5, %1 : f32 + llvm.store %6, %prv1 : f32, !llvm.ptr + omp.yield + } + omp.terminator } omp.terminator } @@ -531,12 +541,15 @@ llvm.func @parallel_nested_workshare_reduction(%ub : i64) { %step = llvm.mlir.constant(1 : i64) : i64 omp.parallel reduction(@add_i32 %0 -> %prv : !llvm.ptr) { - omp.wsloop for (%iv) : i64 = (%lb) to (%ub) step (%step) { - %ival = llvm.trunc %iv : i64 to i32 - %lprv = llvm.load %prv : !llvm.ptr -> i32 - %add = llvm.add %lprv, %ival : i32 - llvm.store %add, %prv : i32, !llvm.ptr - omp.yield + omp.wsloop { + omp.loop_nest (%iv) : i64 = (%lb) to (%ub) step (%step) { + %ival = llvm.trunc %iv : i64 to i32 + %lprv = llvm.load %prv : !llvm.ptr -> i32 + %add = llvm.add %lprv, %ival : i32 + llvm.store %add, %prv : i32, !llvm.ptr + omp.yield + } + omp.terminator } omp.terminator } diff --git a/mlir/test/Target/LLVMIR/openmp-wsloop-reduction-cleanup.mlir b/mlir/test/Target/LLVMIR/openmp-wsloop-reduction-cleanup.mlir index 3842522934e48e0d4f604c2897f69134f9a7241d..7a1a31830ce9bc2e0dbcd1ede4429e20e16dfa87 100644 --- a/mlir/test/Target/LLVMIR/openmp-wsloop-reduction-cleanup.mlir +++ b/mlir/test/Target/LLVMIR/openmp-wsloop-reduction-cleanup.mlir @@ -30,9 +30,12 @@ %loop_ub = llvm.mlir.constant(9 : i32) : i32 %loop_lb = llvm.mlir.constant(0 : i32) : i32 %loop_step = llvm.mlir.constant(1 : i32) : i32 - omp.wsloop byref reduction(@add_reduction_i_32 %1 -> %arg0 : !llvm.ptr, @add_reduction_i_32 %2 -> %arg1 : !llvm.ptr) for (%loop_cnt) : i32 = (%loop_lb) to (%loop_ub) inclusive step (%loop_step) { - llvm.store %0, %arg0 : i32, !llvm.ptr - llvm.store %0, %arg1 : i32, !llvm.ptr + omp.wsloop byref reduction(@add_reduction_i_32 %1 -> %arg0 : !llvm.ptr, @add_reduction_i_32 %2 -> %arg1 : !llvm.ptr) { + omp.loop_nest (%loop_cnt) : i32 = (%loop_lb) to (%loop_ub) inclusive step (%loop_step) { + llvm.store %0, %arg0 : i32, !llvm.ptr + llvm.store %0, %arg1 : i32, !llvm.ptr + omp.yield + } omp.terminator } llvm.return diff --git a/mlir/test/lib/Dialect/Test/CMakeLists.txt b/mlir/test/lib/Dialect/Test/CMakeLists.txt index f63e4d330e6ac1a4a0f1344cfee9ba977ea5c8f5..fab89378093326d64f71e08223f56cbfdcac4798 100644 --- a/mlir/test/lib/Dialect/Test/CMakeLists.txt +++ b/mlir/test/lib/Dialect/Test/CMakeLists.txt @@ -31,8 +31,6 @@ mlir_tablegen(TestOpEnums.cpp.inc -gen-enum-defs) add_public_tablegen_target(MLIRTestEnumDefIncGen) set(LLVM_TARGET_DEFINITIONS TestOps.td) -mlir_tablegen(TestOps.h.inc -gen-op-decls) -mlir_tablegen(TestOps.cpp.inc -gen-op-defs) mlir_tablegen(TestOpsDialect.h.inc -gen-dialect-decls -dialect=test) mlir_tablegen(TestOpsDialect.cpp.inc -gen-dialect-defs -dialect=test) mlir_tablegen(TestPatterns.inc -gen-rewriters) @@ -43,6 +41,8 @@ mlir_tablegen(TestOpsSyntax.h.inc -gen-op-decls) mlir_tablegen(TestOpsSyntax.cpp.inc -gen-op-defs) add_public_tablegen_target(MLIRTestOpsSyntaxIncGen) +add_sharded_ops(TestOps 20) + # Exclude tests from libMLIR.so add_mlir_library(MLIRTestDialect TestAttributes.cpp @@ -56,6 +56,7 @@ add_mlir_library(MLIRTestDialect TestTypes.cpp TestOpsSyntax.cpp TestDialectInterfaces.cpp + ${SHARDED_SRCS} EXCLUDE_FROM_LIBMLIR @@ -66,6 +67,7 @@ add_mlir_library(MLIRTestDialect MLIRTestTypeDefIncGen MLIRTestOpsIncGen MLIRTestOpsSyntaxIncGen + MLIRTestOpsShardGen LINK_LIBS PUBLIC MLIRControlFlowInterfaces diff --git a/mlir/test/lib/Dialect/Test/TestDialect.cpp b/mlir/test/lib/Dialect/Test/TestDialect.cpp index 77fd7e61bd3a068ae27b5d2107fd522da61c2198..bfb9592e6382880cfccaae6c28934e900fd7d63e 100644 --- a/mlir/test/lib/Dialect/Test/TestDialect.cpp +++ b/mlir/test/lib/Dialect/Test/TestDialect.cpp @@ -326,12 +326,9 @@ struct TestOpEffectInterfaceFallback void TestDialect::initialize() { registerAttributes(); registerTypes(); - addOperations< -#define GET_OP_LIST -#include "TestOps.cpp.inc" - >(); registerOpsSyntax(); addOperations(); + registerTestDialectOperations(this); registerDynamicOp(getDynamicGenericOp(this)); registerDynamicOp(getDynamicOneOperandTwoResultsOp(this)); registerDynamicOp(getDynamicCustomParserPrinterOp(this)); diff --git a/mlir/test/lib/Dialect/Test/TestOps.cpp b/mlir/test/lib/Dialect/Test/TestOps.cpp index ce7e476be74e65e0d5f0268b85abde8fd5866a50..47d5b1b19121efa92059b0939f51959e9f9d7005 100644 --- a/mlir/test/lib/Dialect/Test/TestOps.cpp +++ b/mlir/test/lib/Dialect/Test/TestOps.cpp @@ -14,5 +14,4 @@ using namespace mlir; using namespace test; -#define GET_OP_CLASSES #include "TestOps.cpp.inc" diff --git a/mlir/test/mlir-tblgen/shard-op-defs.td b/mlir/test/mlir-tblgen/shard-op-defs.td new file mode 100644 index 0000000000000000000000000000000000000000..84ac6b0fbe9ebeea1cb4fba221bb0f8666f3c372 --- /dev/null +++ b/mlir/test/mlir-tblgen/shard-op-defs.td @@ -0,0 +1,33 @@ +// RUN: mlir-tblgen -gen-op-defs -op-shard-count=2 -I %S/../../include %s | FileCheck %s --check-prefix=DEFS +// RUN: mlir-tblgen -gen-op-decls -op-shard-count=2 -I %S/../../include %s | FileCheck %s --check-prefix=DECLS + +include "mlir/IR/OpBase.td" + +def Test_Dialect : Dialect { + let name = "test"; + let cppNamespace = "test"; +} + +class Test_Op traits = []> + : Op; + +def OpA : Test_Op<"a">; +def OpB : Test_Op<"b">; +def OpC : Test_Op<"c">; + +// DECLS: OpA +// DECLS: OpB +// DECLS: OpC +// DECLS: registerTestDialectOperations( +// DECLS: registerTestDialectOperations0( +// DECLS: registerTestDialectOperations1( + +// DEFS-LABEL: GET_OP_DEFS_0 +// DEFS: void test::registerTestDialectOperations( +// DEFS: void test::registerTestDialectOperations0( +// DEFS: OpAAdaptor +// DEFS: OpBAdaptor + +// DEFS-LABEL: GET_OP_DEFS_1 +// DEFS: void test::registerTestDialectOperations1( +// DEFS: OpCAdaptor diff --git a/mlir/test/python/dialects/llvm.py b/mlir/test/python/dialects/llvm.py index fb4b343b170bae6de9813f3cce655efad882ce36..d9ffdeb65bfd40b412c7e226965522a4bdc74da5 100644 --- a/mlir/test/python/dialects/llvm.py +++ b/mlir/test/python/dialects/llvm.py @@ -107,3 +107,46 @@ def testSmoke(): ) result = llvm.UndefOp(mat64f32_t) # CHECK: %0 = llvm.mlir.undef : !llvm.struct<(f32, f32, f32, f32, f32, f32, f32, f32, f32, f32, f32, f32, f32, f32, f32, f32)> + + +# CHECK-LABEL: testPointerType +@constructAndPrintInModule +def testPointerType(): + ptr = llvm.PointerType.get() + # CHECK: !llvm.ptr + print(ptr) + + ptr_with_addr = llvm.PointerType.get(1) + # CHECK: !llvm.ptr<1> + print(ptr_with_addr) + + +# CHECK-LABEL: testConstant +@constructAndPrintInModule +def testConstant(): + i32 = IntegerType.get_signless(32) + c_128 = llvm.mlir_constant(IntegerAttr.get(i32, 128)) + # CHECK: %{{.*}} = llvm.mlir.constant(128 : i32) : i32 + print(c_128.owner) + + +# CHECK-LABEL: testIntrinsics +@constructAndPrintInModule +def testIntrinsics(): + i32 = IntegerType.get_signless(32) + ptr = llvm.PointerType.get() + c_128 = llvm.mlir_constant(IntegerAttr.get(i32, 128)) + # CHECK: %[[CST128:.*]] = llvm.mlir.constant(128 : i32) : i32 + print(c_128.owner) + + alloca = llvm.alloca(ptr, c_128, i32) + # CHECK: %[[ALLOCA:.*]] = llvm.alloca %[[CST128]] x i32 : (i32) -> !llvm.ptr + print(alloca.owner) + + c_0 = llvm.mlir_constant(IntegerAttr.get(IntegerType.get_signless(8), 0)) + # CHECK: %[[CST0:.+]] = llvm.mlir.constant(0 : i8) : i8 + print(c_0.owner) + + result = llvm.intr_memset(alloca, c_0, c_128, False) + # CHECK: "llvm.intr.memset"(%[[ALLOCA]], %[[CST0]], %[[CST128]]) <{isVolatile = false}> : (!llvm.ptr, i8, i32) -> () + print(result) diff --git a/mlir/test/python/dialects/sparse_tensor/dialect.py b/mlir/test/python/dialects/sparse_tensor/dialect.py index 5666d090c3d5ee67b3af1a135efef604664e8f28..3cc4575eb3e240193d90e71184f2568de34ac42d 100644 --- a/mlir/test/python/dialects/sparse_tensor/dialect.py +++ b/mlir/test/python/dialects/sparse_tensor/dialect.py @@ -2,6 +2,7 @@ from mlir.ir import * from mlir.dialects import sparse_tensor as st +import textwrap def run(f): @@ -15,13 +16,18 @@ def run(f): def testEncodingAttr1D(): with Context() as ctx: parsed = Attribute.parse( - "#sparse_tensor.encoding<{" - " map = (d0) -> (d0 : compressed)," - " posWidth = 16," - " crdWidth = 32" - "}>" + textwrap.dedent( + """\ + #sparse_tensor.encoding<{ + map = (d0) -> (d0 : compressed), + posWidth = 16, + crdWidth = 32, + explicitVal = 1.0 : f64 + }>\ + """ + ) ) - # CHECK: #sparse_tensor.encoding<{ map = (d0) -> (d0 : compressed), posWidth = 16, crdWidth = 32 }> + # CHECK: #sparse_tensor.encoding<{ map = (d0) -> (d0 : compressed), posWidth = 16, crdWidth = 32, explicitVal = 1.000000e+00 : f64 }> print(parsed) casted = st.EncodingAttr(parsed) @@ -38,9 +44,16 @@ def testEncodingAttr1D(): print(f"pos_width: {casted.pos_width}") # CHECK: crd_width: 32 print(f"crd_width: {casted.crd_width}") + # CHECK: explicit_val: 1.000000e+00 + print(f"explicit_val: {casted.explicit_val}") + # CHECK: implicit_val: None + print(f"implicit_val: {casted.implicit_val}") - created = st.EncodingAttr.get(casted.lvl_types, None, None, 0, 0) - # CHECK: #sparse_tensor.encoding<{ map = (d0) -> (d0 : compressed) }> + new_explicit_val = FloatAttr.get_f64(1.0) + created = st.EncodingAttr.get( + casted.lvl_types, None, None, 0, 0, new_explicit_val + ) + # CHECK: #sparse_tensor.encoding<{ map = (d0) -> (d0 : compressed), explicitVal = 1.000000e+00 : f64 }> print(created) # CHECK: created_equal: False print(f"created_equal: {created == casted}") @@ -57,12 +70,16 @@ def testEncodingAttr1D(): def testEncodingAttrStructure(): with Context() as ctx: parsed = Attribute.parse( - "#sparse_tensor.encoding<{" - " map = (d0, d1) -> (d0 : dense, d1 floordiv 4 : dense," - " d1 mod 4 : structured[2, 4])," - " posWidth = 16," - " crdWidth = 32" - "}>" + textwrap.dedent( + """\ + #sparse_tensor.encoding<{ + map = (d0, d1) -> (d0 : dense, d1 floordiv 4 : dense, + d1 mod 4 : structured[2, 4]), + posWidth = 16, + crdWidth = 32, + }>\ + """ + ) ) # CHECK: #sparse_tensor.encoding<{ map = (d0, d1) -> (d0 : dense, d1 floordiv 4 : dense, d1 mod 4 : structured[2, 4]), posWidth = 16, crdWidth = 32 }> print(parsed) @@ -144,11 +161,15 @@ def testEncodingAttrStructure(): def testEncodingAttr2D(): with Context() as ctx: parsed = Attribute.parse( - "#sparse_tensor.encoding<{" - " map = (d0, d1) -> (d1 : dense, d0 : compressed)," - " posWidth = 8," - " crdWidth = 32" - "}>" + textwrap.dedent( + """\ + #sparse_tensor.encoding<{ + map = (d0, d1) -> (d1 : dense, d0 : compressed), + posWidth = 8, + crdWidth = 32, + }>\ + """ + ) ) # CHECK: #sparse_tensor.encoding<{ map = (d0, d1) -> (d1 : dense, d0 : compressed), posWidth = 8, crdWidth = 32 }> print(parsed) @@ -187,11 +208,15 @@ def testEncodingAttrOnTensorType(): with Context() as ctx, Location.unknown(): encoding = st.EncodingAttr( Attribute.parse( - "#sparse_tensor.encoding<{" - " map = (d0) -> (d0 : compressed), " - " posWidth = 64," - " crdWidth = 32" - "}>" + textwrap.dedent( + """\ + #sparse_tensor.encoding<{ + map = (d0) -> (d0 : compressed), + posWidth = 64, + crdWidth = 32, + }>\ + """ + ) ) ) tt = RankedTensorType.get((1024,), F32Type.get(), encoding=encoding) diff --git a/mlir/test/python/dialects/transform_interpreter.py b/mlir/test/python/dialects/transform_interpreter.py index 807a98c49327970453de16b7f23f3c97ff279418..819a3be1db9d5a3a67954b9c706d702235454f31 100644 --- a/mlir/test/python/dialects/transform_interpreter.py +++ b/mlir/test/python/dialects/transform_interpreter.py @@ -45,6 +45,21 @@ def print_other(): # CHECK: this.is.payload +@test_in_context +def transform_options(): + options = interp.TransformOptions() + options.expensive_checks = False + options.enforce_single_top_level_transform_op = True + m = ir.Module.parse( + print_root_module.replace("from interpreter", "transform_options") + ) + payload = ir.Module.parse("module attributes { this.is.payload } {}") + interp.apply_named_sequence(payload, m.body.operations[0], m, options) + + +# CHECK-LABEL: transform_options + + @test_in_context def failed(): payload = ir.Module.parse("module attributes { this.is.payload } {}") diff --git a/mlir/tools/mlir-src-sharder/CMakeLists.txt b/mlir/tools/mlir-src-sharder/CMakeLists.txt new file mode 100644 index 0000000000000000000000000000000000000000..4ef870b61124adf12496ece3a17ef88c90d56997 --- /dev/null +++ b/mlir/tools/mlir-src-sharder/CMakeLists.txt @@ -0,0 +1,14 @@ +set(LLVM_LINK_COMPONENTS Support) +set(LIBS MLIRSupport) + +add_tablegen(mlir-src-sharder MLIR_SRC_SHARDER + mlir-src-sharder.cpp + + DEPENDS + ${LIBS} + ) + +set_target_properties(mlir-src-sharder PROPERTIES FOLDER "Tablegenning") +target_link_libraries(mlir-src-sharder PRIVATE ${LIBS}) + +mlir_check_all_link_libraries(mlir-src-sharder) diff --git a/mlir/tools/mlir-src-sharder/mlir-src-sharder.cpp b/mlir/tools/mlir-src-sharder/mlir-src-sharder.cpp new file mode 100644 index 0000000000000000000000000000000000000000..dc1e2939c7d25b267af2a3108c299c1d2554a301 --- /dev/null +++ b/mlir/tools/mlir-src-sharder/mlir-src-sharder.cpp @@ -0,0 +1,114 @@ +//===- mlir-src-sharder.cpp - A tool for sharder generated source files ---===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#include "mlir/Support/FileUtilities.h" +#include "mlir/Support/LogicalResult.h" +#include "llvm/Support/CommandLine.h" +#include "llvm/Support/InitLLVM.h" +#include "llvm/Support/MemoryBuffer.h" +#include "llvm/Support/ToolOutputFile.h" + +using namespace mlir; + +/// Create a dependency file for `-d` option. +/// +/// This functionality is generally only for the benefit of the build system, +/// and is modeled after the same option in TableGen. +static LogicalResult createDependencyFile(StringRef outputFilename, + StringRef dependencyFile) { + if (outputFilename == "-") { + llvm::errs() << "error: the option -d must be used together with -o\n"; + return failure(); + } + + std::string errorMessage; + std::unique_ptr outputFile = + openOutputFile(dependencyFile, &errorMessage); + if (!outputFile) { + llvm::errs() << errorMessage << "\n"; + return failure(); + } + + outputFile->os() << outputFilename << ":\n"; + outputFile->keep(); + return success(); +} + +int main(int argc, char **argv) { + // FIXME: This is necessary because we link in TableGen, which defines its + // options as static variables.. some of which overlap with our options. + llvm::cl::ResetCommandLineParser(); + + llvm::cl::opt opShardIndex( + "op-shard-index", llvm::cl::desc("The current shard index")); + llvm::cl::opt inputFilename(llvm::cl::Positional, + llvm::cl::desc(""), + llvm::cl::init("-")); + llvm::cl::opt outputFilename( + "o", llvm::cl::desc("Output filename"), llvm::cl::value_desc("filename"), + llvm::cl::init("-")); + llvm::cl::list includeDirs( + "I", llvm::cl::desc("Directory of include files"), + llvm::cl::value_desc("directory"), llvm::cl::Prefix); + llvm::cl::opt dependencyFilename( + "d", llvm::cl::desc("Dependency filename"), + llvm::cl::value_desc("filename"), llvm::cl::init("")); + llvm::cl::opt writeIfChanged( + "write-if-changed", + llvm::cl::desc("Only write to the output file if it changed")); + + llvm::InitLLVM y(argc, argv); + llvm::cl::ParseCommandLineOptions(argc, argv); + + // Open the input file. + std::string errorMessage; + std::unique_ptr inputFile = + openInputFile(inputFilename, &errorMessage); + if (!inputFile) { + llvm::errs() << errorMessage << "\n"; + return 1; + } + + // Write the output to a buffer. + std::string outputStr; + llvm::raw_string_ostream os(outputStr); + os << "#define GET_OP_DEFS_" << opShardIndex << "\n" + << inputFile->getBuffer(); + + // Determine whether we need to write the output file. + bool shouldWriteOutput = true; + if (writeIfChanged) { + // Only update the real output file if there are any differences. This + // prevents recompilation of all the files depending on it if there aren't + // any. + if (auto existingOrErr = + llvm::MemoryBuffer::getFile(outputFilename, /*IsText=*/true)) + if (std::move(existingOrErr.get())->getBuffer() == os.str()) + shouldWriteOutput = false; + } + + // Populate the output file if necessary. + if (shouldWriteOutput) { + std::unique_ptr outputFile = + openOutputFile(outputFilename, &errorMessage); + if (!outputFile) { + llvm::errs() << errorMessage << "\n"; + return 1; + } + outputFile->os() << os.str(); + outputFile->keep(); + } + + // Always write the depfile, even if the main output hasn't changed. If it's + // missing, Ninja considers the output dirty. + if (!dependencyFilename.empty()) + if (failed(createDependencyFile(outputFilename, dependencyFilename))) + return 1; + + return 0; +} diff --git a/mlir/tools/mlir-tblgen/OpDefinitionsGen.cpp b/mlir/tools/mlir-tblgen/OpDefinitionsGen.cpp index 53ed5cb7c043ecad04c2d52aa4a55cbeafb9e0df..63fe5a8099074650faf02bb897a6bfcd752f67aa 100644 --- a/mlir/tools/mlir-tblgen/OpDefinitionsGen.cpp +++ b/mlir/tools/mlir-tblgen/OpDefinitionsGen.cpp @@ -4303,32 +4303,15 @@ void OpOperandAdaptorEmitter::emitDef( emitter.adaptor.writeDefTo(os); } -// Emits the opcode enum and op classes. -static void emitOpClasses(const RecordKeeper &recordKeeper, - const std::vector &defs, raw_ostream &os, - bool emitDecl) { - // First emit forward declaration for each class, this allows them to refer - // to each others in traits for example. - if (emitDecl) { - os << "#if defined(GET_OP_CLASSES) || defined(GET_OP_FWD_DEFINES)\n"; - os << "#undef GET_OP_FWD_DEFINES\n"; - for (auto *def : defs) { - Operator op(*def); - NamespaceEmitter emitter(os, op.getCppNamespace()); - os << "class " << op.getCppClassName() << ";\n"; - } - os << "#endif\n\n"; - } - - IfDefScope scope("GET_OP_CLASSES", os); +/// Emit the class declarations or definitions for the given op defs. +static void +emitOpClasses(const RecordKeeper &recordKeeper, + const std::vector &defs, raw_ostream &os, + const StaticVerifierFunctionEmitter &staticVerifierEmitter, + bool emitDecl) { if (defs.empty()) return; - // Generate all of the locally instantiated methods first. - StaticVerifierFunctionEmitter staticVerifierEmitter(os, recordKeeper); - os << formatv(opCommentHeader, "Local Utility Method", "Definitions"); - staticVerifierEmitter.emitOpConstraints(defs, emitDecl); - for (auto *def : defs) { Operator op(*def); if (emitDecl) { @@ -4358,34 +4341,145 @@ static void emitOpClasses(const RecordKeeper &recordKeeper, } } -// Emits a comma-separated list of the ops. -static void emitOpList(const std::vector &defs, raw_ostream &os) { - IfDefScope scope("GET_OP_LIST", os); +/// Emit the declarations for the provided op classes. +static void emitOpClassDecls(const RecordKeeper &recordKeeper, + const std::vector &defs, + raw_ostream &os) { + // First emit forward declaration for each class, this allows them to refer + // to each others in traits for example. + for (auto *def : defs) { + Operator op(*def); + NamespaceEmitter emitter(os, op.getCppNamespace()); + os << "class " << op.getCppClassName() << ";\n"; + } + + // Emit the op class declarations. + IfDefScope scope("GET_OP_CLASSES", os); + if (defs.empty()) + return; + StaticVerifierFunctionEmitter staticVerifierEmitter(os, recordKeeper); + staticVerifierEmitter.collectOpConstraints(defs); + emitOpClasses(recordKeeper, defs, os, staticVerifierEmitter, + /*emitDecl=*/true); +} + +/// Emit the definitions for the provided op classes. +static void emitOpClassDefs(const RecordKeeper &recordKeeper, + ArrayRef defs, raw_ostream &os, + StringRef constraintPrefix = "") { + if (defs.empty()) + return; + + // Generate all of the locally instantiated methods first. + StaticVerifierFunctionEmitter staticVerifierEmitter(os, recordKeeper, + constraintPrefix); + os << formatv(opCommentHeader, "Local Utility Method", "Definitions"); + staticVerifierEmitter.collectOpConstraints(defs); + staticVerifierEmitter.emitOpConstraints(defs); - interleave( - // TODO: We are constructing the Operator wrapper instance just for - // getting it's qualified class name here. Reduce the overhead by having a - // lightweight version of Operator class just for that purpose. - defs, [&os](Record *def) { os << Operator(def).getQualCppClassName(); }, - [&os]() { os << ",\n"; }); + // Emit the classes. + emitOpClasses(recordKeeper, defs, os, staticVerifierEmitter, + /*emitDecl=*/false); } +/// Emit op declarations for all op records. static bool emitOpDecls(const RecordKeeper &recordKeeper, raw_ostream &os) { emitSourceFileHeader("Op Declarations", os, recordKeeper); std::vector defs = getRequestedOpDefinitions(recordKeeper); - emitOpClasses(recordKeeper, defs, os, /*emitDecl=*/true); + emitOpClassDecls(recordKeeper, defs, os); + + // If we are generating sharded op definitions, emit the sharded op + // registration hooks. + SmallVector, 4> shardedDefs; + shardOpDefinitions(defs, shardedDefs); + if (defs.empty() || shardedDefs.size() <= 1) + return false; + + Dialect dialect = Operator(defs.front()).getDialect(); + NamespaceEmitter ns(os, dialect); + + const char *const opRegistrationHook = + "void register{0}Operations{1}({2}::{0} *dialect);\n"; + os << formatv(opRegistrationHook, dialect.getCppClassName(), "", + dialect.getCppNamespace()); + for (unsigned i = 0; i < shardedDefs.size(); ++i) { + os << formatv(opRegistrationHook, dialect.getCppClassName(), i, + dialect.getCppNamespace()); + } return false; } +/// Generate the dialect op registration hook and the op class definitions for a +/// shard of ops. +static void emitOpDefShard(const RecordKeeper &recordKeeper, + ArrayRef defs, const Dialect &dialect, + unsigned shardIndex, unsigned shardCount, + raw_ostream &os) { + std::string shardGuard = "GET_OP_DEFS_"; + std::string indexStr = std::to_string(shardIndex); + shardGuard += indexStr; + IfDefScope scope(shardGuard, os); + + // Emit the op registration hook in the first shard. + const char *const opRegistrationHook = + "void {0}::register{1}Operations{2}({0}::{1} *dialect) {{\n"; + if (shardIndex == 0) { + os << formatv(opRegistrationHook, dialect.getCppNamespace(), + dialect.getCppClassName(), ""); + for (unsigned i = 0; i < shardCount; ++i) { + os << formatv(" {0}::register{1}Operations{2}(dialect);\n", + dialect.getCppNamespace(), dialect.getCppClassName(), i); + } + os << "}\n"; + } + + // Generate the per-shard op registration hook. + os << formatv(opCommentHeader, dialect.getCppClassName(), + "Op Registration Hook") + << formatv(opRegistrationHook, dialect.getCppNamespace(), + dialect.getCppClassName(), shardIndex); + for (Record *def : defs) { + os << formatv(" ::mlir::RegisteredOperationName::insert<{0}>(*dialect);\n", + Operator(def).getQualCppClassName()); + } + os << "}\n"; + + // Generate the per-shard op definitions. + emitOpClassDefs(recordKeeper, defs, os, indexStr); +} + +/// Emit op definitions for all op records. static bool emitOpDefs(const RecordKeeper &recordKeeper, raw_ostream &os) { emitSourceFileHeader("Op Definitions", os, recordKeeper); std::vector defs = getRequestedOpDefinitions(recordKeeper); - emitOpList(defs, os); - emitOpClasses(recordKeeper, defs, os, /*emitDecl=*/false); + SmallVector, 4> shardedDefs; + shardOpDefinitions(defs, shardedDefs); + + // If no shard was requested, emit the regular op list and class definitions. + if (shardedDefs.size() == 1) { + { + IfDefScope scope("GET_OP_LIST", os); + interleave( + defs, os, + [&](Record *def) { os << Operator(def).getQualCppClassName(); }, + ",\n"); + } + { + IfDefScope scope("GET_OP_CLASSES", os); + emitOpClassDefs(recordKeeper, defs, os); + } + return false; + } + if (defs.empty()) + return false; + Dialect dialect = Operator(defs.front()).getDialect(); + for (auto [idx, value] : llvm::enumerate(shardedDefs)) { + emitOpDefShard(recordKeeper, value, dialect, idx, shardedDefs.size(), os); + } return false; } diff --git a/mlir/tools/mlir-tblgen/OpGenHelpers.cpp b/mlir/tools/mlir-tblgen/OpGenHelpers.cpp index 7fd34df8460d398075b42154a47a417f4c15bd90..c2a2423a2402699668f1b6be47dcb71ebdf2ed4d 100644 --- a/mlir/tools/mlir-tblgen/OpGenHelpers.cpp +++ b/mlir/tools/mlir-tblgen/OpGenHelpers.cpp @@ -31,6 +31,10 @@ static cl::opt opExcFilter( "op-exclude-regex", cl::desc("Regex of name of op's to exclude (no filter if empty)"), cl::cat(opDefGenCat)); +static cl::opt opShardCount( + "op-shard-count", + cl::desc("The number of shards into which the op classes will be divided"), + cl::cat(opDefGenCat), cl::init(1)); static std::string getOperationName(const Record &def) { auto prefix = def.getValueAsDef("opDialect")->getValueAsString("name"); @@ -79,4 +83,23 @@ bool mlir::tblgen::isPythonReserved(StringRef str) { reserved.insert("issubclass"); reserved.insert("type"); return reserved.contains(str); -} \ No newline at end of file +} + +void mlir::tblgen::shardOpDefinitions( + ArrayRef defs, + SmallVectorImpl> &shardedDefs) { + assert(opShardCount > 0 && "expected a positive shard count"); + if (opShardCount == 1) { + shardedDefs.push_back(defs); + return; + } + + unsigned minShardSize = defs.size() / opShardCount; + unsigned numMissing = defs.size() - minShardSize * opShardCount; + shardedDefs.reserve(opShardCount); + for (unsigned i = 0, start = 0; i < opShardCount; ++i) { + unsigned size = minShardSize + (i < numMissing); + shardedDefs.push_back(defs.slice(start, size)); + start += size; + } +} diff --git a/mlir/tools/mlir-tblgen/OpGenHelpers.h b/mlir/tools/mlir-tblgen/OpGenHelpers.h index 3dcff14d1221ee36c08eb2f44924bcffcc5a1d71..1b43d5d3ce3a7df326bd469e11bc662a631b3db9 100644 --- a/mlir/tools/mlir-tblgen/OpGenHelpers.h +++ b/mlir/tools/mlir-tblgen/OpGenHelpers.h @@ -13,6 +13,7 @@ #ifndef MLIR_TOOLS_MLIRTBLGEN_OPGENHELPERS_H_ #define MLIR_TOOLS_MLIRTBLGEN_OPGENHELPERS_H_ +#include "mlir/Support/LLVM.h" #include "llvm/TableGen/Record.h" #include @@ -28,6 +29,10 @@ getRequestedOpDefinitions(const llvm::RecordKeeper &recordKeeper); /// Regenerate using python -c"print(set(sorted(__import__('keyword').kwlist)))" bool isPythonReserved(llvm::StringRef str); +/// Shard the op defintions into the number of shards set by "op-shard-count". +void shardOpDefinitions(ArrayRef defs, + SmallVectorImpl> &shardedDefs); + } // namespace tblgen } // namespace mlir diff --git a/offload/test/unified_shared_memory/api.c b/offload/test/unified_shared_memory/api.c index c7ab055abb515205b0e050dacfdf17682f02d14b..b938971b4b03cf0f10aad346ea5ae8168d09fc9a 100644 --- a/offload/test/unified_shared_memory/api.c +++ b/offload/test/unified_shared_memory/api.c @@ -9,11 +9,6 @@ #include #include -// --------------------------------------------------------------------------- -// Various definitions copied from OpenMP RTL - -extern void __tgt_register_requires(int64_t); - // End of definitions copied from OpenMP RTL. // --------------------------------------------------------------------------- @@ -32,10 +27,6 @@ void init(int A[], int B[], int C[]) { int main(int argc, char *argv[]) { const int device = omp_get_default_device(); - // Manual registration of requires flags for Clang versions - // that do not support requires. - __tgt_register_requires(8); - // CHECK: Initial device: [[INITIAL_DEVICE:[0-9]+]] printf("Initial device: %d\n", omp_get_initial_device()); // CHECK: Num devices: [[INITIAL_DEVICE]] diff --git a/offload/test/unified_shared_memory/close_manual.c b/offload/test/unified_shared_memory/close_manual.c index 9985e822c05d7a1034cb6ceab4614b4349091523..c588cb1c403a7c9c7d08e52cca8a329eb9344701 100644 --- a/offload/test/unified_shared_memory/close_manual.c +++ b/offload/test/unified_shared_memory/close_manual.c @@ -8,8 +8,6 @@ // --------------------------------------------------------------------------- // Various definitions copied from OpenMP RTL -extern void __tgt_register_requires(int64_t); - extern void __tgt_target_data_begin(int64_t device_id, int32_t arg_num, void **args_base, void **args, int64_t *arg_sizes, int64_t *arg_types); @@ -30,10 +28,6 @@ int main(int argc, char *argv[]) { void *host_alloc = 0, *device_alloc = 0; int *a = (int *)malloc(N * sizeof(int)); - // Manual registration of requires flags for Clang versions - // that do not support requires. - __tgt_register_requires(8); - // Init for (int i = 0; i < N; ++i) { a[i] = 10; diff --git a/offload/test/unified_shared_memory/shared_update.c b/offload/test/unified_shared_memory/shared_update.c index 65db9e4f6bdce21dc47367bee605eab427c1cabd..f8eb11d56a6cad1114d2e2a7163171c554e43509 100644 --- a/offload/test/unified_shared_memory/shared_update.c +++ b/offload/test/unified_shared_memory/shared_update.c @@ -11,11 +11,6 @@ #include #include -// --------------------------------------------------------------------------- -// Various definitions copied from OpenMP RTL - -extern void __tgt_register_requires(int64_t); - // End of definitions copied from OpenMP RTL. // --------------------------------------------------------------------------- @@ -30,10 +25,6 @@ int main(int argc, char *argv[]) { int *alloc = (int *)malloc(N * sizeof(int)); int data[N]; - // Manual registration of requires flags for Clang versions - // that do not support requires. - __tgt_register_requires(8); - for (int i = 0; i < N; ++i) { alloc[i] = 10; data[i] = 1; diff --git a/utils/bazel/llvm-project-overlay/libc/BUILD.bazel b/utils/bazel/llvm-project-overlay/libc/BUILD.bazel index 3df8341712aa9317b029c0da910c02f6af0f35eb..aa9f665c350ae3b1fdbd32184e1c53bfe36f1bf3 100644 --- a/utils/bazel/llvm-project-overlay/libc/BUILD.bazel +++ b/utils/bazel/llvm-project-overlay/libc/BUILD.bazel @@ -23,17 +23,6 @@ package( licenses(["notice"]) -PRINTF_COPTS = [ - "LIBC_COPT_STDIO_USE_SYSTEM_FILE", - "LIBC_COPT_PRINTF_DISABLE_WRITE_INT", -] - -MEMORY_COPTS = [ - # "LIBC_COPT_MEMCPY_X86_USE_REPMOVSB_FROM_SIZE=0", - # "LIBC_COPT_MEMCPY_X86_USE_SOFTWARE_PREFETCHING", - # "LIBC_COPT_MEMSET_X86_USE_SOFTWARE_PREFETCHING", -] - # A flag to pick which `mpfr` to use for math tests. # Usage: `--@llvm-project//libc:mpfr=`. # Flag documentation: https://bazel.build/extending/config @@ -2421,7 +2410,6 @@ libc_support_library( "src/string/memory_utils/op_x86.h", "src/string/memory_utils/utils.h", ], - defines = MEMORY_COPTS, textual_hdrs = [ "src/string/memory_utils/aarch64/inline_bcmp.h", "src/string/memory_utils/aarch64/inline_memcmp.h", @@ -3191,7 +3179,6 @@ libc_function( libc_support_library( name = "printf_config", hdrs = ["src/stdio/printf_core/printf_config.h"], - defines = PRINTF_COPTS, deps = [ ], ) @@ -3199,7 +3186,6 @@ libc_support_library( libc_support_library( name = "printf_core_structs", hdrs = ["src/stdio/printf_core/core_structs.h"], - defines = PRINTF_COPTS, deps = [ ":__support_cpp_string_view", ":__support_fputil_fp_bits", @@ -3210,7 +3196,6 @@ libc_support_library( libc_support_library( name = "printf_parser", hdrs = ["src/stdio/printf_core/parser.h"], - defines = PRINTF_COPTS, deps = [ ":__support_arg_list", ":__support_common", @@ -3231,7 +3216,7 @@ libc_support_library( libc_support_library( name = "printf_mock_parser", hdrs = ["src/stdio/printf_core/parser.h"], - defines = PRINTF_COPTS + ["LIBC_COPT_MOCK_ARG_LIST"], + local_defines = ["LIBC_COPT_MOCK_ARG_LIST"], deps = [ ":__support_arg_list", ":__support_common", @@ -3251,7 +3236,6 @@ libc_support_library( name = "printf_writer", srcs = ["src/stdio/printf_core/writer.cpp"], hdrs = ["src/stdio/printf_core/writer.h"], - defines = PRINTF_COPTS, deps = [ ":__support_cpp_string_view", ":__support_macros_optimization", @@ -3276,7 +3260,6 @@ libc_support_library( "src/stdio/printf_core/string_converter.h", "src/stdio/printf_core/write_int_converter.h", ], - defines = PRINTF_COPTS, deps = [ ":__support_big_int", ":__support_common", @@ -3300,7 +3283,6 @@ libc_support_library( name = "printf_main", srcs = ["src/stdio/printf_core/printf_main.cpp"], hdrs = ["src/stdio/printf_core/printf_main.h"], - defines = PRINTF_COPTS, deps = [ ":__support_arg_list", ":printf_converter", @@ -3313,7 +3295,6 @@ libc_support_library( libc_support_library( name = "vfprintf_internal", hdrs = ["src/stdio/printf_core/vfprintf_internal.h"], - defines = PRINTF_COPTS, deps = [ ":__support_arg_list", ":__support_file_file", @@ -3327,7 +3308,6 @@ libc_function( name = "sprintf", srcs = ["src/stdio/sprintf.cpp"], hdrs = ["src/stdio/sprintf.h"], - defines = PRINTF_COPTS, deps = [ ":__support_arg_list", ":__support_cpp_limits", @@ -3341,7 +3321,6 @@ libc_function( name = "snprintf", srcs = ["src/stdio/snprintf.cpp"], hdrs = ["src/stdio/snprintf.h"], - defines = PRINTF_COPTS, deps = [ ":__support_arg_list", ":errno", @@ -3354,7 +3333,6 @@ libc_function( name = "printf", srcs = ["src/stdio/printf.cpp"], hdrs = ["src/stdio/printf.h"], - defines = PRINTF_COPTS, deps = [ ":__support_arg_list", ":__support_file_file", @@ -3367,7 +3345,6 @@ libc_function( name = "fprintf", srcs = ["src/stdio/fprintf.cpp"], hdrs = ["src/stdio/fprintf.h"], - defines = PRINTF_COPTS, deps = [ ":__support_arg_list", ":__support_file_file", @@ -3380,7 +3357,6 @@ libc_function( name = "vsprintf", srcs = ["src/stdio/vsprintf.cpp"], hdrs = ["src/stdio/vsprintf.h"], - defines = PRINTF_COPTS, deps = [ ":__support_arg_list", ":__support_cpp_limits", @@ -3394,7 +3370,6 @@ libc_function( name = "vsnprintf", srcs = ["src/stdio/vsnprintf.cpp"], hdrs = ["src/stdio/vsnprintf.h"], - defines = PRINTF_COPTS, deps = [ ":__support_arg_list", ":errno", @@ -3407,7 +3382,6 @@ libc_function( name = "vprintf", srcs = ["src/stdio/vprintf.cpp"], hdrs = ["src/stdio/vprintf.h"], - defines = PRINTF_COPTS, deps = [ ":__support_arg_list", ":__support_file_file", @@ -3420,7 +3394,6 @@ libc_function( name = "vfprintf", srcs = ["src/stdio/vfprintf.cpp"], hdrs = ["src/stdio/vfprintf.h"], - defines = PRINTF_COPTS, deps = [ ":__support_arg_list", ":__support_file_file", diff --git a/utils/bazel/llvm-project-overlay/libc/libc_build_rules.bzl b/utils/bazel/llvm-project-overlay/libc/libc_build_rules.bzl index be59e18ffd89a9627d43882cb6d69f111983e52c..ec3714407cb91494d0d118523bb493c1ebff3566 100644 --- a/utils/bazel/llvm-project-overlay/libc/libc_build_rules.bzl +++ b/utils/bazel/llvm-project-overlay/libc/libc_build_rules.bzl @@ -6,6 +6,7 @@ load("@bazel_skylib//lib:paths.bzl", "paths") load("@bazel_skylib//lib:selects.bzl", "selects") +load(":libc_configure_options.bzl", "LIBC_CONFIGURE_OPTIONS") load(":libc_namespace.bzl", "LIBC_NAMESPACE") load(":platforms.bzl", "PLATFORM_CPU_ARM64", "PLATFORM_CPU_X86_64") @@ -21,13 +22,14 @@ def libc_common_copts(): "-DLIBC_NAMESPACE=" + LIBC_NAMESPACE, ] -def _libc_library(name, hidden, copts = [], deps = [], **kwargs): +def _libc_library(name, hidden, copts = [], deps = [], local_defines = [], **kwargs): """Internal macro to serve as a base for all other libc library rules. Args: name: Target name. copts: The special compiler options for the target. deps: The list of target dependencies if any. + local_defines: The list of target local_defines if any. hidden: Whether the symbols should be explicitly hidden or not. **kwargs: All other attributes relevant for the cc_library rule. """ @@ -40,6 +42,7 @@ def _libc_library(name, hidden, copts = [], deps = [], **kwargs): native.cc_library( name = name, copts = copts + libc_common_copts(), + local_defines = local_defines + LIBC_CONFIGURE_OPTIONS, deps = deps, linkstatic = 1, **kwargs diff --git a/utils/bazel/llvm-project-overlay/libc/libc_configure_options.bzl b/utils/bazel/llvm-project-overlay/libc/libc_configure_options.bzl new file mode 100644 index 0000000000000000000000000000000000000000..f780c323d9a996981091ea79103da34bd21dec4c --- /dev/null +++ b/utils/bazel/llvm-project-overlay/libc/libc_configure_options.bzl @@ -0,0 +1,49 @@ +# This file is licensed under the Apache License v2.0 with LLVM Exceptions. +# See https://llvm.org/LICENSE.txt for license information. +# SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception + +"""LLVM libc configuration options. +The canonical list of user options is in 'libc/config/config.json'. +These options are then processed by CMake and turned into preprocessor +definitions. We don't have this logic in Bazel yet but the list of definitions +is discoverable with the following command: + +> git grep -hoE '\bLIBC_COPT_\\w*' -- '*.h' '*.cpp' | sort -u +""" + +# This list of definitions is used to customize LLVM libc. +LIBC_CONFIGURE_OPTIONS = [ + # Documentation in libc/docs/dev/printf_behavior.rst + # "LIBC_COPT_FLOAT_TO_STR_NO_SPECIALIZE_LD", + # "LIBC_COPT_FLOAT_TO_STR_NO_TABLE", + # "LIBC_COPT_FLOAT_TO_STR_USE_DYADIC_FLOAT", + # "LIBC_COPT_FLOAT_TO_STR_USE_DYADIC_FLOAT_LD", + # "LIBC_COPT_FLOAT_TO_STR_USE_INT_CALC", + # "LIBC_COPT_FLOAT_TO_STR_USE_MEGA_LONG_DOUBLE_TABLE", + + # Documentation in libc/src/string/memory_utils/... + # "LIBC_COPT_MEMCPY_USE_EMBEDDED_TINY", + # "LIBC_COPT_MEMCPY_X86_USE_REPMOVSB_FROM_SIZE", + # "LIBC_COPT_MEMCPY_X86_USE_SOFTWARE_PREFETCHING", + # "LIBC_COPT_MEMSET_X86_USE_SOFTWARE_PREFETCHING", + + # Documentation in libc/docs/dev/printf_behavior.rst + # "LIBC_COPT_PRINTF_CONV_ATLAS", + # "LIBC_COPT_PRINTF_DISABLE_FIXED_POINT", + # "LIBC_COPT_PRINTF_DISABLE_FLOAT", + # "LIBC_COPT_PRINTF_DISABLE_INDEX_MODE", + "LIBC_COPT_PRINTF_DISABLE_WRITE_INT", + # "LIBC_COPT_PRINTF_HEX_LONG_DOUBLE", + # "LIBC_COPT_PRINTF_INDEX_ARR_LEN", + # "LIBC_COPT_PRINTF_NO_NULLPTR_CHECKS", + # "LIBC_COPT_SCANF_DISABLE_FLOAT", + # "LIBC_COPT_SCANF_DISABLE_INDEX_MODE", + "LIBC_COPT_STDIO_USE_SYSTEM_FILE", + # "LIBC_COPT_STRING_UNSAFE_WIDE_READ", + # "LIBC_COPT_STRTOFLOAT_DISABLE_CLINGER_FAST_PATH", + # "LIBC_COPT_STRTOFLOAT_DISABLE_EISEL_LEMIRE", + # "LIBC_COPT_STRTOFLOAT_DISABLE_SIMPLE_DECIMAL_CONVERSION", + + # Documentation in libc/src/__support/libc_assert.h + # "LIBC_COPT_USE_C_ASSERT", +] diff --git a/utils/bazel/llvm-project-overlay/libc/test/UnitTest/BUILD.bazel b/utils/bazel/llvm-project-overlay/libc/test/UnitTest/BUILD.bazel index e55804b1ea79e559c0cad4eb24d5d4a99db5b211..6126a4a8fca83069738702b25a99f701fc2eb9be 100644 --- a/utils/bazel/llvm-project-overlay/libc/test/UnitTest/BUILD.bazel +++ b/utils/bazel/llvm-project-overlay/libc/test/UnitTest/BUILD.bazel @@ -65,10 +65,12 @@ libc_support_library( libc_support_library( name = "fp_test_helpers", srcs = [ + "FEnvSafeTest.cpp", "FPExceptMatcher.cpp", "RoundingModeUtils.cpp", ], hdrs = [ + "FEnvSafeTest.h", "FPExceptMatcher.h", "FPMatcher.h", "RoundingModeUtils.h", @@ -82,13 +84,15 @@ libc_support_library( "//libc:__support_cpp_bitset", "//libc:__support_cpp_span", "//libc:__support_cpp_type_traits", + "//libc:__support_cpp_utility", "//libc:__support_fputil_fenv_impl", "//libc:__support_fputil_fp_bits", "//libc:__support_fputil_fpbits_str", "//libc:__support_fputil_rounding_mode", + "//libc:__support_macros_properties_architectures", "//libc:hdr_math_macros", - "//libc:hdr_fenv_macros", - "//libc:types_fenv_t", + "//libc:hdr_fenv_macros", + "//libc:types_fenv_t", ], ) diff --git a/utils/bazel/llvm-project-overlay/libc/test/libc_test_rules.bzl b/utils/bazel/llvm-project-overlay/libc/test/libc_test_rules.bzl index 18056bacfd50cea1dd3f30ef9997ea22066e7543..ae24a41c60418b129ccfffe074efc744b91eae5a 100644 --- a/utils/bazel/llvm-project-overlay/libc/test/libc_test_rules.bzl +++ b/utils/bazel/llvm-project-overlay/libc/test/libc_test_rules.bzl @@ -13,8 +13,9 @@ When performing tests we make sure to always use the internal version. """ load("//libc:libc_build_rules.bzl", "libc_common_copts", "libc_internal_target") +load("//libc:libc_configure_options.bzl", "LIBC_CONFIGURE_OPTIONS") -def libc_test(name, srcs, libc_function_deps = [], copts = [], deps = [], **kwargs): +def libc_test(name, srcs, libc_function_deps = [], copts = [], deps = [], local_defines = [], **kwargs): """Add target for a libc test. Args: @@ -23,12 +24,14 @@ def libc_test(name, srcs, libc_function_deps = [], copts = [], deps = [], **kwar libc_function_deps: List of libc_function targets used by this test. copts: The list of options to add to the C++ compilation command. deps: The list of other libraries to be linked in to the test target. + local_defines: The list of target local_defines if any. **kwargs: Attributes relevant for a libc_test. For example, name, srcs. """ all_function_deps = libc_function_deps + ["//libc:errno"] native.cc_test( name = name, srcs = srcs, + local_defines = local_defines + LIBC_CONFIGURE_OPTIONS, deps = [libc_internal_target(d) for d in all_function_deps] + [ "//libc/test/UnitTest:LibcUnitTest", ] + deps, diff --git a/utils/bazel/llvm-project-overlay/libc/test/src/fenv/BUILD.bazel b/utils/bazel/llvm-project-overlay/libc/test/src/fenv/BUILD.bazel index fc3ab3da3587c57996ea5e6d7b706898e685a1bf..03c94d1db23aa74bf3e4563c4b8e15259d3f00c5 100644 --- a/utils/bazel/llvm-project-overlay/libc/test/src/fenv/BUILD.bazel +++ b/utils/bazel/llvm-project-overlay/libc/test/src/fenv/BUILD.bazel @@ -12,7 +12,10 @@ licenses(["notice"]) libc_test( name = "exception_status_test", - srcs = ["exception_status_test.cpp"], + srcs = [ + "exception_status_test.cpp", + "excepts.h", + ], libc_function_deps = [ "//libc:feclearexcept", "//libc:feraiseexcept", @@ -21,23 +24,33 @@ libc_test( ], deps = [ "//libc:__support_fputil_fenv_impl", - "//libc:hdr_fenv_macros", + "//libc:hdr_fenv_macros", + "//libc/test/UnitTest:fp_test_helpers", ], ) libc_test( name = "rounding_mode_test", - srcs = ["rounding_mode_test.cpp"], + srcs = [ + "excepts.h", + "rounding_mode_test.cpp", + ], libc_function_deps = [ "//libc:fegetround", "//libc:fesetround", ], - deps = ["//libc:hdr_fenv_macros"], + deps = [ + "//libc:hdr_fenv_macros", + "//libc/test/UnitTest:fp_test_helpers", + ], ) libc_test( name = "enabled_exceptions_test", - srcs = ["enabled_exceptions_test.cpp"], + srcs = [ + "enabled_exceptions_test.cpp", + "excepts.h", + ], libc_function_deps = [ "//libc:feclearexcept", "//libc:feraiseexcept", @@ -48,14 +61,17 @@ libc_test( "//libc:__support_common", "//libc:__support_fputil_fenv_impl", "//libc:__support_macros_properties_architectures", + "//libc:hdr_fenv_macros", "//libc/test/UnitTest:fp_test_helpers", - "//libc:hdr_fenv_macros", ], ) libc_test( name = "feholdexcept_test", - srcs = ["feholdexcept_test.cpp"], + srcs = [ + "excepts.h", + "feholdexcept_test.cpp", + ], libc_function_deps = [ "//libc:feholdexcept", ], @@ -64,14 +80,18 @@ libc_test( "//libc:__support_common", "//libc:__support_fputil_fenv_impl", "//libc:__support_macros_properties_architectures", + "//libc:hdr_fenv_macros", + "//libc:types_fenv_t", "//libc/test/UnitTest:fp_test_helpers", - "//libc:types_fenv_t", ], ) libc_test( name = "exception_flags_test", - srcs = ["exception_flags_test.cpp"], + srcs = [ + "exception_flags_test.cpp", + "excepts.h", + ], libc_function_deps = [ "//libc:fegetexceptflag", "//libc:fesetexceptflag", @@ -79,25 +99,34 @@ libc_test( ], deps = [ "//libc:__support_fputil_fenv_impl", - "//libc:types_fexcept_t", + "//libc:hdr_fenv_macros", + "//libc:types_fexcept_t", + "//libc/test/UnitTest:fp_test_helpers", ], ) libc_test( name = "feclearexcept_test", - srcs = ["feclearexcept_test.cpp"], + srcs = [ + "excepts.h", + "feclearexcept_test.cpp", + ], libc_function_deps = [ "//libc:feclearexcept", ], deps = [ "//libc:__support_fputil_fenv_impl", - "//libc:hdr_fenv_macros", + "//libc:hdr_fenv_macros", + "//libc/test/UnitTest:fp_test_helpers", ], ) libc_test( name = "feenableexcept_test", - srcs = ["feenableexcept_test.cpp"], + srcs = [ + "excepts.h", + "feenableexcept_test.cpp", + ], libc_function_deps = [ "//libc:fedisableexcept", "//libc:feenableexcept", @@ -106,25 +135,34 @@ libc_test( deps = [ "//libc:__support_common", "//libc:__support_macros_properties_architectures", - "//libc:hdr_fenv_macros", + "//libc:hdr_fenv_macros", + "//libc/test/UnitTest:fp_test_helpers", ], ) libc_test( name = "feupdateenv_test", - srcs = ["feupdateenv_test.cpp"], + srcs = [ + "excepts.h", + "feupdateenv_test.cpp", + ], libc_function_deps = [ "//libc:feupdateenv", ], deps = [ "//libc:__support_fputil_fenv_impl", - "//libc:types_fenv_t", + "//libc:hdr_fenv_macros", + "//libc:types_fenv_t", + "//libc/test/UnitTest:fp_test_helpers", ], ) libc_test( name = "getenv_and_setenv_test", - srcs = ["getenv_and_setenv_test.cpp"], + srcs = [ + "excepts.h", + "getenv_and_setenv_test.cpp", + ], libc_function_deps = [ "//libc:fegetenv", "//libc:fegetround", @@ -133,6 +171,8 @@ libc_test( ], deps = [ "//libc:__support_fputil_fenv_impl", - "//libc:types_fenv_t", + "//libc:hdr_fenv_macros", + "//libc:types_fenv_t", + "//libc/test/UnitTest:fp_test_helpers", ], ) diff --git a/utils/bazel/llvm-project-overlay/libc/test/src/math/BUILD.bazel b/utils/bazel/llvm-project-overlay/libc/test/src/math/BUILD.bazel index e30c8bf023cf2a4631ee70f656bf091fbfcaf999..4f72a0a8e1863a6a1638136ed4e70cbd71436438 100644 --- a/utils/bazel/llvm-project-overlay/libc/test/src/math/BUILD.bazel +++ b/utils/bazel/llvm-project-overlay/libc/test/src/math/BUILD.bazel @@ -298,6 +298,7 @@ libc_support_library( "//libc:__support_fputil_fp_bits", "//libc:__support_fputil_manipulation_functions", "//libc:hdr_math_macros", + "//libc/test/UnitTest:fp_test_helpers", "//libc/test/UnitTest:LibcUnitTest", ], ) diff --git a/utils/bazel/llvm-project-overlay/lldb/source/Plugins/BUILD.bazel b/utils/bazel/llvm-project-overlay/lldb/source/Plugins/BUILD.bazel index e0907a838148f5e26137525efea300135a9f0239..13fec77fe567bb5d3b170cb0928cb26627bad5aa 100644 --- a/utils/bazel/llvm-project-overlay/lldb/source/Plugins/BUILD.bazel +++ b/utils/bazel/llvm-project-overlay/lldb/source/Plugins/BUILD.bazel @@ -2092,6 +2092,10 @@ cc_library( srcs = glob(["Process/Linux/*.cpp"]), hdrs = glob(["Process/Linux/*.h"]), include_prefix = "Plugins", + target_compatible_with = select({ + "@platforms//os:linux": [], + "//conditions:default": ["@platforms//:incompatible"], + }), deps = [ ":PluginProcessPOSIX", ":PluginProcessUtility", diff --git a/utils/bazel/llvm-project-overlay/llvm/BUILD.bazel b/utils/bazel/llvm-project-overlay/llvm/BUILD.bazel index c9c0edb1dc3109020a75a6d1caee9a9b457db9aa..3223eb92d869ebdd1f78f9c7b5ceaa18645bc7dc 100644 --- a/utils/bazel/llvm-project-overlay/llvm/BUILD.bazel +++ b/utils/bazel/llvm-project-overlay/llvm/BUILD.bazel @@ -636,6 +636,7 @@ cc_binary( name = "llvm-min-tblgen", srcs = [ "utils/TableGen/Attributes.cpp", + "utils/TableGen/ARMTargetDefEmitter.cpp", "utils/TableGen/Basic/CodeGenIntrinsics.cpp", "utils/TableGen/Basic/CodeGenIntrinsics.h", "utils/TableGen/Basic/SDNodeProperties.cpp", @@ -1231,6 +1232,30 @@ cc_library( ], ) +gentbl( + name = "ARMTargetParserDefGen", + tbl_outs = [("-gen-arm-target-def", "include/llvm/TargetParser/ARMTargetParserDef.inc")], + tblgen = ":llvm-min-tblgen", + td_file = "lib/Target/ARM/ARM.td", + td_srcs = [ + ":common_target_td_sources", + ] + glob([ + "lib/Target/ARM/**/*.td", + ]), +) + +gentbl( + name = "AArch64TargetParserDefGen", + tbl_outs = [("-gen-arm-target-def", "include/llvm/TargetParser/AArch64TargetParserDef.inc")], + tblgen = ":llvm-min-tblgen", + td_file = "lib/Target/AArch64/AArch64.td", + td_srcs = [ + ":common_target_td_sources", + ] + glob([ + "lib/Target/AArch64/**/*.td", + ]), +) + gentbl( name = "RISCVTargetParserDefGen", tbl_outs = [("-gen-riscv-target-def", "include/llvm/TargetParser/RISCVTargetParserDef.inc")], @@ -1261,6 +1286,8 @@ cc_library( copts = llvm_copts, includes = ["include"], textual_hdrs = [ + "include/llvm/TargetParser/ARMTargetParserDef.inc", + "include/llvm/TargetParser/AArch64TargetParserDef.inc", "include/llvm/TargetParser/RISCVTargetParserDef.inc", ] + glob([ "include/llvm/TargetParser/*.def", diff --git a/utils/bazel/llvm-project-overlay/mlir/BUILD.bazel b/utils/bazel/llvm-project-overlay/mlir/BUILD.bazel index 63b24b9f46b20adcc30ac59a90526d298b9d1571..6a6f8fc13410028ff6d85dfd6855d226f30bd710 100644 --- a/utils/bazel/llvm-project-overlay/mlir/BUILD.bazel +++ b/utils/bazel/llvm-project-overlay/mlir/BUILD.bazel @@ -5,8 +5,8 @@ # Description: # The MLIR "Multi-Level Intermediate Representation" Compiler Infrastructure -load("@bazel_skylib//rules:expand_template.bzl", "expand_template") load("@bazel_skylib//rules:common_settings.bzl", "bool_flag") +load("@bazel_skylib//rules:expand_template.bzl", "expand_template") load( ":build_defs.bzl", "cc_headers_only", @@ -3652,14 +3652,6 @@ gentbl_cc_library( ], "include/mlir/Dialect/XeGPU/IR/XeGPUTypes.cpp.inc", ), - ( - ["-gen-enum-decls"], - "include/mlir/Dialect/XeGPU/IR/XeGPUEnums.h.inc", - ), - ( - ["-gen-enum-defs"], - "include/mlir/Dialect/XeGPU/IR/XeGPUEnums.cpp.inc", - ), ( [ "-gen-attrdef-decls", @@ -3677,7 +3669,44 @@ gentbl_cc_library( ], tblgen = ":mlir-tblgen", td_file = "include/mlir/Dialect/XeGPU/IR/XeGPU.td", - deps = [":XeGPUTdFiles"], + deps = [ + ":ArithOpsTdFiles", + ":XeGPUTdFiles", + ], +) + +td_library( + name = "XeGPUAttrTdFiles", + srcs = [ + "include/mlir/Dialect/XeGPU/IR/XeGPUAttrs.td", + "include/mlir/Dialect/XeGPU/IR/XeGPUDialect.td", + ], + includes = ["include"], + deps = [ + ":BuiltinDialectTdFiles", + ":OpBaseTdFiles", + ":ShapedOpInterfacesTdFiles", + ":ViewLikeInterfaceTdFiles", + ], +) + +# Separated from the XeGPUIncGen target because the enum declaration causes +# duplicate declarations with the Arith enums. +gentbl_cc_library( + name = "XeGPUEnumsIncGen", + tbl_outs = [ + ( + ["-gen-enum-decls"], + "include/mlir/Dialect/XeGPU/IR/XeGPUEnums.h.inc", + ), + ( + ["-gen-enum-defs"], + "include/mlir/Dialect/XeGPU/IR/XeGPUEnums.cpp.inc", + ), + ], + tblgen = ":mlir-tblgen", + td_file = "include/mlir/Dialect/XeGPU/IR/XeGPUAttrs.td", + deps = [":XeGPUAttrTdFiles"], ) cc_library( @@ -3689,12 +3718,14 @@ cc_library( hdrs = ["include/mlir/Dialect/XeGPU/IR/XeGPU.h"], includes = ["include"], deps = [ + ":ArithDialect", ":BytecodeOpInterface", ":DialectUtils", ":IR", ":ShapedOpInterfaces", ":SideEffectInterfaces", ":ViewLikeInterface", + ":XeGPUEnumsIncGen", ":XeGPUIncGen", "//llvm:Support", ], @@ -9740,6 +9771,15 @@ cc_binary( ], ) +cc_binary( + name = "mlir-src-sharder", + srcs = ["tools/mlir-src-sharder/mlir-src-sharder.cpp"], + deps = [ + ":Support", + "//llvm:Support", + ], +) + cc_binary( name = "mlir-linalg-ods-yaml-gen", srcs = [ @@ -11064,6 +11104,7 @@ cc_library( ":FuncTransforms", ":GPUDialect", ":IR", + ":IndexDialect", ":LinalgDialect", ":LinalgPassIncGen", ":LinalgStructuredOpsIncGen", @@ -11075,6 +11116,7 @@ cc_library( ":MeshShardingInterface", ":MeshTransforms", ":Pass", + ":RuntimeVerifiableOpInterface", ":SCFDialect", ":SCFTransforms", ":SCFUtils", diff --git a/utils/bazel/llvm-project-overlay/mlir/tblgen.bzl b/utils/bazel/llvm-project-overlay/mlir/tblgen.bzl index fdf6a57107ac34c47de05662580afc06af65c5d2..e45ba1fe0ef721191b09466c4481bf8595cc8cb6 100644 --- a/utils/bazel/llvm-project-overlay/mlir/tblgen.bzl +++ b/utils/bazel/llvm-project-overlay/mlir/tblgen.bzl @@ -432,3 +432,136 @@ def gentbl_cc_library( copts = copts, **kwargs ) + +def _gentbl_shard_impl(ctx): + args = ctx.actions.args() + args.add(ctx.file.src_file) + args.add("-op-shard-index", ctx.attr.index) + args.add("-o", ctx.outputs.out.path) + ctx.actions.run( + outputs = [ctx.outputs.out], + inputs = [ctx.file.src_file], + executable = ctx.executable.sharder, + arguments = [args], + use_default_shell_env = True, + mnemonic = "ShardGenerate", + ) + +gentbl_shard_rule = rule( + _gentbl_shard_impl, + doc = "", + output_to_genfiles = True, + attrs = { + "index": attr.int(mandatory = True, doc = ""), + "sharder": attr.label( + doc = "", + executable = True, + cfg = "exec", + ), + "src_file": attr.label( + doc = "", + allow_single_file = True, + mandatory = True, + ), + "out": attr.output( + doc = "", + mandatory = True, + ), + }, +) + +def gentbl_sharded_ops( + name, + tblgen, + sharder, + td_file, + shard_count, + src_file, + src_out, + hdr_out, + test = False, + includes = [], + strip_include_prefix = None, + deps = []): + """Generate sharded op declarations and definitions. + + This special build rule shards op definitions in a TableGen file and generates multiple copies + of a template source file for including and compiling each shard. The rule defines a filegroup + consisting of the source shards, the generated source file, and the generated header file. + + Args: + name: The name of the filegroup. + tblgen: The binary used to produce the output. + sharder: The source file sharder to use. + td_file: The primary table definitions file. + shard_count: The number of op definition shards to produce. + src_file: The source file template. + src_out: The generated source file. + hdr_out: The generated header file. + test: Whether this is a test target. + includes: See gentbl_rule.includes + deps: See gentbl_rule.deps + strip_include_prefix: Attribute to pass through to cc_library. + """ + cc_lib_name = name + "__gentbl_cc_lib" + gentbl_cc_library( + name = cc_lib_name, + strip_include_prefix = strip_include_prefix, + includes = includes, + tbl_outs = [ + ( + [ + "-gen-op-defs", + "-op-shard-count=" + str(shard_count), + ], + src_out, + ), + ( + [ + "-gen-op-decls", + "-op-shard-count=" + str(shard_count), + ], + hdr_out, + ), + ], + tblgen = tblgen, + td_file = td_file, + test = test, + deps = deps, + ) + all_files = [hdr_out, src_out] + for i in range(0, shard_count): + out_file = "shard_copy_" + str(i) + "_" + src_file + gentbl_shard_rule( + index = i, + name = name + "__src_shard" + str(i), + testonly = test, + out = out_file, + sharder = sharder, + src_file = src_file, + ) + all_files.append(out_file) + native.filegroup(name = name, srcs = all_files) + +def gentbl_sharded_op_defs(name, source_file, shard_count): + """Generates multiple copies of a source file that includes sharded op definitions. + + Args: + name: The name of the rule. + source_file: The source to copy. + shard_count: The number of shards. + + Returns: + A list of the copied filenames to be included in the dialect library. + """ + copies = [] + for i in range(0, shard_count): + out_file = "shard_copy_" + str(i) + "_" + source_file + copies.append(out_file) + native.genrule( + name = name + "_shard_" + str(i), + srcs = [source_file], + outs = [out_file], + cmd = "echo -e \"#define GET_OP_DEFS_" + str(i) + "\n$$(cat $(SRCS))\" > $(OUTS)", + ) + return copies diff --git a/utils/bazel/llvm-project-overlay/mlir/test/BUILD.bazel b/utils/bazel/llvm-project-overlay/mlir/test/BUILD.bazel index dc5f4047c286dbcc78a4fc2764fe60cd4fed780b..0ebfcbe284bd3726ebc8eea5ca50a1ef978a0a17 100644 --- a/utils/bazel/llvm-project-overlay/mlir/test/BUILD.bazel +++ b/utils/bazel/llvm-project-overlay/mlir/test/BUILD.bazel @@ -4,7 +4,7 @@ load("@bazel_skylib//rules:expand_template.bzl", "expand_template") load("//llvm:lit_test.bzl", "package_path") -load("//mlir:tblgen.bzl", "gentbl_cc_library", "td_library") +load("//mlir:tblgen.bzl", "gentbl_cc_library", "gentbl_sharded_ops", "td_library") package( default_visibility = ["//visibility:public"], @@ -151,14 +151,6 @@ gentbl_cc_library( name = "TestOpsIncGen", strip_include_prefix = "lib/Dialect/Test", tbl_outs = [ - ( - ["-gen-op-decls"], - "lib/Dialect/Test/TestOps.h.inc", - ), - ( - ["-gen-op-defs"], - "lib/Dialect/Test/TestOps.cpp.inc", - ), ( [ "-gen-dialect-decls", @@ -370,12 +362,25 @@ cc_library( ], ) +gentbl_sharded_ops( + name = "TestDialectOpSrcs", + hdr_out = "lib/Dialect/Test/TestOps.h.inc", + shard_count = 20, + sharder = "//mlir:mlir-src-sharder", + src_file = "lib/Dialect/Test/TestOps.cpp", + src_out = "lib/Dialect/Test/TestOps.cpp.inc", + tblgen = "//mlir:mlir-tblgen", + td_file = "lib/Dialect/Test/TestOps.td", + test = True, + deps = [":TestOpTdFiles"], +) + cc_library( name = "TestDialect", srcs = glob( ["lib/Dialect/Test/*.cpp"], exclude = ["lib/Dialect/Test/TestToLLVMIRTranslation.cpp"], - ), + ) + [":TestDialectOpSrcs"], hdrs = glob(["lib/Dialect/Test/*.h"]), includes = [ "lib/Dialect/Test", @@ -418,9 +423,9 @@ cc_library( "//mlir:SideEffectInterfaces", "//mlir:Support", "//mlir:TensorDialect", - "//mlir:TranslateLib", "//mlir:TransformUtils", "//mlir:Transforms", + "//mlir:TranslateLib", "//mlir:ValueBoundsOpInterface", "//mlir:ViewLikeInterface", ],