Skip to content

Commit a86f6e4

Browse files
committed
[SYCL] Update calls_indirectly property
This allows calls_indirectly property to handle all passed template arguments, but not the only first one. Also applying some minor changes to the spec. Spec & Design: intel#10540
1 parent af8361c commit a86f6e4

File tree

3 files changed

+57
-29
lines changed

3 files changed

+57
-29
lines changed

sycl/include/sycl/ext/oneapi/experimental/virtual_functions.hpp

Lines changed: 49 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -19,16 +19,16 @@ template <typename Set>
1919
inline constexpr indirectly_callable_key::value_t<Set> indirectly_callable_in;
2020

2121
struct calls_indirectly_key {
22-
template <typename First = void, typename... SetIds>
22+
template <typename... SetIds>
2323
using value_t =
2424
sycl::ext::oneapi::experimental::property_value<calls_indirectly_key,
25-
First, SetIds...>;
25+
SetIds...>;
2626
};
2727

2828
inline constexpr calls_indirectly_key::value_t<void> assume_indirect_calls;
2929

30-
template <typename First, typename... Rest>
31-
inline constexpr calls_indirectly_key::value_t<First, Rest...>
30+
template <typename... SetIds>
31+
inline constexpr calls_indirectly_key::value_t<SetIds...>
3232
assume_indirect_calls_to;
3333

3434
template <> struct is_property_key<indirectly_callable_key> : std::true_type {};
@@ -60,16 +60,54 @@ struct PropertyMetaInfo<indirectly_callable_key::value_t<Set>> {
6060
#endif
6161
};
6262

63-
template <typename First, typename... Rest>
64-
struct PropertyMetaInfo<calls_indirectly_key::value_t<First, Rest...>> {
65-
static_assert(
66-
sizeof...(Rest) == 0,
67-
"assume_indirect_calls_to property only supports a single set for now");
63+
// Helper to concatenate several lists of characters into a single string.
64+
// Lists are separated from each other with comma within the resulting string.
65+
template <typename List, typename... Rest> struct ConcatenateCharsToStr;
66+
67+
// Specialization for a single list
68+
template <char... Chars> struct ConcatenateCharsToStr<CharList<Chars...>> {
69+
static constexpr char value[] = {Chars..., '\0'};
70+
};
71+
72+
// Specialization for two lists
73+
template <char... Chars, char... CharsToAppend>
74+
struct ConcatenateCharsToStr<CharList<Chars...>, CharList<CharsToAppend...>>
75+
: ConcatenateCharsToStr<CharList<Chars..., ',', CharsToAppend...>> {};
76+
77+
// Specialization for the case when there are more than two lists
78+
template <char... Chars, char... CharsToAppend, typename... Rest>
79+
struct ConcatenateCharsToStr<CharList<Chars...>, CharList<CharsToAppend...>,
80+
Rest...>
81+
: ConcatenateCharsToStr<CharList<Chars..., ',', CharsToAppend...>,
82+
Rest...> {};
83+
84+
// Helper to convert type T to a list of characters representing the type (its
85+
// mangled name).
86+
template <typename T, size_t... Indices> struct StableNameToCharsHelper {
87+
#ifdef __SYCL_DEVICE_ONLY__
88+
using chars = CharList<__builtin_sycl_unique_stable_name(T)[Indices]...>;
89+
#else
90+
using chars = CharList<>;
91+
#endif
92+
};
93+
94+
// Wrapper helper for the struct above
95+
template <typename T, typename Sequence> struct StableNameToChars;
96+
97+
// Specialization of that wrapper helper which accepts sequence of integers
98+
template <typename T, size_t... Indices>
99+
struct StableNameToChars<T, std::integer_sequence<size_t, Indices...>>
100+
: StableNameToCharsHelper<T, Indices...> {};
101+
102+
template <typename... SetIds>
103+
struct PropertyMetaInfo<calls_indirectly_key::value_t<SetIds...>> {
68104
static constexpr const char *name = "calls-indirectly";
69105
static constexpr const char *value =
70106
#ifdef __SYCL_DEVICE_ONLY__
71-
// FIXME: we should handle Rest... here as well
72-
__builtin_sycl_unique_stable_name(First);
107+
ConcatenateCharsToStr<typename StableNameToChars<
108+
SetIds,
109+
std::make_index_sequence<__builtin_strlen(
110+
__builtin_sycl_unique_stable_name(SetIds))>>::chars...>::value;
73111
#else
74112
"";
75113
#endif

sycl/test/virtual-functions/calls-indirectly-ir.cpp

Lines changed: 5 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -11,16 +11,12 @@
1111
// CHECK: define {{.*}}KInt{{.*}} #[[#ATTR_SET_INT:]]
1212
// CHECK: define {{.*}}KVoid{{.*}} #[[#ATTR_SET_DEFAULT]]
1313
// CHECK: define {{.*}}KUserDefined{{.*}} #[[#ATTR_SET_USER_DEFINED:]]
14-
// TODO: update the check below
15-
// As of now calls_indirectly_property takes into account only the first
16-
// template argument ignoring the rest. This will be fixed in a follow-up
17-
// patches and the test should be updated to reflect that, because current
18-
// behavior is not correct.
19-
// CHECK-disabled: define {{.*}}KMultiple{{.*}} #[[#ATTR_SET_INT]]
14+
// CHECK: define {{.*}}KMultiple{{.*}} #[[#ATTR_SET_MULTIPLE:]]
2015
//
2116
// CHECK-DAG: attributes #[[#ATTR_SET_DEFAULT]] {{.*}} "calls-indirectly"="_ZTSv"
2217
// CHECK-DAG: attributes #[[#ATTR_SET_INT]] {{.*}} "calls-indirectly"="_ZTSi"
2318
// CHECK-DAG: attributes #[[#ATTR_SET_USER_DEFINED]] {{.*}} "calls-indirectly"="_ZTS12user_defined"
19+
// CHECK-DAG: attributes #[[#ATTR_SET_MULTIPLE]] {{.*}} "calls-indirectly"="_ZTSi,_ZTS12user_defined"
2420

2521
#include <sycl/sycl.hpp>
2622

@@ -45,17 +41,14 @@ int main() {
4541
oneapi::properties props_void{oneapi::assume_indirect_calls_to<void>};
4642
oneapi::properties props_user_defined{
4743
oneapi::assume_indirect_calls_to<user_defined>};
48-
// assume_indirect_calls_to is currently limited to a single set, so this test
49-
// is disabled.
50-
// FIXME: re-enable once the restriction is lifted.
51-
// oneapi::properties props_multiple{
52-
// oneapi::assume_indirect_calls_to<int, user_defined>};
44+
oneapi::properties props_multiple{
45+
oneapi::assume_indirect_calls_to<int, user_defined>};
5346

5447
q.single_task<KEmpty>(props_empty, [=]() {});
5548
q.single_task<KInt>(props_int, [=]() {});
5649
q.single_task<KVoid>(props_void, [=]() {});
5750
q.single_task<KUserDefined>(props_user_defined, [=]() {});
58-
// q.single_task<KMultiple>(props_multiple, [=]() {});
51+
q.single_task<KMultiple>(props_multiple, [=]() {});
5952

6053
return 0;
6154
}

sycl/test/virtual-functions/properties-positive.cpp

Lines changed: 3 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -52,17 +52,14 @@ int main() {
5252
oneapi::properties props_void{oneapi::assume_indirect_calls_to<void>};
5353
oneapi::properties props_int{oneapi::assume_indirect_calls_to<int>};
5454
oneapi::properties props_base{oneapi::assume_indirect_calls_to<Base>};
55-
// assume_indirect_calls_to is currently limited to a single set, so this test
56-
// is disabled.
57-
// FIXME: re-enable once the restriction is lifted.
58-
// oneapi::properties props_multiple{
59-
// oneapi::assume_indirect_calls_to<int, Base>};
55+
oneapi::properties props_multiple{
56+
oneapi::assume_indirect_calls_to<int, Base>};
6057

6158
q.single_task(props_empty, [=]() {});
6259
q.single_task(props_void, [=]() {});
6360
q.single_task(props_int, [=]() {});
6461
q.single_task(props_base, [=]() {});
65-
// q.single_task(props_multiple, [=]() {});
62+
q.single_task(props_multiple, [=]() {});
6663

6764
return 0;
6865
}

0 commit comments

Comments
 (0)