From 9a30756c4b0f6db1317c17462c324b8743ab23e6 Mon Sep 17 00:00:00 2001 From: Peter Colberg Date: Thu, 5 May 2022 21:35:16 -0400 Subject: [PATCH] invocation_wrapper: support non-POD types using placement new Each context maintains a pool of manually allocated invocation_wrapper objects, which so far contained only POD types. To support the use of non-POD types, e.g., std::vector, explicitly invoke the constructor using placement new after malloc, and the destructor before free. https://en.cppreference.com/w/cpp/language/new#Placement_new https://github.com/intel/fpga-runtime-for-opencl/pull/103#discussion_r866418903 Signed-off-by: Peter Colberg --- src/acl_context.cpp | 16 +++++++++++----- 1 file changed, 11 insertions(+), 5 deletions(-) diff --git a/src/acl_context.cpp b/src/acl_context.cpp index c22c2f09..f3413ec0 100644 --- a/src/acl_context.cpp +++ b/src/acl_context.cpp @@ -1014,11 +1014,15 @@ static void l_forcibly_release_allocations(cl_context context) { } if (context->invocation_wrapper) { - unsigned i; - for (i = 0; i < context->num_invocation_wrappers_allocated; i++) { - if (context->invocation_wrapper[i]->image->arg_value) - acl_delete_arr(context->invocation_wrapper[i]->image->arg_value); - acl_free(context->invocation_wrapper[i]); + for (unsigned int i = 0; i < context->num_invocation_wrappers_allocated; + i++) { + auto *const wrapper = context->invocation_wrapper[i]; + if (wrapper->image->arg_value) { + acl_delete_arr(wrapper->image->arg_value); + } + // invoke non-default destructors of non-POD types, e.g., std::vector + wrapper->~acl_kernel_invocation_wrapper_t(); + acl_free(wrapper); } acl_free(context->invocation_wrapper); context->invocation_wrapper = 0; @@ -1208,6 +1212,8 @@ l_init_kernel_invocation_wrapper(acl_kernel_invocation_wrapper_t *wrapper, acl_assert_locked(); if (wrapper) { + // invoke non-default constructors of non-POD types, e.g., std::vector + new (wrapper) acl_kernel_invocation_wrapper_t{}; wrapper->id = i; wrapper->image = &(wrapper->image_storage); wrapper->image->arg_value = nullptr;