• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

IntelPython / dpctl / 42864887893

10 Nov 2026 05:25PM UTC coverage: 75.283% (+0.1%) from 75.173%
42864887893

Pull #2384

github

web-flow
Merge 596211a14 into 4db44191f
Pull Request #2384: Enable AdaptiveCpp builds

1077 of 1508 branches covered (71.42%)

Branch coverage included in aggregate %.

48 of 67 new or added lines in 15 files covered. (71.64%)

2 existing lines in 2 files now uncovered.

4177 of 5471 relevant lines covered (76.35%)

289.29 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

86.89
/libsyclinterface/source/dpctl_sycl_queue_interface.cpp
1
//===----- dpctl_sycl_queue_interface.cpp - Implements C API for sycl::queue =//
2
//
3
//                      Data Parallel Control (dpctl)
4
//
5
// Copyright 2020 Intel Corporation
6
//
7
// Licensed under the Apache License, Version 2.0 (the "License");
8
// you may not use this file except in compliance with the License.
9
// You may obtain a copy of the License at
10
//
11
//    http://www.apache.org/licenses/LICENSE-2.0
12
//
13
// Unless required by applicable law or agreed to in writing, software
14
// distributed under the License is distributed on an "AS IS" BASIS,
15
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16
// See the License for the specific language governing permissions and
17
// limitations under the License.
18
//
19
//===----------------------------------------------------------------------===//
20
///
21
/// \file
22
/// This file implements the data types and functions declared in
23
/// dpctl_sycl_queue_interface.h.
24
///
25
//===----------------------------------------------------------------------===//
26

27
#include "dpctl_sycl_queue_interface.h"
28
#include "Config/dpctl_config.h"
29
#include "dpctl_error_handlers.h"
30
#include "dpctl_sycl_context_interface.h"
31
#include "dpctl_sycl_device_interface.h"
32
#include "dpctl_sycl_device_manager.h"
33
#include "dpctl_sycl_type_casters.hpp"
34

35
#include <stddef.h>
36
#include <stdint.h>
37

38
#include <cstdint>
39
#include <exception>
40
#include <optional>
41
#include <sstream>
42
#include <stdexcept>
43
#include <sycl/sycl.hpp> /* SYCL headers   */
44
#include <utility>
45
#include <vector>
46

47
#if defined(SYCL_EXT_ONEAPI_WORK_GROUP_MEMORY) ||                              \
48
    defined(SYCL_EXT_ONEAPI_RAW_KERNEL_ARG)
49
#include "dpctl_sycl_extension_interface.h"
50
#endif
51

52
using namespace sycl;
53

54
#ifndef __ADAPTIVECPP__
55
#define SET_LOCAL_ACCESSOR_ARG(CGH, NDIM, ARGTY, R, IDX)                       \
56
    do {                                                                       \
31 ✔
57
        switch ((ARGTY)) {                                                     \
31 ✔
58
        case DPCTL_INT8_T:                                                     \
3 ✔
59
        {                                                                      \
3 ✔
60
            auto la = local_accessor<std::int8_t, NDIM>(R, CGH);               \
3 ✔
61
            CGH.set_arg(IDX, la);                                              \
3 ✔
62
            return true;                                                       \
3 ✔
63
        }                                                                      \
×
64
        case DPCTL_UINT8_T:                                                    \
3 ✔
65
        {                                                                      \
3 ✔
66
            auto la = local_accessor<std::uint8_t, NDIM>(R, CGH);              \
3 ✔
67
            CGH.set_arg(IDX, la);                                              \
3 ✔
68
            return true;                                                       \
3 ✔
69
        }                                                                      \
×
70
        case DPCTL_INT16_T:                                                    \
3 ✔
71
        {                                                                      \
3 ✔
72
            auto la = local_accessor<std::int16_t, NDIM>(R, CGH);              \
3 ✔
73
            CGH.set_arg(IDX, la);                                              \
3 ✔
74
            return true;                                                       \
3 ✔
75
        }                                                                      \
×
76
        case DPCTL_UINT16_T:                                                   \
3 ✔
77
        {                                                                      \
3 ✔
78
            auto la = local_accessor<std::uint16_t, NDIM>(R, CGH);             \
3 ✔
79
            CGH.set_arg(IDX, la);                                              \
3 ✔
80
            return true;                                                       \
3 ✔
81
        }                                                                      \
×
82
        case DPCTL_INT32_T:                                                    \
3 ✔
83
        {                                                                      \
3 ✔
84
            auto la = local_accessor<std::int32_t, NDIM>(R, CGH);              \
3 ✔
85
            CGH.set_arg(IDX, la);                                              \
3 ✔
86
            return true;                                                       \
3 ✔
87
        }                                                                      \
×
88
        case DPCTL_UINT32_T:                                                   \
3 ✔
89
        {                                                                      \
3 ✔
90
            auto la = local_accessor<std::uint32_t, NDIM>(R, CGH);             \
3 ✔
91
            CGH.set_arg(IDX, la);                                              \
3 ✔
92
            return true;                                                       \
3 ✔
93
        }                                                                      \
×
94
        case DPCTL_INT64_T:                                                    \
3 ✔
95
        {                                                                      \
3 ✔
96
            auto la = local_accessor<std::int64_t, NDIM>(R, CGH);              \
3 ✔
97
            CGH.set_arg(IDX, la);                                              \
3 ✔
98
            return true;                                                       \
3 ✔
99
        }                                                                      \
×
100
        case DPCTL_UINT64_T:                                                   \
3 ✔
101
        {                                                                      \
3 ✔
102
            auto la = local_accessor<std::uint64_t, NDIM>(R, CGH);             \
3 ✔
103
            CGH.set_arg(IDX, la);                                              \
3 ✔
104
            return true;                                                       \
3 ✔
105
        }                                                                      \
×
106
        case DPCTL_FLOAT32_T:                                                  \
3 ✔
107
        {                                                                      \
3 ✔
108
            auto la = local_accessor<float, NDIM>(R, CGH);                     \
3 ✔
109
            CGH.set_arg(IDX, la);                                              \
3 ✔
110
            return true;                                                       \
3 ✔
111
        }                                                                      \
×
112
        case DPCTL_FLOAT64_T:                                                  \
3 ✔
113
        {                                                                      \
3 ✔
114
            auto la = local_accessor<double, NDIM>(R, CGH);                    \
3 ✔
115
            CGH.set_arg(IDX, la);                                              \
3 ✔
116
            return true;                                                       \
3 ✔
117
        }                                                                      \
×
118
        default:                                                               \
1 ✔
119
            error_handler("Kernel argument could not be created.", __FILE__,   \
1 ✔
120
                          __func__, __LINE__, error_level::error);             \
1 ✔
121
            return false;                                                      \
1 ✔
122
        }                                                                      \
31 ✔
123
    } while (0);
31 !
124
#endif
125

126
namespace
127
{
128
#ifndef __ADAPTIVECPP__
129
static_assert(__SYCL_COMPILER_VERSION >= __SYCL_COMPILER_VERSION_REQUIRED,
130
              "The compiler does not meet minimum version requirement");
131
#endif
132

133
using namespace dpctl::syclinterface;
134

135
typedef struct complex
136
{
137
    std::uint64_t real;
138
    std::uint64_t imag;
139
} complexNumber;
140

141
#ifndef __ADAPTIVECPP__
142

143
void set_dependent_events(handler &cgh,
144
                          __dpctl_keep const DPCTLSyclEventRef *DepEvents,
145
                          size_t NDepEvents)
146
{
176 ✔
147
    for (auto i = 0ul; i < NDepEvents; ++i) {
332 ✔
148
        auto ei = unwrap<event>(DepEvents[i]);
156 ✔
149
        if (ei)
156 !
150
            cgh.depends_on(*ei);
156 ✔
151
    }
156 ✔
152
}
176 ✔
153

154
bool set_local_accessor_arg(handler &cgh,
155
                            size_t idx,
156
                            const MDLocalAccessor *mdstruct)
157
{
31 ✔
158
    switch (mdstruct->ndim) {
31 ✔
159
    case 1:
11 ✔
160
    {
11 ✔
161
        auto r = range<1>(mdstruct->dim0);
11 ✔
162
        SET_LOCAL_ACCESSOR_ARG(cgh, 1, mdstruct->dpctl_type_id, r, idx);
11 ✔
163
    }
×
164
    case 2:
10 ✔
165
    {
10 ✔
166
        auto r = range<2>(mdstruct->dim0, mdstruct->dim1);
10 ✔
167
        SET_LOCAL_ACCESSOR_ARG(cgh, 2, mdstruct->dpctl_type_id, r, idx);
10 ✔
168
    }
×
169
    case 3:
10 ✔
170
    {
10 ✔
171
        auto r = range<3>(mdstruct->dim0, mdstruct->dim1, mdstruct->dim2);
10 ✔
172
        SET_LOCAL_ACCESSOR_ARG(cgh, 3, mdstruct->dpctl_type_id, r, idx);
10 ✔
173
    }
×
174
    default:
×
175
        return false;
×
176
    }
31 ✔
177
}
31 ✔
178
/*!
179
 * @brief Set the kernel arg object
180
 *
181
 * @param cgh   SYCL command group handler using which a kernel is going to
182
 * be submitted.
183
 * @param idx   The position of the argument in the list of arguments passed
184
 * to a kernel.
185
 * @param Arg   A void* representing a kernel argument.
186
 * @param Argty A typeid specifying the C++ type of the Arg parameter.
187
 */
188
bool set_kernel_arg(handler &cgh,
189
                    size_t idx,
190
                    __dpctl_keep void *Arg,
191
                    DPCTLKernelArgType ArgTy)
192
{
498 ✔
193
    bool arg_set = true;
498 ✔
194

195
    switch (ArgTy) {
498 ✔
196
    case DPCTL_INT8_T:
3 ✔
197
        cgh.set_arg(idx, *(std::int8_t *)Arg);
3 ✔
198
        break;
3 ✔
199
    case DPCTL_UINT8_T:
3 ✔
200
        cgh.set_arg(idx, *(std::uint8_t *)Arg);
3 ✔
201
        break;
3 ✔
202
    case DPCTL_INT16_T:
9 ✔
203
        cgh.set_arg(idx, *(std::int16_t *)Arg);
9 ✔
204
        break;
9 ✔
205
    case DPCTL_UINT16_T:
3 ✔
206
        cgh.set_arg(idx, *(std::uint16_t *)Arg);
3 ✔
207
        break;
3 ✔
208
    case DPCTL_INT32_T:
9 ✔
209
        cgh.set_arg(idx, *(std::int32_t *)Arg);
9 ✔
210
        break;
9 ✔
211
    case DPCTL_UINT32_T:
11 ✔
212
        cgh.set_arg(idx, *(std::uint32_t *)Arg);
11 ✔
213
        break;
11 ✔
214
    case DPCTL_INT64_T:
9 ✔
215
        cgh.set_arg(idx, *(std::int64_t *)Arg);
9 ✔
216
        break;
9 ✔
217
    case DPCTL_UINT64_T:
14 ✔
218
        cgh.set_arg(idx, *(std::uint64_t *)Arg);
14 ✔
219
        break;
14 ✔
220
    case DPCTL_FLOAT32_T:
9 ✔
221
        cgh.set_arg(idx, *(float *)Arg);
9 ✔
222
        break;
9 ✔
223
    case DPCTL_FLOAT64_T:
9 ✔
224
        cgh.set_arg(idx, *(double *)Arg);
9 ✔
225
        break;
9 ✔
226
    case DPCTL_VOID_PTR:
327 ✔
227
        cgh.set_arg(idx, Arg);
327 ✔
228
        break;
327 ✔
229
    case DPCTL_LOCAL_ACCESSOR:
31 ✔
230
        arg_set = set_local_accessor_arg(cgh, idx, (MDLocalAccessor *)Arg);
31 ✔
231
        break;
31 ✔
232
#ifdef SYCL_EXT_ONEAPI_WORK_GROUP_MEMORY
×
233
    case DPCTL_WORK_GROUP_MEMORY:
31 ✔
234
    {
31 ✔
235
        auto ref = static_cast<DPCTLSyclWorkGroupMemoryRef>(Arg);
31 ✔
236
        RawWorkGroupMemory *raw_mem = unwrap<RawWorkGroupMemory>(ref);
31 ✔
237
        size_t num_bytes = raw_mem->nbytes;
31 ✔
238
        sycl::ext::oneapi::experimental::work_group_memory<char[]> mem{
31 ✔
239
            num_bytes, cgh};
31 ✔
240
        cgh.set_arg(idx, mem);
31 ✔
241
        break;
31 ✔
242
    }
×
243
#endif
×
244
#ifdef SYCL_EXT_ONEAPI_RAW_KERNEL_ARG
×
245
    case DPCTL_RAW_KERNEL_ARG:
30 ✔
246
    {
30 ✔
247
        auto ref = static_cast<DPCTLSyclRawKernelArgRef>(Arg);
30 ✔
248
        std::vector<unsigned char> *raw_arg =
30 ✔
249
            unwrap<std::vector<unsigned char>>(ref);
30 ✔
250
        void *bytes = raw_arg->data();
30 ✔
251
        size_t count = raw_arg->size();
30 ✔
252
        sycl::ext::oneapi::experimental::raw_kernel_arg arg{bytes, count};
30 ✔
253
        cgh.set_arg(idx, arg);
30 ✔
254
        break;
30 ✔
255
    }
×
256
#endif
×
257
    default:
×
258
        arg_set = false;
×
259
        break;
×
260
    }
498 ✔
261
    return arg_set;
498 ✔
262
}
498 ✔
263

264
void set_kernel_args(handler &cgh,
265
                     __dpctl_keep void **Args,
266
                     __dpctl_keep const DPCTLKernelArgType *ArgTypes,
267
                     size_t NArgs)
268
{
176 ✔
269
    for (auto i = 0ul; i < NArgs; ++i) {
673 ✔
270
        if (!set_kernel_arg(cgh, i, Args[i], ArgTypes[i])) {
498 ✔
271
            error_handler("Kernel argument could not be created.", __FILE__,
1 ✔
272
                          __func__, __LINE__);
1 ✔
273
            throw std::invalid_argument(
1 ✔
274
                "Kernel argument could not be created.");
1 ✔
275
        }
1 ✔
276
    }
498 ✔
277
}
176 ✔
278

279
#endif /* #ifndef __ADAPTIVECPP__ */
280

281
std::unique_ptr<property_list> create_property_list(int properties)
282
{
1,864 ✔
283
    std::unique_ptr<property_list> propList;
1,864 ✔
284
    int _prop = properties;
1,864 ✔
285
    if (_prop & DPCTL_ENABLE_PROFILING) {
1,864 ✔
286
        _prop = _prop ^ DPCTL_ENABLE_PROFILING;
86 ✔
287
        if (_prop & DPCTL_IN_ORDER) {
86 ✔
288
            _prop = _prop ^ DPCTL_IN_ORDER;
36 ✔
289
            propList = std::make_unique<property_list>(
36 ✔
290
                sycl::property::queue::enable_profiling(),
36 ✔
291
                sycl::property::queue::in_order());
36 ✔
292
        }
36 ✔
293
        else {
50 ✔
294
            propList = std::make_unique<property_list>(
50 ✔
295
                sycl::property::queue::enable_profiling());
50 ✔
296
        }
50 ✔
297
    }
86 ✔
298
    else if (_prop & DPCTL_IN_ORDER) {
1,778 ✔
299
        _prop = _prop ^ DPCTL_IN_ORDER;
564 ✔
300
        propList =
564 ✔
301
            std::make_unique<property_list>(sycl::property::queue::in_order());
564 ✔
302
    }
564 ✔
303
    else {
1,214 ✔
304
        propList = std::make_unique<property_list>();
1,214 ✔
305
    }
1,214 ✔
306

307
    if (_prop) {
1,864 ✔
308
        std::stringstream ss;
1 ✔
309
        ss << "Invalid queue property argument (" << std::hex << properties
1 ✔
310
           << "), interpreted as (" << (properties ^ _prop) << ").";
1 ✔
311
        error_handler(ss.str(), __FILE__, __func__, __LINE__);
1 ✔
312
    }
1 ✔
313
    return propList;
1,864 ✔
314
}
1,864 ✔
315

316
__dpctl_give DPCTLSyclQueueRef
317
getQueueImpl(__dpctl_keep DPCTLSyclContextRef cRef,
318
             __dpctl_keep DPCTLSyclDeviceRef dRef,
319
             error_handler_callback *handler,
320
             int properties)
321
{
211 ✔
322
    DPCTLSyclQueueRef qRef = nullptr;
211 ✔
323
    qRef = DPCTLQueue_Create(cRef, dRef, handler, properties);
211 ✔
324
    return qRef;
211 ✔
325
}
211 ✔
326

327
} /* end of anonymous namespace */
328

329
DPCTL_API
330
__dpctl_give DPCTLSyclQueueRef
331
DPCTLQueue_Create(__dpctl_keep const DPCTLSyclContextRef CRef,
332
                  __dpctl_keep const DPCTLSyclDeviceRef DRef,
333
                  error_handler_callback *handler,
334
                  int properties)
335
{
1,866 ✔
336
    DPCTLSyclQueueRef q = nullptr;
1,866 ✔
337
    auto dev = unwrap<device>(DRef);
1,866 ✔
338
    auto ctx = unwrap<context>(CRef);
1,866 ✔
339

340
    if (!(dev && ctx)) {
1,866 ✔
341
        error_handler("Cannot create queue from DPCTLSyclContextRef and "
2 ✔
342
                      "DPCTLSyclDeviceRef as input is a nullptr.",
2 ✔
343
                      __FILE__, __func__, __LINE__);
2 ✔
344
        return q;
2 ✔
345
    }
2 ✔
346
    auto propList = create_property_list(properties);
1,864 ✔
347

348
    if (handler) {
1,864 ✔
349
        try {
68 ✔
350
            auto Queue = new queue(*ctx, *dev, DPCTL_AsyncErrorHandler(handler),
68 ✔
351
                                   *propList);
68 ✔
352
            q = wrap<queue>(Queue);
68 ✔
353
        } catch (std::exception const &e) {
68 ✔
354
            error_handler(e, __FILE__, __func__, __LINE__);
×
355
        }
×
356
    }
68 ✔
357
    else {
1,796 ✔
358
        try {
1,796 ✔
359
#ifdef __ADAPTIVECPP__
360
            // a queue with no handler of its own inherits the default handler
361
            // of the AdaptiveCpp context, which calls std::terminate
362
            auto Queue = new queue(*ctx, *dev, DPCTL_AsyncErrorHandler(nullptr),
363
                                   *propList);
364
#else
365
            auto Queue = new queue(*ctx, *dev, *propList);
1,796 ✔
366
#endif
1,796 ✔
367
            q = wrap<queue>(Queue);
1,796 ✔
368
        } catch (std::exception const &e) {
1,796 ✔
369
            error_handler(e, __FILE__, __func__, __LINE__);
1 ✔
370
        }
1 ✔
371
    }
1,796 ✔
372

373
    return q;
1,864 ✔
374
}
1,864 ✔
375

376
__dpctl_give DPCTLSyclQueueRef
377
DPCTLQueue_CreateForDevice(__dpctl_keep const DPCTLSyclDeviceRef DRef,
378
                           error_handler_callback *handler,
379
                           int properties)
380
{
493 ✔
381
    DPCTLSyclContextRef CRef = nullptr;
493 ✔
382
    DPCTLSyclQueueRef QRef = nullptr;
493 ✔
383
    auto Device = unwrap<device>(DRef);
493 ✔
384

385
    if (!Device) {
493 ✔
386
        error_handler("Cannot create queue from NULL device reference.",
282 ✔
387
                      __FILE__, __func__, __LINE__);
282 ✔
388
        return QRef;
282 ✔
389
    }
282 ✔
390
    // Check if a cached default context exists for the device.
391
    CRef = DPCTLDeviceMgr_GetCachedContext(DRef);
211 ✔
392
    // If a cached default context was found, that context will be used to use
393
    // create the new queue. When a default cached context was not found, as
394
    // will be the case for non-root devices, i.e., sub-devices, a new context
395
    // will be allocated. Note that any newly allocated context is not cached.
396
    if (!CRef) {
211 !
397
        context *ContextPtr = nullptr;
×
398
        try {
×
399
            ContextPtr = new context(*Device);
×
400
            CRef = wrap<context>(ContextPtr);
×
401
        } catch (std::exception const &e) {
×
402
            error_handler(e, __FILE__, __func__, __LINE__);
×
403
            delete ContextPtr;
×
404
            return QRef;
×
405
        }
×
406
    }
×
407
    // At this point we have a valid context and the queue can be allocated.
408
    QRef = getQueueImpl(CRef, DRef, handler, properties);
211 ✔
409
    // Free the context
410
    DPCTLContext_Delete(CRef);
211 ✔
411
    return QRef;
211 ✔
412
}
211 ✔
413

414
/*!
415
 * Delete the passed in pointer after verifying it points to a sycl::queue.
416
 */
417
void DPCTLQueue_Delete(__dpctl_take DPCTLSyclQueueRef QRef)
418
{
2,254 ✔
419
    delete unwrap<queue>(QRef);
2,254 ✔
420
}
2,254 ✔
421

422
/*!
423
 * Make copy of sycl::queue referenced by passed pointer
424
 */
425
__dpctl_give DPCTLSyclQueueRef
426
DPCTLQueue_Copy(__dpctl_keep const DPCTLSyclQueueRef QRef)
427
{
116 ✔
428
    auto Queue = unwrap<queue>(QRef);
116 ✔
429
    if (Queue) {
116 ✔
430
        try {
115 ✔
431
            auto CopiedQueue = new queue(*Queue);
115 ✔
432
            return wrap<queue>(CopiedQueue);
115 ✔
433
        } catch (std::exception const &e) {
115 ✔
434
            error_handler(e, __FILE__, __func__, __LINE__);
×
435
            return nullptr;
×
436
        }
×
437
    }
115 ✔
438
    else {
1 ✔
439
        error_handler("Cannot copy DPCTLSyclQueueRef as input is a nullptr",
1 ✔
440
                      __FILE__, __func__, __LINE__);
1 ✔
441
        return nullptr;
1 ✔
442
    }
1 ✔
443
}
116 ✔
444

445
bool DPCTLQueue_AreEq(__dpctl_keep const DPCTLSyclQueueRef QRef1,
446
                      __dpctl_keep const DPCTLSyclQueueRef QRef2)
447
{
13 ✔
448
    if (!(QRef1 && QRef2)) {
13 ✔
449
        error_handler("DPCTLSyclQueueRefs are nullptr.", __FILE__, __func__,
2 ✔
450
                      __LINE__);
2 ✔
451
        return false;
2 ✔
452
    }
2 ✔
453
    return (*unwrap<queue>(QRef1) == *unwrap<queue>(QRef2));
11 ✔
454
}
13 ✔
455

456
DPCTLSyclBackendType DPCTLQueue_GetBackend(__dpctl_keep DPCTLSyclQueueRef QRef)
457
{
10 ✔
458
    auto Q = unwrap<queue>(QRef);
10 ✔
459
    if (Q) {
10 ✔
460
        try {
9 ✔
461
            auto C = Q->get_context();
9 ✔
462
            return DPCTLContext_GetBackend(wrap<context>(&C));
9 ✔
463
        } catch (std::exception const &e) {
9 ✔
464
            error_handler(e, __FILE__, __func__, __LINE__);
×
465
            return DPCTL_UNKNOWN_BACKEND;
×
466
        }
×
467
    }
9 ✔
468
    else
1 ✔
469
        return DPCTL_UNKNOWN_BACKEND;
1 ✔
470
}
10 ✔
471

472
__dpctl_give DPCTLSyclDeviceRef
473
DPCTLQueue_GetDevice(__dpctl_keep const DPCTLSyclQueueRef QRef)
474
{
74 ✔
475
    DPCTLSyclDeviceRef DRef = nullptr;
74 ✔
476
    auto Q = unwrap<queue>(QRef);
74 ✔
477
    if (Q) {
74 ✔
478
        try {
73 ✔
479
            auto Device = new device(Q->get_device());
73 ✔
480
            DRef = wrap<device>(Device);
73 ✔
481
        } catch (std::exception const &e) {
73 ✔
482
            error_handler(e, __FILE__, __func__, __LINE__);
×
483
        }
×
484
    }
73 ✔
485
    else {
1 ✔
486
        error_handler("Could not get the device for this queue.", __FILE__,
1 ✔
487
                      __func__, __LINE__);
1 ✔
488
    }
1 ✔
489
    return DRef;
74 ✔
490
}
74 ✔
491

492
__dpctl_give DPCTLSyclContextRef
493
DPCTLQueue_GetContext(__dpctl_keep const DPCTLSyclQueueRef QRef)
494
{
142 ✔
495
    auto Q = unwrap<queue>(QRef);
142 ✔
496
    DPCTLSyclContextRef CRef = nullptr;
142 ✔
497
    if (Q)
142 ✔
498
        CRef = wrap<context>(new context(Q->get_context()));
132 ✔
499
    else {
10 ✔
500
        error_handler("Could not get the context for this queue.", __FILE__,
10 ✔
501
                      __func__, __LINE__);
10 ✔
502
    }
10 ✔
503
    return CRef;
142 ✔
504
}
142 ✔
505

506
__dpctl_give DPCTLSyclEventRef
507
DPCTLQueue_SubmitRange(__dpctl_keep const DPCTLSyclKernelRef KRef,
508
                       __dpctl_keep const DPCTLSyclQueueRef QRef,
509
                       __dpctl_keep void **Args,
510
                       __dpctl_keep const DPCTLKernelArgType *ArgTypes,
511
                       size_t NArgs,
512
                       __dpctl_keep const size_t Range[3],
513
                       size_t NDims,
514
                       __dpctl_keep const DPCTLSyclEventRef *DepEvents,
515
                       size_t NDepEvents)
516
{
65 ✔
517
    if (!KRef) {
65 ✔
518
        error_handler("Cannot submit the kernel as the kernel is a nullptr.",
2 ✔
519
                      __FILE__, __func__, __LINE__, error_level::error);
2 ✔
520
        return nullptr;
2 ✔
521
    }
2 ✔
522
    if (!QRef) {
63 ✔
523
        error_handler("Cannot submit the kernel as the queue is a nullptr.",
1 ✔
524
                      __FILE__, __func__, __LINE__, error_level::error);
1 ✔
525
        return nullptr;
1 ✔
526
    }
1 ✔
527

528
#ifndef __ADAPTIVECPP__
62 ✔
529
    auto Kernel = unwrap<kernel>(KRef);
62 ✔
530
    auto Queue = unwrap<queue>(QRef);
62 ✔
531
    event e;
62 ✔
532

533
    try {
62 ✔
534
        switch (NDims) {
62 ✔
535
        case 1:
28 ✔
536
        {
28 ✔
537
            e = Queue->submit([&](handler &cgh) {
28 ✔
538
                set_dependent_events(cgh, DepEvents, NDepEvents);
28 ✔
539
                set_kernel_args(cgh, Args, ArgTypes, NArgs);
28 ✔
540
                cgh.parallel_for(range<1>{Range[0]}, *Kernel);
28 ✔
541
            });
28 ✔
542
            return wrap<event>(new event(std::move(e)));
28 ✔
543
        }
×
544
        case 2:
17 ✔
545
        {
17 ✔
546
            e = Queue->submit([&](handler &cgh) {
17 ✔
547
                set_dependent_events(cgh, DepEvents, NDepEvents);
17 ✔
548
                set_kernel_args(cgh, Args, ArgTypes, NArgs);
17 ✔
549
                cgh.parallel_for(range<2>{Range[0], Range[1]}, *Kernel);
17 ✔
550
            });
17 ✔
551
            return wrap<event>(new event(std::move(e)));
17 ✔
552
        }
×
553
        case 3:
17 ✔
554
        {
17 ✔
555
            e = Queue->submit([&](handler &cgh) {
17 ✔
556
                set_dependent_events(cgh, DepEvents, NDepEvents);
17 ✔
557
                set_kernel_args(cgh, Args, ArgTypes, NArgs);
17 ✔
558
                cgh.parallel_for(range<3>{Range[0], Range[1], Range[2]},
17 ✔
559
                                 *Kernel);
17 ✔
560
            });
17 ✔
561
            return wrap<event>(new event(std::move(e)));
17 ✔
562
        }
×
563
        default:
×
NEW
564
            error_handler("Range cannot be greater than three dimensions.",
×
565
                          __FILE__, __func__, __LINE__, error_level::error);
×
566
            return nullptr;
×
567
        }
62 ✔
568
    } catch (std::exception const &e) {
62 ✔
569
        error_handler(e, __FILE__, __func__, __LINE__, error_level::error);
×
570
        return nullptr;
×
571
    } catch (...) {
×
572
        error_handler("Unknown exception encountered", __FILE__, __func__,
×
573
                      __LINE__, error_level::error);
×
574
        return nullptr;
×
575
    }
×
576
#else
577
    error_handler("Dynamic OpenCL-style kernel execution is not supported in "
578
                  "AdaptiveCpp.",
579
                  __FILE__, __func__, __LINE__, error_level::error);
580
    return nullptr;
581
#endif
582
}
62 ✔
583

584
__dpctl_give DPCTLSyclEventRef
585
DPCTLQueue_SubmitNDRange(__dpctl_keep const DPCTLSyclKernelRef KRef,
586
                         __dpctl_keep const DPCTLSyclQueueRef QRef,
587
                         __dpctl_keep void **Args,
588
                         __dpctl_keep const DPCTLKernelArgType *ArgTypes,
589
                         size_t NArgs,
590
                         __dpctl_keep const size_t gRange[3],
591
                         __dpctl_keep const size_t lRange[3],
592
                         size_t NDims,
593
                         __dpctl_keep const DPCTLSyclEventRef *DepEvents,
594
                         size_t NDepEvents)
595
{
116 ✔
596
    if (!KRef) {
116 ✔
597
        error_handler("Cannot submit the kernel as the kernel is a nullptr.",
1 ✔
598
                      __FILE__, __func__, __LINE__, error_level::error);
1 ✔
599
        return nullptr;
1 ✔
600
    }
1 ✔
601
    if (!QRef) {
115 ✔
602
        error_handler("Cannot submit the kernel as the queue is a nullptr.",
1 ✔
603
                      __FILE__, __func__, __LINE__, error_level::error);
1 ✔
604
        return nullptr;
1 ✔
605
    }
1 ✔
606

607
#ifndef __ADAPTIVECPP__
114 ✔
608
    auto Kernel = unwrap<kernel>(KRef);
114 ✔
609
    auto Queue = unwrap<queue>(QRef);
114 ✔
610
    event e;
114 ✔
611

612
    try {
114 ✔
613
        switch (NDims) {
114 ✔
614
        case 1:
100 ✔
615
        {
100 ✔
616
            e = Queue->submit([&](handler &cgh) {
100 ✔
617
                set_dependent_events(cgh, DepEvents, NDepEvents);
100 ✔
618
                set_kernel_args(cgh, Args, ArgTypes, NArgs);
100 ✔
619
                cgh.parallel_for(nd_range<1>{{gRange[0]}, {lRange[0]}},
100 ✔
620
                                 *Kernel);
100 ✔
621
            });
100 ✔
622
            return wrap<event>(new event(std::move(e)));
100 ✔
623
        }
×
624
        case 2:
7 ✔
625
        {
7 ✔
626
            e = Queue->submit([&](handler &cgh) {
7 ✔
627
                set_dependent_events(cgh, DepEvents, NDepEvents);
7 ✔
628
                set_kernel_args(cgh, Args, ArgTypes, NArgs);
7 ✔
629
                cgh.parallel_for(
7 ✔
630
                    nd_range<2>{{gRange[0], gRange[1]}, {lRange[0], lRange[1]}},
7 ✔
631
                    *Kernel);
7 ✔
632
            });
7 ✔
633
            return wrap<event>(new event(std::move(e)));
7 ✔
634
        }
×
635
        case 3:
7 ✔
636
        {
7 ✔
637
            e = Queue->submit([&](handler &cgh) {
7 ✔
638
                set_dependent_events(cgh, DepEvents, NDepEvents);
7 ✔
639
                set_kernel_args(cgh, Args, ArgTypes, NArgs);
7 ✔
640
                cgh.parallel_for(nd_range<3>{{gRange[0], gRange[1], gRange[2]},
7 ✔
641
                                             {lRange[0], lRange[1], lRange[2]}},
7 ✔
642
                                 *Kernel);
7 ✔
643
            });
7 ✔
644
            return wrap<event>(new event(std::move(e)));
7 ✔
645
        }
×
646
        default:
×
NEW
647
            error_handler("Range cannot be greater than three dimensions.",
×
648
                          __FILE__, __func__, __LINE__, error_level::error);
×
649
            return nullptr;
×
650
        }
114 ✔
651
    } catch (std::exception const &e) {
114 ✔
652
        error_handler(e, __FILE__, __func__, __LINE__, error_level::error);
1 ✔
653
        return nullptr;
1 ✔
654
    } catch (...) {
1 ✔
655
        error_handler("Unknown exception encountered", __FILE__, __func__,
×
656
                      __LINE__, error_level::error);
×
657
        return nullptr;
×
658
    }
×
659
#else
660
    error_handler("Dynamic OpenCL-style kernel execution is not supported in "
661
                  "AdaptiveCpp.",
662
                  __FILE__, __func__, __LINE__, error_level::error);
663
    return nullptr;
664
#endif
665
}
114 ✔
666

667
void DPCTLQueue_Wait(__dpctl_keep DPCTLSyclQueueRef QRef)
668
{
37 ✔
669
    // \todo what happens if the QRef is null or a pointer to a valid sycl
670
    // queue
671
    if (QRef) {
37 !
672
        auto SyclQueue = unwrap<queue>(QRef);
37 ✔
673
        if (SyclQueue)
37 !
674
            SyclQueue->wait();
37 ✔
675
    }
37 ✔
676
    else {
×
677
        error_handler("Argument QRef is NULL.", __FILE__, __func__, __LINE__);
×
678
    }
×
679
}
37 ✔
680

681
__dpctl_give DPCTLSyclEventRef
682
DPCTLQueue_Memcpy(__dpctl_keep const DPCTLSyclQueueRef QRef,
683
                  void *Dest,
684
                  const void *Src,
685
                  size_t Count)
686
{
207 ✔
687
    auto Q = unwrap<queue>(QRef);
207 ✔
688
    if (Q) {
207 ✔
689
        sycl::event ev;
206 ✔
690
        try {
206 ✔
691
            ev = Q->memcpy(Dest, Src, Count);
206 ✔
692
        } catch (std::exception const &e) {
206 ✔
693
            error_handler(e, __FILE__, __func__, __LINE__);
8 ✔
694
            return nullptr;
8 ✔
695
        }
8 ✔
696
        return wrap<event>(new event(std::move(ev)));
198 ✔
697
    }
206 ✔
698
    else {
1 ✔
699
        error_handler("QRef passed to memcpy was NULL.", __FILE__, __func__,
1 ✔
700
                      __LINE__);
1 ✔
701
        return nullptr;
1 ✔
702
    }
1 ✔
703
}
207 ✔
704

705
__dpctl_give DPCTLSyclEventRef
706
DPCTLQueue_MemcpyWithEvents(__dpctl_keep const DPCTLSyclQueueRef QRef,
707
                            void *Dest,
708
                            const void *Src,
709
                            size_t Count,
710
                            const DPCTLSyclEventRef *DepEvents,
711
                            size_t DepEventsCount)
712
{
144 ✔
713
    event ev;
144 ✔
714
    auto Q = unwrap<queue>(QRef);
144 ✔
715
    if (Q) {
144 ✔
716
        try {
143 ✔
717
            ev = Q->submit([&](handler &cgh) {
143 ✔
718
                if (DepEvents)
143 ✔
719
                    for (size_t i = 0; i < DepEventsCount; ++i) {
408 ✔
720
                        event *ei = unwrap<event>(DepEvents[i]);
273 ✔
721
                        if (ei)
273 !
722
                            cgh.depends_on(*ei);
273 ✔
723
                    }
273 ✔
724

725
                cgh.memcpy(Dest, Src, Count);
143 ✔
726
            });
143 ✔
727
        } catch (const std::exception &ex) {
143 ✔
728
            error_handler(ex, __FILE__, __func__, __LINE__);
8 ✔
729
            return nullptr;
8 ✔
730
        }
8 ✔
731
    }
143 ✔
732
    else {
1 ✔
733
        error_handler("QRef passed to memcpy was NULL.", __FILE__, __func__,
1 ✔
734
                      __LINE__);
1 ✔
735
        return nullptr;
1 ✔
736
    }
1 ✔
737

738
    return wrap<event>(new event(ev));
135 ✔
739
}
144 ✔
740

741
__dpctl_give DPCTLSyclEventRef
742
DPCTLQueue_CopyData(__dpctl_keep const DPCTLSyclQueueRef QRef,
743
                    void *Dest,
744
                    const void *Src,
745
                    size_t Count)
746
{
52 ✔
747
    auto Q = unwrap<queue>(QRef);
52 ✔
748
    if (Q) {
52 ✔
749
        sycl::event ev;
51 ✔
750
        try {
51 ✔
751
            // Copy uint8_t elements (1 byte each), so Count is a byte count.
752
            ev = Q->copy(static_cast<const std::uint8_t *>(Src),
51 ✔
753
                         static_cast<std::uint8_t *>(Dest), Count);
51 ✔
754
        } catch (std::exception const &e) {
51 ✔
755
            error_handler(e, __FILE__, __func__, __LINE__);
8 ✔
756
            return nullptr;
8 ✔
757
        }
8 ✔
758
        return wrap<event>(new event(std::move(ev)));
43 ✔
759
    }
51 ✔
760
    else {
1 ✔
761
        error_handler("QRef passed to copy was NULL.", __FILE__, __func__,
1 ✔
762
                      __LINE__);
1 ✔
763
        return nullptr;
1 ✔
764
    }
1 ✔
765
}
52 ✔
766

767
__dpctl_give DPCTLSyclEventRef
768
DPCTLQueue_CopyDataWithEvents(__dpctl_keep const DPCTLSyclQueueRef QRef,
769
                              void *Dest,
770
                              const void *Src,
771
                              size_t Count,
772
                              const DPCTLSyclEventRef *DepEvents,
773
                              size_t DepEventsCount)
774
{
24 ✔
775
    auto Q = unwrap<queue>(QRef);
24 ✔
776
    if (Q) {
24 ✔
777
        try {
23 ✔
778
            std::vector<event> dep_events;
23 ✔
779
            if (DepEvents) {
23 ✔
780
                dep_events.reserve(DepEventsCount);
15 ✔
781
                for (size_t i = 0; i < DepEventsCount; ++i) {
30 ✔
782
                    event *ei = unwrap<event>(DepEvents[i]);
15 ✔
783
                    if (ei)
15 !
784
                        dep_events.push_back(*ei);
15 ✔
785
                }
15 ✔
786
            }
15 ✔
787

788
            // Copy uint8_t elements (1 byte each), so Count is a byte count.
789
            auto ev =
23 ✔
790
                Q->copy(static_cast<const std::uint8_t *>(Src),
23 ✔
791
                        static_cast<std::uint8_t *>(Dest), Count, dep_events);
23 ✔
792
            return wrap<event>(new event(std::move(ev)));
23 ✔
793
        } catch (const std::exception &ex) {
23 ✔
794
            error_handler(ex, __FILE__, __func__, __LINE__);
8 ✔
795
            return nullptr;
8 ✔
796
        }
8 ✔
797
    }
23 ✔
798
    else {
1 ✔
799
        error_handler("QRef passed to copy was NULL.", __FILE__, __func__,
1 ✔
800
                      __LINE__);
1 ✔
801
        return nullptr;
1 ✔
802
    }
1 ✔
803
}
24 ✔
804

805
__dpctl_give DPCTLSyclEventRef
806
DPCTLQueue_Prefetch(__dpctl_keep DPCTLSyclQueueRef QRef,
807
                    const void *Ptr,
808
                    size_t Count)
809
{
16 ✔
810
    auto Q = unwrap<queue>(QRef);
16 ✔
811
    if (Q) {
16 ✔
812
        if (Ptr) {
15 ✔
813
            sycl::event ev;
7 ✔
814
            try {
7 ✔
815
                ev = Q->prefetch(Ptr, Count);
7 ✔
816
            } catch (std::exception const &e) {
7 ✔
817
                error_handler(e, __FILE__, __func__, __LINE__);
×
818
                return nullptr;
×
819
            }
×
820
            return wrap<event>(new event(std::move(ev)));
7 ✔
821
        }
7 ✔
822
        else {
8 ✔
823
            error_handler("Attempt to prefetch USM-allocation at nullptr.",
8 ✔
824
                          __FILE__, __func__, __LINE__);
8 ✔
825
            return nullptr;
8 ✔
826
        }
8 ✔
827
    }
15 ✔
828
    else {
1 ✔
829
        error_handler("QRef passed to prefetch was NULL.", __FILE__, __func__,
1 ✔
830
                      __LINE__);
1 ✔
831
        return nullptr;
1 ✔
832
    }
1 ✔
833
}
16 ✔
834

835
__dpctl_give DPCTLSyclEventRef
836
DPCTLQueue_MemAdvise(__dpctl_keep DPCTLSyclQueueRef QRef,
837
                     const void *Ptr,
838
                     size_t Count,
839
                     int Advice)
840
{
16 ✔
841
    auto Q = unwrap<queue>(QRef);
16 ✔
842
    if (Q) {
16 ✔
843
        sycl::event ev;
15 ✔
844
        try {
15 ✔
845
            ev = Q->mem_advise(Ptr, Count, Advice);
15 ✔
846
        } catch (std::exception const &e) {
15 ✔
847
            error_handler(e, __FILE__, __func__, __LINE__);
×
848
            return nullptr;
×
849
        }
×
850
        return wrap<event>(new event(std::move(ev)));
15 ✔
851
    }
15 ✔
852
    else {
1 ✔
853
        error_handler("QRef passed to prefetch was NULL.", __FILE__, __func__,
1 ✔
854
                      __LINE__);
1 ✔
855
        return nullptr;
1 ✔
856
    }
1 ✔
857
}
16 ✔
858

859
bool DPCTLQueue_IsInOrder(__dpctl_keep const DPCTLSyclQueueRef QRef)
860
{
1,072 ✔
861
    auto Q = unwrap<queue>(QRef);
1,072 ✔
862
    if (Q) {
1,072 ✔
863
        return Q->is_in_order();
1,071 ✔
864
    }
1,071 ✔
865
    else
1 ✔
866
        return false;
1 ✔
867
}
1,072 ✔
868

869
bool DPCTLQueue_GetLastEvent_Available(void)
870
{
23 ✔
871
#ifdef SYCL_EXT_ONEAPI_IN_ORDER_QUEUE_EVENTS
23 ✔
872
    return true;
23 ✔
873
#else
874
    return false;
875
#endif
876
}
23 ✔
877

878
__dpctl_give DPCTLSyclEventRef
879
DPCTLQueue_GetLastEvent(__dpctl_keep const DPCTLSyclQueueRef QRef)
880
{
17 ✔
881
#ifdef SYCL_EXT_ONEAPI_IN_ORDER_QUEUE_EVENTS
17 ✔
882
    auto Q = unwrap<queue>(QRef);
17 ✔
883
    if (!Q) {
17 ✔
884
        error_handler("QRef passed to GetLastEvent was NULL.", __FILE__,
1 ✔
885
                      __func__, __LINE__);
1 ✔
886
        return nullptr;
1 ✔
887
    }
1 ✔
888
    if (!Q->is_in_order()) {
16 ✔
889
        error_handler("Queue passed to GetLastEvent is not in-order.", __FILE__,
1 ✔
890
                      __func__, __LINE__);
1 ✔
891
        return nullptr;
1 ✔
892
    }
1 ✔
893
    try {
15 ✔
894
        std::optional<event> ev = Q->ext_oneapi_get_last_event();
15 ✔
895
        if (!ev.has_value()) {
15 ✔
896
            return nullptr;
2 ✔
897
        }
2 ✔
898
        return wrap<event>(new event(std::move(*ev)));
13 ✔
899
    } catch (std::exception const &e) {
15 ✔
900
        error_handler(e, __FILE__, __func__, __LINE__);
×
901
        return nullptr;
×
902
    }
×
903
#else
904
    (void)QRef;
905
    return nullptr;
906
#endif
907
}
15 ✔
908

909
bool DPCTLQueue_HasEnableProfiling(__dpctl_keep const DPCTLSyclQueueRef QRef)
910
{
67 ✔
911
    auto Q = unwrap<queue>(QRef);
67 ✔
912
    if (Q) {
67 ✔
913
        return Q->has_property<sycl::property::queue::enable_profiling>();
66 ✔
914
    }
66 ✔
915
    else
1 ✔
916
        return false;
1 ✔
917
}
67 ✔
918

919
size_t DPCTLQueue_Hash(__dpctl_keep const DPCTLSyclQueueRef QRef)
920
{
55 ✔
921
    auto Q = unwrap<queue>(QRef);
55 ✔
922
    if (Q) {
55 ✔
923
        std::hash<queue> hash_fn;
52 ✔
924
        return hash_fn(*Q);
52 ✔
925
    }
52 ✔
926
    else {
3 ✔
927
        error_handler("Argument QRef is NULL.", __FILE__, __func__, __LINE__);
3 ✔
928
        return 0;
3 ✔
929
    }
3 ✔
930
}
55 ✔
931

932
__dpctl_give DPCTLSyclEventRef DPCTLQueue_SubmitBarrierForEvents(
933
    __dpctl_keep const DPCTLSyclQueueRef QRef,
934
    __dpctl_keep const DPCTLSyclEventRef *DepEvents,
935
    size_t NDepEvents)
936
{
117 ✔
937
    auto Q = unwrap<queue>(QRef);
117 ✔
938
    event e;
117 ✔
939
    if (Q) {
117 !
940
        try {
117 ✔
941
#ifdef __ADAPTIVECPP__
942
            // A kernel waits only for its dependencies, so depend on all prior
943
            // work
944
            auto prior = Q->get_wait_list();
945
#endif
946
            e = Q->submit([&](handler &cgh) {
117 ✔
947
                // Depend on any event that was specified by the caller.
948
                if (NDepEvents)
117 ✔
949
                    for (auto i = 0ul; i < NDepEvents; ++i)
18 ✔
950
                        cgh.depends_on(*unwrap<event>(DepEvents[i]));
12 ✔
951

952
#ifndef __ADAPTIVECPP__
117 ✔
953
                cgh.ext_oneapi_barrier();
117 ✔
954
#else
955
                cgh.depends_on(prior);
956
                class dpctl_barrier_task;
957
                cgh.single_task<dpctl_barrier_task>([=]() {});
958
#endif
959
            });
117 ✔
960
        } catch (std::exception const &e) {
117 ✔
961
            error_handler(e, __FILE__, __func__, __LINE__);
×
962
            return nullptr;
×
963
        }
×
964

965
        return wrap<event>(new event(std::move(e)));
117 ✔
966
    }
117 ✔
967
    else {
×
968
        error_handler("Argument QRef is NULL", __FILE__, __func__, __LINE__);
×
969
        return nullptr;
×
970
    }
×
971
}
117 ✔
972

973
__dpctl_give DPCTLSyclEventRef
974
DPCTLQueue_SubmitBarrier(__dpctl_keep const DPCTLSyclQueueRef QRef)
975
{
1 ✔
976
    return DPCTLQueue_SubmitBarrierForEvents(QRef, nullptr, 0);
1 ✔
977
}
1 ✔
978

979
__dpctl_give DPCTLSyclEventRef
980
DPCTLQueue_Memset(__dpctl_keep const DPCTLSyclQueueRef QRef,
981
                  void *USMRef,
982
                  uint8_t Value,
983
                  size_t Count)
984
{
131 ✔
985
    auto Q = unwrap<queue>(QRef);
131 ✔
986
    if (Q && USMRef) {
131 !
987
        sycl::event ev;
130 ✔
988
        try {
130 ✔
989
            ev = Q->memset(USMRef, static_cast<int>(Value), Count);
130 ✔
990
        } catch (std::exception const &e) {
130 ✔
991
            error_handler(e, __FILE__, __func__, __LINE__);
×
992
            return nullptr;
×
993
        }
×
994
        return wrap<event>(new event(std::move(ev)));
130 ✔
995
    }
130 ✔
996
    else {
1 ✔
997
        error_handler("QRef or USMRef passed to memset were NULL.", __FILE__,
1 ✔
998
                      __func__, __LINE__);
1 ✔
999
        return nullptr;
1 ✔
1000
    }
1 ✔
1001
}
131 ✔
1002

1003
__dpctl_give DPCTLSyclEventRef
1004
DPCTLQueue_MemsetWithEvents(__dpctl_keep const DPCTLSyclQueueRef QRef,
1005
                            void *USMRef,
1006
                            uint8_t Value,
1007
                            size_t Count,
1008
                            const DPCTLSyclEventRef *DepEvents,
1009
                            size_t DepEventsCount)
1010
{
110 ✔
1011
    event ev;
110 ✔
1012
    auto Q = unwrap<queue>(QRef);
110 ✔
1013
    if (Q && USMRef) {
110 !
1014
        try {
109 ✔
1015
            ev = Q->submit([&](handler &cgh) {
109 ✔
1016
                if (DepEvents)
109 !
1017
                    for (size_t i = 0; i < DepEventsCount; ++i) {
218 ✔
1018
                        event *ei = unwrap<event>(DepEvents[i]);
109 ✔
1019
                        if (ei)
109 !
1020
                            cgh.depends_on(*ei);
109 ✔
1021
                    }
109 ✔
1022

1023
                cgh.memset(USMRef, static_cast<int>(Value), Count);
109 ✔
1024
            });
109 ✔
1025
        } catch (const std::exception &ex) {
109 ✔
1026
            error_handler(ex, __FILE__, __func__, __LINE__);
×
1027
            return nullptr;
×
1028
        }
×
1029
    }
109 ✔
1030
    else {
1 ✔
1031
        error_handler("QRef or USMRef passed to memset_async were NULL.",
1 ✔
1032
                      __FILE__, __func__, __LINE__);
1 ✔
1033
        return nullptr;
1 ✔
1034
    }
1 ✔
1035

1036
    return wrap<event>(new event(std::move(ev)));
109 ✔
1037
}
110 ✔
1038

1039
__dpctl_give DPCTLSyclEventRef
1040
DPCTLQueue_Fill8(__dpctl_keep const DPCTLSyclQueueRef QRef,
1041
                 void *USMRef,
1042
                 uint8_t Value,
1043
                 size_t Count)
1044
{
29 ✔
1045
    auto Q = unwrap<queue>(QRef);
29 ✔
1046
    if (Q && USMRef) {
29 !
1047
        sycl::event ev;
28 ✔
1048
        try {
28 ✔
1049
            ev = Q->fill<uint8_t>(USMRef, Value, Count);
28 ✔
1050
        } catch (std::exception const &e) {
28 ✔
1051
            error_handler(e, __FILE__, __func__, __LINE__);
×
1052
            return nullptr;
×
1053
        }
×
1054
        return wrap<event>(new event(std::move(ev)));
28 ✔
1055
    }
28 ✔
1056
    else {
1 ✔
1057
        error_handler("QRef or USMRef passed to fill8 were NULL.", __FILE__,
1 ✔
1058
                      __func__, __LINE__);
1 ✔
1059
        return nullptr;
1 ✔
1060
    }
1 ✔
1061
}
29 ✔
1062

1063
__dpctl_give DPCTLSyclEventRef
1064
DPCTLQueue_Fill8WithEvents(__dpctl_keep const DPCTLSyclQueueRef QRef,
1065
                           void *USMRef,
1066
                           uint8_t Value,
1067
                           size_t Count,
1068
                           const DPCTLSyclEventRef *DepEvents,
1069
                           size_t DepEventsCount)
1070
{
10 ✔
1071
    auto Q = unwrap<queue>(QRef);
10 ✔
1072
    if (Q && USMRef) {
10 !
1073
        sycl::event ev;
9 ✔
1074
        try {
9 ✔
1075
            std::vector<event> dep_events;
9 ✔
1076
            if (DepEvents) {
9 !
1077
                dep_events.reserve(DepEventsCount);
9 ✔
1078
                for (size_t i = 0; i < DepEventsCount; ++i) {
18 ✔
1079
                    event *ei = unwrap<event>(DepEvents[i]);
9 ✔
1080
                    if (ei)
9 !
1081
                        dep_events.push_back(*ei);
9 ✔
1082
                }
9 ✔
1083
            }
9 ✔
1084
            ev = Q->fill<uint8_t>(USMRef, Value, Count, dep_events);
9 ✔
1085
        } catch (std::exception const &e) {
9 ✔
1086
            error_handler(e, __FILE__, __func__, __LINE__);
×
1087
            return nullptr;
×
1088
        }
×
1089
        return wrap<event>(new event(std::move(ev)));
9 ✔
1090
    }
9 ✔
1091
    else {
1 ✔
1092
        error_handler("QRef or USMRef passed to fill8_async were NULL.",
1 ✔
1093
                      __FILE__, __func__, __LINE__);
1 ✔
1094
        return nullptr;
1 ✔
1095
    }
1 ✔
1096
}
10 ✔
1097

1098
__dpctl_give DPCTLSyclEventRef
1099
DPCTLQueue_Fill16(__dpctl_keep const DPCTLSyclQueueRef QRef,
1100
                  void *USMRef,
1101
                  uint16_t Value,
1102
                  size_t Count)
1103
{
24 ✔
1104
    auto Q = unwrap<queue>(QRef);
24 ✔
1105
    if (Q && USMRef) {
24 !
1106
        sycl::event ev;
23 ✔
1107
        try {
23 ✔
1108
            ev = Q->fill<uint16_t>(USMRef, Value, Count);
23 ✔
1109
        } catch (std::exception const &e) {
23 ✔
1110
            error_handler(e, __FILE__, __func__, __LINE__);
×
1111
            return nullptr;
×
1112
        }
×
1113
        return wrap<event>(new event(std::move(ev)));
23 ✔
1114
    }
23 ✔
1115
    else {
1 ✔
1116
        error_handler("QRef or USMRef passed to fill16 were NULL.", __FILE__,
1 ✔
1117
                      __func__, __LINE__);
1 ✔
1118
        return nullptr;
1 ✔
1119
    }
1 ✔
1120
}
24 ✔
1121

1122
__dpctl_give DPCTLSyclEventRef
1123
DPCTLQueue_Fill16WithEvents(__dpctl_keep const DPCTLSyclQueueRef QRef,
1124
                            void *USMRef,
1125
                            uint16_t Value,
1126
                            size_t Count,
1127
                            const DPCTLSyclEventRef *DepEvents,
1128
                            size_t DepEventsCount)
1129
{
9 ✔
1130
    auto Q = unwrap<queue>(QRef);
9 ✔
1131
    if (Q && USMRef) {
9 !
1132
        sycl::event ev;
8 ✔
1133
        try {
8 ✔
1134
            std::vector<event> dep_events;
8 ✔
1135
            if (DepEvents) {
8 !
1136
                dep_events.reserve(DepEventsCount);
8 ✔
1137
                for (size_t i = 0; i < DepEventsCount; ++i) {
16 ✔
1138
                    event *ei = unwrap<event>(DepEvents[i]);
8 ✔
1139
                    if (ei)
8 !
1140
                        dep_events.push_back(*ei);
8 ✔
1141
                }
8 ✔
1142
            }
8 ✔
1143
            ev = Q->fill<uint16_t>(USMRef, Value, Count, dep_events);
8 ✔
1144
        } catch (std::exception const &e) {
8 ✔
1145
            error_handler(e, __FILE__, __func__, __LINE__);
×
1146
            return nullptr;
×
1147
        }
×
1148
        return wrap<event>(new event(std::move(ev)));
8 ✔
1149
    }
8 ✔
1150
    else {
1 ✔
1151
        error_handler("QRef or USMRef passed to fill16_async were NULL.",
1 ✔
1152
                      __FILE__, __func__, __LINE__);
1 ✔
1153
        return nullptr;
1 ✔
1154
    }
1 ✔
1155
}
9 ✔
1156

1157
__dpctl_give DPCTLSyclEventRef
1158
DPCTLQueue_Fill32(__dpctl_keep const DPCTLSyclQueueRef QRef,
1159
                  void *USMRef,
1160
                  uint32_t Value,
1161
                  size_t Count)
1162
{
27 ✔
1163
    auto Q = unwrap<queue>(QRef);
27 ✔
1164
    if (Q && USMRef) {
27 !
1165
        sycl::event ev;
26 ✔
1166
        try {
26 ✔
1167
            ev = Q->fill<uint32_t>(USMRef, Value, Count);
26 ✔
1168
        } catch (std::exception const &e) {
26 ✔
1169
            error_handler(e, __FILE__, __func__, __LINE__);
×
1170
            return nullptr;
×
1171
        }
×
1172
        return wrap<event>(new event(std::move(ev)));
26 ✔
1173
    }
26 ✔
1174
    else {
1 ✔
1175
        error_handler("QRef or USMRef passed to fill32 were NULL.", __FILE__,
1 ✔
1176
                      __func__, __LINE__);
1 ✔
1177
        return nullptr;
1 ✔
1178
    }
1 ✔
1179
}
27 ✔
1180

1181
__dpctl_give DPCTLSyclEventRef
1182
DPCTLQueue_Fill32WithEvents(__dpctl_keep const DPCTLSyclQueueRef QRef,
1183
                            void *USMRef,
1184
                            uint32_t Value,
1185
                            size_t Count,
1186
                            const DPCTLSyclEventRef *DepEvents,
1187
                            size_t DepEventsCount)
1188
{
9 ✔
1189
    auto Q = unwrap<queue>(QRef);
9 ✔
1190
    if (Q && USMRef) {
9 !
1191
        sycl::event ev;
8 ✔
1192
        try {
8 ✔
1193
            std::vector<event> dep_events;
8 ✔
1194
            if (DepEvents) {
8 !
1195
                dep_events.reserve(DepEventsCount);
8 ✔
1196
                for (size_t i = 0; i < DepEventsCount; ++i) {
16 ✔
1197
                    event *ei = unwrap<event>(DepEvents[i]);
8 ✔
1198
                    if (ei)
8 !
1199
                        dep_events.push_back(*ei);
8 ✔
1200
                }
8 ✔
1201
            }
8 ✔
1202
            ev = Q->fill<uint32_t>(USMRef, Value, Count, dep_events);
8 ✔
1203
        } catch (std::exception const &e) {
8 ✔
1204
            error_handler(e, __FILE__, __func__, __LINE__);
×
1205
            return nullptr;
×
1206
        }
×
1207
        return wrap<event>(new event(std::move(ev)));
8 ✔
1208
    }
8 ✔
1209
    else {
1 ✔
1210
        error_handler("QRef or USMRef passed to fill32_async were NULL.",
1 ✔
1211
                      __FILE__, __func__, __LINE__);
1 ✔
1212
        return nullptr;
1 ✔
1213
    }
1 ✔
1214
}
9 ✔
1215

1216
__dpctl_give DPCTLSyclEventRef
1217
DPCTLQueue_Fill64(__dpctl_keep const DPCTLSyclQueueRef QRef,
1218
                  void *USMRef,
1219
                  uint64_t Value,
1220
                  size_t Count)
1221
{
33 ✔
1222
    auto Q = unwrap<queue>(QRef);
33 ✔
1223
    if (Q && USMRef) {
33 !
1224
        sycl::event ev;
32 ✔
1225
        try {
32 ✔
1226
            ev = Q->fill<uint64_t>(USMRef, Value, Count);
32 ✔
1227
        } catch (std::exception const &e) {
32 ✔
1228
            error_handler(e, __FILE__, __func__, __LINE__);
×
1229
            return nullptr;
×
1230
        }
×
1231
        return wrap<event>(new event(std::move(ev)));
32 ✔
1232
    }
32 ✔
1233
    else {
1 ✔
1234
        error_handler("QRef or USMRef passed to fill64 were NULL.", __FILE__,
1 ✔
1235
                      __func__, __LINE__);
1 ✔
1236
        return nullptr;
1 ✔
1237
    }
1 ✔
1238
}
33 ✔
1239

1240
__dpctl_give DPCTLSyclEventRef
1241
DPCTLQueue_Fill64WithEvents(__dpctl_keep const DPCTLSyclQueueRef QRef,
1242
                            void *USMRef,
1243
                            uint64_t Value,
1244
                            size_t Count,
1245
                            const DPCTLSyclEventRef *DepEvents,
1246
                            size_t DepEventsCount)
1247
{
9 ✔
1248
    auto Q = unwrap<queue>(QRef);
9 ✔
1249
    if (Q && USMRef) {
9 !
1250
        sycl::event ev;
8 ✔
1251
        try {
8 ✔
1252
            std::vector<event> dep_events;
8 ✔
1253
            if (DepEvents) {
8 !
1254
                dep_events.reserve(DepEventsCount);
8 ✔
1255
                for (size_t i = 0; i < DepEventsCount; ++i) {
16 ✔
1256
                    event *ei = unwrap<event>(DepEvents[i]);
8 ✔
1257
                    if (ei)
8 !
1258
                        dep_events.push_back(*ei);
8 ✔
1259
                }
8 ✔
1260
            }
8 ✔
1261
            ev = Q->fill<uint64_t>(USMRef, Value, Count, dep_events);
8 ✔
1262
        } catch (std::exception const &e) {
8 ✔
1263
            error_handler(e, __FILE__, __func__, __LINE__);
×
1264
            return nullptr;
×
1265
        }
×
1266
        return wrap<event>(new event(std::move(ev)));
8 ✔
1267
    }
8 ✔
1268
    else {
1 ✔
1269
        error_handler("QRef or USMRef passed to fill64_async were NULL.",
1 ✔
1270
                      __FILE__, __func__, __LINE__);
1 ✔
1271
        return nullptr;
1 ✔
1272
    }
1 ✔
1273
}
9 ✔
1274

1275
__dpctl_give DPCTLSyclEventRef
1276
DPCTLQueue_Fill128(__dpctl_keep const DPCTLSyclQueueRef QRef,
1277
                   void *USMRef,
1278
                   uint64_t *Value,
1279
                   size_t Count)
1280
{
29 ✔
1281
    auto Q = unwrap<queue>(QRef);
29 ✔
1282
    if (Q && USMRef && Value) {
29 !
1283
        sycl::event ev;
20 ✔
1284
        try {
20 ✔
1285
            complexNumber Val;
20 ✔
1286
            Val.real = Value[0];
20 ✔
1287
            Val.imag = Value[1];
20 ✔
1288
            ev = Q->fill(USMRef, Val, Count);
20 ✔
1289
        } catch (std::exception const &e) {
20 ✔
1290
            error_handler(e, __FILE__, __func__, __LINE__);
×
1291
            return nullptr;
×
1292
        }
×
1293
        return wrap<event>(new event(std::move(ev)));
20 ✔
1294
    }
20 ✔
1295
    else {
9 ✔
1296
        error_handler("QRef, USMRef, or Value passed to fill128 were NULL.",
9 ✔
1297
                      __FILE__, __func__, __LINE__);
9 ✔
1298
        return nullptr;
9 ✔
1299
    }
9 ✔
1300
}
29 ✔
1301

1302
__dpctl_give DPCTLSyclEventRef
1303
DPCTLQueue_Fill128WithEvents(__dpctl_keep const DPCTLSyclQueueRef QRef,
1304
                             void *USMRef,
1305
                             uint64_t *Value,
1306
                             size_t Count,
1307
                             const DPCTLSyclEventRef *DepEvents,
1308
                             size_t DepEventsCount)
1309
{
17 ✔
1310
    auto Q = unwrap<queue>(QRef);
17 ✔
1311
    if (Q && USMRef && Value) {
17 !
1312
        sycl::event ev;
8 ✔
1313
        try {
8 ✔
1314
            std::vector<event> dep_events;
8 ✔
1315
            if (DepEvents) {
8 !
1316
                dep_events.reserve(DepEventsCount);
8 ✔
1317
                for (size_t i = 0; i < DepEventsCount; ++i) {
16 ✔
1318
                    event *ei = unwrap<event>(DepEvents[i]);
8 ✔
1319
                    if (ei)
8 !
1320
                        dep_events.push_back(*ei);
8 ✔
1321
                }
8 ✔
1322
            }
8 ✔
1323
            complexNumber Val;
8 ✔
1324
            Val.real = Value[0];
8 ✔
1325
            Val.imag = Value[1];
8 ✔
1326
            ev = Q->fill(USMRef, Val, Count, dep_events);
8 ✔
1327
        } catch (std::exception const &e) {
8 ✔
1328
            error_handler(e, __FILE__, __func__, __LINE__);
×
1329
            return nullptr;
×
1330
        }
×
1331
        return wrap<event>(new event(std::move(ev)));
8 ✔
1332
    }
8 ✔
1333
    else {
9 ✔
1334
        error_handler(
9 ✔
1335
            "QRef, USMRef, or Value passed to fill128_async were NULL.",
9 ✔
1336
            __FILE__, __func__, __LINE__);
9 ✔
1337
        return nullptr;
9 ✔
1338
    }
9 ✔
1339
}
17 ✔
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE TRIAL · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2026 Coveralls, Inc