Skip to content

Commit b1c9b93

Browse files
MrSidimsbader
authored andcommitted
[SYCL] Add support for discard access modes
cl::sycl::discard_write and cl::sycl::discard_read_write are now supported. Do not proceed copying buffer from device to host and vice versa if any of mentioned modes are set. Signed-off-by: Dmitry Sidorov <[email protected]>
1 parent 848fc42 commit b1c9b93

File tree

3 files changed

+67
-11
lines changed

3 files changed

+67
-11
lines changed

sycl/include/CL/sycl/detail/buffer_impl.hpp

+18-8
Original file line numberDiff line numberDiff line change
@@ -262,7 +262,7 @@ template <typename AllocatorT> class buffer_impl {
262262

263263
public:
264264
void moveMemoryTo(QueueImplPtr Queue, std::vector<cl::sycl::event> DepEvents,
265-
EventImplPtr Event);
265+
EventImplPtr Event, cl::sycl::access::mode Mode);
266266

267267
void fill(QueueImplPtr Queue, std::vector<cl::sycl::event> DepEvents,
268268
EventImplPtr Event, const void *Pattern, size_t PatternSize,
@@ -281,7 +281,7 @@ template <typename AllocatorT> class buffer_impl {
281281
bool isValidAccessToMem(cl::sycl::access::mode AccessMode);
282282

283283
void allocate(QueueImplPtr Queue, std::vector<cl::sycl::event> DepEvents,
284-
EventImplPtr Event, cl::sycl::access::mode mode);
284+
EventImplPtr Event);
285285

286286
cl_mem getOpenCLMem() const;
287287

@@ -409,7 +409,7 @@ void buffer_impl<AllocatorT>::copy(
409409
template <typename AllocatorT>
410410
void buffer_impl<AllocatorT>::moveMemoryTo(
411411
QueueImplPtr Queue, std::vector<cl::sycl::event> DepEvents,
412-
EventImplPtr Event) {
412+
EventImplPtr Event, cl::sycl::access::mode Mode) {
413413

414414
ContextImplPtr Context = detail::getSyclObjImpl(Queue->get_context());
415415

@@ -431,6 +431,10 @@ void buffer_impl<AllocatorT>::moveMemoryTo(
431431

432432
// Copy from OCL device to host device.
433433
if (!OCLState.Queue->is_host() && Queue->is_host()) {
434+
if (Mode == cl::sycl::access::mode::discard_write &&
435+
Mode == cl::sycl::access::mode::discard_read_write)
436+
return;
437+
434438
const size_t ByteSize = get_size();
435439

436440
std::vector<cl_event> CLEvents =
@@ -484,13 +488,18 @@ void buffer_impl<AllocatorT>::moveMemoryTo(
484488

485489
std::vector<cl_event> CLEvents =
486490
detail::getOrWaitEvents(std::move(DepEvents), Context);
491+
if (Mode == cl::sycl::access::mode::discard_write &&
492+
Mode == cl::sycl::access::mode::discard_read_write)
493+
return;
494+
487495
cl_event &WriteBufEvent = Event->getHandleRef();
488496
// Enqueue copying from host to new OCL buffer.
489497
Error =
490498
clEnqueueWriteBuffer(OCLState.Queue->getHandleRef(), OCLState.Mem,
491499
/*blocking_write=*/CL_FALSE, /*offset=*/0,
492-
ByteSize, BufPtr, CLEvents.size(), CLEvents.data(),
493-
&WriteBufEvent); // replace &WriteBufEvent to NULL
500+
ByteSize, BufPtr, CLEvents.size(),
501+
CLEvents.data(), /*replace &WriteBufEvent
502+
to NULL*/ &WriteBufEvent);
494503
CHECK_OCL_CODE(Error);
495504
Event->setContextImpl(Context);
496505

@@ -507,8 +516,10 @@ buffer_impl<AllocatorT>::convertSycl2OCLMode(cl::sycl::access::mode mode) {
507516
case cl::sycl::access::mode::read:
508517
return CL_MEM_READ_ONLY;
509518
case cl::sycl::access::mode::write:
519+
case cl::sycl::access::mode::discard_write:
510520
return CL_MEM_WRITE_ONLY;
511521
case cl::sycl::access::mode::read_write:
522+
case cl::sycl::access::mode::discard_read_write:
512523
case cl::sycl::access::mode::atomic:
513524
return CL_MEM_READ_WRITE;
514525
default:
@@ -534,8 +545,7 @@ bool buffer_impl<AllocatorT>::isValidAccessToMem(
534545
template <typename AllocatorT>
535546
void buffer_impl<AllocatorT>::allocate(QueueImplPtr Queue,
536547
std::vector<cl::sycl::event> DepEvents,
537-
EventImplPtr Event,
538-
cl::sycl::access::mode mode) {
548+
EventImplPtr Event) {
539549

540550
detail::waitEvents(DepEvents);
541551

@@ -556,7 +566,7 @@ void buffer_impl<AllocatorT>::allocate(QueueImplPtr Queue,
556566
cl_int Error;
557567

558568
cl_mem Mem =
559-
clCreateBuffer(Context->getHandleRef(), convertSycl2OCLMode(mode),
569+
clCreateBuffer(Context->getHandleRef(), CL_MEM_READ_WRITE,
560570
ByteSize, nullptr, &Error);
561571
CHECK_OCL_CODE(Error);
562572

sycl/include/CL/sycl/detail/scheduler/requirements.h

+3-3
Original file line numberDiff line numberDiff line change
@@ -105,15 +105,15 @@ class BufferStorage : public BufferRequirement {
105105
void allocate(QueueImplPtr Queue, std::vector<cl::sycl::event> DepEvents,
106106
EventImplPtr Event) override {
107107
assert(m_Buffer != nullptr && "BufferStorage::m_Buffer is nullptr");
108-
m_Buffer->allocate(std::move(Queue), std::move(DepEvents), std::move(Event),
109-
Mode);
108+
m_Buffer->allocate(std::move(Queue), std::move(DepEvents),
109+
std::move(Event));
110110
}
111111

112112
void moveMemoryTo(QueueImplPtr Queue, std::vector<cl::sycl::event> DepEvents,
113113
EventImplPtr Event) override {
114114
assert(m_Buffer != nullptr && "BufferStorage::m_Buffer is nullptr");
115115
m_Buffer->moveMemoryTo(std::move(Queue), std::move(DepEvents),
116-
std::move(Event));
116+
std::move(Event), Mode);
117117
}
118118

119119
void fill(QueueImplPtr Queue, std::vector<cl::sycl::event> DepEvents,

sycl/test/basic_tests/accessor/accessor.cpp

+46
Original file line numberDiff line numberDiff line change
@@ -174,4 +174,50 @@ int main() {
174174
}
175175
}
176176
}
177+
178+
// Discard write accessor.
179+
{
180+
try {
181+
sycl::queue Queue;
182+
sycl::buffer<int, 1> buf(sycl::range<1>(3));
183+
184+
Queue.submit([&](sycl::handler& cgh) {
185+
auto dev_acc = buf.get_access<sycl::access::mode::discard_write>(cgh);
186+
187+
cgh.parallel_for<class test_discard_write>(
188+
sycl::range<1>{3},
189+
[=](sycl::id<1> index) { dev_acc[index] = 42; });
190+
});
191+
192+
auto host_acc = buf.get_access<sycl::access::mode::read>();
193+
for (int i = 0; i != 3; ++i)
194+
assert(host_acc[i] == 42);
195+
196+
} catch (cl::sycl::exception e) {
197+
std::cout << "SYCL exception caught: " << e.what();
198+
return 1;
199+
}
200+
}
201+
202+
// Discard read-write accessor.
203+
{
204+
try {
205+
sycl::queue Queue;
206+
sycl::buffer<int, 1> buf(sycl::range<1>(3));
207+
208+
Queue.submit([&](sycl::handler& cgh) {
209+
auto dev_acc = buf.get_access<sycl::access::mode::write>(cgh);
210+
211+
cgh.parallel_for<class test_discard_read_write>(
212+
sycl::range<1>{3},
213+
[=](sycl::id<1> index) { dev_acc[index] = 42; });
214+
});
215+
216+
auto host_acc =
217+
buf.get_access<sycl::access::mode::discard_read_write>();
218+
} catch (cl::sycl::exception e) {
219+
std::cout << "SYCL exception caught: " << e.what();
220+
return 1;
221+
}
222+
}
177223
}

0 commit comments

Comments
 (0)