1 /* 2 * cl_context.cpp - CL context 3 * 4 * Copyright (c) 2015 Intel Corporation 5 * 6 * Licensed under the Apache License, Version 2.0 (the "License"); 7 * you may not use this file except in compliance with the License. 8 * You may obtain a copy of the License at 9 * 10 * http://www.apache.org/licenses/LICENSE-2.0 11 * 12 * Unless required by applicable law or agreed to in writing, software 13 * distributed under the License is distributed on an "AS IS" BASIS, 14 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 15 * See the License for the specific language governing permissions and 16 * limitations under the License. 17 * 18 * Author: Wind Yuan <feng.yuan (at) intel.com> 19 */ 20 21 22 #include "cl_context.h" 23 #include "cl_kernel.h" 24 #include "cl_device.h" 25 #include <utility> 26 27 #undef XCAM_CL_MAX_EVENT_SIZE 28 #define XCAM_CL_MAX_EVENT_SIZE 256 29 30 #define OCL_EXT_NAME_CREATE_BUFFER_FROM_LIBVA_INTEL "clCreateBufferFromLibvaIntel" 31 #define OCL_EXT_NAME_CREATE_BUFFER_FROM_FD_INTEL "clCreateBufferFromFdINTEL" 32 #define OCL_EXT_NAME_CREATE_IMAGE_FROM_LIBVA_INTEL "clCreateImageFromLibvaIntel" 33 #define OCL_EXT_NAME_CREATE_IMAGE_FROM_FD_INTEL "clCreateImageFromFdINTEL" 34 #define OCL_EXT_NAME_GET_MEM_OBJECT_FD_INTEL "clGetMemObjectFdIntel" 35 36 namespace XCam { 37 38 class CLKernel; 39 40 void 41 CLContext::context_pfn_notify ( 42 const char* erro_info, 43 const void *private_info, 44 size_t cb, 45 void *user_data 46 ) 47 { 48 CLContext *context = (CLContext*) user_data; 49 XCAM_UNUSED (context); 50 XCAM_UNUSED (erro_info); 51 XCAM_UNUSED (private_info); 52 XCAM_UNUSED (cb); 53 XCAM_LOG_DEBUG ("cl context pfn error:%s", XCAM_STR (erro_info)); 54 } 55 56 void CLContext::program_pfn_notify ( 57 cl_program program, void *user_data) 58 { 59 CLContext *context = (CLContext*) user_data; 60 char kernel_names [XCAM_CL_MAX_STR_SIZE]; 61 62 XCAM_UNUSED (context); 63 XCAM_UNUSED (program); 64 xcam_mem_clear (kernel_names); 65 //clGetProgramInfo (program, CL_PROGRAM_KERNEL_NAMES, sizeof (kernel_names) - 1, kernel_names, NULL); 66 //XCAM_LOG_DEBUG ("cl program report error on kernels: %s", kernel_names); 67 } 68 69 uint32_t 70 CLContext::event_list_2_id_array ( 71 CLEventList &events_wait, 72 cl_event *cl_events, uint32_t max_count) 73 { 74 uint32_t num_of_events_wait = 0; 75 76 for (CLEventList::iterator iter = events_wait.begin (); 77 iter != events_wait.end (); ++iter) { 78 SmartPtr<CLEvent> &event = *iter; 79 80 if (num_of_events_wait >= max_count) { 81 XCAM_LOG_WARNING ("CLEventList(%d) larger than id_array(max_count:%d)", (uint32_t)events_wait.size(), max_count); 82 break; 83 } 84 XCAM_ASSERT (event->get_event_id ()); 85 cl_events[num_of_events_wait++] = event->get_event_id (); 86 } 87 88 return num_of_events_wait; 89 } 90 91 92 CLContext::CLContext (SmartPtr<CLDevice> &device) 93 : _context_id (NULL) 94 , _device (device) 95 { 96 if (!init_context ()) { 97 XCAM_LOG_ERROR ("CL init context failed"); 98 } 99 100 XCAM_LOG_DEBUG ("CLContext constructed"); 101 } 102 103 CLContext::~CLContext () 104 { 105 destroy_context (); 106 XCAM_LOG_DEBUG ("CLContext destructed"); 107 } 108 109 void 110 CLContext::terminate () 111 { 112 //_kernel_map.clear (); 113 _cmd_queue_list.clear (); 114 } 115 116 XCamReturn 117 CLContext::flush () 118 { 119 cl_int error_code = CL_SUCCESS; 120 cl_command_queue cmd_queue_id = NULL; 121 SmartPtr<CLCommandQueue> cmd_queue = get_default_cmd_queue (); 122 123 XCAM_ASSERT (cmd_queue.ptr ()); 124 cmd_queue_id = cmd_queue->get_cmd_queue_id (); 125 error_code = clFlush (cmd_queue_id); 126 127 XCAM_FAIL_RETURN ( 128 WARNING, 129 error_code == CL_SUCCESS, 130 XCAM_RETURN_ERROR_CL, 131 "CL flush cmdqueue failed with error_code:%d", error_code); 132 133 return XCAM_RETURN_NO_ERROR; 134 } 135 136 137 XCamReturn 138 CLContext::finish () 139 { 140 cl_int error_code = CL_SUCCESS; 141 cl_command_queue cmd_queue_id = NULL; 142 SmartPtr<CLCommandQueue> cmd_queue = get_default_cmd_queue (); 143 144 XCAM_ASSERT (cmd_queue.ptr ()); 145 cmd_queue_id = cmd_queue->get_cmd_queue_id (); 146 error_code = clFinish (cmd_queue_id); 147 148 XCAM_FAIL_RETURN ( 149 WARNING, 150 error_code == CL_SUCCESS, 151 XCAM_RETURN_ERROR_CL, 152 "CL finish cmdqueue failed with error_code:%d", error_code); 153 154 return XCAM_RETURN_NO_ERROR; 155 } 156 157 bool 158 CLContext::init_context () 159 { 160 cl_context context_id = NULL; 161 cl_int err_code = 0; 162 cl_device_id device_id = _device->get_device_id (); 163 164 XCAM_ASSERT (_context_id == NULL); 165 166 if (!_device->is_inited()) { 167 XCAM_LOG_ERROR ("create cl context failed since device is not initialized"); 168 return false; 169 } 170 171 context_id = 172 clCreateContext (NULL, 1, &device_id, 173 CLContext::context_pfn_notify, this, 174 &err_code); 175 if (err_code != CL_SUCCESS) 176 { 177 XCAM_LOG_WARNING ("create cl context failed, error:%d", err_code); 178 return false; 179 } 180 _context_id = context_id; 181 return true; 182 } 183 184 bool 185 CLContext::init_cmd_queue (SmartPtr<CLContext> &self) 186 { 187 XCAM_ASSERT (_cmd_queue_list.empty ()); 188 XCAM_ASSERT (self.ptr() == this); 189 SmartPtr<CLCommandQueue> cmd_queue = create_cmd_queue (self); 190 if (!cmd_queue.ptr ()) 191 return false; 192 193 _cmd_queue_list.push_back (cmd_queue); 194 return true; 195 } 196 197 SmartPtr<CLCommandQueue> 198 CLContext::get_default_cmd_queue () 199 { 200 CLCmdQueueList::iterator iter; 201 202 XCAM_ASSERT (!_cmd_queue_list.empty ()); 203 if (_cmd_queue_list.empty ()) 204 return NULL; 205 iter = _cmd_queue_list.begin (); 206 return *iter; 207 } 208 209 void 210 CLContext::destroy_context () 211 { 212 if (!is_valid ()) 213 return; 214 clReleaseContext (_context_id); 215 _context_id = NULL; 216 } 217 218 XCamReturn 219 CLContext::execute_kernel ( 220 const SmartPtr<CLKernel> kernel, 221 const SmartPtr<CLCommandQueue> queue, 222 CLEventList &events_wait, 223 SmartPtr<CLEvent> &event_out) 224 { 225 XCAM_ASSERT (kernel.ptr ()); 226 227 cl_int error_code = CL_SUCCESS; 228 cl_command_queue cmd_queue_id = NULL; 229 cl_event *event_out_id = NULL; 230 cl_event events_id_wait[XCAM_CL_MAX_EVENT_SIZE]; 231 uint32_t num_of_events_wait = 0; 232 uint32_t work_group_size = 1; 233 const size_t *local_sizes = NULL; 234 cl_kernel kernel_id = kernel->get_kernel_id (); 235 CLWorkSize work_size = kernel->get_work_size (); 236 SmartPtr<CLCommandQueue> cmd_queue = queue; 237 238 if (!cmd_queue.ptr ()) { 239 cmd_queue = get_default_cmd_queue (); 240 } 241 XCAM_ASSERT (cmd_queue.ptr ()); 242 243 cmd_queue_id = cmd_queue->get_cmd_queue_id (); 244 num_of_events_wait = event_list_2_id_array (events_wait, events_id_wait, XCAM_CL_MAX_EVENT_SIZE); 245 if (event_out.ptr ()) 246 event_out_id = &event_out->get_event_id (); 247 248 for (uint32_t i = 0; i < work_size.dim; ++i) { 249 work_group_size *= work_size.local[i]; 250 } 251 if (work_group_size) 252 local_sizes = work_size.local; 253 else 254 local_sizes = NULL; 255 256 error_code = 257 clEnqueueNDRangeKernel ( 258 cmd_queue_id, kernel_id, 259 work_size.dim, NULL, work_size.global, local_sizes, 260 num_of_events_wait, (num_of_events_wait ? events_id_wait : NULL), 261 event_out_id); 262 263 XCAM_FAIL_RETURN( 264 WARNING, 265 error_code == CL_SUCCESS, 266 XCAM_RETURN_ERROR_CL, 267 "execute kernel(%s) failed with error_code:%d", 268 kernel->get_kernel_name (), error_code); 269 270 return XCAM_RETURN_NO_ERROR; 271 } 272 273 XCamReturn 274 CLContext::set_event_callback ( 275 SmartPtr<CLEvent> &event, cl_int status, 276 void (*callback) (cl_event, cl_int, void*), 277 void *user_data) 278 { 279 XCAM_ASSERT (event.ptr () && event->get_event_id ()); 280 cl_int error_code = clSetEventCallback (event->get_event_id (), status, callback, user_data); 281 return (error_code == CL_SUCCESS ? XCAM_RETURN_NO_ERROR : XCAM_RETURN_ERROR_CL); 282 } 283 284 SmartPtr<CLCommandQueue> 285 CLContext::create_cmd_queue (SmartPtr<CLContext> &self) 286 { 287 cl_device_id device_id = _device->get_device_id (); 288 cl_command_queue cmd_queue_id = NULL; 289 cl_int err_code = 0; 290 SmartPtr<CLCommandQueue> result; 291 292 XCAM_ASSERT (self.ptr() == this); 293 294 #if defined (CL_VERSION_2_0) && (CL_VERSION_2_0 == 1) 295 cmd_queue_id = clCreateCommandQueueWithProperties (_context_id, device_id, 0, &err_code); 296 #else 297 cmd_queue_id = clCreateCommandQueue (_context_id, device_id, 0, &err_code); 298 #endif 299 if (err_code != CL_SUCCESS) { 300 XCAM_LOG_WARNING ("create CL command queue failed, errcode:%d", err_code); 301 return NULL; 302 } 303 304 result = new CLCommandQueue (self, cmd_queue_id); 305 return result; 306 } 307 308 cl_kernel 309 CLContext::generate_kernel_id ( 310 CLKernel *kernel, 311 const uint8_t *source, size_t length, 312 CLContext::KernelBuildType type, 313 uint8_t **gen_binary, size_t *binary_size, 314 const char *build_option) 315 { 316 struct CLProgram { 317 cl_program id; 318 319 CLProgram () 320 : id (NULL) 321 {} 322 ~CLProgram () { 323 if (id) 324 clReleaseProgram (id); 325 } 326 }; 327 328 CLProgram program; 329 cl_kernel kernel_id = NULL; 330 cl_int error_code = CL_SUCCESS; 331 cl_device_id device_id = _device->get_device_id (); 332 const char * name = kernel->get_kernel_name (); 333 334 XCAM_ASSERT (source && length); 335 XCAM_ASSERT (name); 336 337 switch (type) { 338 case KERNEL_BUILD_SOURCE: 339 program.id = 340 clCreateProgramWithSource ( 341 _context_id, 1, 342 (const char**)(&source), (const size_t *)&length, 343 &error_code); 344 break; 345 case KERNEL_BUILD_BINARY: 346 program.id = 347 clCreateProgramWithBinary ( 348 _context_id, 1, &device_id, 349 (const size_t *)&length, (const uint8_t**)(&source), 350 NULL, &error_code); 351 break; 352 } 353 354 XCAM_FAIL_RETURN ( 355 WARNING, 356 error_code == CL_SUCCESS, 357 NULL, 358 "cl create program failed with error_cod:%d", error_code); 359 XCAM_ASSERT (program.id); 360 361 error_code = clBuildProgram (program.id, 1, &device_id, build_option, CLContext::program_pfn_notify, this); 362 if (error_code != CL_SUCCESS) { 363 //char error_log [XCAM_CL_MAX_STR_SIZE]; 364 char error_log [1024 * 1024 + 32]; 365 xcam_mem_clear (error_log); 366 clGetProgramBuildInfo (program.id, device_id, CL_PROGRAM_BUILD_LOG, sizeof (error_log) - 1, error_log, NULL); 367 XCAM_LOG_WARNING ("CL build program failed on %s, build log:%s", name, error_log); 368 return NULL; 369 } 370 371 if (gen_binary != NULL && binary_size != NULL) { 372 error_code = clGetProgramInfo (program.id, CL_PROGRAM_BINARY_SIZES, sizeof (size_t) * 1, binary_size, NULL); 373 if (error_code != CL_SUCCESS) { 374 XCAM_LOG_WARNING ("CL query binary sizes failed on %s, errcode:%d", name, error_code); 375 } 376 377 *gen_binary = (uint8_t *) xcam_malloc0 (sizeof (uint8_t) * (*binary_size)); 378 379 error_code = clGetProgramInfo (program.id, CL_PROGRAM_BINARIES, sizeof (uint8_t *) * 1, gen_binary, NULL); 380 if (error_code != CL_SUCCESS) { 381 XCAM_LOG_WARNING ("CL query program binaries failed on %s, errcode:%d", name, error_code); 382 } 383 } 384 385 kernel_id = clCreateKernel (program.id, name, &error_code); 386 XCAM_FAIL_RETURN ( 387 WARNING, 388 error_code == CL_SUCCESS, 389 NULL, 390 "cl create kernel(%s) failed with error_cod:%d", name, error_code); 391 392 return kernel_id; 393 } 394 395 void 396 CLContext::destroy_kernel_id (cl_kernel &kernel_id) 397 { 398 if (kernel_id) { 399 clReleaseKernel (kernel_id); 400 kernel_id = NULL; 401 } 402 } 403 404 #if 0 405 bool 406 CLContext::insert_kernel (SmartPtr<CLKernel> &kernel) 407 { 408 std::string kernel_name = kernel->get_kernel_name (); 409 CLKernelMap::iterator i_pos = _kernel_map.lower_bound (kernel_name); 410 411 XCAM_ASSERT (!kernel_name.empty()); 412 if (i_pos != _kernel_map.end () && !_kernel_map.key_comp ()(kernel_name, i_pos->first)) { 413 // need update 414 i_pos->second = kernel; 415 XCAM_LOG_DEBUG ("kernel:%s already exist in context, now update to new one", kernel_name.c_str()); 416 return true; 417 } 418 419 _kernel_map.insert (i_pos, std::make_pair (kernel_name, kernel)); 420 return true; 421 } 422 #endif 423 424 cl_mem 425 CLContext::create_image ( 426 cl_mem_flags flags, const cl_image_format& format, 427 const cl_image_desc &image_info, void *host_ptr) 428 { 429 cl_mem mem_id = NULL; 430 cl_int errcode = CL_SUCCESS; 431 432 mem_id = clCreateImage ( 433 _context_id, flags, 434 &format, &image_info, 435 host_ptr, &errcode); 436 437 XCAM_FAIL_RETURN ( 438 WARNING, 439 errcode == CL_SUCCESS, 440 NULL, 441 "create cl image failed, errcode:%d", errcode); 442 return mem_id; 443 } 444 445 void 446 CLContext::destroy_mem (cl_mem mem_id) 447 { 448 if (mem_id) 449 clReleaseMemObject (mem_id); 450 } 451 452 cl_mem 453 CLContext::create_buffer (uint32_t size, cl_mem_flags flags, void *host_ptr) 454 { 455 cl_mem mem_id = NULL; 456 cl_int errcode = CL_SUCCESS; 457 458 XCAM_ASSERT (_context_id); 459 460 mem_id = clCreateBuffer ( 461 _context_id, flags, 462 size, host_ptr, 463 &errcode); 464 465 XCAM_FAIL_RETURN ( 466 WARNING, 467 errcode == CL_SUCCESS, 468 NULL, 469 "create cl buffer failed, errcode:%d", errcode); 470 return mem_id; 471 } 472 473 cl_mem 474 CLContext::create_sub_buffer ( 475 cl_mem main_mem, 476 cl_buffer_region region, 477 cl_mem_flags flags) 478 { 479 cl_mem sub_mem = NULL; 480 cl_int errcode = CL_SUCCESS; 481 482 sub_mem = clCreateSubBuffer (main_mem, flags, CL_BUFFER_CREATE_TYPE_REGION, ®ion, &errcode); 483 XCAM_FAIL_RETURN ( 484 WARNING, 485 errcode == CL_SUCCESS, 486 NULL, 487 "create sub buffer failed, errcode:%d", errcode); 488 489 return sub_mem; 490 } 491 492 XCamReturn 493 CLContext::enqueue_read_buffer ( 494 cl_mem buf_id, void *ptr, 495 uint32_t offset, uint32_t size, 496 bool block, 497 CLEventList &events_wait, 498 SmartPtr<CLEvent> &event_out) 499 { 500 SmartPtr<CLCommandQueue> cmd_queue; 501 cl_command_queue cmd_queue_id = NULL; 502 cl_event *event_out_id = NULL; 503 cl_event events_id_wait[XCAM_CL_MAX_EVENT_SIZE]; 504 uint32_t num_of_events_wait = 0; 505 cl_int errcode = CL_SUCCESS; 506 507 cmd_queue = get_default_cmd_queue (); 508 cmd_queue_id = cmd_queue->get_cmd_queue_id (); 509 num_of_events_wait = event_list_2_id_array (events_wait, events_id_wait, XCAM_CL_MAX_EVENT_SIZE); 510 if (event_out.ptr ()) 511 event_out_id = &event_out->get_event_id (); 512 513 XCAM_ASSERT (_context_id); 514 XCAM_ASSERT (cmd_queue_id); 515 errcode = clEnqueueReadBuffer ( 516 cmd_queue_id, buf_id, 517 (block ? CL_BLOCKING : CL_NON_BLOCKING), 518 offset, size, ptr, 519 num_of_events_wait, (num_of_events_wait ? events_id_wait : NULL), 520 event_out_id); 521 522 XCAM_FAIL_RETURN ( 523 WARNING, 524 errcode == CL_SUCCESS, 525 XCAM_RETURN_ERROR_CL, 526 "cl enqueue read buffer failed with error_code:%d", errcode); 527 528 return XCAM_RETURN_NO_ERROR; 529 } 530 531 XCamReturn 532 CLContext::enqueue_write_buffer ( 533 cl_mem buf_id, void *ptr, 534 uint32_t offset, uint32_t size, 535 bool block, 536 CLEventList &events_wait, 537 SmartPtr<CLEvent> &event_out) 538 { 539 SmartPtr<CLCommandQueue> cmd_queue; 540 cl_command_queue cmd_queue_id = NULL; 541 cl_event *event_out_id = NULL; 542 cl_event events_id_wait[XCAM_CL_MAX_EVENT_SIZE]; 543 uint32_t num_of_events_wait = 0; 544 cl_int errcode = CL_SUCCESS; 545 546 cmd_queue = get_default_cmd_queue (); 547 cmd_queue_id = cmd_queue->get_cmd_queue_id (); 548 num_of_events_wait = event_list_2_id_array (events_wait, events_id_wait, XCAM_CL_MAX_EVENT_SIZE); 549 if (event_out.ptr ()) 550 event_out_id = &event_out->get_event_id (); 551 552 XCAM_ASSERT (_context_id); 553 XCAM_ASSERT (cmd_queue_id); 554 errcode = clEnqueueWriteBuffer ( 555 cmd_queue_id, buf_id, 556 (block ? CL_BLOCKING : CL_NON_BLOCKING), 557 offset, size, ptr, 558 num_of_events_wait, (num_of_events_wait ? events_id_wait : NULL), 559 event_out_id); 560 561 XCAM_FAIL_RETURN ( 562 WARNING, 563 errcode == CL_SUCCESS, 564 XCAM_RETURN_ERROR_CL, 565 "cl enqueue write buffer failed with error_code:%d", errcode); 566 567 return XCAM_RETURN_NO_ERROR; 568 } 569 570 XCamReturn 571 CLContext::enqueue_map_buffer ( 572 cl_mem buf_id, void *&ptr, 573 uint32_t offset, uint32_t size, 574 bool block, 575 cl_map_flags map_flags, 576 CLEventList &events_wait, 577 SmartPtr<CLEvent> &event_out) 578 { 579 SmartPtr<CLCommandQueue> cmd_queue; 580 cl_command_queue cmd_queue_id = NULL; 581 cl_event *event_out_id = NULL; 582 cl_event events_id_wait[XCAM_CL_MAX_EVENT_SIZE]; 583 uint32_t num_of_events_wait = 0; 584 cl_int errcode = CL_SUCCESS; 585 void *out_ptr = NULL; 586 587 cmd_queue = get_default_cmd_queue (); 588 cmd_queue_id = cmd_queue->get_cmd_queue_id (); 589 num_of_events_wait = event_list_2_id_array (events_wait, events_id_wait, XCAM_CL_MAX_EVENT_SIZE); 590 if (event_out.ptr ()) 591 event_out_id = &event_out->get_event_id (); 592 593 XCAM_ASSERT (_context_id); 594 XCAM_ASSERT (cmd_queue_id); 595 out_ptr = clEnqueueMapBuffer ( 596 cmd_queue_id, buf_id, 597 (block ? CL_BLOCKING : CL_NON_BLOCKING), 598 map_flags, 599 offset, size, 600 num_of_events_wait, (num_of_events_wait ? events_id_wait : NULL), 601 event_out_id, 602 &errcode); 603 604 XCAM_FAIL_RETURN ( 605 WARNING, 606 out_ptr && errcode == CL_SUCCESS, 607 XCAM_RETURN_ERROR_CL, 608 "cl enqueue map buffer failed with error_code:%d", errcode); 609 610 ptr = out_ptr; 611 return XCAM_RETURN_NO_ERROR; 612 } 613 614 615 XCamReturn 616 CLContext::enqueue_map_image ( 617 cl_mem buf_id, void *&ptr, 618 const size_t *origin, 619 const size_t *region, 620 size_t *image_row_pitch, 621 size_t *image_slice_pitch, 622 bool block, 623 cl_map_flags map_flags, 624 CLEventList &events_wait, 625 SmartPtr<CLEvent> &event_out) 626 { 627 SmartPtr<CLCommandQueue> cmd_queue; 628 cl_command_queue cmd_queue_id = NULL; 629 cl_event *event_out_id = NULL; 630 cl_event events_id_wait[XCAM_CL_MAX_EVENT_SIZE]; 631 uint32_t num_of_events_wait = 0; 632 cl_int errcode = CL_SUCCESS; 633 void *out_ptr = NULL; 634 635 cmd_queue = get_default_cmd_queue (); 636 cmd_queue_id = cmd_queue->get_cmd_queue_id (); 637 num_of_events_wait = event_list_2_id_array (events_wait, events_id_wait, XCAM_CL_MAX_EVENT_SIZE); 638 if (event_out.ptr ()) 639 event_out_id = &event_out->get_event_id (); 640 641 XCAM_ASSERT (_context_id); 642 XCAM_ASSERT (cmd_queue_id); 643 644 out_ptr = clEnqueueMapImage ( 645 cmd_queue_id, buf_id, 646 (block ? CL_BLOCKING : CL_NON_BLOCKING), 647 map_flags, 648 origin, 649 region, 650 image_row_pitch, 651 image_slice_pitch, 652 num_of_events_wait, (num_of_events_wait ? events_id_wait : NULL), 653 event_out_id, 654 &errcode); 655 656 XCAM_FAIL_RETURN ( 657 WARNING, 658 out_ptr && errcode == CL_SUCCESS, 659 XCAM_RETURN_ERROR_CL, 660 "cl enqueue map buffer failed with error_code:%d", errcode); 661 662 ptr = out_ptr; 663 return XCAM_RETURN_NO_ERROR; 664 } 665 666 XCamReturn 667 CLContext::enqueue_unmap ( 668 cl_mem mem_id, 669 void *ptr, 670 CLEventList &events_wait, 671 SmartPtr<CLEvent> &event_out) 672 { 673 SmartPtr<CLCommandQueue> cmd_queue; 674 cl_command_queue cmd_queue_id = NULL; 675 cl_event *event_out_id = NULL; 676 cl_event events_id_wait[XCAM_CL_MAX_EVENT_SIZE]; 677 uint32_t num_of_events_wait = 0; 678 cl_int errcode = CL_SUCCESS; 679 680 cmd_queue = get_default_cmd_queue (); 681 cmd_queue_id = cmd_queue->get_cmd_queue_id (); 682 num_of_events_wait = event_list_2_id_array (events_wait, events_id_wait, XCAM_CL_MAX_EVENT_SIZE); 683 if (event_out.ptr ()) 684 event_out_id = &event_out->get_event_id (); 685 686 XCAM_ASSERT (_context_id); 687 XCAM_ASSERT (cmd_queue_id); 688 errcode = clEnqueueUnmapMemObject ( 689 cmd_queue_id, mem_id, ptr, 690 num_of_events_wait, (num_of_events_wait ? events_id_wait : NULL), 691 event_out_id); 692 693 XCAM_FAIL_RETURN ( 694 WARNING, 695 errcode == CL_SUCCESS, 696 XCAM_RETURN_ERROR_CL, 697 "cl enqueue unmap buffer failed with error_code:%d", errcode); 698 699 return XCAM_RETURN_NO_ERROR; 700 } 701 702 CLCommandQueue::CLCommandQueue (SmartPtr<CLContext> &context, cl_command_queue id) 703 : _context (context) 704 , _cmd_queue_id (id) 705 { 706 XCAM_ASSERT (context.ptr ()); 707 XCAM_ASSERT (id); 708 XCAM_LOG_DEBUG ("CLCommandQueue constructed"); 709 } 710 711 CLCommandQueue::~CLCommandQueue () 712 { 713 destroy (); 714 XCAM_LOG_DEBUG ("CLCommandQueue desstructed"); 715 } 716 717 void 718 CLCommandQueue::destroy () 719 { 720 if (_cmd_queue_id == NULL) 721 return; 722 723 clReleaseCommandQueue (_cmd_queue_id); 724 _cmd_queue_id = NULL; 725 } 726 727 }; 728