================ @@ -0,0 +1,77 @@ +// RUN: %clang_cc1 -fsycl-is-device -triple spir64-unknown-unknown -disable-llvm-passes -emit-llvm %s -o - | FileCheck %s + +// This test code generation when sycl_external attribute is used + +// Function defined and not used - symbols emitted +[[clang::sycl_external]] int square(int x) { return x*x; } +// CHECK: define dso_local spir_func noundef i32 @_Z6squarei + +// Function defined and used - symbols emitted +[[clang::sycl_external]] int squareUsed(int x) { return x*x; } +// CHECK: define dso_local spir_func noundef i32 @_Z10squareUsedi + +// Constexpr function defined and not used - symbols emitted +[[clang::sycl_external]] constexpr int squareInlined(int x) { return x*x; } +// CHECK: define linkonce_odr spir_func noundef i32 @_Z13squareInlinedi + +// Function declared but not defined or used - no symbols emitted +[[clang::sycl_external]] int declOnly(); +// CHECK-NOT: define {{.*}} i32 @_Z8declOnlyv + + +// FIXME: Function declared and used but not defined - emit external reference +[[clang::sycl_external]] void declUsed(int y); + +// Function declared with the attribute and later defined - symbols emitted +[[clang::sycl_external]] int func1(int arg); +int func1(int arg) { return arg; } +// CHECK: define dso_local spir_func noundef i32 @_Z5func1i + +class A { +// Defaulted special member functions - no symbols emitted + [[clang::sycl_external]] A& operator=(A& a) = default; +}; + +class B { + [[clang::sycl_external]] virtual void BFunc1WithAttr() { int i = 1; } ---------------- tahonermann wrote:
Sorry, Sindhu, but I think we should reverse course on this change. Here is what the SYCL 2020 specification has to say about virtual functions (emphasis mine): - [Section 3.1, Overview](https://registry.khronos.org/SYCL/specs/sycl-2020/html/sycl-2020.html#_overview): > However, some C++ language features are not permitted inside kernels, due to the limitations imposed by the capabilities of the underlying heterogeneous platforms. **These features include virtual functions**, virtual inheritance, throwing/catching exceptions, and run-time type-information. These features are available outside kernels as normal. ... - [Section 5.4. Language restrictions for device functions](https://registry.khronos.org/SYCL/specs/sycl-2020/html/sycl-2020.html#sec:language.restrictions.kernels): > The odr-use of polymorphic classes and classes with virtual inheritance is allowed. However, **no virtual member functions are allowed to be called in a [device function](https://registry.khronos.org/SYCL/specs/sycl-2020/html/sycl-2020.html#device-function)**. The SYCL specification does not differentiate between unqualified calls (that use dynamic dispatch) and qualified calls (that are performed like a non-virtual member function call), nor does it address devirtualized calls (which I wouldn't expect it to, but DPC++ apparently allows devirtualized unqualified calls in device functions). A [SYCL WG issue](https://github.com/KhronosGroup/SYCL-Docs/issues/565) already exists to clarify the specification. I expect that issue to eventually be resolved such that qualified calls are allowed and unqualified ones are not (regardless of whether they can be devirtualized; devirtualization is not specified by the C++ standard and any reliance on it would be non-portable. Perhaps we'll want to allow such devirtualized calls in the future; if so, we should emit a non-portable warning for such uses if that support is added). So, I think we should permit the `sycl_external` attribute to be present on declarations of virtual functions and, if a definition is present, emitted in device code (perhaps dependent on whether the function is also inline, but we'll deal with that separately). Since pure virtual functions can have definitions, this allowance should extend to them as well. https://github.com/llvm/llvm-project/pull/140282 _______________________________________________ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits