Commit: 29a1cb5cc8ea68d35fbb6556c3816d96fb14c6cf Author: Nikita Sirgienko Date: Thu Mar 31 23:15:41 2022 +0200 Branches: cycles_oneapi https://developer.blender.org/rB29a1cb5cc8ea68d35fbb6556c3816d96fb14c6cf
Cycles: Improve runtime error handling for oneAPI rendering Now errors in oneAPI kernel during initialization and pre-render Cycles stages (like device-side memory allocaitons) will be properly handled during oneAPI rendering and will be shown into UI. =================================================================== M intern/cycles/device/oneapi/device_impl.cpp M intern/cycles/device/oneapi/device_impl.h M intern/cycles/device/oneapi/queue.cpp M intern/cycles/device/oneapi/queue.h M intern/cycles/kernel/device/oneapi/dll_interface_template.h M intern/cycles/kernel/device/oneapi/kernel.cpp =================================================================== diff --git a/intern/cycles/device/oneapi/device_impl.cpp b/intern/cycles/device/oneapi/device_impl.cpp index c9dff23690b..99974f25405 100644 --- a/intern/cycles/device/oneapi/device_impl.cpp +++ b/intern/cycles/device/oneapi/device_impl.cpp @@ -12,6 +12,13 @@ CCL_NAMESPACE_BEGIN +static void queue_error_cb(const char *message, void *user_ptr) +{ + if (user_ptr) { + *((std::string *)user_ptr) = message; + } +} + OneapiDevice::OneapiDevice(const DeviceInfo &info, oneAPIDLLInterface &oneapi_dll_object, Stats &stats, @@ -26,12 +33,14 @@ OneapiDevice::OneapiDevice(const DeviceInfo &info, { need_texture_info = false; + (oneapi_dll.oneapi_set_error_cb)(queue_error_cb, &oneapi_error_string); + // Oneapi calls should be initialised on this moment; assert(oneapi_dll.oneapi_create_queue != nullptr); bool is_finished_ok = (oneapi_dll.oneapi_create_queue)(device_queue, info.num); if (is_finished_ok == false) { - set_error("oneAPI queue initialization error: got runtime exception"); + set_error("oneAPI queue initialization error: got runtime exception \"" + oneapi_error_string + "\""); } else { VLOG(1) << "oneAPI queue has been successfully created for the device \"" << info.description @@ -42,7 +51,7 @@ OneapiDevice::OneapiDevice(const DeviceInfo &info, size_t globals_segment_size; is_finished_ok = (oneapi_dll.oneapi_kernel_globals_size)(device_queue, globals_segment_size); if (is_finished_ok == false) { - set_error("oneAPI constant memory initialization got runtime exception"); + set_error("oneAPI constant memory initialization got runtime exception \"" + oneapi_error_string + "\""); } else { VLOG(1) << "Successfuly created global/constant memory segment (kernel globals object)"; @@ -94,7 +103,7 @@ bool OneapiDevice::load_kernels(const uint requested_features) bool is_finished_ok = (oneapi_dll.oneapi_trigger_runtime_compilation)(device_queue); if (is_finished_ok == false) { - set_error("oneAPI kernel load: got runtime exception"); + set_error("oneAPI kernel load: got runtime exception \"" + oneapi_error_string + "\""); } else { VLOG(1) << "Runtime compilation done for \"" << info.description << "\""; @@ -163,6 +172,11 @@ SyclQueue *OneapiDevice::sycl_queue() return device_queue; } +string OneapiDevice::oneapi_error_message() +{ + return string(oneapi_error_string.c_str()); +} + oneAPIDLLInterface OneapiDevice::oneapi_dll_object() { return oneapi_dll; @@ -248,7 +262,10 @@ void OneapiDevice::mem_copy_from(device_memory &mem, size_t y, size_t w, size_t assert(mem.device_pointer); char *shifted_host = (char *)mem.host_pointer + offset; char *shifted_device = (char *)mem.device_pointer + offset; - (oneapi_dll.oneapi_usm_memcpy)(device_queue, shifted_host, shifted_device, size); + bool is_finished_ok = (oneapi_dll.oneapi_usm_memcpy)(device_queue, shifted_host, shifted_device, size); + if (is_finished_ok == false) { + set_error("oneAPI memory operation error: got runtime exception \"" + oneapi_error_string + "\""); + } } } @@ -268,7 +285,10 @@ void OneapiDevice::mem_zero(device_memory &mem) } assert(device_queue); - (oneapi_dll.oneapi_usm_memset)(device_queue, (void *)mem.device_pointer, 0, mem.memory_size()); + bool is_finished_ok = (oneapi_dll.oneapi_usm_memset)(device_queue, (void *)mem.device_pointer, 0, mem.memory_size()); + if (is_finished_ok == false) { + set_error("oneAPI memory operation error: got runtime exception \"" + oneapi_error_string + "\""); + } } void OneapiDevice::mem_free(device_memory &mem) diff --git a/intern/cycles/device/oneapi/device_impl.h b/intern/cycles/device/oneapi/device_impl.h index 1176b85b40d..d18018bbc4c 100644 --- a/intern/cycles/device/oneapi/device_impl.h +++ b/intern/cycles/device/oneapi/device_impl.h @@ -26,6 +26,7 @@ class OneapiDevice : public Device { void *kg_memory_device; size_t kg_memory_size = (size_t)0; oneAPIDLLInterface oneapi_dll; + std::string oneapi_error_string; public: virtual BVHLayoutMask get_bvh_layout_mask() const override; @@ -56,6 +57,8 @@ class OneapiDevice : public Device { SyclQueue *sycl_queue(); + string oneapi_error_message(); + oneAPIDLLInterface oneapi_dll_object(); void *kernel_globals_device_pointer(); diff --git a/intern/cycles/device/oneapi/queue.cpp b/intern/cycles/device/oneapi/queue.cpp index 1ea8c0e69ae..8747796bb76 100644 --- a/intern/cycles/device/oneapi/queue.cpp +++ b/intern/cycles/device/oneapi/queue.cpp @@ -146,13 +146,6 @@ int OneapiDeviceQueue::num_concurrent_busy_states() const } } -static void queue_error_cb(const char *message, void *user_ptr) -{ - if (user_ptr) { - *((std::string *)user_ptr) = message; - } -} - void OneapiDeviceQueue::init_execution() { oneapi_device->load_texture_info(); @@ -162,7 +155,6 @@ void OneapiDeviceQueue::init_execution() assert(device_queue); assert(kg_dptr); kernel_context = new KernelContext{device_queue, kg_dptr, with_kernel_statistics}; - (oneapi_dll.oneapi_set_error_cb)(queue_error_cb, &kernel_error_string); debug_init_execution(); } @@ -268,7 +260,7 @@ bool OneapiDeviceQueue::enqueue(DeviceKernel kernel, if (is_finished_ok == false) { oneapi_device->set_error("oneAPI kernel \"" + std::string(device_kernel_as_string(kernel)) + - "\" execution error: got runtime exception \"" + kernel_error_string + + "\" execution error: got runtime exception \"" + oneapi_device->oneapi_error_message() + "\""); } @@ -281,7 +273,9 @@ bool OneapiDeviceQueue::synchronize() return false; } - (oneapi_dll.oneapi_queue_synchronize)(oneapi_device->sycl_queue()); + bool is_finished_ok = (oneapi_dll.oneapi_queue_synchronize)(oneapi_device->sycl_queue()); + if (is_finished_ok == false) + oneapi_device->set_error("oneAPI unknown kernel execution error: got runtime exception \"" + oneapi_device->oneapi_error_message() + "\""); debug_synchronize(); diff --git a/intern/cycles/device/oneapi/queue.h b/intern/cycles/device/oneapi/queue.h index 1ca184c8cbe..7bf37382026 100644 --- a/intern/cycles/device/oneapi/queue.h +++ b/intern/cycles/device/oneapi/queue.h @@ -46,7 +46,6 @@ class OneapiDeviceQueue : public DeviceQueue { OneapiDevice *oneapi_device; oneAPIDLLInterface oneapi_dll; KernelContext *kernel_context; - std::string kernel_error_string; static std::set<DeviceKernel> SUPPORTED_KERNELS; bool with_kernel_statistics; }; diff --git a/intern/cycles/kernel/device/oneapi/dll_interface_template.h b/intern/cycles/kernel/device/oneapi/dll_interface_template.h index cf6facdb105..18d66407974 100644 --- a/intern/cycles/kernel/device/oneapi/dll_interface_template.h +++ b/intern/cycles/kernel/device/oneapi/dll_interface_template.h @@ -15,10 +15,10 @@ DLL_INTERFACE_CALL(oneapi_usm_alloc_device, void *, SyclQueue *queue, size_t mem DLL_INTERFACE_CALL(oneapi_usm_free, void, SyclQueue *queue, void *usm_ptr) DLL_INTERFACE_CALL( - oneapi_usm_memcpy, void, SyclQueue *queue, void *dest, void *src, size_t num_bytes) -DLL_INTERFACE_CALL(oneapi_queue_synchronize, void, SyclQueue *queue) + oneapi_usm_memcpy, bool, SyclQueue *queue, void *dest, void *src, size_t num_bytes) +DLL_INTERFACE_CALL(oneapi_queue_synchronize, bool, SyclQueue *queue) DLL_INTERFACE_CALL(oneapi_usm_memset, - void, + bool, SyclQueue *queue, void *usm_ptr, unsigned char value, diff --git a/intern/cycles/kernel/device/oneapi/kernel.cpp b/intern/cycles/kernel/device/oneapi/kernel.cpp index c0736e9b8b7..18ae5249646 100644 --- a/intern/cycles/kernel/device/oneapi/kernel.cpp +++ b/intern/cycles/kernel/device/oneapi/kernel.cpp @@ -116,34 +116,56 @@ void oneapi_usm_free(SyclQueue *queue_, void *usm_ptr) sycl::free(usm_ptr, *queue); } -void oneapi_usm_memcpy(SyclQueue *queue_, void *dest, void *src, size_t num_bytes) +bool oneapi_usm_memcpy(SyclQueue *queue_, void *dest, void *src, size_t num_bytes) { assert(queue_); sycl::queue *queue = reinterpret_cast<sycl::queue *>(queue_); check_usm(queue_, dest, true); check_usm(queue_, src, true); - queue->memcpy(dest, src, num_bytes); + try { + sycl::event mem_event = queue->memcpy(dest, src, num_bytes); + mem_event.wait_and_throw(); + return true; + } + catch (sycl::exception const &e) { + if (s_error_cb) { + s_error_cb(e.what(), s_error_user_ptr); + } + return false; + } } -void oneapi_usm_memset(SyclQueue *queue_, void *usm_ptr, unsigned char value, size_t num_bytes) +bool oneapi_usm_memset(SyclQueue *queue_, void *usm_ptr, unsigned char value, size_t num_bytes) { assert(queue_); sycl::queue *queue = reinterpret_cast<sycl::queue *>(queue_); check_usm(queue_, usm_ptr, true); - queue->memset(usm_ptr, value, num_bytes); + try { + sycl::event mem_event = queue->memset(usm_ptr, value, num_bytes); + mem_event.wait_and_throw(); + return true; + } + catch (sycl::exception const &e) { + if (s_error_cb) { + s_error_cb(e.what(), s_error_user_ptr); + } + return false; + } } -void oneapi_queue_synchronize(SyclQueue *queue_) +bool oneapi_queue_synchronize(SyclQueue *queue_) { assert(queue_); sycl::queue *queue = reinterpret_cast<sycl::queue *>(queue_); try { queue->wait_and_throw(); + return true; } catch (sycl::exception const &e) { if (s_error_cb) { s_error_cb(e.what(), s_error_user_ptr); } + return false; } } _______________________________________________ Bf-blender-cvs mailing list Bf-blender-cvs@blender.org List details, subscription details or unsubscribe: https://lists.blender.org/mailman/listinfo/bf-blender-cvs