From 5cede5f7d7a83b35906e7d141ce58788c67456a7 Mon Sep 17 00:00:00 2001 From: Michael D Toguchi Date: Wed, 23 Jun 2021 18:13:12 -0700 Subject: [PATCH 1/5] [Driver][SYCL] Allow for known aliases to be used for -fsycl-targets When using -fsycl-targets, usage is clumsy as we want the full triple to be used: spir64-unknown-unknown-sycldevice Allow for just the 'arch' to be specified, which will be expanded: spir64 -> spir64-unknown-unknown-sycldevice spir64_gen -> spir64_gen-unknown-unknown-sycldevice spir64_fpga -> spir64_fpga-unknown-unknown-sycldevice spir64_x86_64 -> spir64_x86_64-unknown-unknown-sycldevice --- clang/lib/Driver/Driver.cpp | 16 ++++++++++++++-- clang/test/Driver/sycl-offload.c | 28 ++++++++++++++++++++++------ 2 files changed, 36 insertions(+), 8 deletions(-) diff --git a/clang/lib/Driver/Driver.cpp b/clang/lib/Driver/Driver.cpp index e927ec4f140d9..a1f9fa1ef1cbf 100644 --- a/clang/lib/Driver/Driver.cpp +++ b/clang/lib/Driver/Driver.cpp @@ -706,6 +706,18 @@ static bool isValidSYCLTriple(llvm::Triple T) { return true; } +// Create a triple based off of the input provided. Allow for short aliases +// of known arch strings, which will be expanded to the full triple for usage +// during the compilation. +static llvm::Triple resolveSYCLTriple(Compilation &C, StringRef TripleStr) { + SmallVector SYCLAlias = {"spir64", "spir64_fpga", + "spir64_x86_64", "spir64_gen"}; + if (std::find(SYCLAlias.begin(), SYCLAlias.end(), TripleStr) + != SYCLAlias.end()) + return C.getDriver().MakeSYCLDeviceTriple(TripleStr); + return llvm::Triple(TripleStr); +} + void Driver::CreateOffloadingDeviceToolChains(Compilation &C, InputList &Inputs) { @@ -897,7 +909,7 @@ void Driver::CreateOffloadingDeviceToolChains(Compilation &C, if (SYCLTargetsValues) { if (SYCLTargetsValues->getNumValues()) { for (StringRef Val : SYCLTargetsValues->getValues()) { - llvm::Triple TT(Val); + llvm::Triple TT(resolveSYCLTriple(C, Val)); if (!isValidSYCLTriple(TT)) { Diag(clang::diag::err_drv_invalid_sycl_target) << Val; continue; @@ -4565,7 +4577,7 @@ class OffloadingActionBuilder final { if (SYCLTargets) { llvm::StringMap FoundNormalizedTriples; for (const char *Val : SYCLTargets->getValues()) { - llvm::Triple TT(Val); + llvm::Triple TT(resolveSYCLTriple(C, Val)); std::string NormalizedName = TT.normalize(); // Make sure we don't have a duplicate triple. diff --git a/clang/test/Driver/sycl-offload.c b/clang/test/Driver/sycl-offload.c index 3a1368c3a24fb..c71321e16311a 100644 --- a/clang/test/Driver/sycl-offload.c +++ b/clang/test/Driver/sycl-offload.c @@ -96,16 +96,24 @@ /// Check no error for -fsycl-targets with good triple // RUN: %clang -### -fsycl-targets=spir-unknown-unknown-sycldevice -fsycl %s 2>&1 \ -// RUN: | FileCheck -check-prefix=CHK-SYCL-FPGA-TRIPLE %s +// RUN: | FileCheck -check-prefix=CHK-SYCL-TARGET %s +// RUN: %clang -### -fsycl-targets=spir64 -fsycl %s 2>&1 \ +// RUN: | FileCheck -check-prefix=CHK-SYCL-TARGET %s // RUN: %clang -### -fsycl-targets=spir64_fpga-unknown-unknown-sycldevice -fsycl %s 2>&1 \ -// RUN: | FileCheck -check-prefix=CHK-SYCL-FPGA-TRIPLE %s +// RUN: | FileCheck -check-prefix=CHK-SYCL-TARGET %s +// RUN: %clang -### -fsycl-targets=spir64_fpga -fsycl %s 2>&1 \ +// RUN: | FileCheck -check-prefix=CHK-SYCL-TARGET %s // RUN: %clang -### -fsycl-targets=spir64_x86_64-unknown-unknown-sycldevice -fsycl %s 2>&1 \ -// RUN: | FileCheck -check-prefix=CHK-SYCL-FPGA-TRIPLE %s +// RUN: | FileCheck -check-prefix=CHK-SYCL-TARGET %s +// RUN: %clang -### -fsycl-targets=spir64_x86_64 -fsycl %s 2>&1 \ +// RUN: | FileCheck -check-prefix=CHK-SYCL-TARGET %s // RUN: %clang -### -fsycl-targets=spir64_gen-unknown-unknown-sycldevice -fsycl %s 2>&1 \ -// RUN: | FileCheck -check-prefix=CHK-SYCL-FPGA-TRIPLE %s +// RUN: | FileCheck -check-prefix=CHK-SYCL-TARGET %s +// RUN: %clang -### -fsycl-targets=spir64_gen -fsycl %s 2>&1 \ +// RUN: | FileCheck -check-prefix=CHK-SYCL-TARGET %s // RUN: %clang_cl -### -fsycl-targets=spir-unknown-unknown-sycldevice -fsycl %s 2>&1 \ -// RUN: | FileCheck -check-prefix=CHK-SYCL-FPGA-TRIPLE %s -// CHK-SYCL-FPGA-TRIPLE-NOT: error: SYCL target is invalid +// RUN: | FileCheck -check-prefix=CHK-SYCL-TARGET %s +// CHK-SYCL-TARGET-NOT: error: SYCL target is invalid /// Check error for -fsycl-[add|link]-targets with bad triple // RUN: %clang -### -fsycl-add-targets=spir64_bad-unknown-unknown-sycldevice:dummy.spv -fsycl %s 2>&1 \ @@ -302,6 +310,8 @@ // RUN: touch %t.o // RUN: %clang -### -ccc-print-phases -target x86_64-unknown-linux-gnu -fsycl -fno-sycl-device-lib=all -o %t.out -lsomelib -fsycl-targets=spir64-unknown-unknown-sycldevice %t.o 2>&1 \ // RUN: | FileCheck -DINPUT=%t.o -check-prefix=CHK-UBACTIONS %s +// RUN: %clang -### -ccc-print-phases -target x86_64-unknown-linux-gnu -fsycl -fno-sycl-device-lib=all -o %t.out -lsomelib -fsycl-targets=spir64 %t.o 2>&1 \ +// RUN: | FileCheck -DINPUT=%t.o -check-prefix=CHK-UBACTIONS %s // RUN: mkdir -p %t_dir // RUN: touch %t_dir/dummy // RUN: %clang -### -ccc-print-phases -target x86_64-unknown-linux-gnu -fsycl -fno-sycl-device-lib=all -o %t.out -lsomelib -fsycl-targets=spir64-unknown-unknown-sycldevice %t_dir/dummy 2>&1 \ @@ -625,10 +635,16 @@ /// Ahead of Time compilation for fpga, gen, cpu // RUN: %clang -target x86_64-unknown-linux-gnu -ccc-print-phases -fsycl-use-footer -fsycl -fno-sycl-device-lib=all -fsycl-targets=spir64_fpga-unknown-unknown-sycldevice %s 2>&1 \ // RUN: | FileCheck %s -check-prefixes=CHK-PHASES-AOT,CHK-PHASES-FPGA +// RUN: %clang -target x86_64-unknown-linux-gnu -ccc-print-phases -fsycl-use-footer -fsycl -fno-sycl-device-lib=all -fsycl-targets=spir64_fpga %s 2>&1 \ +// RUN: | FileCheck %s -check-prefixes=CHK-PHASES-AOT,CHK-PHASES-FPGA // RUN: %clang -target x86_64-unknown-linux-gnu -ccc-print-phases -fsycl-use-footer -fsycl -fno-sycl-device-lib=all -fsycl-targets=spir64_gen-unknown-unknown-sycldevice %s 2>&1 \ // RUN: | FileCheck %s -check-prefixes=CHK-PHASES-AOT,CHK-PHASES-GEN +// RUN: %clang -target x86_64-unknown-linux-gnu -ccc-print-phases -fsycl-use-footer -fsycl -fno-sycl-device-lib=all -fsycl-targets=spir64_gen %s 2>&1 \ +// RUN: | FileCheck %s -check-prefixes=CHK-PHASES-AOT,CHK-PHASES-GEN // RUN: %clang -target x86_64-unknown-linux-gnu -ccc-print-phases -fsycl-use-footer -fsycl -fno-sycl-device-lib=all -fsycl-targets=spir64_x86_64-unknown-unknown-sycldevice %s 2>&1 \ // RUN: | FileCheck %s -check-prefixes=CHK-PHASES-AOT,CHK-PHASES-CPU +// RUN: %clang -target x86_64-unknown-linux-gnu -ccc-print-phases -fsycl-use-footer -fsycl -fno-sycl-device-lib=all -fsycl-targets=spir64_x86_64 %s 2>&1 \ +// RUN: | FileCheck %s -check-prefixes=CHK-PHASES-AOT,CHK-PHASES-CPU // CHK-PHASES-AOT: 0: input, "[[INPUT:.+\.c]]", c++, (host-sycl) // CHK-PHASES-AOT: 1: preprocessor, {0}, c++-cpp-output, (host-sycl) // CHK-PHASES-AOT: 2: append-footer, {1}, c++, (host-sycl) From 723477765e3b1faed9d1ec430906c0e1cfdc59de Mon Sep 17 00:00:00 2001 From: Michael D Toguchi Date: Wed, 23 Jun 2021 18:23:25 -0700 Subject: [PATCH 2/5] clang format --- clang/lib/Driver/Driver.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/clang/lib/Driver/Driver.cpp b/clang/lib/Driver/Driver.cpp index a1f9fa1ef1cbf..3127916ea4074 100644 --- a/clang/lib/Driver/Driver.cpp +++ b/clang/lib/Driver/Driver.cpp @@ -712,8 +712,8 @@ static bool isValidSYCLTriple(llvm::Triple T) { static llvm::Triple resolveSYCLTriple(Compilation &C, StringRef TripleStr) { SmallVector SYCLAlias = {"spir64", "spir64_fpga", "spir64_x86_64", "spir64_gen"}; - if (std::find(SYCLAlias.begin(), SYCLAlias.end(), TripleStr) - != SYCLAlias.end()) + if (std::find(SYCLAlias.begin(), SYCLAlias.end(), TripleStr) != + SYCLAlias.end()) return C.getDriver().MakeSYCLDeviceTriple(TripleStr); return llvm::Triple(TripleStr); } From 7f245a16d0c673130ca966d1a41712b793da7c86 Mon Sep 17 00:00:00 2001 From: Michael D Toguchi Date: Thu, 24 Jun 2021 13:40:55 -0700 Subject: [PATCH 3/5] Adjust documentation for aliases and make sure -Xsycl-target* applies --- clang/lib/Driver/ToolChains/SYCL.cpp | 2 +- clang/test/Driver/sycl-offload.c | 3 +++ sycl/doc/GetStartedGuide.md | 12 +++++++----- sycl/doc/UsersManual.md | 2 ++ 4 files changed, 13 insertions(+), 6 deletions(-) diff --git a/clang/lib/Driver/ToolChains/SYCL.cpp b/clang/lib/Driver/ToolChains/SYCL.cpp index 93711d3732ed1..d51d200f253da 100644 --- a/clang/lib/Driver/ToolChains/SYCL.cpp +++ b/clang/lib/Driver/ToolChains/SYCL.cpp @@ -671,7 +671,7 @@ void SYCLToolChain::TranslateTargetOpt(const llvm::opt::ArgList &Args, OptNoTriple = A->getOption().matches(Opt); if (A->getOption().matches(Opt_EQ)) { // Passing device args: -X= -opt=val. - if (A->getValue() != getTripleString()) + if (getDriver().MakeSYCLDeviceTriple(A->getValue()) != getTriple()) // Provided triple does not match current tool chain. continue; } else if (!OptNoTriple) diff --git a/clang/test/Driver/sycl-offload.c b/clang/test/Driver/sycl-offload.c index c71321e16311a..2f8807bf391e7 100644 --- a/clang/test/Driver/sycl-offload.c +++ b/clang/test/Driver/sycl-offload.c @@ -820,6 +820,9 @@ // RUN: %clang -### -target x86_64-unknown-linux-gnu -fsycl -fsycl-targets=spir64-unknown-unknown-sycldevice,spir64_gen-unknown-unknown-sycldevice \ // RUN: -Xsycl-target-backend=spir64_gen-unknown-unknown-sycldevice "-device skl -cl-opt-disable" -Xsycl-target-linker=spir64-unknown-unknown-sycldevice "-cl-denorms-are-zero" %s 2>&1 \ // RUN: | FileCheck -check-prefixes=CHK-TOOLS-MULT-OPTS,CHK-TOOLS-MULT-OPTS-NEG %s +// RUN: %clang -### -target x86_64-unknown-linux-gnu -fsycl -fsycl-targets=spir64,spir64_gen \ +// RUN: -Xsycl-target-backend=spir64_gen "-device skl -cl-opt-disable" -Xsycl-target-linker=spir64 "-cl-denorms-are-zero" %s 2>&1 \ +// RUN: | FileCheck -check-prefixes=CHK-TOOLS-MULT-OPTS,CHK-TOOLS-MULT-OPTS-NEG %s // CHK-TOOLS-MULT-OPTS: clang-offload-wrapper{{.*}} "-link-opts=-cl-denorms-are-zero"{{.*}} "-target=spir64" // CHK-TOOLS-MULT-OPTS: ocloc{{.*}} "-device" "skl"{{.*}} "-cl-opt-disable" // CHK-TOOLS-MULT-OPTS-NEG-NOT: clang-offload-wrapper{{.*}} "-compile-opts=-device skl -cl-opt-disable"{{.*}} "-target=spir64" diff --git a/sycl/doc/GetStartedGuide.md b/sycl/doc/GetStartedGuide.md index 2bb04d5e0aa7d..2dc8907031e3a 100644 --- a/sycl/doc/GetStartedGuide.md +++ b/sycl/doc/GetStartedGuide.md @@ -490,11 +490,13 @@ clang++ -fsycl -fsycl-targets=nvptx64-nvidia-cuda-sycldevice \ ``` To build simple-sycl-app ahead of time for GPU, CPU or Accelerator devices, -specify the target architecture: +specify the target architecture. The examples provided use a supported +alias for the target, representing a full triple. Additional details can +be found in the [Users Manual](UsersManual.md#generic-options). -```-fsycl-targets=spir64_gen-unknown-unknown-sycldevice``` for GPU, -```-fsycl-targets=spir64_x86_64-unknown-unknown-sycldevice``` for CPU, -```-fsycl-targets=spir64_fpga-unknown-unknown-sycldevice``` for Accelerator. +```-fsycl-targets=spir64_gen``` for GPU, +```-fsycl-targets=spir64_x86_64``` for CPU, +```-fsycl-targets=spir64_fpga``` for Accelerator. Multiple target architectures are supported. @@ -502,7 +504,7 @@ E.g., this command builds simple-sycl-app for GPU and CPU devices in ahead of time mode: ```bash -clang++ -fsycl -fsycl-targets=spir64_gen-unknown-unknown-sycldevice,spir64_x86_64-unknown-unknown-sycldevice simple-sycl-app.cpp -o simple-sycl-app-aot.exe +clang++ -fsycl -fsycl-targets=spir64_gen,spir64_x86_64 simple-sycl-app.cpp -o simple-sycl-app-aot.exe ``` Additionally, user can pass specific options of AOT compiler to diff --git a/sycl/doc/UsersManual.md b/sycl/doc/UsersManual.md index e27b64842177b..51a940cd10fc2 100644 --- a/sycl/doc/UsersManual.md +++ b/sycl/doc/UsersManual.md @@ -31,6 +31,8 @@ and not recommended to use in production environment. Intel FPGA; * spir64_gen-unknown-unknown-sycldevice - generate code ahead of time for Intel Processor Graphics; + Shorter aliases of the above triples can also be used: + * spir64, spir64_x86_64, spir64_fpga, spir64_gen Available in special build configuration: * nvptx64-nvidia-cuda-sycldevice - generate code ahead of time for CUDA target; From ed134e979f3a08c6597c225f86a90f1934c87672 Mon Sep 17 00:00:00 2001 From: Michael D Toguchi Date: Thu, 24 Jun 2021 14:20:46 -0700 Subject: [PATCH 4/5] Augment existing Make SYCL triple function instead of creating new --- clang/lib/Driver/Driver.cpp | 34 ++++++++++++++-------------------- 1 file changed, 14 insertions(+), 20 deletions(-) diff --git a/clang/lib/Driver/Driver.cpp b/clang/lib/Driver/Driver.cpp index 3127916ea4074..ea7169e9182e0 100644 --- a/clang/lib/Driver/Driver.cpp +++ b/clang/lib/Driver/Driver.cpp @@ -706,18 +706,6 @@ static bool isValidSYCLTriple(llvm::Triple T) { return true; } -// Create a triple based off of the input provided. Allow for short aliases -// of known arch strings, which will be expanded to the full triple for usage -// during the compilation. -static llvm::Triple resolveSYCLTriple(Compilation &C, StringRef TripleStr) { - SmallVector SYCLAlias = {"spir64", "spir64_fpga", - "spir64_x86_64", "spir64_gen"}; - if (std::find(SYCLAlias.begin(), SYCLAlias.end(), TripleStr) != - SYCLAlias.end()) - return C.getDriver().MakeSYCLDeviceTriple(TripleStr); - return llvm::Triple(TripleStr); -} - void Driver::CreateOffloadingDeviceToolChains(Compilation &C, InputList &Inputs) { @@ -909,7 +897,7 @@ void Driver::CreateOffloadingDeviceToolChains(Compilation &C, if (SYCLTargetsValues) { if (SYCLTargetsValues->getNumValues()) { for (StringRef Val : SYCLTargetsValues->getValues()) { - llvm::Triple TT(resolveSYCLTriple(C, Val)); + llvm::Triple TT(MakeSYCLDeviceTriple(Val)); if (!isValidSYCLTriple(TT)) { Diag(clang::diag::err_drv_invalid_sycl_target) << Val; continue; @@ -1858,12 +1846,18 @@ void Driver::PrintHelp(bool ShowHidden) const { } llvm::Triple Driver::MakeSYCLDeviceTriple(StringRef TargetArch) const { - llvm::Triple TT; - TT.setArchName(TargetArch); - TT.setVendor(llvm::Triple::UnknownVendor); - TT.setOS(llvm::Triple::UnknownOS); - TT.setEnvironment(llvm::Triple::SYCLDevice); - return TT; + SmallVector SYCLAlias = {"spir", "spir64", "spir64_fpga", + "spir64_x86_64", "spir64_gen"}; + if (std::find(SYCLAlias.begin(), SYCLAlias.end(), TargetArch) != + SYCLAlias.end()) { + llvm::Triple TT; + TT.setArchName(TargetArch); + TT.setVendor(llvm::Triple::UnknownVendor); + TT.setOS(llvm::Triple::UnknownOS); + TT.setEnvironment(llvm::Triple::SYCLDevice); + return TT; + } + return llvm::Triple(TargetArch); } // Print the help from any of the given tools which are used for AOT @@ -4577,7 +4571,7 @@ class OffloadingActionBuilder final { if (SYCLTargets) { llvm::StringMap FoundNormalizedTriples; for (const char *Val : SYCLTargets->getValues()) { - llvm::Triple TT(resolveSYCLTriple(C, Val)); + llvm::Triple TT(C.getDriver().MakeSYCLDeviceTriple(Val)); std::string NormalizedName = TT.normalize(); // Make sure we don't have a duplicate triple. From 2500a6fbb85819e56d8eded600bcc5ff224c42ca Mon Sep 17 00:00:00 2001 From: Michael D Toguchi Date: Fri, 25 Jun 2021 11:49:40 -0700 Subject: [PATCH 5/5] Address review comments --- clang/lib/Driver/Driver.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/clang/lib/Driver/Driver.cpp b/clang/lib/Driver/Driver.cpp index ea7169e9182e0..c04f561a49519 100644 --- a/clang/lib/Driver/Driver.cpp +++ b/clang/lib/Driver/Driver.cpp @@ -1846,8 +1846,8 @@ void Driver::PrintHelp(bool ShowHidden) const { } llvm::Triple Driver::MakeSYCLDeviceTriple(StringRef TargetArch) const { - SmallVector SYCLAlias = {"spir", "spir64", "spir64_fpga", - "spir64_x86_64", "spir64_gen"}; + ArrayRef SYCLAlias = {"spir", "spir64", "spir64_fpga", + "spir64_x86_64", "spir64_gen"}; if (std::find(SYCLAlias.begin(), SYCLAlias.end(), TargetArch) != SYCLAlias.end()) { llvm::Triple TT;