[Clang] Added options for integrated backend.

Following the new flow for external object code emission,
provide flags to switch between integrated and external
backend similar to the integrated assembler options.

SPIR-V target is the only user of this functionality at
this point.

This patch also updated SPIR-V documentation to clarify
that integrated object code emission for SPIR-V is an
experimental feature.

Differential Revision: https://reviews.llvm.org/D125679
This commit is contained in:
Anastasia Stulova 2022-05-25 12:01:42 +01:00
parent 87936c7b13
commit 730dc4e9bc
7 changed files with 83 additions and 6 deletions

View File

@ -3180,8 +3180,8 @@ Generic Targets
.. code-block:: console
$ clang -target spirv32 test.cl
$ clang -target spirv64 test.cl
$ clang -target spirv32 -c test.cl
$ clang -target spirv64 -c test.cl
More details can be found in :ref:`the SPIR-V support section <spir-v>`.
@ -3657,8 +3657,8 @@ Example usage for OpenCL kernel compilation:
.. code-block:: console
$ clang -target spirv32 test.cl
$ clang -target spirv64 test.cl
$ clang -target spirv32 -c test.cl
$ clang -target spirv64 -c test.cl
Both invocations of Clang will result in the generation of a SPIR-V binary file
`test.o` for 32 bit and 64 bit respectively. This file can be imported
@ -3669,6 +3669,18 @@ Converting to SPIR-V produced with the optimization levels other than `-O0` is
currently available as an experimental feature and it is not guaranteed to work
in all cases.
Clang also supports integrated generation of SPIR-V without use of ``llvm-spirv``
tool as an experimental feature when ``-fintegrated-objemitter`` flag is passed in
the command line.
.. code-block:: console
$ clang -target spirv32 -fintegrated-objemitter -c test.cl
Note that only very basic functionality is supported at this point and therefore
it is not suitable for arbitrary use cases. This feature is only enabled when clang
build is configured with ``-DLLVM_EXPERIMENTAL_TARGETS_TO_BUILD=SPIRV`` option.
Linking is done using ``spirv-link`` from `the SPIRV-Tools project
<https://github.com/KhronosGroup/SPIRV-Tools#linker>`_. Similar to other external
linkers, Clang will expect ``spirv-link`` to be installed separately and to be
@ -3676,6 +3688,10 @@ present in the ``PATH`` environment variable. Please refer to `the build and
installation instructions
<https://github.com/KhronosGroup/SPIRV-Tools#build>`_.
.. code-block:: console
$ clang -target spirv64 test1.cl test2.cl
.. _clang-cl:
clang-cl

View File

@ -4170,6 +4170,13 @@ def fno_integrated_cc1 : Flag<["-"], "fno-integrated-cc1">,
Flags<[CoreOption, NoXarchOption]>, Group<f_Group>,
HelpText<"Spawn a separate process for each cc1">;
def fintegrated_objemitter : Flag<["-"], "fintegrated-objemitter">,
Flags<[CoreOption, NoXarchOption]>, Group<f_Group>,
HelpText<"Use internal machine object code emitter.">;
def fno_integrated_objemitter : Flag<["-"], "fno-integrated-objemitter">,
Flags<[CoreOption, NoXarchOption]>, Group<f_Group>,
HelpText<"Use external machine object code emitter.">;
def : Flag<["-"], "integrated-as">, Alias<fintegrated_as>, Flags<[NoXarchOption]>;
def : Flag<["-"], "no-integrated-as">, Alias<fno_integrated_as>,
Flags<[CC1Option, FlangOption, NoXarchOption]>;

View File

@ -385,11 +385,23 @@ public:
/// by default.
virtual bool IsIntegratedAssemblerDefault() const { return false; }
/// IsIntegratedBackendDefault - Does this tool chain enable
/// -fintegrated-objemitter by default.
virtual bool IsIntegratedBackendDefault() const { return true; }
/// IsIntegratedBackendSupported - Does this tool chain support
/// -fintegrated-objemitter.
virtual bool IsIntegratedBackendSupported() const { return true; }
/// IsNonIntegratedBackendSupported - Does this tool chain support
/// -fno-integrated-objemitter.
virtual bool IsNonIntegratedBackendSupported() const { return false; }
/// Check if the toolchain should use the integrated assembler.
virtual bool useIntegratedAs() const;
/// Check if the toolchain should use the integrated backend.
virtual bool useIntegratedBackend() const { return true; }
virtual bool useIntegratedBackend() const;
/// Check if the toolchain should use AsmParser to parse inlineAsm when
/// integrated assembler is not default.

View File

@ -106,6 +106,34 @@ bool ToolChain::useIntegratedAs() const {
IsIntegratedAssemblerDefault());
}
bool ToolChain::useIntegratedBackend() const {
assert(
((IsIntegratedBackendDefault() && IsIntegratedBackendSupported()) ||
(!IsIntegratedBackendDefault() || IsNonIntegratedBackendSupported())) &&
"(Non-)integrated backend set incorrectly!");
bool IBackend = Args.hasFlag(options::OPT_fintegrated_objemitter,
options::OPT_fno_integrated_objemitter,
IsIntegratedBackendDefault());
// Diagnose when integrated-objemitter options are not supported by this
// toolchain.
unsigned DiagID;
if ((IBackend && !IsIntegratedBackendSupported()) ||
(!IBackend && !IsNonIntegratedBackendSupported()))
DiagID = clang::diag::err_drv_unsupported_opt_for_target;
else
DiagID = clang::diag::warn_drv_unsupported_opt_for_target;
Arg *A = Args.getLastArg(options::OPT_fno_integrated_objemitter);
if (A && !IsNonIntegratedBackendSupported())
D.Diag(DiagID) << A->getAsString(Args) << Triple.getTriple();
A = Args.getLastArg(options::OPT_fintegrated_objemitter);
if (A && !IsIntegratedBackendSupported())
D.Diag(DiagID) << A->getAsString(Args) << Triple.getTriple();
return IBackend;
}
bool ToolChain::useRelaxRelocations() const {
return ENABLE_X86_RELAX_RELOCATIONS;
}

View File

@ -64,8 +64,9 @@ public:
: ToolChain(D, Triple, Args) {}
bool useIntegratedAs() const override { return true; }
bool useIntegratedBackend() const override { return false; }
bool IsIntegratedBackendDefault() const override { return false; }
bool IsNonIntegratedBackendSupported() const override { return true; }
bool IsMathErrnoDefault() const override { return false; }
bool isCrossCompiling() const override { return true; }
bool isPICDefault() const override { return false; }

View File

@ -605,3 +605,8 @@
// CHECK_JMC_WARN_NOT_ELF: -fjmc works only for ELF; option ignored
// CHECK_NOJMC-NOT: -fjmc
// CHECK_JMC: -fjmc
// RUN: %clang -### -fintegrated-objemitter -target x86_64 %s 2>&1 | FileCheck -check-prefix=CHECK-INT-OBJEMITTER %s
// CHECK-INT-OBJEMITTER-NOT: unsupported option '-fintegrated-objemitter' for target
// RUN: %clang -### -fno-integrated-objemitter -target x86_64 %s 2>&1 | FileCheck -check-prefix=CHECK-NOINT-OBJEMITTER %s
// CHECK-NOINT-OBJEMITTER: unsupported option '-fno-integrated-objemitter' for target

View File

@ -69,3 +69,11 @@
// SPLINK-SAME: "-o" [[BC:".*bc"]]
// SPLINK: {{llvm-spirv.*"}} [[BC]] "-o" [[SPV2:".*o"]]
// SPLINK: {{spirv-link.*"}} [[SPV1]] [[SPV2]] "-o" "a.out"
//-----------------------------------------------------------------------------
// Check external vs internal object emission.
// RUN: %clang -### --target=spirv64 -fno-integrated-objemitter %s 2>&1 | FileCheck --check-prefix=XTOR %s
// RUN: %clang -### --target=spirv64 -fintegrated-objemitter %s 2>&1 | FileCheck --check-prefix=BACKEND %s
// XTOR: {{llvm-spirv.*"}}
// BACKEND-NOT: {{llvm-spirv.*"}}