@@ -154,6 +154,8 @@ runKernelWithArg(KernelType KernelName, ArgType Arg) {
154
154
// The pure virtual class aimed to store lambda/functors of any type.
155
155
class HostKernelBase {
156
156
public:
157
+ // NOTE: InstatitateKernelOnHost() should not be called.
158
+ virtual void InstatitateKernelOnHost () = 0;
157
159
// Return pointer to the lambda object.
158
160
// Used to extract captured variables.
159
161
virtual char *getPtr () = 0;
@@ -172,6 +174,50 @@ class HostKernel : public HostKernelBase {
172
174
public:
173
175
HostKernel (KernelType Kernel) : MKernel(Kernel) {}
174
176
177
+ // This function is needed for host-side compilation to keep kernels
178
+ // instantitated. This is important for debuggers to be able to associate
179
+ // kernel code instructions with source code lines.
180
+ // NOTE: InstatitateKernelOnHost() should not be called.
181
+ void InstatitateKernelOnHost () override {
182
+ if constexpr (std::is_same_v<KernelArgType, void >) {
183
+ runKernelWithoutArg (MKernel);
184
+ } else if constexpr (std::is_same_v<KernelArgType, sycl::id<Dims>>) {
185
+ sycl::id ID = InitializedVal<Dims, id>::template get<0 >();
186
+ runKernelWithArg<const KernelArgType &>(MKernel, ID);
187
+ } else if constexpr (std::is_same_v<KernelArgType, item<Dims, true >> ||
188
+ std::is_same_v<KernelArgType, item<Dims, false >>) {
189
+ constexpr bool HasOffset =
190
+ std::is_same_v<KernelArgType, item<Dims, true >>;
191
+ KernelArgType Item = IDBuilder::createItem<Dims, HasOffset>(
192
+ InitializedVal<Dims, range>::template get<1 >(),
193
+ InitializedVal<Dims, id>::template get<0 >());
194
+ runKernelWithArg<KernelArgType>(MKernel, Item);
195
+ } else if constexpr (std::is_same_v<KernelArgType, nd_item<Dims>>) {
196
+ sycl::range<Dims> Range = InitializedVal<Dims, range>::template get<1 >();
197
+ sycl::id<Dims> ID = InitializedVal<Dims, id>::template get<0 >();
198
+ sycl::group<Dims> Group =
199
+ IDBuilder::createGroup<Dims>(Range, Range, Range, ID);
200
+ sycl::item<Dims, true > GlobalItem =
201
+ IDBuilder::createItem<Dims, true >(Range, ID, ID);
202
+ sycl::item<Dims, false > LocalItem =
203
+ IDBuilder::createItem<Dims, false >(Range, ID);
204
+ KernelArgType NDItem =
205
+ IDBuilder::createNDItem<Dims>(GlobalItem, LocalItem, Group);
206
+ runKernelWithArg<const KernelArgType>(MKernel, NDItem);
207
+ } else if constexpr (std::is_same_v<KernelArgType, sycl::group<Dims>>) {
208
+ sycl::range<Dims> Range = InitializedVal<Dims, range>::template get<1 >();
209
+ sycl::id<Dims> ID = InitializedVal<Dims, id>::template get<0 >();
210
+ KernelArgType Group =
211
+ IDBuilder::createGroup<Dims>(Range, Range, Range, ID);
212
+ runKernelWithArg<KernelArgType>(MKernel, Group);
213
+ } else {
214
+ // Assume that anything else can be default-constructed. If not, this
215
+ // should fail to compile and the implementor should implement a generic
216
+ // case for the new argument type.
217
+ runKernelWithArg<KernelArgType>(MKernel, KernelArgType{});
218
+ }
219
+ }
220
+
175
221
char *getPtr () override { return reinterpret_cast <char *>(&MKernel); }
176
222
177
223
~HostKernel () = default ;
0 commit comments